forked from joekrill/silverbullet-treeview
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathapi.ts
111 lines (99 loc) · 2.88 KB
/
api.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
import { editor, space } from "$sb/syscalls.ts";
import { PageMeta } from "$sb/types.ts";
export type NodeData = {
/**
* The complete page or folder name.
*/
name: string;
/**
* The name to display in the node to the user (generally the last
* portion of the `name`)
*/
title: string;
/**
* True if this node represents the current active page
*/
isCurrentPage?: boolean;
nodeType: string;
};
export type PageData = PageMeta & NodeData & {
nodeType: "page";
};
export type FolderData = NodeData & {
nodeType: "folder";
};
export type TreeNode = {
data: PageData | FolderData;
nodes: TreeNode[];
};
/**
* Generates a TreeNode array from the list of pages in the current space.
*/
export async function getPageTree(excludeRegex: string) {
const currentPage = await editor.getCurrentPage();
let pages = await space.listPages();
const root = { nodes: [] as TreeNode[] };
if (excludeRegex !== "") {
try {
const pageRegExp = new RegExp(excludeRegex);
pages = pages.filter((o) =>
// exclude pages which match the regex
!pageRegExp.test(o.name)
);
} catch (err: unknown) {
console.error("filtering by pageExcludeRegex failed", err);
}
}
pages.sort((a, b) => a.name.localeCompare(b.name)).forEach((page) => {
page.name.split("/").reduce((parent, title, currentIndex, parts) => {
const isLeaf = parts.length - 1 === currentIndex;
let node = parent.nodes.find((child) => child.data.title === title);
if (node) {
if (isLeaf && !("created" in node.data)) {
// The node was found but is currently identified as a "folder",
// so we need to change it to a "page" type.
node.data = {
...page,
title,
isCurrentPage: currentPage === page.name,
nodeType: "page",
};
}
return node;
}
if (isLeaf) {
// We're at the last part of the page name, so this reprents the page itself.
node = {
data: {
...page,
title,
isCurrentPage: currentPage === page.name,
nodeType: "page",
},
nodes: [],
};
} else {
// This is an intermediate part of the page name and a node doesn't exist
// yet, so this represents a "folder" (and may be converted to a page
// at some later iteration, if the page is found)
const name = parts.slice(0, currentIndex + 1).join("/");
node = {
data: {
title,
// A folder can still be the "current page" if it's being created
isCurrentPage: currentPage === name,
name,
nodeType: "folder",
},
nodes: [],
};
}
parent.nodes.push(node);
return node;
}, root);
});
return {
nodes: root.nodes,
currentPage,
};
}