# holgerkrupp/scan architecture

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

- Interactive diagram: https://gitdiagram.com/holgerkrupp/scan
- Repository: https://github.com/holgerkrupp/scan

## Overview

Scan is a native macOS document-scanning app. Users discover and select a scanner, capture pages through a device backend, review them, then process and export files; Shortcuts can initiate scans through App Intents. Fujitsu USB model drivers share a SCSI command engine, while USB, Image Capture, Epjitsu, and Wi-Fi paths provide distinct scanner integrations. Export supports alignment, image processing, OCR, and document-aware filenames. The excerpts show the workspace invoking capture and export components; some unsampled integrations are included from the tree and README, with uncertain connections omitted.

Main entry points: [`Scan/ViewModels/ScannerWorkspaceViewModel.swift`](https://github.com/holgerkrupp/scan/blob/main/Scan/ViewModels/ScannerWorkspaceViewModel.swift) (Scan workspace), [`Scan/ContentView.swift`](https://github.com/holgerkrupp/scan/blob/main/Scan/ContentView.swift) (Scanning workspace UI), [`Scan/ScannerCore/ScannerDriver.swift`](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerDriver.swift) (Driver registry), [`Scan/OutputPipeline/ScanOutputWriter.swift`](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/ScanOutputWriter.swift) (Output writer)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_app["App and workspace"]
  node_content["Scanning workspace UI<br/>[ContentView.swift]"]
  node_intents["App Intents"]
  node_workspace["Scan workspace"]
  node_navigation["Page navigation"]
  node_quicklook["Page Quick Look"]
end

subgraph group_scan["Scanner integration"]
  node_usbdiscovery["USB discovery and transport"]
  node_icabackend["Image Capture backend"]
  node_driverregistry["Driver registry"]
  node_fujitsu["Fujitsu SCSI engine"]
  node_profiles["Fujitsu model profiles"]
  node_fujitsudrivers["Fujitsu model drivers"]
  node_epjitsu["Epjitsu USB drivers"]
  node_wifi["Fujitsu Wi-Fi driver"]
  node_feedsettings["Feeder settings"]
end

subgraph group_output["Page processing and export"]
  node_processor["Image processing"]
  node_alignment["Page alignment"]
  node_writer["Output writer"]
  node_analysis["Document analysis"]
  node_naming["Filename suggestions"]
  node_ocr["OCR runner"]
end

subgraph group_support["Scanner information"]
  node_details["Scanner details"]
  node_detailsview["Scanner details UI"]
  node_stats["Scan statistics"]
end

node_user(("Mac user"))
node_shortcuts(("Shortcuts / Siri"))

node_user -->|"uses"| node_content
node_shortcuts -->|"invokes"| node_intents
node_content -->|"drives"| node_workspace
node_intents -->|"requests scans"| node_workspace
node_workspace -.->|"selects driver"| node_driverregistry
node_usbdiscovery -->|"provides devices"| node_icabackend
node_icabackend -->|"uses drivers"| node_driverregistry
node_driverregistry -->|"dispatches models"| node_fujitsudrivers
node_driverregistry -.->|"dispatches models"| node_epjitsu
node_driverregistry -.->|"dispatches backend"| node_wifi
node_fujitsudrivers -->|"creates device"| node_fujitsu
node_fujitsu -->|"uses profile"| node_profiles
node_fujitsu -->|"applies settings"| node_feedsettings
node_workspace -->|"processes pages"| node_processor
node_processor -->|"aligns pages"| node_alignment
node_workspace -->|"exports pages"| node_writer
node_writer -->|"processes images"| node_processor
node_writer -->|"analyzes text"| node_analysis
node_writer -.->|"suggests names"| node_naming
node_workspace -->|"runs OCR"| node_ocr
node_content -->|"navigates pages"| node_navigation
node_content -.->|"previews pages"| node_quicklook
node_workspace -->|"builds details"| node_details
node_content -->|"shows details"| node_detailsview
node_detailsview -->|"renders details"| node_details
node_detailsview -->|"shows statistics"| node_stats

click node_content "https://github.com/holgerkrupp/scan/blob/main/Scan/ContentView.swift"
click node_intents "https://github.com/holgerkrupp/scan/blob/main/Scan/AppIntents/ScanAppIntents.swift"
click node_workspace "https://github.com/holgerkrupp/scan/blob/main/Scan/ViewModels/ScannerWorkspaceViewModel.swift"
click node_navigation "https://github.com/holgerkrupp/scan/blob/main/Scan/ViewModels/PageGridNavigation.swift"
click node_quicklook "https://github.com/holgerkrupp/scan/blob/main/Scan/PageQuickLook.swift"
click node_usbdiscovery "https://github.com/holgerkrupp/scan/blob/main/Scan/USBTransport/USBScannerDiscovery.swift"
click node_icabackend "https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ImageCaptureScannerBackend.swift"
click node_driverregistry "https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerDriver.swift"
click node_fujitsu "https://github.com/holgerkrupp/scan/blob/main/Scan/FujitsuSCSIOverUSB/FujitsuScanSnapDevice.swift"
click node_profiles "https://github.com/holgerkrupp/scan/blob/main/Scan/FujitsuSCSIOverUSB/FujitsuScanSnapModelProfile.swift"
click node_fujitsudrivers "https://github.com/holgerkrupp/scan/tree/main/Scan/FujitsuSCSIOverUSB"
click node_epjitsu "https://github.com/holgerkrupp/scan/tree/main/Scan/EpjitsuUSB"
click node_wifi "https://github.com/holgerkrupp/scan/blob/main/Scan/WiFiTransport/FujitsuScanSnapWiFiDriver.swift"
click node_feedsettings "https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerFeedSettings.swift"
click node_processor "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/ScanImageProcessor.swift"
click node_alignment "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/PageAlignment.swift"
click node_writer "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/ScanOutputWriter.swift"
click node_analysis "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/DocumentAnalysis.swift"
click node_naming "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/DocumentNameSuggester.swift"
click node_ocr "https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/OCRmyPDFRunner.swift"
click node_details "https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerDetails.swift"
click node_detailsview "https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerDetailsView.swift"
click node_stats "https://github.com/holgerkrupp/scan/blob/main/Scan/Statistics/ScanStatistics.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_content,node_intents,node_workspace,node_navigation,node_quicklook,node_user toneBlue
class node_usbdiscovery,node_icabackend,node_driverregistry,node_fujitsu,node_profiles,node_fujitsudrivers,node_epjitsu,node_wifi,node_feedsettings toneAmber
class node_processor,node_alignment,node_writer,node_analysis,node_naming,node_ocr toneMint
class node_details,node_detailsview,node_stats toneRose
class node_shortcuts toneIndigo
```

## Components

### App and workspace

- [Scanning workspace UI](https://github.com/holgerkrupp/scan/blob/main/Scan/ContentView.swift): `Scan/ContentView.swift`
- [App Intents](https://github.com/holgerkrupp/scan/blob/main/Scan/AppIntents/ScanAppIntents.swift): `Scan/AppIntents/ScanAppIntents.swift`
- [Scan workspace](https://github.com/holgerkrupp/scan/blob/main/Scan/ViewModels/ScannerWorkspaceViewModel.swift): `Scan/ViewModels/ScannerWorkspaceViewModel.swift`
- [Page navigation](https://github.com/holgerkrupp/scan/blob/main/Scan/ViewModels/PageGridNavigation.swift): `Scan/ViewModels/PageGridNavigation.swift`
- [Page Quick Look](https://github.com/holgerkrupp/scan/blob/main/Scan/PageQuickLook.swift): `Scan/PageQuickLook.swift`

### Scanner integration

- [USB discovery and transport](https://github.com/holgerkrupp/scan/blob/main/Scan/USBTransport/USBScannerDiscovery.swift): `Scan/USBTransport/USBScannerDiscovery.swift`
- [Image Capture backend](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ImageCaptureScannerBackend.swift): `Scan/ScannerCore/ImageCaptureScannerBackend.swift`
- [Driver registry](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerDriver.swift): `Scan/ScannerCore/ScannerDriver.swift`
- [Fujitsu SCSI engine](https://github.com/holgerkrupp/scan/blob/main/Scan/FujitsuSCSIOverUSB/FujitsuScanSnapDevice.swift): `Scan/FujitsuSCSIOverUSB/FujitsuScanSnapDevice.swift`
- [Fujitsu model profiles](https://github.com/holgerkrupp/scan/blob/main/Scan/FujitsuSCSIOverUSB/FujitsuScanSnapModelProfile.swift): `Scan/FujitsuSCSIOverUSB/FujitsuScanSnapModelProfile.swift`
- [Fujitsu model drivers](https://github.com/holgerkrupp/scan/tree/main/Scan/FujitsuSCSIOverUSB): `Scan/FujitsuSCSIOverUSB`
- [Epjitsu USB drivers](https://github.com/holgerkrupp/scan/tree/main/Scan/EpjitsuUSB): `Scan/EpjitsuUSB`
- [Fujitsu Wi-Fi driver](https://github.com/holgerkrupp/scan/blob/main/Scan/WiFiTransport/FujitsuScanSnapWiFiDriver.swift): `Scan/WiFiTransport/FujitsuScanSnapWiFiDriver.swift`
- [Feeder settings](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerFeedSettings.swift): `Scan/ScannerCore/ScannerFeedSettings.swift`

### Page processing and export

- [Image processing](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/ScanImageProcessor.swift): `Scan/OutputPipeline/ScanImageProcessor.swift`
- [Page alignment](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/PageAlignment.swift): `Scan/OutputPipeline/PageAlignment.swift`
- [Output writer](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/ScanOutputWriter.swift): `Scan/OutputPipeline/ScanOutputWriter.swift`
- [Document analysis](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/DocumentAnalysis.swift): `Scan/OutputPipeline/DocumentAnalysis.swift`
- [Filename suggestions](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/DocumentNameSuggester.swift): `Scan/OutputPipeline/DocumentNameSuggester.swift`
- [OCR runner](https://github.com/holgerkrupp/scan/blob/main/Scan/OutputPipeline/OCRmyPDFRunner.swift): `Scan/OutputPipeline/OCRmyPDFRunner.swift`

### Scanner information

- [Scanner details](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerCore/ScannerDetails.swift): `Scan/ScannerCore/ScannerDetails.swift`
- [Scanner details UI](https://github.com/holgerkrupp/scan/blob/main/Scan/ScannerDetailsView.swift): `Scan/ScannerDetailsView.swift`
- [Scan statistics](https://github.com/holgerkrupp/scan/blob/main/Scan/Statistics/ScanStatistics.swift): `Scan/Statistics/ScanStatistics.swift`

### Other components

- **Mac user**
- **Shortcuts / Siri**

## Connections

- Mac user → Scanning workspace UI: uses (evidence: `Scan/ContentView.swift`)
- Shortcuts / Siri → App Intents: invokes
- Scanning workspace UI → Scan workspace: drives (evidence: `Scan/ContentView.swift`)
- App Intents → Scan workspace: requests scans (evidence: `Scan/AppIntents/ScanAppIntents.swift`)
- Scan workspace → Driver registry: selects driver
- USB discovery and transport → Image Capture backend: provides devices (evidence: `Scan/ScannerCore/ImageCaptureScannerBackend.swift`)
- Image Capture backend → Driver registry: uses drivers (evidence: `Scan/ScannerCore/ImageCaptureScannerBackend.swift`)
- Driver registry → Fujitsu model drivers: dispatches models (evidence: `Scan/ScannerCore/ScannerDriver.swift`)
- Driver registry → Epjitsu USB drivers: dispatches models (evidence: `Scan/EpjitsuUSB/ScanSnapS300Driver.swift`)
- Driver registry → Fujitsu Wi-Fi driver: dispatches backend (evidence: `Scan/WiFiTransport/FujitsuScanSnapWiFiDriver.swift`)
- Fujitsu model drivers → Fujitsu SCSI engine: creates device (evidence: `Scan/FujitsuSCSIOverUSB/FujitsuScanSnapIX1500Driver.swift`)
- Fujitsu SCSI engine → Fujitsu model profiles: uses profile (evidence: `Scan/FujitsuSCSIOverUSB/FujitsuScanSnapDevice.swift`)
- Fujitsu SCSI engine → Feeder settings: applies settings (evidence: `Scan/FujitsuSCSIOverUSB/FujitsuScanSnapDevice.swift`)
- Scan workspace → Image processing: processes pages (evidence: `Scan/ViewModels/ScannerWorkspaceViewModel.swift`)
- Image processing → Page alignment: aligns pages (evidence: `Scan/OutputPipeline/ScanImageProcessor.swift`)
- Scan workspace → Output writer: exports pages (evidence: `Scan/ViewModels/ScannerWorkspaceViewModel.swift`)
- Output writer → Image processing: processes images (evidence: `Scan/OutputPipeline/ScanOutputWriter.swift`)
- Output writer → Document analysis: analyzes text (evidence: `Scan/OutputPipeline/ScanOutputWriter.swift`)
- Output writer → Filename suggestions: suggests names
- Scan workspace → OCR runner: runs OCR (evidence: `Scan/ViewModels/ScannerWorkspaceViewModel.swift`)
- Scanning workspace UI → Page navigation: navigates pages (evidence: `Scan/ContentView.swift`)
- Scanning workspace UI → Page Quick Look: previews pages
- Scan workspace → Scanner details: builds details (evidence: `Scan/ViewModels/ScannerWorkspaceViewModel.swift`)
- Scanning workspace UI → Scanner details UI: shows details (evidence: `Scan/ContentView.swift`)
- Scanner details UI → Scanner details: renders details (evidence: `Scan/ScannerDetailsView.swift`)
- Scanner details UI → Scan statistics: shows statistics (evidence: `Scan/ScannerDetailsView.swift`)
