Skip to content

iOS: complete chip files gallery — dedup, folders, streaming viewer, previews, gallery UX, QoL - #8287

Merged
azooz2003-bit merged 99 commits into
mainfrom
feat-chipgal-complete
Jul 17, 2026
Merged

azooz2003-bit merged 99 commits into
mainfrom
feat-chipgal-complete

Conversation

@azooz2003-bit

@azooz2003-bit azooz2003-bit commented Jul 16, 2026 •

Copy link
Copy Markdown
Collaborator

The complete chip-files-gallery program as one PR (consolidates the former stack per owner request; supersedes #8075, /8086, /8088, /8090, /8103, /8105, /8113, /8121, /8130).

Gallery rows dedup by canonical filesystem identity (symlinks and on-disk case; deleted files keep their lexical row). Folders browse recursively from every entry point with inline navigation pushes, gated by the new mobile.artifactFolderAccess setting (subtree default, oneLevel legacy) with symlink-escape denial and a terminal-scope list RPC; referenced directories appear as gallery rows with capped child counts. Large text renders on an explicit TextKit 1 non-contiguous stack with progressive streaming (first chunk immediately, bounded 256 KiB appends deferred while scrolling), animated Top/End jumps that land at line 1 and true final content, and a 64 MiB cap stating actual size. Client-side preview dispatch adds PDFKit, AVPlayer media via temp files (512 MiB cap), QuickLook documents, structured raw/rendered Markdown, and UTF-8 sniffing for extensionless files with no wire-kind changes. Text features: Highlightr 2.3.0 (MIT; highlight.js BSD-3-Clause) size-thresholded highlighting with an expandable explainer pill, in-file search with match navigation, O(viewport) line-number gutter with go-to-line, wrap toggle and pinch font persisted per kind. Gallery UX: sheet-wide filter chips and sort over the kept Created/Attached/Referenced disclosure groups, sequential page fill so loads only extend the list bottom, image grid, and UIPageViewController swipe paging (one opaque controller per path; cross-page compositing structurally impossible; folders skipped). QoL: mtime-keyed content cache (instant re-opens), zero-jank live refresh with a "N new files" pill, Share/Save to Files/Copy actions, image zoom/pan. Server perf per #8044: bounded per-page stat work, ordering cached per generation, stale-generation cursors restart paging, LRU-bounded artifact index, session records indexed by surface with scan fallback and self-heal (fixes restored sessions losing the scope picker and groups), cell-width tap hit-testing for CJK. Accessibility: huge documents expose one capped element (fixes an AX enumeration livelock). Missing files hidden by default behind a "Show missing files" setting; unified document glyphs; folder counts properly inflected; transcript path taps authorized by session; owner-reported In View authorization fixed.

Verified through four adversarial evidence rounds on a driven simulator (two independent verifier rejections drove rounds 2-4); package suites: CmuxAgentChat 332, CmuxAgentChatUI 93+, CmuxMobileShell 484, plus settings suites; iOS-simulator triple builds for all touched packages; EN+JA localization audited throughout. The chip-on-top hotfix shipped separately in #8124.

🤖 Generated with Claude Code


View with Codesmith Autofix with Codesmith
Need help on this PR? Tag /codesmith with what you need. Autofix is disabled.


Summary by cubic

Completes the iOS chip files gallery with canonical‑path dedup, recursive folder browsing, rich previews, and a fast streaming text viewer. Adds filter/sort and swipe paging, improves caching and performance, and ensures the End bottom‑pin flushes at EOF so jumps land at final content; gates the terminal files chip behind a beta setting and presents viewers before loading for a smoother open.

  • New Features

    • Gallery: de‑dup by canonical path; Created/Attached/Referenced groups with filter chips and sort; pages extend only the bottom; image grid; swipe between files; directories show capped child counts and open inline; terminal files chip gated behind a beta setting.
    • Folders: recursive browsing from any entry; symlink‑escape denied; new mobile.artifactFolderAccess (subtree default, one‑level legacy).
    • Previews: route by filename/MIME to PDFKit, AVPlayer (512 MB cap), Quick Look, rendered/raw Markdown, and UTF‑8 text sniffing; viewers are presented before download; folders are skipped in swipe order; fitted images allow pager swipes.
    • Text: progressive streaming on TextKit 1 with jump to top/end, 64 MB cap, line‑number gutter and go‑to‑line; in‑file search; syntax highlighting via Highlightr 2.3.0 with size‑aware opt‑out; wrap toggle and pinch‑to‑zoom font saved per kind.
    • QoL: mtime‑keyed content cache for instant reopens; live refresh with a “N new files” pill; Share, Save to Files, and Copy actions; image zoom/pan.
  • Bug Fixes

    • Authorization and paging: restart on stale generations; keep restored sessions’ scope/groups; authorize transcript taps per session; fix “In View” scan authorization.
    • Terminal and taps: measure hit targets by terminal cell width (CJK) and parse bare filenames; listed paths remain authorized as views change.
    • Accessibility and UX: expose huge docs as one capped element; hide missing files by default; correct folder counts and unify document glyphs; present viewer first to avoid blank waits; allow paging gestures when images fit.
    • Viewer jumps: converge top/end jumps after layout, keep End bottom‑pinned while streaming, bound end‑jump settling, drain the final bottom‑pin flush so EOF jumps finish at true final content, never defer appends for pin‑owned scrolls, and rearm End jumps on cold‑opens/while streaming.
    • Repo/UI: restored ghostty and bonsplit submodule pointers to match main; resolved workspace Highlightr 2.3.0 pin; restored main’s sidebar row‑slot view to fix a self‑capture regression.

Written for commit b778014. Summary will update on new commits.

Review in cubic

Summary by CodeRabbit

  • New Features
    • Added capped directory browsing with truncation indicators and per-folder child counts.
    • Expanded artifact galleries with filters, sorting, swipe paging, eager paging, and live refresh.
    • Upgraded artifact viewer to support folder/image/PDF/media/Quick Look/text+Markdown/binary, with find-in-file, line jumping, syntax highlighting, and share/save/copy.
    • Added streamed artifact fetching and on-device caching for preview bytes.
    • Added mobile settings for folder access (subtree vs one-level) and a “show missing files” toggle.
  • Bug Fixes
    • Improved UTF-8 streaming/typing detection and tap hit-testing for wide Unicode.
  • Documentation
    • Documented the new folder-access and “show missing files” settings.

cmux reload-cloud and others added 30 commits July 14, 2026 12:10
SessionGallerySnapshot is a typealias of the shared ChatArtifactGallerySnapshot,
whose behavior is covered by ChatArtifactGallerySnapshotTests in CmuxAgentChat.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
…h(for:)

Apply the injected ChatArtifactPathCanonicalizer to the requested path and each
candidate so single-path resolution returns the same identity key that
artifactPaths(limit:) lists, keeping scope identity consistent across both
entrypoints.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The caseless ChatArtifactViewerRouting namespace enum fails the iOS
package-conventions lint; extend the receiver instead.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Move the terminal artifact RPCs to MobileChatEventSource+TerminalArtifacts
so MobileChatEventSource stays under the 500-line tracking threshold, move
the two new capability constants next to their computed properties in
MobileShellComposite+Capabilities, and move parseMobileSection plus
parseMarkdownSection into KeyboardShortcutSettingsFileStore+SectionParsers
so the hard-capped store and composite files end at or below their base
line counts.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The UIKit-gated viewer never compiles in host swift test runs, so the
non-exiting guard only surfaced in an iOS-triple build.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Legacy-client directory filtering now uses one fileExists check per indexed
path instead of a full attribute stat, and directory rows count children
with an unsorted name listing instead of building the sorted, stat-enriched
500-entry listing just to read its count.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Use a lazy shallow enumerator that exits after cap+1 entries so a gallery
row over a huge folder costs at most 501 reads instead of materializing
every child name.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The router already trusted wire MIME for extensionless PDFs but not for
audio/video, so a MIME-typed recording without a known extension fell
through to the binary placeholder. Route media by extension UTType or
MIME UTType, matching the PDF check.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Pinned above the bottom toolbar it covered the input row users type
into; anchored at the top safe-area inset instead, sliding in from the
top edge.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
cmux reload-cloud and others added 4 commits July 16, 2026 18:08
The consolidation merge staged stale worktree submodule checkouts,
reverting main's pointers this branch never intended to touch.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In
`@Packages/iOS/CmuxAgentChatUI/Sources/CmuxAgentChatUI/Artifacts/ChatArtifactTextViewCoordinator.swift`:
- Around line 141-189: Centralize boundary-jump cancellation in a shared helper
that clears both endJumpTarget/endJumpConvergence and topJumpConvergence. Use
this helper before drag, go-to-line, and search navigation, including
immediately before scrollRangeToVisible(currentRange) in
applyCurrentSearchHighlight, while preserving the existing navigation behavior.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 08e0b526-a428-4f86-845a-e4fb2ccfdddd

📥 Commits

Reviewing files that changed from the base of the PR and between 5d8e9b7 and 0877122.

⛔ Files ignored due to path filters (1)
  • ios/cmux.xcworkspace/xcshareddata/swiftpm/Package.resolved is excluded by !**/Package.resolved
📒 Files selected for processing (10)
  • Packages/Shared/CmuxAgentChat/Sources/CmuxAgentChat/Artifacts/ChatArtifactGalleryClassifier.swift
  • Packages/Shared/CmuxAgentChat/Sources/CmuxAgentChat/Artifacts/ChatArtifactGalleryGlyphPresentation.swift
  • Packages/Shared/CmuxAgentChat/Sources/CmuxAgentChat/Artifacts/ChatArtifactGalleryGlyphTint.swift
  • Packages/Shared/CmuxAgentChat/Tests/CmuxAgentChatTests/ChatArtifactGalleryClassifierTests.swift
  • Packages/iOS/CmuxAgentChatUI/Sources/CmuxAgentChatUI/Artifacts/ChatArtifactFolderView.swift
  • Packages/iOS/CmuxAgentChatUI/Sources/CmuxAgentChatUI/Artifacts/ChatArtifactGalleryGlyphTint+SwiftUI.swift
  • Packages/iOS/CmuxAgentChatUI/Sources/CmuxAgentChatUI/Artifacts/ChatArtifactTextJumpConvergence.swift
  • Packages/iOS/CmuxAgentChatUI/Sources/CmuxAgentChatUI/Artifacts/ChatArtifactTextViewCoordinator.swift
  • Packages/iOS/CmuxAgentChatUI/Tests/CmuxAgentChatUITests/ChatArtifactTextJumpConvergenceTests.swift
  • Packages/iOS/CmuxMobileShellUI/Sources/CmuxMobileShellUI/TerminalArtifactGalleryItemView.swift

@cursor

cursor Bot commented Jul 17, 2026

Copy link
Copy Markdown

Bugbot is paused — on-demand spend limit reached

Bugbot uses usage-based billing for this team and has hit its on-demand spend limit.

A team admin can raise the spend limit in the Cursor dashboard, or wait for the next billing cycle to continue.

cmux reload-cloud and others added 14 commits July 16, 2026 23:26
A missed end-of-animation callback left the append policy deferring
forever: the pin's own scrolls kept appends queued, the storage stayed
truncated below the file end, and End parked short believing it was at
the bottom. Only user-driven scrolling defers now; animated jumps are
protected by convergence re-targeting instead.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
* test(ios): cover reconnect overlap cleanup

* fix(ios): retire superseded reconnect sessions

* test(ios): isolate saved dev Mac instances

* fix(ios): enforce build compatibility boundaries

* test(ios): cover startup status auth race

* fix(ios): reuse connect token for identity check

* test(auth): preserve selected team during refresh outage

* fix(auth): keep selected team effective during startup

* test(auth): keep cached sessions restoring until ready

* fix(ios): wait for auth restore before reconnect

* test(ios): cover compatibility review regressions

* fix(ios): address compatibility review findings

* test(ios): use deterministic compatibility timestamps

---------

Co-authored-by: cmux reload-cloud <cmux-reload-cloud@users.noreply.github.com>
# Conflicts:
#	Packages/iOS/CmuxMobileShell/Sources/CmuxMobileShell/IOSBuildScopedPairedMacStore.swift
The main-merge commit swept stale worktree submodule checkouts in via
git add -A; pointer drift breaks main's newer bonsplit API call sites.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
A merge auto-resolution dropped an explicit self capture in a file this
branch never intentionally touched.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@azooz2003-bit
azooz2003-bit merged commit 5daf9f7 into main Jul 17, 2026
5 checks passed
azooz2003-bit added a commit that referenced this pull request Jul 17, 2026
Brings the artifact viewer stack (zoomable image, PDFKit, AVKit, QuickLook
hosts behind ChatArtifactViewerDestination and closure-based
ChatArtifactLoader) that the Changes viewer will reuse for binary files.
Conflicts were additive unions in the capability extension, its tests, and
WorkspaceDetailView state.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant