55
66import type { TreeNode } from '../services/FolderTree.ts'
77
8+ import PQueue from 'p-queue'
89import { Folder , Node , View , getNavigation } from '@nextcloud/files'
910import { translate as t } from '@nextcloud/l10n'
10- import { subscribe } from '@nextcloud/event-bus'
11+ import { emit , subscribe } from '@nextcloud/event-bus'
1112import { isSamePath } from '@nextcloud/paths'
1213import { loadState } from '@nextcloud/initial-state'
1314
@@ -29,6 +30,37 @@ const isFolderTreeEnabled = loadState('files', 'config', { folder_tree: true }).
2930
3031const Navigation = getNavigation ( )
3132
33+ const queue = new PQueue ( { concurrency : 5 , intervalCap : 5 , interval : 200 } ) // Limit number of concurrent view registrations as this could potentially be very large
34+
35+ const getOnToggleOpen = ( node : TreeNode | Folder ) => {
36+ return async ( open : boolean , view : View ) : Promise < void > => {
37+ if ( ! open ) {
38+ return
39+ }
40+ // @ts -expect-error Custom property
41+ if ( view . loaded ) {
42+ return
43+ }
44+ // @ts -expect-error Custom property
45+ view . loading = true
46+ const nodes = await getFolderTreeNodes ( node . path )
47+ try {
48+ const promises = nodes . map ( node => queue . add ( ( ) => registerTreeNodeView ( node ) ) )
49+ await Promise . allSettled ( promises )
50+ } catch ( error ) {
51+ // Skip duplicate view registration errors
52+ }
53+ // @ts -expect-error Custom property
54+ view . loading = false
55+ // @ts -expect-error Custom property
56+ view . loaded = true
57+ // @ts -expect-error No payload
58+ emit ( 'files:navigation:updated' )
59+ // @ts -expect-error No payload
60+ emit ( 'files:folder-tree:expanded' )
61+ }
62+ }
63+
3264const registerTreeNodeView = ( node : TreeNode ) => {
3365 Navigation . register ( new View ( {
3466 id : encodeSource ( node . source ) ,
@@ -40,6 +72,7 @@ const registerTreeNodeView = (node: TreeNode) => {
4072 order : 0 , // TODO Allow undefined order for natural sort
4173
4274 getContents,
75+ onToggleOpen : getOnToggleOpen ( node ) ,
4376
4477 params : {
4578 view : folderTreeId ,
@@ -60,6 +93,7 @@ const registerFolderView = (folder: Folder) => {
6093 order : 0 , // TODO Allow undefined order for natural sort
6194
6295 getContents,
96+ onToggleOpen : getOnToggleOpen ( folder ) ,
6397
6498 params : {
6599 view : folderTreeId ,
@@ -134,13 +168,14 @@ const registerFolderTreeRoot = () => {
134168
135169const registerFolderTreeChildren = async ( ) => {
136170 const nodes = await getFolderTreeNodes ( )
137- for ( const node of nodes ) {
138- registerTreeNodeView ( node )
139- }
171+ const promises = nodes . map ( node => queue . add ( ( ) => registerTreeNodeView ( node ) ) )
172+ await Promise . allSettled ( promises )
140173
141174 subscribe ( 'files:node:created' , onCreateNode )
142175 subscribe ( 'files:node:deleted' , onDeleteNode )
143176 subscribe ( 'files:node:moved' , onMoveNode )
177+ // @ts -expect-error No payload
178+ emit ( 'files:folder-tree:initialized' )
144179}
145180
146181export const registerFolderTreeView = async ( ) => {
0 commit comments