Skip to content

Commit 702fe9e

Browse files
committed
Extracted and extended a basic integration test
1 parent 2c3de3d commit 702fe9e

File tree

4 files changed

+190
-99
lines changed

4 files changed

+190
-99
lines changed

src/custom-sort/custom-sort.ts

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -618,6 +618,22 @@ export const sortOrderNeedsBookmarksOrder = (...orders: Array<CustomSortOrder |
618618
export type ModifiedTime = number
619619
export type CreatedTime = number
620620

621+
// TODO: determine how to selectively unmock the Vault.recurseChildren in integration jest test.
622+
// Until then the implementation for testing is supplied explicitly below, copied from Obsidian code
623+
624+
const recurseChildrenForUnitTests = ((root: TFolder, cb: (file: TAbstractFile) => any) => {
625+
for (let itemsToIterate: TAbstractFile[] = [root]; itemsToIterate.length > 0;) {
626+
let firstItem = itemsToIterate.pop();
627+
if (firstItem) {
628+
cb(firstItem)
629+
if (isFolder(firstItem)) {
630+
let childrenOfFolder = (firstItem as TFolder).children;
631+
itemsToIterate = itemsToIterate.concat(childrenOfFolder)
632+
}
633+
}
634+
}
635+
})
636+
621637
export const determineDatesForFolder = (folder: TFolder, recursive?: boolean): [ModifiedTime, CreatedTime] => {
622638
let mtimeOfFolder: ModifiedTime = DEFAULT_FOLDER_MTIME
623639
let ctimeOfFolder: CreatedTime = DEFAULT_FOLDER_CTIME
@@ -635,7 +651,7 @@ export const determineDatesForFolder = (folder: TFolder, recursive?: boolean): [
635651
}
636652

637653
if (recursive) {
638-
Vault.recurseChildren(folder, checkFile)
654+
(Vault?.recurseChildren ?? recurseChildrenForUnitTests)(folder, checkFile)
639655
} else {
640656
folder.children.forEach((item) => checkFile(item))
641657
}
Lines changed: 112 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,112 @@
1+
import {
2+
TAbstractFile,
3+
TFolder,
4+
Vault
5+
} from "obsidian";
6+
import {
7+
DEFAULT_FOLDER_CTIME,
8+
determineFolderDatesIfNeeded,
9+
determineSortingGroup,
10+
FolderItemForSorting
11+
} from "../../custom-sort/custom-sort";
12+
import {
13+
CustomSortGroupType,
14+
CustomSortOrder,
15+
CustomSortSpec
16+
} from "../../custom-sort/custom-sort-types";
17+
import {
18+
TIMESTAMP_OLDEST,
19+
TIMESTAMP_NEWEST,
20+
mockTFolderWithChildren, TIMESTAMP_DEEP_NEWEST, TIMESTAMP_DEEP_OLDEST
21+
} from "../mocks";
22+
23+
describe('determineFolderDatesIfNeeded', () => {
24+
it('should not be triggered if not needed - sorting method does not require it', () => {
25+
// given
26+
const folder: TFolder = mockTFolderWithChildren('Test folder 1')
27+
const OUTSIDERS_GROUP_IDX = 0
28+
const sortSpec: CustomSortSpec = {
29+
targetFoldersPaths: ['/'],
30+
groups: [{
31+
type: CustomSortGroupType.Outsiders,
32+
order: CustomSortOrder.alphabetical
33+
}],
34+
outsidersGroupIdx: OUTSIDERS_GROUP_IDX
35+
}
36+
37+
// when
38+
const result: FolderItemForSorting = determineSortingGroup(folder, sortSpec)
39+
determineFolderDatesIfNeeded([result], sortSpec)
40+
41+
// then
42+
expect(result.ctime).toEqual(DEFAULT_FOLDER_CTIME)
43+
expect(result.mtime).toEqual(DEFAULT_FOLDER_CTIME)
44+
})
45+
it.each(
46+
[
47+
[CustomSortOrder.byCreatedTimeReverseAdvanced, undefined],
48+
[CustomSortOrder.byCreatedTimeAdvanced, undefined],
49+
[CustomSortOrder.byModifiedTimeAdvanced, undefined],
50+
[CustomSortOrder.byModifiedTimeReverseAdvanced, undefined],
51+
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeReverseAdvanced],
52+
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeAdvanced],
53+
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeAdvanced],
54+
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeReverseAdvanced],
55+
])('should correctly determine dates, if triggered by %s under default %s (no deep orders requested)', (order: CustomSortOrder, folderOrder: CustomSortOrder | undefined) => {
56+
// given
57+
const folder: TFolder = mockTFolderWithChildren('Test folder 1')
58+
const OUTSIDERS_GROUP_IDX = 0
59+
const sortSpec: CustomSortSpec = {
60+
targetFoldersPaths: ['/'],
61+
defaultOrder: folderOrder,
62+
groups: [{
63+
type: CustomSortGroupType.Outsiders,
64+
order: order
65+
}],
66+
outsidersGroupIdx: OUTSIDERS_GROUP_IDX
67+
}
68+
69+
// when
70+
const result: FolderItemForSorting = determineSortingGroup(folder, sortSpec)
71+
determineFolderDatesIfNeeded([result], sortSpec)
72+
73+
// then
74+
expect(result.ctime).toEqual(TIMESTAMP_OLDEST)
75+
expect(result.mtime).toEqual(TIMESTAMP_NEWEST)
76+
})
77+
it.each(
78+
[
79+
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeReverseAdvancedRecursive],
80+
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeAdvancedRecursive],
81+
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeAdvancedRecursive],
82+
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeReverseAdvancedRecursive],
83+
[CustomSortOrder.byCreatedTimeReverseAdvancedRecursive, CustomSortOrder.byCreatedTimeReverseAdvanced],
84+
[CustomSortOrder.byCreatedTimeAdvancedRecursive, CustomSortOrder.byCreatedTimeAdvanced],
85+
[CustomSortOrder.byModifiedTimeAdvancedRecursive, CustomSortOrder.byModifiedTimeAdvanced],
86+
[CustomSortOrder.byModifiedTimeReverseAdvancedRecursive, CustomSortOrder.byModifiedTimeReverseAdvanced],
87+
])('should correctly determine dates, if triggered by %s under default %s (deep orders)', (order: CustomSortOrder, folderOrder: CustomSortOrder | undefined) => {
88+
// given
89+
const folder: TFolder = mockTFolderWithChildren('Test folder 1')
90+
const OUTSIDERS_GROUP_IDX = 0
91+
const sortSpec: CustomSortSpec = {
92+
targetFoldersPaths: ['/'],
93+
defaultOrder: folderOrder,
94+
groups: [{
95+
type: CustomSortGroupType.Outsiders,
96+
order: order
97+
}],
98+
outsidersGroupIdx: OUTSIDERS_GROUP_IDX
99+
}
100+
101+
// when
102+
const result: FolderItemForSorting = determineSortingGroup(folder, sortSpec)
103+
determineFolderDatesIfNeeded([result], sortSpec)
104+
105+
// then
106+
expect(result.ctime).toEqual(TIMESTAMP_DEEP_OLDEST)
107+
expect(result.mtime).toEqual(TIMESTAMP_DEEP_NEWEST)
108+
})
109+
})
110+
111+
112+

src/test/mocks.ts

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
import {
2+
TFile,
3+
TFolder,
4+
Vault
5+
} from "obsidian";
6+
7+
export const mockTFile = (basename: string, ext: string, size?: number, ctime?: number, mtime?: number): TFile => {
8+
return {
9+
stat: {
10+
ctime: ctime ?? 0,
11+
mtime: mtime ?? 0,
12+
size: size ?? 0
13+
},
14+
basename: basename,
15+
extension: ext,
16+
vault: {} as Vault, // To satisfy TS typechecking
17+
path: `Some parent folder/${basename}.${ext}`,
18+
name: `${basename}.${ext}`,
19+
parent: {} as TFolder // To satisfy TS typechecking
20+
}
21+
}
22+
23+
export const mockTFolder = (name: string, children?: Array<TFolder|TFile>, parent?: TFolder): TFolder => {
24+
return {
25+
isRoot(): boolean { return name === '/' },
26+
vault: {} as Vault, // To satisfy TS typechecking
27+
path: `${name}`,
28+
name: name,
29+
parent: parent ?? ({} as TFolder), // To satisfy TS typechecking
30+
children: children ?? []
31+
}
32+
}
33+
34+
export const MOCK_TIMESTAMP: number = 1656417542418
35+
export const TIMESTAMP_OLDEST: number = MOCK_TIMESTAMP
36+
export const TIMESTAMP_DEEP_OLDEST: number = TIMESTAMP_OLDEST - 1000
37+
export const TIMESTAMP_NEWEST: number = MOCK_TIMESTAMP + 1000
38+
export const TIMESTAMP_DEEP_NEWEST: number = TIMESTAMP_NEWEST + 1000
39+
export const TIMESTAMP_INBETWEEN: number = MOCK_TIMESTAMP + 500
40+
41+
export const mockTFolderWithChildren = (name: string): TFolder => {
42+
const subchild1: TFile = mockTFile('Sub-child file 1 created as deep oldest, modified recently', 'md', 100, TIMESTAMP_DEEP_OLDEST, TIMESTAMP_NEWEST)
43+
const subfolder1: TFolder = mockTFolder('Subfolder with deep-oldest child file', [subchild1])
44+
45+
const subchild2: TFile = mockTFile('Sub-child file 1 created as deep newest, modified recently', 'md', 100, TIMESTAMP_OLDEST, TIMESTAMP_DEEP_NEWEST)
46+
const subfolder2: TFolder = mockTFolder('Subfolder with deep-newest child file', [subchild2])
47+
48+
const child1: TFolder = mockTFolder('Section A')
49+
const child2: TFolder = mockTFolder('Section B')
50+
const child3: TFile = mockTFile('Child file 1 created as oldest, modified recently', 'md', 100, TIMESTAMP_OLDEST, TIMESTAMP_NEWEST)
51+
const child4: TFile = mockTFile('Child file 2 created as newest, not modified at all', 'md', 100, TIMESTAMP_NEWEST, TIMESTAMP_NEWEST)
52+
const child5: TFile = mockTFile('Child file 3 created inbetween, modified inbetween', 'md', 100, TIMESTAMP_INBETWEEN, TIMESTAMP_INBETWEEN)
53+
54+
return mockTFolder(name, [child1, child2, child3, child4, child5, subfolder1, subfolder2])
55+
}

src/test/unit/custom-sort.spec.ts

Lines changed: 6 additions & 98 deletions
Original file line numberDiff line numberDiff line change
@@ -43,48 +43,12 @@ import {
4343
ObsidianIconFolder_PluginInstance,
4444
ObsidianIconFolderPlugin_Data
4545
} from "../../utils/ObsidianIconFolderPluginSignature";
46-
47-
const mockTFile = (basename: string, ext: string, size?: number, ctime?: number, mtime?: number): TFile => {
48-
return {
49-
stat: {
50-
ctime: ctime ?? 0,
51-
mtime: mtime ?? 0,
52-
size: size ?? 0
53-
},
54-
basename: basename,
55-
extension: ext,
56-
vault: {} as Vault, // To satisfy TS typechecking
57-
path: `Some parent folder/${basename}.${ext}`,
58-
name: `${basename}.${ext}`,
59-
parent: {} as TFolder // To satisfy TS typechecking
60-
}
61-
}
62-
63-
const mockTFolder = (name: string, children?: Array<TFolder|TFile>, parent?: TFolder): TFolder => {
64-
return {
65-
isRoot(): boolean { return name === '/' },
66-
vault: {} as Vault, // To satisfy TS typechecking
67-
path: `${name}`,
68-
name: name,
69-
parent: parent ?? ({} as TFolder), // To satisfy TS typechecking
70-
children: children ?? []
71-
}
72-
}
73-
74-
const MOCK_TIMESTAMP: number = 1656417542418
75-
const TIMESTAMP_OLDEST: number = MOCK_TIMESTAMP
76-
const TIMESTAMP_NEWEST: number = MOCK_TIMESTAMP + 1000
77-
const TIMESTAMP_INBETWEEN: number = MOCK_TIMESTAMP + 500
78-
79-
const mockTFolderWithChildren = (name: string): TFolder => {
80-
const child1: TFolder = mockTFolder('Section A')
81-
const child2: TFolder = mockTFolder('Section B')
82-
const child3: TFile = mockTFile('Child file 1 created as oldest, modified recently', 'md', 100, TIMESTAMP_OLDEST, TIMESTAMP_NEWEST)
83-
const child4: TFile = mockTFile('Child file 2 created as newest, not modified at all', 'md', 100, TIMESTAMP_NEWEST, TIMESTAMP_NEWEST)
84-
const child5: TFile = mockTFile('Child file 3 created inbetween, modified inbetween', 'md', 100, TIMESTAMP_INBETWEEN, TIMESTAMP_INBETWEEN)
85-
86-
return mockTFolder(name, [child1, child2, child3, child4, child5])
87-
}
46+
import {
47+
MOCK_TIMESTAMP,
48+
mockTFile,
49+
mockTFolder,
50+
mockTFolderWithChildren
51+
} from "../mocks";
8852

8953
const MockedLoc: Pos = {
9054
start: {col:0,offset:0,line:0},
@@ -2520,62 +2484,6 @@ describe('determineSortingGroup', () => {
25202484
})
25212485
})
25222486

2523-
describe('determineFolderDatesIfNeeded', () => {
2524-
it('should not be triggered if not needed - sorting method does not require it', () => {
2525-
// given
2526-
const folder: TFolder = mockTFolderWithChildren('Test folder 1')
2527-
const OUTSIDERS_GROUP_IDX = 0
2528-
const sortSpec: CustomSortSpec = {
2529-
targetFoldersPaths: ['/'],
2530-
groups: [{
2531-
type: CustomSortGroupType.Outsiders,
2532-
order: CustomSortOrder.alphabetical
2533-
}],
2534-
outsidersGroupIdx: OUTSIDERS_GROUP_IDX
2535-
}
2536-
2537-
// when
2538-
const result: FolderItemForSorting = determineSortingGroup(folder, sortSpec)
2539-
determineFolderDatesIfNeeded([result], sortSpec)
2540-
2541-
// then
2542-
expect(result.ctime).toEqual(DEFAULT_FOLDER_CTIME)
2543-
expect(result.mtime).toEqual(DEFAULT_FOLDER_CTIME)
2544-
})
2545-
it.each(
2546-
[
2547-
[CustomSortOrder.byCreatedTimeReverseAdvanced, undefined],
2548-
[CustomSortOrder.byCreatedTimeAdvanced, undefined],
2549-
[CustomSortOrder.byModifiedTimeAdvanced, undefined],
2550-
[CustomSortOrder.byModifiedTimeReverseAdvanced, undefined],
2551-
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeReverseAdvanced],
2552-
[CustomSortOrder.alphabetical, CustomSortOrder.byCreatedTimeAdvanced],
2553-
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeAdvanced],
2554-
[CustomSortOrder.alphabetical, CustomSortOrder.byModifiedTimeReverseAdvanced]
2555-
])('should correctly determine dates, if triggered by %s under default %s', (order: CustomSortOrder, folderOrder: CustomSortOrder | undefined) => {
2556-
// given
2557-
const folder: TFolder = mockTFolderWithChildren('Test folder 1')
2558-
const OUTSIDERS_GROUP_IDX = 0
2559-
const sortSpec: CustomSortSpec = {
2560-
targetFoldersPaths: ['/'],
2561-
defaultOrder: folderOrder,
2562-
groups: [{
2563-
type: CustomSortGroupType.Outsiders,
2564-
order: order
2565-
}],
2566-
outsidersGroupIdx: OUTSIDERS_GROUP_IDX
2567-
}
2568-
2569-
// when
2570-
const result: FolderItemForSorting = determineSortingGroup(folder, sortSpec)
2571-
determineFolderDatesIfNeeded([result], sortSpec)
2572-
2573-
// then
2574-
expect(result.ctime).toEqual(TIMESTAMP_OLDEST)
2575-
expect(result.mtime).toEqual(TIMESTAMP_NEWEST)
2576-
})
2577-
})
2578-
25792487
describe('matchGroupRegex', () => {
25802488
it( 'should correctly handle no match', () => {
25812489
// given

0 commit comments

Comments
 (0)