# AutoIngest **Author:** Jeremy Anderson **Contact:** info@dcos.net **Website:** [dcos.net](https://dcos.net) --- ## What It Does AutoIngest is a Windows tray-resident tool that silently moves photos off an SD card or USB drive into a dated folder on your PC. Plug in the card, the `.jpg`s are **moved** (not copied) to `~/Pictures/YYYY-MM-DD/`, and any RAW/HEIC/PNG files are converted to JPG and the originals removed from the card. A small toast pops into the corner while it's working, then disappears. Duplicate-aware within a single day — if you re-insert the same card on the same day, byte-identical files are skipped. Built for eBay sellers who just want the photos off the camera and into a folder, with nothing to click. ## Features ### Silent move-import (the core) - Polls for removable drives every 4 seconds via kernel32 `GetDriveType` and `GetVolumeInformationW` - Probes DCIM, Pictures, and root folders for image files - **Moves** JPG/JPEG files directly to `~/Pictures//` — no dupes left on the device - Converts all other formats (RAW, HEIC, PNG, etc.) to progressive JPG, then deletes the original from the card - Same-day duplicate aware: within today's import folder, byte-identical files (matched by size then SHA-256) are skipped rather than re-imported - Verify-before-delete: a file is only removed from the card after the destination is confirmed present and correctly sized - Single-instance enforcement via named mutex ### Toast UI - Lives in the system tray by default — no window at startup - A small borderless toast pops into the bottom-right corner when an import starts - Shows live status (`Moving 3/12: IMG_004.jpg`) and a scrolling log - Auto-hides ~4 seconds after the import completes - Left-click the tray icon to peek at status on demand; right-click for the menu (show status, open import folder, reset drive memory, about, exit) ### Image Conversion - Powered by [Magick.NET](https://github.com/dlemstra/Magick.NET) (ImageMagick 7 bindings) - Handles 30+ input formats: JPG, PNG, BMP, TIFF, WebP, CR2, CR3, NEF, ARW, DNG, HEIC, HEIF, SVG, RAW, and more - Converts at native resolution (no downscaling) to preserve full image detail - Outputs progressive, optimized JPG ## Architecture ``` AutoIngest/ ├── AutoIngest.csproj Project file, package reference, assembly metadata ├── App/ WinForms UI layer (namespace AutoIngest.App) │ ├── Program.cs Entry point, single-instance mutex │ ├── MainForm.cs Tray icon, toast show/hide, monitor wiring │ ├── MainForm.Designer.cs Toast popup layout (WinForms Designer) │ ├── MainForm.resx Designer resource header │ └── app.manifest Windows 10/11 compatibility manifest ├── Core/ Config/models layer (namespace AutoIngest.Core) │ └── ConfigManager.cs JSON config persistence └── Engine/ Import/conversion layer (namespace AutoIngest.Engine) ├── SDCardMonitor.cs Background drive polling, photo discovery, move/convert pipeline └── ImageConverter.cs Magick.NET wrapper for universal format-to-JPG conversion ``` **Single NuGet dependency:** `Magick.NET-Q16-AnyCPU` ## Design Decisions | Decision | Rationale | |----------|-----------| | Move, not copy | The card is the source of truth; leaving dupes after import causes confusion. Move it once, done. | | Same-day dedupe | Re-inserting a card on the same day shouldn't double-import. Within today's folder, byte-identical files are skipped; name collisions with different content get a `_1`, `_2` suffix. (We are not a cross-day dedupe tool — different days go in different folders.) | | Tray + toast, no main window | This is a silent utility. You shouldn't have to manage a window — it just tells you when it's working. | | C# / .NET 8 over Python | Single-exe deployment. No runtime, pip, or native extension installation on the end user's PC. | | WinForms over WPF | Simple, direct control layout, no XAML complexity. | | Magick.NET over System.Drawing | One library handles all 30+ formats including RAW, HEIC, SVG. | | kernel32 P/Invoke over WMI | Deterministic, fast drive detection without COM initialization overhead. | | Polling (4s interval) over WMI events | WMI event subscriptions require COM apartment threading and have inconsistent delivery across Windows versions. | | Flat output directory | Matches the workflow: pull to date folder, open in browser, attach to listing. | ## Building ### Prerequisites - Windows 10/11 - [Visual Studio 2022 Community](https://visualstudio.microsoft.com/vs/community/) (free) with ".NET desktop development" workload - .NET 8 SDK (installed by VS2022 with the desktop workload) ### Build from Visual Studio 1. Open `AutoIngest.sln` 2. Build → Build Solution (or Ctrl+Shift+B) 3. The output exe is in `AutoIngest/bin/Debug/net8.0-windows/` ### Build from command line ```bat cd AutoIngest dotnet restore dotnet build -c Release ``` ### Publish as single exe ```bat REM Framework-dependent (~15 MB, requires .NET 8 desktop runtime on target PC) publish.bat REM Self-contained (~60-80 MB, runs on any Win10/11 PC) publish-standalone.bat ``` ## Deployment Copy the resulting `AutoIngest.exe` to the target PC. No installer required. - **Framework-dependent build:** Requires .NET 8 Desktop Runtime. Windows 11 includes this by default. Windows 10 may need it from [dotnet.microsoft.com](https://dotnet.microsoft.com/download/dotnet/8.0). - **Self-contained build:** No prerequisites. Runs on any Windows 10/11 PC. ## Configuration Config file: `~/.autoingest_config.json` — created automatically on first run. Holds JPG quality and auto-import toggle. ## Tech Stack | Component | Technology | |-----------|------------| | Language | C# 12 / .NET 8 | | UI Framework | Windows Forms | | Image Processing | Magick.NET-Q16-AnyCPU (ImageMagick 7) | | Drive Detection | kernel32 `GetDriveType` + `GetVolumeInformationW` via P/Invoke | | Serialization | System.Text.Json | | Target | Windows 10 1809+ / Windows 11 | ## License MS-PL (Microsoft Public License). See [LICENSE](LICENSE). Author: Jeremy Anderson (info@dcos.net, https://dcos.net).