veryfront 0.1.85 → 0.1.86

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/esm/deno.js CHANGED
@@ -1,6 +1,6 @@
1
1
  export default {
2
2
  "name": "veryfront",
3
- "version": "0.1.85",
3
+ "version": "0.1.86",
4
4
  "license": "Apache-2.0",
5
5
  "nodeModulesDir": "auto",
6
6
  "exclude": [
@@ -12,6 +12,9 @@ export declare class VeryfrontFSAdapter implements FSAdapter {
12
12
  private initialized;
13
13
  /** Resolves when file list initialization is complete (for coordinating reads) */
14
14
  private fileListReadyResolve;
15
+ /** Single-flight background rewarm when the file list cache disappears */
16
+ private fileListWarmupPromise;
17
+ private fileListWarmupKey;
15
18
  private projectData?;
16
19
  private apiBaseUrl;
17
20
  private apiToken;
@@ -29,6 +32,7 @@ export declare class VeryfrontFSAdapter implements FSAdapter {
29
32
  constructor(config: FSAdapterConfig);
30
33
  initialize(): Promise<void>;
31
34
  private isPersistentCacheInvalidated;
35
+ private scheduleFileListWarmup;
32
36
  getPokeMetrics(): {
33
37
  received: number;
34
38
  invalidationsTriggered: number;
@@ -1 +1 @@
1
- {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../../../../../../src/src/platform/adapters/fs/veryfront/adapter.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../../../../../../src/src/platform/adapters/fs/veryfront/adapter.ts"],"names":[],"mappings":"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"}
@@ -27,6 +27,9 @@ export class VeryfrontFSAdapter {
27
27
  initialized = false;
28
28
  /** Resolves when file list initialization is complete (for coordinating reads) */
29
29
  fileListReadyResolve = null;
30
+ /** Single-flight background rewarm when the file list cache disappears */
31
+ fileListWarmupPromise = null;
32
+ fileListWarmupKey = null;
30
33
  projectData;
31
34
  apiBaseUrl;
32
35
  apiToken;
@@ -94,6 +97,9 @@ export class VeryfrontFSAdapter {
94
97
  hasResult: !!result,
95
98
  resultSize: result?.length ?? 0,
96
99
  });
100
+ if (!result?.length) {
101
+ this.scheduleFileListWarmup("getFileList miss", cacheKey);
102
+ }
97
103
  return result;
98
104
  },
99
105
  hasCachedFileList: async () => {
@@ -109,6 +115,9 @@ export class VeryfrontFSAdapter {
109
115
  hasResult,
110
116
  resultSize: result?.length ?? 0,
111
117
  });
118
+ if (!hasResult) {
119
+ this.scheduleFileListWarmup("hasCachedFileList miss", cacheKey);
120
+ }
112
121
  return hasResult;
113
122
  },
114
123
  isPersistentCacheInvalidated: (prefix) => this.isPersistentCacheInvalidated(prefix),
@@ -132,6 +141,9 @@ export class VeryfrontFSAdapter {
132
141
  resultSize: result?.length ?? 0,
133
142
  hasContent: result?.filter((f) => f.content)?.length ?? 0,
134
143
  });
144
+ if (!result?.length) {
145
+ this.scheduleFileListWarmup("getFileListCache miss", cacheKey);
146
+ }
135
147
  return result;
136
148
  });
137
149
  this.dirOps = new DirectoryOperations(this.client, this.cache, this.normalizer, contentContextGetter);
@@ -280,6 +292,65 @@ export class VeryfrontFSAdapter {
280
292
  isPersistentCacheInvalidated(prefix) {
281
293
  return isPrefixBeingInvalidated(prefix);
282
294
  }
295
+ scheduleFileListWarmup(reason, cacheKey) {
296
+ if (!this.initialized || !this.contentContext)
297
+ return;
298
+ const effectiveCacheKey = cacheKey ?? buildFileListCacheKey(this.contentContext);
299
+ if (this.fileListWarmupPromise && this.fileListWarmupKey === effectiveCacheKey) {
300
+ logger.debug("File list warmup already in progress", {
301
+ reason,
302
+ cacheKey: effectiveCacheKey,
303
+ });
304
+ return;
305
+ }
306
+ const warmupContext = this.contentContext;
307
+ let warmupPromise = null;
308
+ warmupPromise = (async () => {
309
+ try {
310
+ const existing = await this.cache.getAsync(effectiveCacheKey);
311
+ if (existing?.length) {
312
+ logger.debug("Skipping file list warmup because cache is already populated", {
313
+ reason,
314
+ cacheKey: effectiveCacheKey,
315
+ fileCount: existing.length,
316
+ });
317
+ return;
318
+ }
319
+ logger.debug("Starting file list warmup", {
320
+ reason,
321
+ cacheKey: effectiveCacheKey,
322
+ sourceType: warmupContext.sourceType,
323
+ branch: warmupContext.branch,
324
+ environmentName: warmupContext.environmentName,
325
+ releaseId: warmupContext.releaseId,
326
+ });
327
+ const files = await fetchFileListForContext(this.client, warmupContext);
328
+ await this.cache.setAsync(effectiveCacheKey, files);
329
+ logger.debug("File list warmup complete", {
330
+ reason,
331
+ cacheKey: effectiveCacheKey,
332
+ totalFiles: files.length,
333
+ filesWithContent: files.filter((file) => file.content).length,
334
+ });
335
+ }
336
+ catch (error) {
337
+ logger.warn("File list warmup failed", {
338
+ reason,
339
+ cacheKey: effectiveCacheKey,
340
+ error: error instanceof Error ? error.message : String(error),
341
+ });
342
+ }
343
+ finally {
344
+ if (warmupPromise && this.fileListWarmupPromise === warmupPromise) {
345
+ this.fileListWarmupPromise = null;
346
+ this.fileListWarmupKey = null;
347
+ }
348
+ }
349
+ })();
350
+ this.fileListWarmupPromise = warmupPromise;
351
+ this.fileListWarmupKey = effectiveCacheKey;
352
+ this.readOps.setFileListReadyPromise(warmupPromise);
353
+ }
283
354
  getPokeMetrics() {
284
355
  return this.wsManager.getPokeMetrics();
285
356
  }
@@ -317,6 +388,8 @@ export class VeryfrontFSAdapter {
317
388
  this.statOps.clearIndex();
318
389
  this.dirOps.clearTree();
319
390
  this.initialized = false;
391
+ this.fileListWarmupPromise = null;
392
+ this.fileListWarmupKey = null;
320
393
  logger.debug("Disposed");
321
394
  }
322
395
  getCacheStats() {
@@ -342,6 +415,7 @@ export class VeryfrontFSAdapter {
342
415
  hasFiles: !!files,
343
416
  fileCount: files?.length ?? 0,
344
417
  });
418
+ this.scheduleFileListWarmup("getAllSourceFiles miss", cacheKey);
345
419
  return [];
346
420
  }
347
421
  const fileSummary = summarizeFileList(files);
@@ -429,6 +503,8 @@ export class VeryfrontFSAdapter {
429
503
  if (contextChanged) {
430
504
  this.statOps.clearIndex();
431
505
  this.dirOps.clearTree();
506
+ this.fileListWarmupPromise = null;
507
+ this.fileListWarmupKey = null;
432
508
  logger.debug("Cleared index and dirTree due to context change", {
433
509
  oldContext,
434
510
  newContext: context,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "veryfront",
3
- "version": "0.1.85",
3
+ "version": "0.1.86",
4
4
  "description": "The simplest way to build AI-powered apps",
5
5
  "keywords": [
6
6
  "react",
package/src/deno.js CHANGED
@@ -1,6 +1,6 @@
1
1
  export default {
2
2
  "name": "veryfront",
3
- "version": "0.1.85",
3
+ "version": "0.1.86",
4
4
  "license": "Apache-2.0",
5
5
  "nodeModulesDir": "auto",
6
6
  "exclude": [
@@ -49,6 +49,9 @@ export class VeryfrontFSAdapter implements FSAdapter {
49
49
 
50
50
  /** Resolves when file list initialization is complete (for coordinating reads) */
51
51
  private fileListReadyResolve: (() => void) | null = null;
52
+ /** Single-flight background rewarm when the file list cache disappears */
53
+ private fileListWarmupPromise: Promise<void> | null = null;
54
+ private fileListWarmupKey: string | null = null;
52
55
 
53
56
  private projectData?: Project;
54
57
  private apiBaseUrl: string;
@@ -140,6 +143,10 @@ export class VeryfrontFSAdapter implements FSAdapter {
140
143
  resultSize: result?.length ?? 0,
141
144
  });
142
145
 
146
+ if (!result?.length) {
147
+ this.scheduleFileListWarmup("getFileList miss", cacheKey);
148
+ }
149
+
143
150
  return result;
144
151
  },
145
152
  hasCachedFileList: async () => {
@@ -158,6 +165,10 @@ export class VeryfrontFSAdapter implements FSAdapter {
158
165
  resultSize: result?.length ?? 0,
159
166
  });
160
167
 
168
+ if (!hasResult) {
169
+ this.scheduleFileListWarmup("hasCachedFileList miss", cacheKey);
170
+ }
171
+
161
172
  return hasResult;
162
173
  },
163
174
  isPersistentCacheInvalidated: (prefix: string) => this.isPersistentCacheInvalidated(prefix),
@@ -202,6 +213,10 @@ export class VeryfrontFSAdapter implements FSAdapter {
202
213
  hasContent: result?.filter((f) => f.content)?.length ?? 0,
203
214
  });
204
215
 
216
+ if (!result?.length) {
217
+ this.scheduleFileListWarmup("getFileListCache miss", cacheKey);
218
+ }
219
+
205
220
  return result;
206
221
  },
207
222
  );
@@ -389,6 +404,73 @@ export class VeryfrontFSAdapter implements FSAdapter {
389
404
  return isPrefixBeingInvalidated(prefix);
390
405
  }
391
406
 
407
+ private scheduleFileListWarmup(reason: string, cacheKey?: string): void {
408
+ if (!this.initialized || !this.contentContext) return;
409
+
410
+ const effectiveCacheKey = cacheKey ?? buildFileListCacheKey(this.contentContext);
411
+
412
+ if (this.fileListWarmupPromise && this.fileListWarmupKey === effectiveCacheKey) {
413
+ logger.debug("File list warmup already in progress", {
414
+ reason,
415
+ cacheKey: effectiveCacheKey,
416
+ });
417
+ return;
418
+ }
419
+
420
+ const warmupContext = this.contentContext;
421
+ let warmupPromise: Promise<void> | null = null;
422
+ warmupPromise = (async () => {
423
+ try {
424
+ const existing = await this.cache.getAsync<Array<{ path: string; content?: string }>>(
425
+ effectiveCacheKey,
426
+ );
427
+
428
+ if (existing?.length) {
429
+ logger.debug("Skipping file list warmup because cache is already populated", {
430
+ reason,
431
+ cacheKey: effectiveCacheKey,
432
+ fileCount: existing.length,
433
+ });
434
+ return;
435
+ }
436
+
437
+ logger.debug("Starting file list warmup", {
438
+ reason,
439
+ cacheKey: effectiveCacheKey,
440
+ sourceType: warmupContext.sourceType,
441
+ branch: warmupContext.branch,
442
+ environmentName: warmupContext.environmentName,
443
+ releaseId: warmupContext.releaseId,
444
+ });
445
+
446
+ const files = await fetchFileListForContext(this.client, warmupContext);
447
+ await this.cache.setAsync(effectiveCacheKey, files);
448
+
449
+ logger.debug("File list warmup complete", {
450
+ reason,
451
+ cacheKey: effectiveCacheKey,
452
+ totalFiles: files.length,
453
+ filesWithContent: files.filter((file) => file.content).length,
454
+ });
455
+ } catch (error) {
456
+ logger.warn("File list warmup failed", {
457
+ reason,
458
+ cacheKey: effectiveCacheKey,
459
+ error: error instanceof Error ? error.message : String(error),
460
+ });
461
+ } finally {
462
+ if (warmupPromise && this.fileListWarmupPromise === warmupPromise) {
463
+ this.fileListWarmupPromise = null;
464
+ this.fileListWarmupKey = null;
465
+ }
466
+ }
467
+ })();
468
+
469
+ this.fileListWarmupPromise = warmupPromise;
470
+ this.fileListWarmupKey = effectiveCacheKey;
471
+ this.readOps.setFileListReadyPromise(warmupPromise);
472
+ }
473
+
392
474
  getPokeMetrics(): {
393
475
  received: number;
394
476
  invalidationsTriggered: number;
@@ -442,6 +524,8 @@ export class VeryfrontFSAdapter implements FSAdapter {
442
524
  this.statOps.clearIndex();
443
525
  this.dirOps.clearTree();
444
526
  this.initialized = false;
527
+ this.fileListWarmupPromise = null;
528
+ this.fileListWarmupKey = null;
445
529
 
446
530
  logger.debug("Disposed");
447
531
  }
@@ -473,6 +557,7 @@ export class VeryfrontFSAdapter implements FSAdapter {
473
557
  hasFiles: !!files,
474
558
  fileCount: files?.length ?? 0,
475
559
  });
560
+ this.scheduleFileListWarmup("getAllSourceFiles miss", cacheKey);
476
561
  return [];
477
562
  }
478
563
 
@@ -584,6 +669,8 @@ export class VeryfrontFSAdapter implements FSAdapter {
584
669
  if (contextChanged) {
585
670
  this.statOps.clearIndex();
586
671
  this.dirOps.clearTree();
672
+ this.fileListWarmupPromise = null;
673
+ this.fileListWarmupKey = null;
587
674
  logger.debug("Cleared index and dirTree due to context change", {
588
675
  oldContext,
589
676
  newContext: context,