Files
portainer/app/react/components/form-components/FilePicker/utils.test.ts
T

122 lines
3.4 KiB
TypeScript

import { Directory, File, FileNode } from './types';
import {
isDirectory,
getAllFilePaths,
getFolderState,
filterToPattern,
} from './utils';
function file(name: string): File {
return { name };
}
function dir(name: string, children: FileNode[] = []): Directory {
return { name, children };
}
describe('isDirectory', () => {
it('returns true when the item has a children property', () => {
expect(isDirectory(dir('src'))).toBe(true);
});
it('returns true when the children property is present but undefined', () => {
const dirWithUndefinedChildren: Directory = {
name: 'empty',
children: undefined,
};
expect(isDirectory(dirWithUndefinedChildren)).toBe(true);
});
it('returns false for a file without children', () => {
expect(isDirectory(file('foo.ts'))).toBe(false);
});
});
describe('getAllFilePaths', () => {
it('returns the node path for a single file', () => {
expect(getAllFilePaths(file('foo.ts'), 'foo.ts')).toEqual(['foo.ts']);
});
it('returns all child file paths for a flat directory', () => {
const node = dir('src', [file('a.ts'), file('b.ts')]);
expect(getAllFilePaths(node, 'src')).toEqual(['src/a.ts', 'src/b.ts']);
});
it('returns an empty array for an empty directory', () => {
expect(getAllFilePaths(dir('empty'), 'empty')).toEqual([]);
});
it('returns deeply nested file paths', () => {
const node = dir('root', [dir('sub', [file('deep.ts')])]);
expect(getAllFilePaths(node, 'root')).toEqual(['root/sub/deep.ts']);
});
it('returns all paths across multiple nested levels', () => {
const node = dir('a', [
file('top.ts'),
dir('b', [file('nested.ts'), dir('c', [file('deep.ts')])]),
]);
expect(getAllFilePaths(node, 'a').sort()).toEqual([
'a/b/c/deep.ts',
'a/b/nested.ts',
'a/top.ts',
]);
});
});
describe('getFolderState', () => {
const tree = dir('src', [file('a.ts'), file('b.ts')]);
it('returns unchecked when no files are selected', () => {
expect(getFolderState(tree, new Set(), 'src')).toBe('unchecked');
});
it('returns checked when all files in the directory are selected', () => {
expect(getFolderState(tree, new Set(['src/a.ts', 'src/b.ts']), 'src')).toBe(
'checked'
);
});
it('returns indeterminate when some but not all files are selected', () => {
expect(getFolderState(tree, new Set(['src/a.ts']), 'src')).toBe(
'indeterminate'
);
});
it('returns unchecked for an empty directory', () => {
expect(getFolderState(dir('empty'), new Set(), 'empty')).toBe('unchecked');
});
it('ignores selected paths outside the directory', () => {
expect(getFolderState(tree, new Set(['other/file.ts']), 'src')).toBe(
'unchecked'
);
});
});
describe('filterToPattern', () => {
it('wraps plain text with wildcards', () => {
expect(filterToPattern('foo')).toBe('*foo*');
});
it('leaves a glob pattern with * unchanged', () => {
expect(filterToPattern('*.yml')).toBe('*.yml');
});
it('leaves a glob pattern with ? unchanged', () => {
expect(filterToPattern('file?.ts')).toBe('file?.ts');
});
it('trims whitespace before wrapping plain text', () => {
expect(filterToPattern(' foo ')).toBe('*foo*');
});
it('trims whitespace before preserving a glob', () => {
expect(filterToPattern(' *.yml ')).toBe('*.yml');
});
it('handles empty string after trimming', () => {
expect(filterToPattern(' ')).toBe('**');
});
});