summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--frontend/lib/drive_server.ts78
1 files changed, 1 insertions, 77 deletions
diff --git a/frontend/lib/drive_server.ts b/frontend/lib/drive_server.ts
index 41b9c71..8af0356 100644
--- a/frontend/lib/drive_server.ts
+++ b/frontend/lib/drive_server.ts
@@ -1,5 +1,5 @@
1import { spawnSync } from 'child_process' 1import { spawnSync } from 'child_process'
2import { DriveLsEntry, DriveTreeNode, DriveTreeResponse, DriveLogEntry } from './drive_types' 2import { DriveLsEntry, DriveLogEntry } from './drive_types'
3import { Drive_split_path, Drive_basename } from './drive_shared' 3import { Drive_split_path, Drive_basename } from './drive_shared'
4 4
5/** 5/**
@@ -120,82 +120,6 @@ export async function Drive_stat(path: string): Promise<string> {
120 return result.stdout.trim(); 120 return result.stdout.trim();
121} 121}
122 122
123/// builds a filesystem tree from Drive_ls entries
124export async function Drive_tree(): Promise<DriveTreeResponse> {
125 const entries = await Drive_ls('/', true);
126
127 const nodesMap = new Map<string, DriveTreeNode>();
128 const rootNodes: DriveTreeNode[] = [];
129
130 // First pass: create all nodes
131 entries.forEach(entry => {
132 const node: DriveTreeNode = {
133 path: entry.path,
134 name: Drive_basename(entry.path),
135 type: entry.type,
136 lastmod: entry.lastmod,
137 blob: entry.blob,
138 size: entry.size,
139 author: entry.author,
140 children: entry.type === "dir" ? [] : undefined
141 };
142 nodesMap.set(entry.path, node);
143 });
144
145 // Second pass: build hierarchy
146 entries.forEach(entry => {
147 const pathParts = Drive_split_path(entry.path);
148 const node = nodesMap.get(entry.path)!;
149
150 if (pathParts.length === 1) {
151 // Root level item
152 rootNodes.push(node);
153 } else {
154 // Find parent path by reconstructing it
155 const parentParts = pathParts.slice(0, -1);
156 const parentPath = '/' + parentParts.join('/');
157 const parent = nodesMap.get(parentPath);
158
159 if (parent && parent.children) {
160 parent.children.push(node);
161 } else {
162 // If parent not found, add to root
163 rootNodes.push(node);
164 }
165 }
166 });
167
168 // Third pass: calculate directory sizes and sort all levels
169 const calculateSizesAndSort = (nodes: DriveTreeNode[]): DriveTreeNode[] => {
170 // First, recursively process children and calculate their sizes
171 nodes.forEach(node => {
172 if (node.children) {
173 node.children = calculateSizesAndSort(node.children);
174
175 // If this is a directory, calculate its size as sum of all children
176 if (node.type === "dir") {
177 node.size = node.children.reduce((total, child) => {
178 return total + (child.size || 0);
179 }, 0);
180 }
181 }
182 });
183
184 // Then sort: directories first, then files, both alphabetically
185 const sorted = nodes.sort((a, b) => {
186 // Directories first, then files
187 if (a.type === "dir" && b.type === "file") return -1;
188 if (a.type === "file" && b.type === "dir") return 1;
189
190 // Both same type, sort alphabetically by name (case-insensitive)
191 return a.name.toLowerCase().localeCompare(b.name.toLowerCase());
192 });
193
194 return sorted;
195 };
196
197 return { root: calculateSizesAndSort(rootNodes) };
198}
199 123
200/// lists only directories (recursively) from the given path 124/// lists only directories (recursively) from the given path
201export async function Drive_ls_directories(path: string = '/'): Promise<DriveLsEntry[]> { 125export async function Drive_ls_directories(path: string = '/'): Promise<DriveLsEntry[]> {