# msulemans/local-lens architecture

> Architecture diagram of the GitHub repository msulemans/local-lens, generated by GitDiagram from its file tree, README and a sample of source files (last updated 2026-09-27). It is an AI-made overview: check details against the source.

- Interactive diagram: https://gitdiagram.com/msulemans/local-lens
- Repository: https://github.com/msulemans/local-lens

## Overview

Local Lens is a native Mac research workspace that finds public sources, saves their passages, and presents answers with inspectable citations. A user selects Quick, Deep, Academic, or News; the workspace plans bounded searches, acquires and extracts pages, retrieves saved passages, and compiles cited answers or evidence-only results. Reports expose coverage, gaps, and conflicting or independent evidence; users can inspect citations and reopen or export saved research. The graph reflects documented capabilities and sampled orchestration; unsampled subsystem wiring is shown only where the README or module boundaries support it.

Main entry points: [`Sources/LocalLensApp/LivingResearchMapView.swift`](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/LivingResearchMapView.swift) (Living Research Map), [`Sources/LocalLensApp/ResearchWorkspaceModel.swift`](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/ResearchWorkspaceModel.swift) (Workspace model), [`Sources/LocalLensCore/ResearchRunner.swift`](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchRunner.swift) (Research runner), [`Sources/LocalLensCore/LiveQuick.swift`](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LiveQuick.swift) (Quick runner)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_workspace["Research workspace"]
  node_workspace["Living Research Map"]
  node_model["Workspace model"]
end

subgraph group_research["Planning and research"]
  node_plan["Mode planning"]
  node_runner["Research runner"]
  node_quickrunner["Quick runner<br/>[LiveQuick.swift]"]
  node_search["Search adapters"]
  node_scholar["Scholarly adapters"]
end

subgraph group_evidence["Evidence and answers"]
  node_acquire["Safe acquisition"]
  node_fetch["Bounded fetch<br/>[BoundedFetch.swift]"]
  node_extract["Page extraction"]
  node_pdf["PDF extraction"]
  node_index["Lexical retrieval<br/>[LexicalIndex.swift]"]
  node_provider["Answer providers"]
  node_compiler["Citation compiler"]
  node_contrast["Evidence comparison"]
end

subgraph group_persistence["Saved research"]
  node_store[("Snapshot store")]
  node_history[("Research history")]
  node_artifact["Answer artifacts"]
  node_export["Citation export"]
end

node_user(("Researcher"))
node_searchservices(("Search services"))
node_hosted(("Hosted or local model"))

node_user -->|"asks or inspects"| node_workspace
node_workspace -->|"updates workspace"| node_model
node_model -->|"plans mode"| node_plan
node_model -->|"runs research"| node_runner
node_model -->|"runs Quick"| node_quickrunner
node_model -->|"loads and saves"| node_history
node_runner -->|"searches queries"| node_search
node_runner -->|"acquires sources"| node_acquire
node_runner -->|"shares snapshots"| node_store
node_runner -->|"compiles answer"| node_quickrunner
node_search -->|"queries"| node_searchservices
node_scholar -.->|"queries scholarly"| node_searchservices
node_acquire -->|"fetches pages"| node_fetch
node_fetch -->|"extracts HTML"| node_extract
node_fetch -->|"extracts PDF"| node_pdf
node_extract -->|"stores passages"| node_store
node_pdf -->|"stores passages"| node_store
node_quickrunner -->|"reads snapshots"| node_store
node_quickrunner -->|"retrieves passages"| node_index
node_quickrunner -.->|"requests answer"| node_provider
node_provider -.->|"sends passages"| node_hosted
node_quickrunner -->|"compiles citations"| node_compiler
node_compiler -->|"resolves passages"| node_index
node_runner -->|"assesses evidence"| node_contrast
node_model -->|"records result"| node_artifact
node_workspace -->|"inspects citations"| node_compiler
node_workspace -->|"shows evidence gaps"| node_contrast
node_workspace -->|"exports sources"| node_export
node_workspace -->|"reopens research"| node_history

click node_workspace "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/LivingResearchMapView.swift"
click node_model "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/ResearchWorkspaceModel.swift"
click node_plan "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchModePolicy.swift"
click node_runner "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchRunner.swift"
click node_quickrunner "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LiveQuick.swift"
click node_search "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SearchAdapter.swift"
click node_scholar "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/OpenAlexSearchAdapter.swift"
click node_acquire "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SafeAcquisition.swift"
click node_fetch "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/BoundedFetch.swift"
click node_extract "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/HTMLExtraction.swift"
click node_pdf "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/PDFExtraction.swift"
click node_store "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SnapshotStore.swift"
click node_index "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LexicalIndex.swift"
click node_provider "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LocalAnswerProvider.swift"
click node_compiler "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/CitationCompiler.swift"
click node_contrast "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/EvidenceContrast.swift"
click node_history "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchHistory.swift"
click node_artifact "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LiveAnswerArtifact.swift"
click node_export "https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/CitationExport.swift"

classDef toneNeutral fill:#f8fafc,stroke:#334155,stroke-width:1.5px,color:#0f172a
classDef toneBlue fill:#dbeafe,stroke:#2563eb,stroke-width:1.5px,color:#172554
classDef toneAmber fill:#fef3c7,stroke:#d97706,stroke-width:1.5px,color:#78350f
classDef toneMint fill:#dcfce7,stroke:#16a34a,stroke-width:1.5px,color:#14532d
classDef toneRose fill:#ffe4e6,stroke:#e11d48,stroke-width:1.5px,color:#881337
classDef toneIndigo fill:#e0e7ff,stroke:#4f46e5,stroke-width:1.5px,color:#312e81
classDef toneTeal fill:#ccfbf1,stroke:#0f766e,stroke-width:1.5px,color:#134e4a
class node_workspace,node_model toneBlue
class node_plan,node_runner,node_quickrunner,node_search,node_scholar toneAmber
class node_acquire,node_fetch,node_extract,node_pdf,node_index,node_provider,node_compiler,node_contrast toneMint
class node_store,node_history,node_artifact,node_export toneRose
class node_user,node_searchservices,node_hosted toneIndigo
```

## Components

### Research workspace

- [Living Research Map](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/LivingResearchMapView.swift): `Sources/LocalLensApp/LivingResearchMapView.swift`
- [Workspace model](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensApp/ResearchWorkspaceModel.swift): `Sources/LocalLensApp/ResearchWorkspaceModel.swift`

### Planning and research

- [Mode planning](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchModePolicy.swift): `Sources/LocalLensCore/ResearchModePolicy.swift`
- [Research runner](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchRunner.swift): `Sources/LocalLensCore/ResearchRunner.swift`
- [Quick runner](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LiveQuick.swift): `Sources/LocalLensCore/LiveQuick.swift`
- [Search adapters](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SearchAdapter.swift): `Sources/LocalLensCore/SearchAdapter.swift`
- [Scholarly adapters](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/OpenAlexSearchAdapter.swift): `Sources/LocalLensCore/OpenAlexSearchAdapter.swift`

### Evidence and answers

- [Safe acquisition](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SafeAcquisition.swift): `Sources/LocalLensCore/SafeAcquisition.swift`
- [Bounded fetch](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/BoundedFetch.swift): `Sources/LocalLensCore/BoundedFetch.swift`
- [Page extraction](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/HTMLExtraction.swift): `Sources/LocalLensCore/HTMLExtraction.swift`
- [PDF extraction](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/PDFExtraction.swift): `Sources/LocalLensCore/PDFExtraction.swift`
- [Lexical retrieval](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LexicalIndex.swift): `Sources/LocalLensCore/LexicalIndex.swift`
- [Answer providers](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LocalAnswerProvider.swift): `Sources/LocalLensCore/LocalAnswerProvider.swift`
- [Citation compiler](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/CitationCompiler.swift): `Sources/LocalLensCore/CitationCompiler.swift`
- [Evidence comparison](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/EvidenceContrast.swift): `Sources/LocalLensCore/EvidenceContrast.swift`

### Saved research

- [Snapshot store](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/SnapshotStore.swift): `Sources/LocalLensCore/SnapshotStore.swift`
- [Research history](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/ResearchHistory.swift): `Sources/LocalLensCore/ResearchHistory.swift`
- [Answer artifacts](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/LiveAnswerArtifact.swift): `Sources/LocalLensCore/LiveAnswerArtifact.swift`
- [Citation export](https://github.com/msulemans/local-lens/blob/main/Sources/LocalLensCore/CitationExport.swift): `Sources/LocalLensCore/CitationExport.swift`

### Other components

- **Researcher**
- **Search services**
- **Hosted or local model**

## Connections

- Researcher → Living Research Map: asks or inspects
- Living Research Map → Workspace model: updates workspace
- Workspace model → Mode planning: plans mode
- Workspace model → Research runner: runs research
- Workspace model → Quick runner: runs Quick
- Workspace model → Research history: loads and saves
- Research runner → Search adapters: searches queries
- Research runner → Safe acquisition: acquires sources
- Research runner → Snapshot store: shares snapshots
- Research runner → Quick runner: compiles answer
- Search adapters → Search services: queries
- Scholarly adapters → Search services: queries scholarly
- Safe acquisition → Bounded fetch: fetches pages
- Bounded fetch → Page extraction: extracts HTML
- Bounded fetch → PDF extraction: extracts PDF
- Page extraction → Snapshot store: stores passages
- PDF extraction → Snapshot store: stores passages
- Quick runner → Snapshot store: reads snapshots
- Quick runner → Lexical retrieval: retrieves passages
- Quick runner → Answer providers: requests answer
- Answer providers → Hosted or local model: sends passages
- Quick runner → Citation compiler: compiles citations
- Citation compiler → Lexical retrieval: resolves passages
- Research runner → Evidence comparison: assesses evidence
- Workspace model → Answer artifacts: records result
- Living Research Map → Citation compiler: inspects citations
- Living Research Map → Evidence comparison: shows evidence gaps
- Living Research Map → Citation export: exports sources
- Living Research Map → Research history: reopens research
