chore(8.0): final pre-RC1 sweep — API consistency, named errors, orphans, zero-cast codebase
This commit is contained in:
parent
970e08c466
commit
1f7e365a4e
237 changed files with 1951 additions and 49413 deletions
|
|
@ -1,7 +1,7 @@
|
|||
/**
|
||||
* Path Resolution System with High-Performance Caching
|
||||
*
|
||||
* PRODUCTION-READY path resolution for VFS
|
||||
* Path resolution for the VFS
|
||||
* Handles millions of paths efficiently with multi-layer caching
|
||||
*/
|
||||
|
||||
|
|
@ -201,8 +201,9 @@ export class PathResolver {
|
|||
* Falls back to graph traversal if MetadataIndex unavailable
|
||||
*/
|
||||
private async resolveWithMetadataIndex(path: string): Promise<string> {
|
||||
// Access MetadataIndexManager from brain instance (not storage — metadataIndex lives on Brainy)
|
||||
const metadataIndex = (this.brain as any).metadataIndex
|
||||
// Access MetadataIndexManager from brain instance (not storage — metadataIndex
|
||||
// lives on Brainy). Bracket access reaches the private field.
|
||||
const metadataIndex = this.brain['metadataIndex']
|
||||
|
||||
if (!metadataIndex) {
|
||||
// MetadataIndex not available, use graph traversal
|
||||
|
|
@ -256,7 +257,7 @@ export class PathResolver {
|
|||
|
||||
// Use proper graph traversal to find children
|
||||
// VFS relationships are now part of the knowledge graph
|
||||
const relations = await this.brain.getRelations({
|
||||
const relations = await this.brain.related({
|
||||
from: parentId,
|
||||
type: VerbType.Contains
|
||||
})
|
||||
|
|
@ -293,7 +294,7 @@ export class PathResolver {
|
|||
async getChildren(dirId: string): Promise<VFSEntity[]> {
|
||||
// Use O(1) graph relationships (VFS creates these in mkdir/writeFile)
|
||||
// VFS relationships are now part of the knowledge graph (no special filtering needed)
|
||||
const relations = await this.brain.getRelations({
|
||||
const relations = await this.brain.related({
|
||||
from: dirId,
|
||||
type: VerbType.Contains
|
||||
})
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
/**
|
||||
* Virtual Filesystem Implementation
|
||||
*
|
||||
* PRODUCTION-READY VFS built on Brainy
|
||||
* Virtual filesystem built on Brainy
|
||||
* Real code, no mocks, actual working implementation
|
||||
*/
|
||||
|
||||
|
|
@ -102,8 +102,9 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
* Access to BlobStorage for unified file storage
|
||||
*/
|
||||
private get blobStorage() {
|
||||
// TypeScript doesn't know about blobStorage on storage, use type assertion
|
||||
const storage = this.brain['storage'] as any
|
||||
// Bracket access reaches Brainy's private `storage` field; `blobStorage`
|
||||
// is a public (optional) member of BaseStorage, set during brain.init().
|
||||
const storage = this.brain['storage']
|
||||
if (!storage?.blobStorage) {
|
||||
throw new Error(
|
||||
'BlobStorage not available. The storage adapter must run ' +
|
||||
|
|
@ -224,7 +225,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
if (existingRoot) {
|
||||
// Root exists - verify metadata is correct
|
||||
const metadata = (existingRoot as any).metadata || existingRoot
|
||||
const metadata = existingRoot.metadata || existingRoot
|
||||
|
||||
if (!metadata.vfsType || metadata.vfsType !== 'directory') {
|
||||
console.warn('⚠️ VFS: Root metadata incomplete, repairing...')
|
||||
|
|
@ -316,7 +317,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
for (const duplicate of duplicates) {
|
||||
try {
|
||||
await this.brain.delete(duplicate.id)
|
||||
await this.brain.remove(duplicate.id)
|
||||
console.log(`VFS: Deleted old root ${duplicate.id.substring(0, 8)}`)
|
||||
} catch (error) {
|
||||
console.warn(`VFS: Failed to delete old root ${duplicate.id}:`, error)
|
||||
|
|
@ -493,7 +494,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
})
|
||||
|
||||
// Ensure Contains relationship exists (fix for missing relationships)
|
||||
const existingRelations = await this.brain.getRelations({
|
||||
const existingRelations = await this.brain.related({
|
||||
from: parentId,
|
||||
to: existingId,
|
||||
type: VerbType.Contains
|
||||
|
|
@ -588,7 +589,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
}
|
||||
|
||||
// Delete the entity
|
||||
await this.brain.delete(entityId)
|
||||
await this.brain.remove(entityId)
|
||||
|
||||
// Invalidate caches
|
||||
this.pathResolver.invalidatePath(path)
|
||||
|
|
@ -659,7 +660,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
// Get all Contains relationships for this level (in-memory query)
|
||||
for (const parentId of currentLevel) {
|
||||
const relations = await this.brain.getRelations({
|
||||
const relations = await this.brain.related({
|
||||
from: parentId,
|
||||
type: VerbType.Contains
|
||||
})
|
||||
|
|
@ -933,7 +934,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
*
|
||||
* Optimized for cloud storage using batch operations
|
||||
* - Uses gatherDescendants() for efficient graph traversal + batch fetch
|
||||
* - Uses deleteMany() for chunked transactional deletion
|
||||
* - Uses removeMany() for chunked transactional deletion
|
||||
* - Parallel blob cleanup with chunking
|
||||
*
|
||||
* Performance improvement: 4-8x faster on cloud storage (GCS, S3, R2, Azure)
|
||||
|
|
@ -981,10 +982,10 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
// Phase 3: Batch delete all entities (including root directory)
|
||||
const allIds = [...descendants.map(d => d.id), entityId]
|
||||
await this.brain.deleteMany({ ids: allIds, continueOnError: false })
|
||||
await this.brain.removeMany({ ids: allIds, continueOnError: false })
|
||||
} else {
|
||||
// No children or not recursive - just delete the directory entity
|
||||
await this.brain.delete(entityId)
|
||||
await this.brain.remove(entityId)
|
||||
}
|
||||
|
||||
// Invalidate caches (recursive invalidation handles all descendants)
|
||||
|
|
@ -1250,8 +1251,9 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
// Ensure entity has proper VFS metadata structure
|
||||
// Handle both nested and flat metadata structures for compatibility
|
||||
if (!entity.metadata || !entity.metadata.vfsType) {
|
||||
// Check if metadata is at top level (legacy structure)
|
||||
const anyEntity = entity as any
|
||||
// Check if metadata is at top level (legacy structure). Legacy entities
|
||||
// carried VFS fields as extra top-level properties not modeled on Entity.
|
||||
const anyEntity = entity as Entity & Record<string, unknown>
|
||||
if (anyEntity.vfsType || anyEntity.path) {
|
||||
entity.metadata = {
|
||||
path: anyEntity.path || '/',
|
||||
|
|
@ -1387,8 +1389,8 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
// Field 'accessed' still exists in metadata for backward compat but won't update
|
||||
|
||||
private async countRelationships(entityId: string): Promise<number> {
|
||||
const relations = await this.brain.getRelations({ from: entityId })
|
||||
const relationsTo = await this.brain.getRelations({ to: entityId })
|
||||
const relations = await this.brain.related({ from: entityId })
|
||||
const relationsTo = await this.brain.related({ to: entityId })
|
||||
return relations.length + relationsTo.length
|
||||
}
|
||||
|
||||
|
|
@ -1760,7 +1762,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
// legacy data path that hits the copy operation).
|
||||
const newEntity = await this.brain.add({
|
||||
type: srcEntity.type,
|
||||
subtype: (srcEntity as any).subtype ?? 'vfs-file',
|
||||
subtype: srcEntity.subtype ?? 'vfs-file',
|
||||
data: srcEntity.data,
|
||||
vector: options?.preserveVector ? srcEntity.vector : undefined,
|
||||
metadata: {
|
||||
|
|
@ -1791,7 +1793,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
// Copy relationships if requested
|
||||
if (options?.preserveRelationships) {
|
||||
const relations = await this.brain.getRelations({ from: srcEntity.id })
|
||||
const relations = await this.brain.related({ from: srcEntity.id })
|
||||
for (const relation of relations) {
|
||||
if (relation.type !== VerbType.Contains) {
|
||||
// Skip relationship without Contains type
|
||||
|
|
@ -2097,8 +2099,8 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
// Use proper Brainy relationship API to get all relationships
|
||||
const [fromRelations, toRelations] = await Promise.all([
|
||||
this.brain.getRelations({ from: entityId }),
|
||||
this.brain.getRelations({ to: entityId })
|
||||
this.brain.related({ from: entityId }),
|
||||
this.brain.related({ to: entityId })
|
||||
])
|
||||
|
||||
// Add outgoing relationships
|
||||
|
|
@ -2136,8 +2138,8 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
|
||||
// Use proper Brainy relationship API
|
||||
const [fromRelations, toRelations] = await Promise.all([
|
||||
this.brain.getRelations({ from: entityId }),
|
||||
this.brain.getRelations({ to: entityId })
|
||||
this.brain.related({ from: entityId }),
|
||||
this.brain.related({ to: entityId })
|
||||
])
|
||||
|
||||
// Process outgoing relationships (excluding Contains for parent-child)
|
||||
|
|
@ -2185,7 +2187,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
await this.brain.relate({
|
||||
from: fromEntityId,
|
||||
to: toEntityId,
|
||||
type: type as any, // Convert string to VerbType
|
||||
type: type as VerbType, // Convert string to VerbType
|
||||
metadata: { isVFS: true } // Mark as VFS relationship
|
||||
})
|
||||
|
||||
|
|
@ -2201,7 +2203,7 @@ export class VirtualFileSystem implements IVirtualFileSystem {
|
|||
const toEntityId = await this.pathResolver.resolve(to)
|
||||
|
||||
// Find and delete the relationship
|
||||
const relations = await this.brain.getRelations({ from: fromEntityId })
|
||||
const relations = await this.brain.related({ from: fromEntityId })
|
||||
for (const relation of relations) {
|
||||
if (relation.to === toEntityId && (!type || relation.type === type)) {
|
||||
// Delete the relationship using brain.unrelate
|
||||
|
|
|
|||
|
|
@ -31,6 +31,13 @@ export interface ImportOptions {
|
|||
importId?: string // Unique import identifier (auto-generated if not provided)
|
||||
projectId?: string // Project identifier grouping related imports
|
||||
customMetadata?: Record<string, any> // Custom metadata to attach
|
||||
|
||||
/**
|
||||
* Internal: per-import tracking metadata (importIds, projectId, importedAt,
|
||||
* importSource, plus customMetadata) threaded from `import()` into the
|
||||
* directory/file helpers. Not intended to be set by callers.
|
||||
*/
|
||||
_trackingMetadata?: Record<string, unknown>
|
||||
}
|
||||
|
||||
export interface ImportResult {
|
||||
|
|
@ -96,7 +103,7 @@ export class DirectoryImporter {
|
|||
if (stats.isFile()) {
|
||||
await this.importFile(sourcePath, options.targetPath || '/', result)
|
||||
} else if (stats.isDirectory()) {
|
||||
await this.importDirectory(sourcePath, enhancedOptions as any, result)
|
||||
await this.importDirectory(sourcePath, enhancedOptions, result)
|
||||
}
|
||||
} catch (error) {
|
||||
result.failed.push({
|
||||
|
|
@ -220,7 +227,7 @@ export class DirectoryImporter {
|
|||
await collectDirs(sourcePath, targetPath)
|
||||
|
||||
// Create all directories
|
||||
const trackingMetadata = (options as any)._trackingMetadata || {}
|
||||
const trackingMetadata = options._trackingMetadata || {}
|
||||
for (const dirPath of dirsToCreate) {
|
||||
try {
|
||||
await this.vfs.mkdir(dirPath, {
|
||||
|
|
@ -324,7 +331,7 @@ export class DirectoryImporter {
|
|||
}
|
||||
|
||||
// Write to VFS
|
||||
const trackingMetadata = (options as any)._trackingMetadata || {}
|
||||
const trackingMetadata = options._trackingMetadata || {}
|
||||
await this.vfs.writeFile(vfsPath, content, {
|
||||
generateEmbedding: options.generateEmbeddings,
|
||||
extractMetadata: options.extractMetadata,
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ import { RelationshipValue } from '../SemanticPathParser.js'
|
|||
* Relationship Projection: /related-to/<path>/depth-N/types-X,Y
|
||||
*
|
||||
* Uses EXISTING infrastructure:
|
||||
* - Brainy.getRelations() for graph traversal (REAL - line 803 in brainy.ts)
|
||||
* - Brainy.related() for graph traversal
|
||||
* - GraphAdjacencyIndex for O(1) neighbor lookups (REAL)
|
||||
* - VerbType enum for relationship types (REAL - graphTypes.ts)
|
||||
*/
|
||||
|
|
@ -28,7 +28,7 @@ export class RelationshipProjection extends BaseProjectionStrategy {
|
|||
* Note: Graph queries don't use FindParams, but we provide this for consistency
|
||||
*/
|
||||
toQuery(value: RelationshipValue, subpath?: string): FindParams {
|
||||
// This is informational - actual resolution uses getRelations()
|
||||
// This is informational - actual resolution uses related()
|
||||
return {
|
||||
where: {
|
||||
vfsType: 'file'
|
||||
|
|
@ -42,7 +42,7 @@ export class RelationshipProjection extends BaseProjectionStrategy {
|
|||
}
|
||||
|
||||
/**
|
||||
* Resolve relationships using REAL Brainy.getRelations()
|
||||
* Resolve relationships using REAL Brainy.related()
|
||||
* Uses GraphAdjacencyIndex for O(1) graph traversal
|
||||
*/
|
||||
async resolve(brain: Brainy, vfs: VirtualFileSystem, value: RelationshipValue): Promise<string[]> {
|
||||
|
|
@ -71,7 +71,7 @@ export class RelationshipProjection extends BaseProjectionStrategy {
|
|||
}
|
||||
|
||||
/**
|
||||
* Recursive graph traversal using REAL Brainy.getRelations()
|
||||
* Recursive graph traversal using REAL Brainy.related()
|
||||
*/
|
||||
private async traverseRelationships(
|
||||
brain: Brainy,
|
||||
|
|
@ -88,7 +88,7 @@ export class RelationshipProjection extends BaseProjectionStrategy {
|
|||
visited.add(entityId)
|
||||
|
||||
// Get outgoing relationships (REAL method - line 803 in brainy.ts)
|
||||
const relations = await brain.getRelations({
|
||||
const relations = await brain.related({
|
||||
from: entityId,
|
||||
limit: 100
|
||||
})
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue