feat: write /rewrite and /refine results back into the source app#197
Merged
Conversation
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
…nhance user feedback Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
Signed-off-by: Logan Nguyen <lg.131.dev@gmail.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Overview
Sends
/rewriteand/refineresults straight back into the app you were working in, replacing the text you had selected. After a rewrite finishes you can drop it into the source app with one click (or automatically), without copying and pasting by hand.Highlights
/rewriteand/refineresult. It pastes the rewrite into the source app while the Thuki overlay stays open, so you can replace repeatedly, and confirms with a brief checkmark.?next to a settings-section heading explains what the whole group does, distinct from the per-row helpers.How it works
Backend (
replace.rs). AnNSWorkspaceactivation observer records the PID of the last non-Thuki app to activate; because Thuki's overlay is a non-activating panel, summoning it never overwrites that target.replace_selectionsaves the clipboard, writes the rewrite to it (tagged transient so clipboard-history managers skip it), activates the target app, posts a synthetic Cmd+V directly to the target process withCGEventPostToPid, then restores the clipboard. Posting to the process rather than the system key window is what lets the paste land in the source app while Thuki's panel stays key and visible. Paste is used over an Accessibility selected-text write because Cmd+V reliably replaces the selection where an AX write collapses to the caret once focus leaves.Configuration. A new
[behavior]section (auto_replace,auto_close) flows throughdefaults→schema→loader, is exposed viaget_config, and is edited from the Behavior tab.write_field_to_disknow materializes an allowed-but-not-yet-persisted section before patching, so toggling a brand-new field on a config file seeded before the section existed works instead of failing withUnknownSection.Frontend. The new commands go through the existing unified dispatch in
App.tsx: the replaceable trigger is carried on the assistant message viauseOllama,ChatBubblerenders the Replace button for those results, and both the manual and automatic paths send the same rendered text (turn-boundary tokens stripped) back to the source app.Security
The write path is gated three ways: it no-ops when Accessibility is not granted, when there is no observed target app, and when secure input is active (a focused password field or iTerm Secure Keyboard Entry), so a rewrite can never be pasted into a credential field. Section and field names are validated against the existing allowlist before any TOML is written, so the new on-disk-section creation can only ever materialize a real schema section.
Testing
bun run test:all:coverage— 1517 frontend tests and 896 backend tests pass; the 100% line-coverage gate holds on both sides.bun run validate-build— ESLint,cargo clippy -D warnings,tsc, Prettier, and the full release build/bundle all pass with no warnings.macOS-only feature; requires the Accessibility permission Thuki already uses for its hotkey.