Skip to content

feat(rag): typed HelpCorpusAdapter protocol; localize dynamic import#10

Merged
silversurfer562 merged 1 commit into
mainfrom
feat/help-corpus-adapter
May 8, 2026
Merged

feat(rag): typed HelpCorpusAdapter protocol; localize dynamic import#10
silversurfer562 merged 1 commit into
mainfrom
feat/help-corpus-adapter

Conversation

@silversurfer562
Copy link
Copy Markdown
Member

Phase A of specs/architecture-realignment. Closes code-review finding #4.

AttuneHelpCorpus.__init__ now takes a typed HelpCorpusAdapter. The dynamic import is gone from the module body and lives in one classmethod factory (from_attune_help()). Existing call site in pipeline.py updated; existing 7 tests updated; 2 new tests verify the protocol path works without attune-help in scope.

Deviation from design.md noted in commit body: shipped a smaller protocol (templates_root, version) than the draft (iter_entries, name, version) because iteration already lives in DirectoryCorpus.

308 passed, 3 xpassed.

🤖 Generated with Claude Code

Phase A of specs/architecture-realignment (workspace-level spec
2026-05-08). Closes finding #4 from the 2026-05-07 code-review:
``importlib.import_module("attune_help")`` lived at the module body
of attune_rag.corpus.attune_help, hiding the rag→help dependency
from static analysis.

Changes:

- New ``attune_rag/corpus/help_adapter.py`` defines the
  ``HelpCorpusAdapter`` Protocol (``templates_root``, ``version``).
  Smaller surface than the design.md draft (no ``iter_entries``);
  iteration stays in DirectoryCorpus where it already lives. Honest-
  to-the-code wins.

- ``AttuneHelpCorpus.__init__`` now takes an adapter explicitly.
  ``AttuneHelpCorpus.from_attune_help()`` is the convenience factory
  that does the dynamic import inside one classmethod call instead of
  the module body. Static analyzers see the rag→help boundary as a
  runtime-only dependency in this single function.

- Module-level ``_BundledAdapter`` frozen dataclass implements the
  protocol for the bundled-help case. Lifted out of the factory body
  because Python's class-body scoping rules don't see enclosing-
  function locals (one test made me discover this the hard way).

Two new tests:
- ``test_corpus_works_with_injected_adapter`` exercises the protocol
  path end-to-end; verifies the adapter is the only import surface
  needed for a working corpus.
- ``test_invalid_templates_root_raises`` verifies adapter validation
  fails at construction with a clear error.

Existing 7 tests updated to use ``.from_attune_help()``. Full suite:
308 passed, 3 xpassed.

Co-Authored-By: Claude Opus 4.7 <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