Skip to content

refactor(spi): decouple plugins from core graph model via declaration records#7

Merged
Schr0d merged 13 commits into
mainfrom
feature/plugin-spi-adapter
Apr 14, 2026
Merged

refactor(spi): decouple plugins from core graph model via declaration records#7
Schr0d merged 13 commits into
mainfrom
feature/plugin-spi-adapter

Conversation

@Schr0d

@Schr0d Schr0d commented Apr 14, 2026

Copy link
Copy Markdown
Owner

$EXISTING

Documentation

  • CHANGELOG.md: Voice polished v0.6.0.2 entry — rewrote bullets to lead with what users can do, not implementation details. Added test count (233).
  • README.md, README-zh.md, DESIGN.md, TODOS.md: Reviewed, no updates needed (all current).
  • VERSION: Already bumped to 0.6.0.2 by /ship, covers all changes.
  • Project memory updated to reflect current version, test count, and new declaration-based SPI architecture.

Schr0d and others added 13 commits April 14, 2026 11:00
…ion, re-exported enums

Introduce the foundational SPI types in com.archon.core.plugin that will
replace direct graph model usage in language plugins. Plugins will return
declarations instead of building the graph themselves.

New types:
- DependencyDeclaration record (source/target IDs, edge type, confidence, evidence, dynamic flag)
- ModuleDeclaration record (ID, node type, source path, confidence)
- EdgeType enum (IMPORTS, CALLS, IMPLEMENTS, EXTENDS, USES)
- Confidence enum (HIGH, MEDIUM, LOW)
- NodeType enum (CLASS, MODULE, PACKAGE, SERVICE, CONTROLLER)

Both records have compact canonical constructors with null/blank validation.
28 tests pass (0 failures).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Code review finding I-1: confidence was the only reference parameter
not validated in compact constructors. Both records now reject null
confidence with a clear NPE message. Tests added for both.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…DomainStrategy, add declaration fields to ParseResult

LanguagePlugin interface changes:
- Remove DependencyGraph.MutableBuilder parameter from parseFromContent()
- Remove getDomainStrategy() (dead code — DomainDetector is used directly)
- Remove DomainStrategy import

ParseResult changes:
- Add moduleDeclarations and declarations fields
- Add full constructor with all 6 fields
- Existing constructors delegate to full constructor with empty lists for new fields

ParseOrchestrator changes:
- Updated to call parseFromContent() without builder
- New mergeGraphIntoBuilder() merges each plugin's returned graph into shared builder
- Removed unused DomainStrategy import

Tests updated in LanguagePluginTest, ParseResultTest, PluginDiscovererTest,
and ParseOrchestratorTest to match new interface.

Note: Production plugins (archon-java, archon-js, archon-python) will be
updated in subsequent tasks. archon-core tests pass independently.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…stale test methods

Remove production-dead DomainStrategy implementations from all three plugin
modules (Java, JS, Python) along with their test files and the getDomainStrategy()
override from each plugin class. AnalysisPipeline uses DomainDetector directly.

Delete GraphBuilder, a fluent wrapper around DependencyGraph.MutableBuilder that
added no value after the SPI change. Migrate all core and CLI callers to use
MutableBuilder directly, converting chained fluent calls to sequential statements.

- Net: -612 lines of dead code, 0 functional behavior change
- Plugin modules still reference GraphBuilder internally (AstVisitor, etc.)
  — those will be migrated in Tasks 5-7

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
… declarations

ParseOrchestrator now supports two paths:
- Declaration path (primary): collects ModuleDeclaration and DependencyDeclaration
  records from plugins, deduplicates nodes, builds edges with skip-on-missing-target
  semantics, and strips namespace prefixes.
- Legacy path (backward compat): if a plugin returns empty declarations, falls back
  to merging its returned graph into the shared builder.

This allows incremental migration of plugins from graph-returning to
declaration-returning. Plugins will be migrated in subsequent tasks.

Also adds knownNodeIds() to MutableBuilder and fixes DependencyGraphTest
references to deleted GraphBuilder.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- JavaPlugin: remove builder param, collect ModuleDeclaration and
  DependencyDeclaration alongside graph, return 6-arg ParseResult
- AstVisitor: replace GraphBuilder with DependencyGraph.MutableBuilder,
  add declaration collection lists and getters
- JavaParserPlugin: replace GraphBuilder with MutableBuilder, switch
  graph.BlindSpot to plugin.BlindSpot
- BlindSpotDetector: switch from graph.BlindSpot (4-arg) to
  plugin.BlindSpot (3-arg: type, location, description)
- Tests: update all test files for new API, add declaration verification
  tests for module and dependency declarations

Zero GraphBuilder and graph.BlindSpot references remain in archon-java.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Remove builder param from parseFromContent (matching updated SPI), create
local MutableBuilder for backward-compat graph, collect ModuleDeclaration
and DependencyDeclaration lists alongside graph nodes/edges, and return
ParseResult with all six fields populated. Add two new tests verifying
declaration output. All 8 tests pass.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Remove builder param from parseFromContent (interface already changed).
Create local MutableBuilder for backward-compat graph. Collect
ModuleDeclaration and DependencyDeclaration lists alongside graph
edges. Return both via ParseResult for ParseOrchestrator consumption.

Same pattern as JS plugin: plugin-package enums imported directly,
graph-package enums used with fully qualified names.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
DiffCommand.buildBaseGraph was calling parseFromContent with a 4-arg
signature (filePath, content, context, MutableBuilder) that no longer
exists on the LanguagePlugin interface. Updated to use the 3-arg
signature and manually merge the returned ParseResult graph into the
temp builder before stripping namespace prefixes.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…extraction

- Remove dead declaration fields from AstVisitor (never populated)
- Delete orphaned graph/BlindSpot, DomainStrategy, DomainStrategyTest
- Fix stale Javadoc in LanguagePlugin (MutableBuilder → declarations)
- Add INTERFACE/ENUM to NodeType, detect in AstVisitor/JavaPlugin
- Extract ParseContext.MAX_FILE_SIZE shared constant
- Extract DependencyGraph.mergeInto() static helper
- Extract DeclarationPlugin and GraphTestBuilders test utilities
- Add EnumSyncTest for compile-time enum safety
- Add 3 missing ParseOrchestrator test paths

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…o core, harden validation

- Extract shared DeclarationGraphBuilder utility eliminating duplicated
  declarations-to-graph conversion logic from ParseOrchestrator,
  DiffCommand, and JavaParserPlugin (3 call sites -> 1)
- Replace System.err.println warnings with collected warnings in
  ParseResult error list (testable, redirectable)
- Move ModuleDetector from archon-java to archon-core/util, eliminating
  cli -> java compile-time dependency and ~20 lines of reflection
- Add namespace prefix validation to ModuleDeclaration and
  DependencyDeclaration IDs (catches missing prefix at construction)
- Add equals/hashCode to BlindSpot for safe Set/Map usage
- Change archon-cli build.gradle: implementation -> runtimeOnly for
  archon-java dependency
- Update EdgeSkipWarningTest to verify warnings via parseErrors instead
  of System.err capture
- Add DeclarationGraphBuilderTest (8 tests), DependencyGraphTest additions
  for mergeInto/knownNodeIds, ParseResultTest additions for null graph

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@Schr0d Schr0d merged commit 7ba1ab8 into main Apr 14, 2026
1 check passed
Schr0d added a commit that referenced this pull request Apr 15, 2026
- Update AnalyzeCommand description to mention impact assessment
- README/README-zh: remove view/impact/check/ecp references, update
  CLI to analyze+diff only, remove archon-viz from architecture, add
  v0.7 to roadmap, update blind spots (Spring DI now detected)
- CHANGELOG: add v0.7.1.0 entry for SpringDIPostProcessor + command slash
- skill.md/SKILL.md: replace view --format json with analyze --format
  agent, remove Spring DI from blind spots lists
- TODOS: mark #4/#6/#8 DONE, mark #5/#7 OBSOLETE, update remaining
  items to reflect current state

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Schr0d added a commit that referenced this pull request Apr 16, 2026
* feat(core): add SPRING_DI edge type to both EdgeType enums

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(spi): add postProcess() hook to LanguagePlugin for post-parse edge discovery

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(core): integrate postProcess hook into ParseOrchestrator with graph rebuild

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(java): add ArchUnit dependency and ClassDirectoryFinder for Maven/Gradle auto-detection

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(java): SpringDIPostProcessor with ArchUnit bytecode scanning for Spring DI

Uses ArchUnit ClassFileImporter to scan compiled .class files for Spring DI
patterns: @Autowired fields, @resource fields, and constructor injection.
Resolves interface types to concrete @Component/@Service/@repository
implementations and reports ambiguous injections as blind spots.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat(java): wire SpringDIPostProcessor into JavaPlugin.postProcess()

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* legal: add THIRD-PARTY-NOTICES for ArchUnit Apache 2.0

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(java): support javax.annotation.Resource + add @Autowired constructor test

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* chore: bump version to 0.7.1.0 for SpringDIPostProcessor

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor(cli): slash to analyze + diff only, merge impact into analyze --target

Remove check, ecp, view commands. Impact analysis now via analyze --target.
EcpGenerator stub removed.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: sync all docs for v0.7.1.0 command consolidation + Spring DI

- Update AnalyzeCommand description to mention impact assessment
- README/README-zh: remove view/impact/check/ecp references, update
  CLI to analyze+diff only, remove archon-viz from architecture, add
  v0.7 to roadmap, update blind spots (Spring DI now detected)
- CHANGELOG: add v0.7.1.0 entry for SpringDIPostProcessor + command slash
- skill.md/SKILL.md: replace view --format json with analyze --format
  agent, remove Spring DI from blind spots lists
- TODOS: mark #4/#6/#8 DONE, mark #5/#7 OBSOLETE, update remaining
  items to reflect current state

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(cli): pipe buffer deadlock, ArchUnit log spam, and test coverage

- Fix CliGitAdapter pipe buffer deadlock: drain output stream
  concurrently with waitFor() to prevent 60s hangs on large git show
- Add logback.xml to suppress ArchUnit/Javaparser DEBUG logging
- Cap unbounded module listing in analyze --target (max 20 shown)
- Add 5 tests for resolveTarget/stripNamespacePrefix (replaced
  deleted ImpactCommandTest coverage)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: update CHANGELOG with bug fixes for v0.7.1.0

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor(viz): remove dead ViewCommand and visualization classes

ViewCommand was removed from ArchonCli in the CLI consolidation but the
class and its dependency tree were left behind. Removed:
- ViewCommand, ViewCommandTest (dead CLI entry point)
- TerminalRenderer, TerminalRendererTest (only used by ViewCommand)
- PerspectiveBuilder, PerspectiveBuilderTest (unused visualization)
- NodeGroup, NodeView, EdgeView, PerspectiveView (internal to above)

Kept: JsonSerializer, DiffSerializer, ViewServer (used by analyze/diff)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix(cli): --json output no longer mixed with text summary

Moved --json output handling before agent format auto-detection so JSON
output short-circuits cleanly instead of printing after the human-readable
summary.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant