Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
123 commits
Select commit Hold shift + click to select a range
914245d
mockup(a): Margin — doc comments + ask-about (UI only)
itsdestin Sep 24, 2026
f04d723
fix(a): margin rail overflow + marker misalignment (doc-comments mockup)
itsdestin Sep 24, 2026
8911e8e
mockup(a): reading/comments modes + inline ask-about pill (round 2, U…
itsdestin Sep 24, 2026
b791fb9
mockup(a): round 3 polish — selection menu reuse, anchor-position pop…
itsdestin Sep 24, 2026
be0face
mockup(a): round 3 coordinator fixes — expand race, card wrap, FAB cl…
itsdestin Sep 24, 2026
58c9f86
fix(mockup-a): highlight comments whose selection crosses bold, links…
itsdestin Sep 24, 2026
41dd702
mockup(a): Comments button in the drawer header; Ask Your Assistant a…
itsdestin Sep 24, 2026
116ac20
fix(mockup-a): comment-pane footer stays at the bottom and never cove…
itsdestin Sep 24, 2026
807237c
mockup(a): Comments button beside Edit; Ask/Show resolved float over …
itsdestin Sep 24, 2026
fa70ec0
mockup(a): Comments pops in and out with the file list, like Edit
itsdestin Sep 24, 2026
d041a72
mockup(a): bring the comments UI in line with the design guide
itsdestin Sep 24, 2026
be7a9e1
mockup(a): Comments/Edit stay over the document; Show resolved gets a…
itsdestin Sep 24, 2026
af801bb
mockup(a): hover shows just the comment; clicking a highlight opens C…
itsdestin Sep 24, 2026
441bb43
mockup(a): resolve toggle on each card, send inside the reply field, …
itsdestin Sep 24, 2026
a23c0df
mockup(a): drop the quote from comment cards; offset floating buttons…
itsdestin Sep 24, 2026
247dc85
mockup(a): reply send is a 20px arrow button that nests inside the field
itsdestin Sep 24, 2026
21fa55e
mockup(a): comment list stacks from the top; clicking a comment focus…
itsdestin Sep 24, 2026
40cde9a
mockup(a): smaller reply send button with more air around it
itsdestin Sep 24, 2026
2e327c4
mockup(a): four comment-pane framings to compare (?commentsPane=)
itsdestin Sep 24, 2026
b48e60d
mockup(a): combined comment pane, rounded panel + title row + Show Re…
itsdestin Sep 24, 2026
fa7ce56
mockup(a): drop the count from the comment pane's title
itsdestin Sep 24, 2026
3a5d2ec
mockup(a): comments on Word documents and spreadsheet cells
itsdestin Sep 25, 2026
e0f8805
mockup(a): phone comment sheet sits above the composer
itsdestin Sep 25, 2026
29b9b30
mockup(a): verify.sh green for the comments mockup
itsdestin Sep 25, 2026
1c4fdf4
mockup(a): reply straight from the hover card
itsdestin Sep 25, 2026
cbed2f8
mockup(a): resolve from the hover card
itsdestin Sep 25, 2026
91c637b
mockup(a): right-click replaces the selection menu instead of doublin…
itsdestin Sep 25, 2026
c4bcf0f
mockup(a): Ask-about chip — caret lines up, app chip styling, no icon
itsdestin Sep 25, 2026
8cae68d
mockup(a): chips point back at their source text
itsdestin Sep 26, 2026
a05df77
mockup(a): older chips find their source by label
itsdestin Sep 26, 2026
cb4a7d0
mockup(a): chat-message chips light up their message too
itsdestin Sep 26, 2026
f59d6cb
polish: Ask Your Assistant's sent message reads as a list
itsdestin Sep 26, 2026
fe12ac0
polish: code files get the same comments panel and chip linking
itsdestin Sep 26, 2026
258ec49
polish: highlighted text keeps the document's colour on dark themes
itsdestin Sep 26, 2026
3077541
polish: Projects screen gets Comments beside Edit and Ask Your Assistant
itsdestin Sep 26, 2026
ab0632d
polish: spreadsheet comments name their sheet tab
itsdestin Sep 26, 2026
e8c1624
polish: delete the losing comment-panel framings
itsdestin Sep 26, 2026
3091645
mockup(a): Comments button counts open comments only
itsdestin Sep 26, 2026
394af87
fix(command drawer): closed scrim can never paint its blur
itsdestin Sep 26, 2026
0d21e7e
workbench: a deck's real-app pane obeys its theme
itsdestin Sep 26, 2026
48d66f7
comments: no stray full-width comment sheet on desktop
itsdestin Sep 26, 2026
cb5a063
comments: a clicked thread opens once, never again on remount
itsdestin Sep 26, 2026
97b7ee9
comments panel: Show Resolved under the title, and a close ×
itsdestin Sep 26, 2026
7b57681
Ask Your Assistant: solid, visibly sends, one summary chip
itsdestin Sep 26, 2026
488df31
Projects screen: Ask Your Assistant opens the new-session dialog
itsdestin Sep 26, 2026
a219ab9
Add doc-comments shared types and main-process store (T1)
itsdestin Sep 26, 2026
d29c3a2
Add doc-comments re-anchoring shared module (T2)
itsdestin Sep 26, 2026
281bb2a
doc-comments: fix T1 implementation-review findings (F1, F3, F4, F5)
itsdestin Sep 26, 2026
4163d74
doc-comments: fix T2 review findings (F1 perf, F2, F3)
itsdestin Sep 26, 2026
0d646bb
ModelSwitchPrompt.test: fix flaky Escape-key dialog test
itsdestin Sep 26, 2026
82954ed
doc-comments: Word (.docx) comment read, main process (T10)
itsdestin Sep 26, 2026
1caf22e
doc-comments: Excel (.xlsx) comment read, main process (T12)
itsdestin Sep 26, 2026
0fb0dd4
busy-app-render-budget: drain the real scheduler before opening a window
itsdestin Sep 26, 2026
fb295c5
doc-comments: fix T10/T12 implementation-review findings (F1-F6)
itsdestin Sep 26, 2026
4af03e3
doc-comments: compose-ref wire-format rewrite (T7)
itsdestin Sep 26, 2026
4cd0185
fix(comments): T7 review findings — path-hijack, suffix ambiguity, su…
itsdestin Sep 26, 2026
58ee463
doc-comments: docComments:* IPC surface, watcher, remote relay (T3)
itsdestin Sep 26, 2026
e0aec68
fix(doc-comments): gate projectRoot against known roots (T3 review, F…
itsdestin Sep 26, 2026
63d49b1
doc-comments: Word (.docx) comment writing — add/reply/resolve/reopen…
itsdestin Sep 27, 2026
a4275bf
doc-comments: Excel (.xlsx) comment writing — add/reply/resolve/reope…
itsdestin Sep 27, 2026
c496576
fix(doc-comments): T11 review findings F1-F5 — docx write path
itsdestin Sep 27, 2026
ad3f523
android: T16 — Kotlin reader for Word (.docx) comments
itsdestin Sep 27, 2026
eb6dad4
android: T18 — Kotlin reader for Excel (.xlsx) comments, plus the xls…
itsdestin Sep 27, 2026
9e1735a
android: T4 — SessionService.kt parity for docComments:* IPC surface
itsdestin Sep 27, 2026
89198ed
android: F1/F2/F3 review fixes — doc-comments read-path security & pa…
itsdestin Sep 27, 2026
d283cc2
android: F4 review finding — document docComments reader threading co…
itsdestin Sep 27, 2026
3e0748f
desktop: F2/F3 review fixes — xlsx chartsheet parity fixture + decomp…
itsdestin Sep 27, 2026
364cbec
desktop: F5 review finding — drift guard for shared Android/desktop d…
itsdestin Sep 27, 2026
e0d4823
android: T4 review fixes — F1/F2/F3/F4/F6 (docComments IPC parity)
itsdestin Sep 27, 2026
75ef08f
doc-comments: rewire the renderer's comments store onto real IPC (T5)
itsdestin Sep 27, 2026
86aa252
test(doc-comments): drop unused beforeEach import
itsdestin Sep 27, 2026
92f3eeb
doc-comments: T5 review fixes — F1,F3,F4,F5,F6,F7,F8,F9
itsdestin Sep 27, 2026
2c528b7
android: T17 docx comment writing (add/reply/resolve/reopen/move)
itsdestin Sep 27, 2026
445b4b5
android: T17 review F1/F5 — fsync before atomic replace, well-formedn…
itsdestin Sep 27, 2026
68d8d25
desktop: T17 review F1 — fsync before rename in doc-comments write pi…
itsdestin Sep 27, 2026
f90f87e
android: T17 review F2 — exception boundary on native docx write disp…
itsdestin Sep 27, 2026
31665e0
doc-comments: T14 — wire real anchoring into the highlight layer
itsdestin Sep 27, 2026
36315a8
doc-comments: T6 — "text no longer found" UI for detached comments
itsdestin Sep 27, 2026
f2c3ca4
doc-comments: T14 review fixes — F1-F6 (anchoring perf + honest states)
itsdestin Sep 27, 2026
75f1601
doc-comments: T13 xlsx write path — rewrite to surgical OOXML edits
itsdestin Sep 27, 2026
067af27
doc-comments: T8 — the assistant's six document-comment native tools
itsdestin Sep 28, 2026
06f5fcb
doc-comments: ask before Word/Excel comment mutations only (permissio…
itsdestin Sep 28, 2026
d0d4bed
doc-comments: add real Excel/Google-Sheets threaded-comments referenc…
itsdestin Sep 28, 2026
62c3cf7
doc-comments: fix T8 review findings F1-F4
itsdestin Sep 28, 2026
35c5d90
doc-comments: correct two factual errors in the xlsx-threaded manifest
itsdestin Sep 28, 2026
95db76e
doc-comments: T9a/T9b — Claude Code MCP tools + docx/xlsx pending-mut…
itsdestin Sep 28, 2026
568985a
doc-comments: close the accept-edits permission gap using Claude Code…
itsdestin Sep 28, 2026
00752bd
doc-comments: fix T9a/T9b adversarial review findings #1-#4, report #5
itsdestin Sep 28, 2026
afebe3d
doc-comments: T12/T13 xlsx rewrite — Excel 365 threaded comments, not…
itsdestin Sep 28, 2026
6546fc1
doc-comments: T3 per-document watcher, T5 reply reconcile, T11 file-o…
itsdestin Sep 28, 2026
4b7836d
doc-comments: Android parity — reply enrichment + file-open-elsewhere…
itsdestin Sep 28, 2026
ae4c309
doc-comments: gate docComments:watch/unwatch on authorizeBytesRead + …
itsdestin Sep 28, 2026
ffda4b6
doc-comments: xlsx T12/T13 adversarial review fixes (F1-F7) + reply e…
itsdestin Sep 28, 2026
ad7a60d
doc-comments: Android Excel threaded comments — T18 (read) + T19 (write)
itsdestin Sep 28, 2026
38c74c2
doc-comments: strip XML-illegal control chars instead of refusing; re…
itsdestin Sep 28, 2026
b07d4c3
doc-comments: fix xlsx/docx write-path whole-archive buffering; add m…
itsdestin Sep 28, 2026
627ca74
doc-comments: Android MCP asset parity + pending-mutation queue (T9c/…
itsdestin Sep 28, 2026
6f01460
doc-comments: T21 cross-platform golden-fixture parity for xlsx + doc…
itsdestin Sep 28, 2026
564af4d
doc-comments: address T9c/T20 review findings #2/#3 + cheap hardening…
itsdestin Sep 28, 2026
610acd5
fix(doc-comments): address final desktop and Android review findings
itsdestin Sep 28, 2026
fdd3db1
test: comments stress pin compares 200 vs 1,000 comments in one run i…
itsdestin Sep 28, 2026
0dcf987
workbench: mock-only toggles for docComments save-failure states
itsdestin Sep 28, 2026
8a1e412
Merge origin/master into session/comments-mock-a
itsdestin Sep 28, 2026
41c099e
test: make the comment stress pins and the heavy docx/markdown tests …
itsdestin Sep 28, 2026
2e6170e
fix(doc-comments): show resolved-thread replies; open Comments mode f…
itsdestin Sep 28, 2026
3d520d1
fix(doc-comments): a code file's comment lands in its own project, so…
itsdestin Sep 28, 2026
435f5a0
fix(doc-comments): fresh comment drafts survive typing; code files ge…
itsdestin Sep 28, 2026
3cde0c4
fix(doc-comments): typing no longer erases itself — commit drafts exp…
itsdestin Sep 28, 2026
c980784
feat(doc-comments): backend for editing and deleting comments/replies
itsdestin Sep 28, 2026
9eecef9
feat(doc-comments): edit and delete for comments and replies (renderer)
itsdestin Sep 28, 2026
1dd1617
feat(android): port doc-comments edit/delete to Kotlin
itsdestin Sep 28, 2026
a589572
fix(comments): stop cursor flicker across Resolve/Edit/Delete row
itsdestin Sep 28, 2026
72c80a6
feat(comments): edit box buttons inside the field, drop draft's Delet…
itsdestin Sep 28, 2026
b83bb40
fix(comments): icons ride the name line so comment text and the edit …
itsdestin Sep 28, 2026
346d3e7
fix(comments): one shared comment box so text, caret and send arrow l…
itsdestin Sep 28, 2026
629a7d3
fix(comments): edit mode matches the composer, hides its own controls…
itsdestin Sep 28, 2026
815cbb3
fix(comments): floating card's buttons ride the name line so the edit…
itsdestin Sep 28, 2026
09e90dc
fix(comments): keep the shared comment box's classes static (design l…
itsdestin Sep 28, 2026
ff863e3
fix(comments): "Editing" is plain muted text with the pencil, no dark…
itsdestin Sep 28, 2026
95d13c6
test(doc-comments): extend T21 golden-fixture parity to edit/delete
itsdestin Sep 28, 2026
511618d
Merge branch 'master' into session/comments-mock-a
itsdestin Sep 29, 2026
aba0d66
fix(doc-comments): stop Word/Excel saves from damaging files; fix And…
itsdestin Sep 29, 2026
e02f79c
fix(doc-comments): five everyday comment bugs from the PR review
itsdestin Sep 29, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
779 changes: 779 additions & 0 deletions app/src/main/assets/doc-comments-mcp.js

Large diffs are not rendered by default.

116 changes: 92 additions & 24 deletions app/src/main/kotlin/com/youcoded/app/artifacts/CasWrite.kt
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,96 @@ data class CasResult(
val actualUpdatedAt: String?,
)

/**
* Acquire the mkdir lock at [lockPath], blocking (real `Thread.sleep` retries —
* this whole module is the synchronous, non-suspend style `casWrite`
* established) until acquired or [LOCK_MAX_WAIT_MS] elapses. Shared by
* `casWrite` and `mutateFileUnderLock` below so both use IDENTICAL lock
* semantics — same mkdir-is-atomic primitive, same 30s stale-lock break —
* which matters once a SECOND caller (`mutateFileUnderLock`, added for F1,
* T4 doc-comments implementation review) needs to exclude not just other
* callers of `casWrite` but a wholly separate process racing the same file.
*/
private fun acquireLock(lockPath: Path): Boolean {
val start = System.currentTimeMillis()
while (true) {
try {
Files.createDirectory(lockPath)
return true // Lock acquired
} catch (e: java.nio.file.FileAlreadyExistsException) {
// Stale-lock heuristic: if the lock dir is older than LOCK_STALE_MS,
// the holding process likely crashed — break the lock and retry.
try {
val attrs = Files.readAttributes(lockPath, BasicFileAttributes::class.java)
val mtime = attrs.lastModifiedTime().toMillis()
if (System.currentTimeMillis() - mtime > LOCK_STALE_MS) {
lockPath.toFile().deleteRecursively()
continue
}
} catch (_: Exception) {
// Ignore stat errors — lock may have just been released
}
if (System.currentTimeMillis() - start > LOCK_MAX_WAIT_MS) {
return false
}
Thread.sleep(LOCK_RETRY_MS)
}
}
}

/**
* Read-modify-write [target] entirely INSIDE the mkdir lock — Kotlin port of
* desktop's `cas-write.ts` `mutateFileUnderLock` (F1, T4 doc-comments
* implementation review, blocker). This is the primitive for a file with no
* CAS version field of its own: a caller that reads outside the lock and
* writes back after loses an update from whoever wrote in between. Reuses
* [acquireLock] — the SAME lock path naming (`<target>.lock`) and 30s
* stale-lock timeout `casWrite` above already uses — so this app's own
* writers, desktop's `cas-write.ts` (a dev instance and the built app sharing
* `~/.claude`), and the Claude Code MCP script's own dependency-free
* reimplementation of this exact algorithm (design §9.1 point 2, §9.2) all
* exclude each other over the same file, not just callers inside one JVM.
*
* @param mutate receives the current on-disk content (null when the file
* doesn't exist) and returns the new content, or null to skip
* the write entirely — a failed lookup must never write
* anything, not even an unchanged copy.
* @return false when the lock couldn't be acquired within the timeout.
*/
fun mutateFileUnderLock(target: Path, mutate: (String?) -> String?): Boolean {
Files.createDirectories(target.parent)
val lockPath = target.parent.resolve(target.fileName.toString() + ".lock")
if (!acquireLock(lockPath)) return false
try {
val onDisk: String? = try {
target.toFile().readText(Charsets.UTF_8)
} catch (e: java.io.FileNotFoundException) {
null
} catch (e: java.io.IOException) {
if (!target.toFile().exists()) null else throw e
}
val next = mutate(onDisk)
if (next != null) {
// Same atomic write shape as casWrite below: tmp → fsync → rename.
val tmp = target.parent.resolve(target.fileName.toString() + ".tmp")
tmp.toFile().writeText(next, Charsets.UTF_8)
FileChannel.open(tmp, StandardOpenOption.READ, StandardOpenOption.WRITE).use { ch -> ch.force(true) }
try {
Files.move(tmp, target, StandardCopyOption.ATOMIC_MOVE, StandardCopyOption.REPLACE_EXISTING)
} catch (_: java.nio.file.AtomicMoveNotSupportedException) {
Files.move(tmp, target, StandardCopyOption.REPLACE_EXISTING)
}
}
return true
} finally {
lockPath.toFile().deleteRecursively()
}
}

/** Convenience overload accepting a String path (matches most call sites). */
fun mutateFileUnderLock(target: String, mutate: (String?) -> String?): Boolean =
mutateFileUnderLock(File(target).toPath(), mutate)

/**
* Atomic write-then-rename with optional CAS check, protected by a
* mkdir-based lock.
Expand Down Expand Up @@ -62,30 +152,8 @@ fun casWrite(

val lockPath = target.parent.resolve(target.fileName.toString() + ".lock")

// Acquire lock — retry up to LOCK_MAX_WAIT_MS
val start = System.currentTimeMillis()
while (true) {
try {
Files.createDirectory(lockPath)
break // Lock acquired
} catch (e: java.nio.file.FileAlreadyExistsException) {
// Stale-lock heuristic: if the lock dir is older than LOCK_STALE_MS,
// the holding process likely crashed — break the lock and retry.
try {
val attrs = Files.readAttributes(lockPath, BasicFileAttributes::class.java)
val mtime = attrs.lastModifiedTime().toMillis()
if (System.currentTimeMillis() - mtime > LOCK_STALE_MS) {
lockPath.toFile().deleteRecursively()
continue
}
} catch (_: Exception) {
// Ignore stat errors — lock may have just been released
}
if (System.currentTimeMillis() - start > LOCK_MAX_WAIT_MS) {
return CasResult(committed = false, actualUpdatedAt = null)
}
Thread.sleep(LOCK_RETRY_MS)
}
if (!acquireLock(lockPath)) {
return CasResult(committed = false, actualUpdatedAt = null)
}

try {
Expand Down
Loading
Loading