# Import Map Pre-Resolution in Understand-Anything: Eliminating Re-Parsing in File Analyzers

> Learn how import map pre-resolution in Understand Anything eliminates re-parsing by building a shared context for fast in-memory lookups in file analyzers.

- Repository: [Yuxiang Lin/Understand-Anything](https://github.com/Lum1104/Understand-Anything)
- Tags: internals
- Published: 2026-05-31

---

**Import map pre-resolution builds a shared resolution context once at script startup, allowing every file analyzer to resolve imports via cheap in-memory lookups instead of re-parsing configuration files.**

The Understand-Anything project by Lum1104 implements a high-performance import analysis pipeline that avoids expensive re-parsing operations. By leveraging **import map pre-resolution**, the system processes large monorepos with linear time complexity rather than quadratic degradation. This article examines how `extract-import-map.mjs` constructs a reusable resolution context that eliminates redundant file system operations during per-file import analysis.

## The Bottleneck of Per-File Configuration Parsing

Traditional static analysis tools often re-read configuration files for every source file they analyze. When resolving TypeScript imports, this means repeatedly parsing [`tsconfig.json`](https://github.com/Lum1104/Understand-Anything/blob/main/tsconfig.json) files; for Go projects, re-reading `go.mod` modules; and for PHP codebases, re-parsing [`composer.json`](https://github.com/Lum1104/Understand-Anything/blob/main/composer.json) autoload maps. This approach creates O(n×m) complexity where n is the file count and m is the configuration depth, causing severe performance degradation in large codebases.

## Architecture of the Pre-Resolution Cache

The solution implemented in `understand-anything-plugin/skills/understand/extract-import-map.mjs` separates expensive I/O operations from per-file resolution logic. The system loads all configuration data once, indexes it into memory-efficient data structures, and provides read-only access to individual file analyzers.

### One-Time Loading of TypeScript, Go, and PHP Configurations

The pipeline begins by eagerly loading all project configurations before processing individual files. Three specialized functions parse and cache these settings:

- `loadTsConfigs` parses every [`tsconfig.json`](https://github.com/Lum1104/Understand-Anything/blob/main/tsconfig.json) found in the project and stores results in a `Map`, eliminating per-file re-reads of compiler options.
- `loadGoModules` performs the same caching operation for all `go.mod` files discovered during the project scan.
- `loadPhpAutoloads` extracts PSR-4 autoload mappings from every [`composer.json`](https://github.com/Lum1104/Understand-Anything/blob/main/composer.json) into a reusable lookup table.

These functions execute during script initialization, ensuring that JSON and CSON parsing occurs exactly once regardless of how many files reference these configurations.

### Constructing the Shared Resolution Context

After collecting the project files, the `buildResolutionContext` function assembles a single immutable context object used by all resolvers. This context contains:

- `fileSet`: A `Set` of every project-relative file path for O(1) existence checks.
- `tsConfigs`, `goModules`, `phpAutoloads`: The pre-parsed configuration maps from the previous step.
- Language-specific indexes (`javaIndex`, `kotlinIndex`, `csIndex`) built via `buildSuffixIndex` for rapid package-to-path resolution.

This construction happens once per execution, immediately after the file list collection completes.

### Stateless Resolution Functions

Each language resolver—`resolveTsJsImport`, `resolveGoImport`, `resolvePhpImport`, and others—receives the shared context as a parameter. These functions perform pure computation without file system access, looking up pre-loaded maps and probing the in-memory `fileSet`. For example, the TypeScript resolver locates the nearest configuration directory using the cached `tsConfigs` map:

```javascript
const tsConfigDir = findNearestConfigDir(importerDir, ctx.tsConfigs);

```

This pattern ensures that resolving an import requires only map lookups and string manipulation, avoiding any disk I/O or parsing overhead during per-file analysis.

## Performance Characteristics: Linear Time Complexity

By deferring all heavy I/O to the initialization phase, import map pre-resolution transforms the algorithmic complexity of the analysis pipeline. The expensive operations—reading configuration files, parsing JSON, and building suffix indexes—execute exactly once. Per-file resolution becomes a series of cheap hashtable lookups, reducing the total runtime from O(n×m) to O(n) with respect to the file count.

This architecture produces deterministic results even when processing enterprise-scale monorepos containing thousands of source files and hundreds of configuration files.

## Practical Implementation Workflow

The following pattern demonstrates how client code leverages the pre-resolution architecture:

```javascript
// Step 1: Load the project files (produced by scan-project.mjs)
const input = JSON.parse(readFileSync('project-files.json', 'utf-8'));

// Step 2: Build the one-time resolution context
const ctx = buildResolutionContext(input.projectRoot, input.files);

// Step 3: Resolve imports for individual TypeScript files
const file = input.files[0]; // e.g., { path: 'src/foo.ts', imports: [...] }
const imports = file.imports.map(i => ({
  source: i.source,
  resolved: resolveTsJsImport(i.source, file, ctx),
}));

// Step 4: Resolve Go imports using the same cached context
const goResolved = resolveGoImport('github.com/example/util', file, ctx);

```

Notice that `ctx` remains constant across all resolution calls, while the resolution functions remain pure and stateless.

## Summary

- **Pre-resolution** eliminates redundant parsing by loading [`tsconfig.json`](https://github.com/Lum1104/Understand-Anything/blob/main/tsconfig.json), `go.mod`, and [`composer.json`](https://github.com/Lum1104/Understand-Anything/blob/main/composer.json) exactly once during script initialization.
- The `buildResolutionContext` function in `extract-import-map.mjs` creates an immutable lookup cache containing file sets, configuration maps, and language-specific indexes.
- Language resolvers operate as pure functions that read from the shared context without performing file system operations.
- This architecture guarantees linear time complexity relative to file count, making large-scale repository analysis feasible.
- The Understand-Anything project implements this pattern to ensure deterministic, high-performance import resolution across TypeScript, Go, PHP, Java, Kotlin, and C# codebases.

## Frequently Asked Questions

### What specific configuration files does the pre-resolution system cache?

The system caches TypeScript compiler configurations ([`tsconfig.json`](https://github.com/Lum1104/Understand-Anything/blob/main/tsconfig.json)), Go module definitions (`go.mod`), and PHP autoload mappings ([`composer.json`](https://github.com/Lum1104/Understand-Anything/blob/main/composer.json)). According to the source code in `understand-anything-plugin/skills/understand/extract-import-map.mjs`, these are loaded via `loadTsConfigs`, `loadGoModules`, and `loadPhpAutoloads` respectively, with results stored in JavaScript `Map` objects for constant-time access.

### How does the resolution context handle different programming languages?

The `buildResolutionContext` function constructs language-specific indexes for Java, Kotlin, and C# using `buildSuffixIndex`, while storing TypeScript, Go, and PHP configurations in dedicated maps. Each resolver function—such as `resolveTsJsImport` or `resolveGoImport`—receives this unified context and accesses only the relevant portions for its target language.

### Why is import map pre-resolution more efficient than on-demand parsing?

On-demand parsing requires reading and parsing configuration files every time an import statement is encountered, resulting in quadratic complexity. Pre-resolution performs all heavy I/O and parsing once at startup, reducing per-file resolution to simple hashtable lookups and string operations that execute in constant time.

### Where can I find the test suite that validates this behavior?

The deterministic behavior and absence of per-file re-parsing are verified in `tests/skill/understand/test_extract_import_map.test.mjs`. This test suite ensures that the import-map generation pipeline produces consistent results without redundant file system access across multiple execution scenarios.