ADR-0011: Extensibility Strategy for Processing Lenses
DateFebruary 8, 2026
CategoryDomain Logic
Tagsprocessing-flowfeature-flags
Context
- Future features may want to apply different "processing lenses" (e.g., meeting extraction, contact capture, receipts parsing) that transform or enrich
InboxItem during processing.
- We need a design that allows incremental addition of lenses without destabilizing the core processing pipeline.
Decision
We will design processing as a small, pluggable pipeline with a first-class ProcessingLens interface and a registry of lenses. Lenses may be enabled/disabled and versioned.
Core principles:
- Minimal core: the default processing UI and taxonomy (see ADR-0008) remain authoritative.
- Lenses operate as optional, deterministic transforms that can:
- Suggest a
ProcessedType and metadata (tags, category, context)
- Populate
actionDetails (e.g., parsed date for Defer)
- Provide validation warnings or auto-suggestions
- Lenses must be pure (no side effects) and return a typed result; any persistence must be done by the central processing orchestrator.
- Lens metadata (id, version, description, enabled) will be stored so processed items can record which lens (if any) influenced them.
Scope boundaries:
- This ADR defines the high-level strategy and constraints for lenses. Specific lens implementations (e.g., receipts parser) will be separate ADRs or design documents.
Rationale
- Pluggability allows evolving functionality without changing the processing core.
- Versioning lenses protects against behavior changes affecting historical processed items; storing lens id/version with the
ProcessedItem improves reproducibility.
- Pure lenses simplify testing and reasoning.
Consequences
-
Positive:
- Easy to add specialized processors later (ML-based or heuristic) behind feature flags.
- Clear separation of concerns: UI/orchestration vs transformation logic.
-
Downsides:
- Additional coordination when lenses should be chained (need deterministic ordering).
- Slight implementation overhead for registry, versioning, and lens contracts.
Implementation notes
- Define a
ProcessingLens interface in the codebase with a stable input/output contract and a light-weight result object.
- Store
lensId and lensVersion (nullable) on ProcessedItem when a lens materially affects the result.
- Start with a single default/no-op lens and add a registry that can be extended behind feature flags.