v0.7.0 — Scan Control, Privacy, and a Faster Interface
Everything merged since v0.6.0 (PRs #91–#117).
Scan control (#114)
- Folder exclusion list — Settings gains an on/off toggle plus an editable list of excluded folders (seeded with
node_modules,.git,~/Library/Caches,~/Library/Application Support). Excluded folders are skipped entirely during traversal, not just hidden from results. A right-click "Exclude This Folder" action is available in Largest Files/Folders, Tree Explorer, Cleanup Review, and Duplicate Review (where it targets the file's containing folder). - Live streaming results — the scanner emits throttled in-progress snapshots, so ranked views populate and re-sort while a scan is still running instead of showing "No Items" until it finishes.
- Cancel keeps partial results — cancelling leaves the last streamed snapshot browsable (marked partial) instead of resetting to an empty window.
- Pause/resume — long scans pause and resume from the toolbar (in-memory only; does not survive quitting).
- Rate/elapsed readout — the scan header shows an EMA-smoothed items/sec estimate and elapsed time.
Privacy (#113)
- Redaction toggle — a new Privacy setting masks file/folder names and paths across the entire UI (inspector, tables, tree, duplicates, cleanup, sheets, tooltips, accessibility labels) with stable per-session placeholders like "File 3.mp4" / "Folder 1". Sizes, dates, and counts stay real, and Trash/move/reveal/copy-path always operate on real paths — masking is display-layer only. Built for screen-sharing and screenshots.
Fixes
- Settings controls appeared stuck (#116) —
FilterStorechanges never propagated intoScanStore.objectWillChange, so toggles/steppers didn't visually update until unrelated navigation forced a re-render. Pre-existing bug (reproduces on v0.6.0), caught during redaction verification. - Tree / Storage Map rendered empty on large scans (#112) — depth-first retention exhausted the shared budget before the scan root's own children were retained. Root-level children are now always kept.
- Duplicate detection found almost nothing in typical folders (#112) — default candidate threshold lowered 100 MB → 10 MB, now user-tunable via a Settings stepper; empty states name the active threshold instead of misdirecting.
- Verify Now polish — re-verify taps on an already-completed group are a guaranteed no-op (#105); verification that finds no duplicate groups no longer invalidates caches (#106); cancelling mid-verify clears the spinner correctly and persist failures surface instead of dying silently (#103, #109).
- "Clear Filters" no longer renders as a dead button when no filters are active (#112).
- Search debounce is cancellable and recents persistence is serialized — rapid typing can't resurrect stale queries or interleave writes (#93).
Error surfacing & reliability
- Scan and bookmark failures are categorized (permission denied / missing folder / stale bookmark) and alerts name the affected path instead of a generic message (#96, #102, #108).
- Reveal/Open/Copy Path failures now surface through the standard error alert instead of no-op'ing (#100), including in the keeper comparison sheet (#109).
- Duplicate hash cache I/O errors are reported instead of swallowed (#98); the scanner's error propagation, cancellation checks, and hashing budget policy were tightened (#97).
- Transactional Trash moves preflight in a single pass and capture partial-rollback state so a failed batch reports exactly what moved back (#95); missing-on-disk selections are reported before the move starts (#94).
scan(_:)runs in a structured TaskGroup with a re-entry guard so rapid rescans can't race two scans against each other (#99).
Performance
Scan engine
autoreleasepoolaround the parallel enumeration hot loop cuts peak memory on broad scans; SHA-256 hex encoding uses a lookup table instead of per-byteString(format:)(#112).- Cleanup selection planning collapsed from O(N²) ancestor scans to a hash-join pass (#94).
Interface
- Per-row store subscriptions eliminated; the inspector uses native styling (#107);
StorageItemRowregainedEquatablediff-skipping (#92). - Derived-cache keys normalize irrelevant filter dimensions, so no-op filter changes stop wiping still-valid caches (#101).
- Type Breakdown's up-to-4000-row lists use
LazyVStack; mounted-volume enumeration is cached instead of hittingFileManagerevery sidebar render (#112). - Size bars in Tree Explorer, Type Breakdown, and the Overview storage map are drawn with a shared
Canvasinstead of a per-rowGeometryReader, removing a layout pass per visible row; type/category breakdowns cache per scan + query; "Expand All" enablement no longer re-walks the retained tree; sidebar volume capacity strings no longer do synchronous disk I/O per render (#117).
Website
- The project site was redesigned: dark, data-forward landing page with an animated scan-window hero, and every page (guides, FAQ, privacy, changelog, shortcuts, architecture) unified on one shared design system and nav (#117).
Install
Download StorageScope-0.7.0.dmg, open it, and drag StorageScope to Applications. Requires macOS 14+.
Verify the download:
shasum -a 256 -c StorageScope-0.7.0.dmg.sha256