getMemoryFiles method

Future<List<MemoryFileInfo>> getMemoryFiles({
  1. bool forceIncludeExternal = false,
})

Discovers and loads all memory files from managed, user, project, and local sources.

Implementation

Future<List<MemoryFileInfo>> getMemoryFiles({
  bool forceIncludeExternal = false,
}) async {
  final result = <MemoryFileInfo>[];
  final processedPaths = <String>{};
  final includeExternal = forceIncludeExternal;

  // 1. Managed memory
  result.addAll(
    await processMemoryFile(
      _getManagedNeomageMdPath(),
      MemoryType.managed,
      processedPaths,
      includeExternal,
    ),
  );
  result.addAll(
    await processMdRules(
      rulesDir: _getManagedNeomageRulesDir(),
      type: MemoryType.managed,
      processedPaths: processedPaths,
      includeExternal: includeExternal,
      conditionalRule: false,
    ),
  );

  // 2. User memory
  if (_isSettingSourceEnabled('userSettings')) {
    result.addAll(
      await processMemoryFile(
        _getUserNeomageMdPath(),
        MemoryType.user,
        processedPaths,
        true,
      ),
    );
    result.addAll(
      await processMdRules(
        rulesDir: _getUserNeomageRulesDir(),
        type: MemoryType.user,
        processedPaths: processedPaths,
        includeExternal: true,
        conditionalRule: false,
      ),
    );
  }

  // 3. Project and Local files (traverse from CWD up to root)
  final originalCwd = _getOriginalCwd();
  final dirs = <String>[];
  var currentDir = originalCwd;
  while (true) {
    dirs.add(currentDir);
    final parent = currentDir.substring(0, currentDir.lastIndexOf('/'));
    if (parent == currentDir || parent.isEmpty) break;
    currentDir = parent;
  }

  // Detect nested worktree to skip duplicated Project files
  final gitRoot = _findGitRoot(originalCwd);
  final canonicalRoot = _findCanonicalGitRoot(originalCwd);
  final isNestedWorktree =
      gitRoot != null &&
      canonicalRoot != null &&
      gitRoot.toLowerCase() != canonicalRoot.toLowerCase() &&
      _pathInWorkingPath(gitRoot, canonicalRoot);

  // Process from root downward to CWD
  for (final dir in dirs.reversed) {
    final skipProject =
        isNestedWorktree &&
        _pathInWorkingPath(dir, canonicalRoot) &&
        !_pathInWorkingPath(dir, gitRoot);

    // Project memory
    if (_isSettingSourceEnabled('projectSettings') && !skipProject) {
      result.addAll(
        await processMemoryFile(
          '$dir/NEOMAGE.md',
          MemoryType.project,
          processedPaths,
          includeExternal,
        ),
      );
      result.addAll(
        await processMemoryFile(
          '$dir/.neomage/NEOMAGE.md',
          MemoryType.project,
          processedPaths,
          includeExternal,
        ),
      );
      result.addAll(
        await processMdRules(
          rulesDir: '$dir/.neomage/rules',
          type: MemoryType.project,
          processedPaths: processedPaths,
          includeExternal: includeExternal,
          conditionalRule: false,
        ),
      );
    }

    // Local memory
    if (_isSettingSourceEnabled('localSettings')) {
      result.addAll(
        await processMemoryFile(
          '$dir/NEOMAGE.local.md',
          MemoryType.local,
          processedPaths,
          includeExternal,
        ),
      );
    }
  }

  _cachedFiles.value = result;
  return result;
}