things-api 0.18.0 → 0.19.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +18 -9
- package/deputy/AppIcon.icns +0 -0
- package/deputy/VERSION +1 -1
- package/deputy/helpers-Info.plist +4 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/CodeResources +0 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/Helpers/things-reader.app/Contents/Info.plist +3 -1
- package/deputy/prebuilt/Things API Helper.app/Contents/Helpers/things-reader.app/Contents/MacOS/things-reader +0 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/Helpers/things-reader.app/Contents/Resources/AppIcon.icns +0 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/Helpers/things-reader.app/Contents/_CodeSignature/CodeResources +15 -2
- package/deputy/prebuilt/Things API Helper.app/Contents/Info.plist +5 -1
- package/deputy/prebuilt/Things API Helper.app/Contents/MacOS/things-deputy +0 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/Resources/AppIcon.icns +0 -0
- package/deputy/prebuilt/Things API Helper.app/Contents/_CodeSignature/CodeResources +14 -2
- package/deputy/reader/Info.plist +2 -0
- package/deputy/reader/entitlements.plist +30 -0
- package/deputy/reader/main.swift +129 -40
- package/deputy/src/server.swift +25 -2
- package/deputy/src/tcc.swift +58 -0
- package/dist/audit/schema.d.ts +30 -1
- package/dist/audit/schema.js.map +1 -1
- package/dist/capability.d.ts +322 -0
- package/dist/capability.js +706 -0
- package/dist/capability.js.map +1 -0
- package/dist/cli/commands/doctor.d.ts +13 -1
- package/dist/cli/commands/doctor.js +141 -5
- package/dist/cli/commands/doctor.js.map +1 -1
- package/dist/cli/commands/helpers.js +189 -51
- package/dist/cli/commands/helpers.js.map +1 -1
- package/dist/cli/commands/mcp.js +8 -0
- package/dist/cli/commands/mcp.js.map +1 -1
- package/dist/cli/commands/op-result.js +6 -0
- package/dist/cli/commands/op-result.js.map +1 -1
- package/dist/cli/commands/reads.js +47 -1
- package/dist/cli/commands/reads.js.map +1 -1
- package/dist/cli/commands/repeat-flags.js +34 -2
- package/dist/cli/commands/repeat-flags.js.map +1 -1
- package/dist/cli/commands/setup.d.ts +9 -0
- package/dist/cli/commands/setup.js +76 -83
- package/dist/cli/commands/setup.js.map +1 -1
- package/dist/cli/commands/writes.d.ts +1 -1
- package/dist/cli/commands/writes.js +311 -142
- package/dist/cli/commands/writes.js.map +1 -1
- package/dist/cli/dry-run.d.ts +1 -1
- package/dist/cli/dry-run.js +1 -1
- package/dist/cli/glyphs.d.ts +23 -4
- package/dist/cli/glyphs.js +46 -19
- package/dist/cli/glyphs.js.map +1 -1
- package/dist/cli/help.d.ts +1 -1
- package/dist/cli/help.js +49 -27
- package/dist/cli/help.js.map +1 -1
- package/dist/cli/interrupt.d.ts +54 -6
- package/dist/cli/interrupt.js +78 -12
- package/dist/cli/interrupt.js.map +1 -1
- package/dist/cli/main.js +8 -5
- package/dist/cli/main.js.map +1 -1
- package/dist/cli/period.d.ts +3 -1
- package/dist/cli/period.js +1 -1
- package/dist/cli/period.js.map +1 -1
- package/dist/cli/read-driver.js +26 -1
- package/dist/cli/read-driver.js.map +1 -1
- package/dist/cli/render.d.ts +31 -4
- package/dist/cli/render.js +127 -15
- package/dist/cli/render.js.map +1 -1
- package/dist/client.d.ts +23 -3
- package/dist/client.js +36 -13
- package/dist/client.js.map +1 -1
- package/dist/contracts.d.ts +8 -4
- package/dist/contracts.js +1 -1
- package/dist/contracts.js.map +1 -1
- package/dist/deputy/install.d.ts +234 -6
- package/dist/deputy/install.js +843 -31
- package/dist/deputy/install.js.map +1 -1
- package/dist/deputy/notices.js +2 -2
- package/dist/deputy/notices.js.map +1 -1
- package/dist/deputy/protocol.d.ts +59 -5
- package/dist/deputy/protocol.js +48 -11
- package/dist/deputy/protocol.js.map +1 -1
- package/dist/deputy/routing.d.ts +37 -0
- package/dist/deputy/routing.js +181 -27
- package/dist/deputy/routing.js.map +1 -1
- package/dist/deputy/wake.d.ts +61 -0
- package/dist/deputy/wake.js +149 -0
- package/dist/deputy/wake.js.map +1 -0
- package/dist/diagnose.d.ts +19 -4
- package/dist/diagnose.js +64 -8
- package/dist/diagnose.js.map +1 -1
- package/dist/direct-setup.d.ts +104 -0
- package/dist/direct-setup.js +658 -0
- package/dist/direct-setup.js.map +1 -0
- package/dist/host-access.d.ts +75 -0
- package/dist/host-access.js +177 -0
- package/dist/host-access.js.map +1 -0
- package/dist/index.d.ts +20 -5
- package/dist/index.js +14 -1
- package/dist/index.js.map +1 -1
- package/dist/mcp/server.d.ts +27 -1
- package/dist/mcp/server.js +308 -109
- package/dist/mcp/server.js.map +1 -1
- package/dist/op-result.d.ts +9 -0
- package/dist/op-result.js +13 -1
- package/dist/op-result.js.map +1 -1
- package/dist/read/filter-contract.d.ts +1 -1
- package/dist/read/filter-contract.js +4 -0
- package/dist/read/filter-contract.js.map +1 -1
- package/dist/read/shape.js +4 -0
- package/dist/read/shape.js.map +1 -1
- package/dist/read/views.d.ts +29 -0
- package/dist/read/views.js +60 -0
- package/dist/read/views.js.map +1 -1
- package/dist/session-grant.d.ts +48 -0
- package/dist/session-grant.js +185 -0
- package/dist/session-grant.js.map +1 -0
- package/dist/surface-copy.d.ts +19 -3
- package/dist/surface-copy.js +19 -3
- package/dist/surface-copy.js.map +1 -1
- package/dist/wizard.d.ts +58 -0
- package/dist/wizard.js +174 -0
- package/dist/wizard.js.map +1 -0
- package/dist/write/availability.d.ts +1 -16
- package/dist/write/availability.js +10 -65
- package/dist/write/availability.js.map +1 -1
- package/dist/write/batch.d.ts +20 -0
- package/dist/write/batch.js +111 -21
- package/dist/write/batch.js.map +1 -1
- package/dist/write/capabilities.d.ts +9 -0
- package/dist/write/capabilities.js +2 -0
- package/dist/write/capabilities.js.map +1 -1
- package/dist/write/clear-reminder.js +1 -1
- package/dist/write/clear-reminder.js.map +1 -1
- package/dist/write/commands.d.ts +22 -7
- package/dist/write/commands.js +231 -254
- package/dist/write/commands.js.map +1 -1
- package/dist/write/failure-hints.d.ts +32 -7
- package/dist/write/failure-hints.js +9 -14
- package/dist/write/failure-hints.js.map +1 -1
- package/dist/write/guards.js +22 -4
- package/dist/write/guards.js.map +1 -1
- package/dist/write/lock.d.ts +16 -13
- package/dist/write/lock.js +55 -0
- package/dist/write/lock.js.map +1 -1
- package/dist/write/make-repeating-project.js +9 -13
- package/dist/write/make-repeating-project.js.map +1 -1
- package/dist/write/move.js +9 -12
- package/dist/write/move.js.map +1 -1
- package/dist/write/operations.d.ts +51 -29
- package/dist/write/operations.js +16 -0
- package/dist/write/operations.js.map +1 -1
- package/dist/write/opid.d.ts +72 -14
- package/dist/write/opid.js +152 -8
- package/dist/write/opid.js.map +1 -1
- package/dist/write/param-schema.d.ts +80 -0
- package/dist/write/param-schema.js +754 -0
- package/dist/write/param-schema.js.map +1 -0
- package/dist/write/pipeline.d.ts +110 -5
- package/dist/write/pipeline.js +288 -14
- package/dist/write/pipeline.js.map +1 -1
- package/dist/write/pre-state.d.ts +38 -16
- package/dist/write/pre-state.js +117 -22
- package/dist/write/pre-state.js.map +1 -1
- package/dist/write/promote-clone.js +658 -444
- package/dist/write/promote-clone.js.map +1 -1
- package/dist/write/reorder.js +25 -8
- package/dist/write/reorder.js.map +1 -1
- package/dist/write/repeat-collateral.d.ts +31 -0
- package/dist/write/repeat-collateral.js +153 -0
- package/dist/write/repeat-collateral.js.map +1 -0
- package/dist/write/repeat-rule.d.ts +28 -1
- package/dist/write/repeat-rule.js +54 -4
- package/dist/write/repeat-rule.js.map +1 -1
- package/dist/write/resolution-timestamps.d.ts +11 -0
- package/dist/write/resolution-timestamps.js +108 -40
- package/dist/write/resolution-timestamps.js.map +1 -1
- package/dist/write/reversibility.js +4 -0
- package/dist/write/reversibility.js.map +1 -1
- package/dist/write/template-mutation.d.ts +137 -0
- package/dist/write/template-mutation.js +598 -0
- package/dist/write/template-mutation.js.map +1 -0
- package/dist/write/undo.js +10 -20
- package/dist/write/undo.js.map +1 -1
- package/dist/write/update-fields.d.ts +151 -0
- package/dist/write/update-fields.js +427 -0
- package/dist/write/update-fields.js.map +1 -0
- package/dist/write/vectors/applescript.js +6 -10
- package/dist/write/vectors/applescript.js.map +1 -1
- package/dist/write/vectors/registry.d.ts +1 -1
- package/dist/write/vectors/registry.js +10 -2
- package/dist/write/vectors/registry.js.map +1 -1
- package/dist/write/vectors/shortcuts.js +2 -2
- package/dist/write/vectors/shortcuts.js.map +1 -1
- package/dist/write/vectors/simulator.js +15 -4
- package/dist/write/vectors/simulator.js.map +1 -1
- package/dist/write/vectors/types.d.ts +268 -1
- package/dist/write/vectors/ui-certification.js +63 -13
- package/dist/write/vectors/ui-certification.js.map +1 -1
- package/dist/write/vectors/ui-chord.d.ts +144 -0
- package/dist/write/vectors/ui-chord.js +428 -0
- package/dist/write/vectors/ui-chord.js.map +1 -0
- package/dist/write/vectors/ui-drag.d.ts +8 -4
- package/dist/write/vectors/ui-drag.js +2 -0
- package/dist/write/vectors/ui-drag.js.map +1 -1
- package/dist/write/vectors/ui-recipes.d.ts +70 -3
- package/dist/write/vectors/ui-recipes.js +482 -44
- package/dist/write/vectors/ui-recipes.js.map +1 -1
- package/dist/write/vectors/ui.d.ts +280 -10
- package/dist/write/vectors/ui.js +1068 -77
- package/dist/write/vectors/ui.js.map +1 -1
- package/dist/write/vectors/url-scheme.js +3 -0
- package/dist/write/vectors/url-scheme.js.map +1 -1
- package/dist/write/verify/delta.d.ts +62 -0
- package/dist/write/verify/delta.js +36 -2
- package/dist/write/verify/delta.js.map +1 -1
- package/dist/write/verify/poller.d.ts +4 -1
- package/dist/write/verify/poller.js +14 -0
- package/dist/write/verify/poller.js.map +1 -1
- package/package.json +2 -1
- package/schema/envelope.schema.json +6 -4
- package/scripts/build-helpers.sh +5 -0
- package/skills/things-cli/SKILL.md +5 -3
- package/skills/things-cli/references/contracts.md +1 -0
- package/skills/things-cli/references/data-model.md +3 -0
- package/skills/things-cli/references/errors.md +1 -1
- package/skills/things-cli/references/gui.md +1 -0
- package/skills/things-cli/references/repeating.md +6 -0
- package/skills/things-cli/references/tag-cleanup.md +64 -0
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import { UI_DRIVE_OPS } from "../operations.js";
|
|
2
2
|
/** The manifest profile — records the tier + Things build the suite certified. */
|
|
3
|
-
export const UI_CERTIFICATION_PROFILE = "UIC1 + UIC3 + AXDRAG2 + UIC5 + UIC6 + UIC7 + UIC7b + HEADCERT1 +
|
|
4
|
-
"UIC8 promote-via-clone compounds in-VM (golden-v2 / Things 3.22.12)
|
|
3
|
+
export const UI_CERTIFICATION_PROFILE = "UIC1 + UIC3 + AXDRAG2 + UIC5 + UIC6 + UIC7 + UIC7b + HEADCERT1 + HEADXPROJ + DISS1 in-VM (Things 3.22.11) + " +
|
|
4
|
+
"UIC8 promote-via-clone compounds in-VM (golden-v2 / Things 3.22.12) + RDLG2 recipe re-point + " +
|
|
5
|
+
"HXPC1 heading-ellipsis/Move-picker paths in-VM (golden-v4 / Things 3.23) + " +
|
|
6
|
+
"CHORDMH1 heading-order arrow chords in-VM (golden-v4 / Things 3.23) — on-device pending";
|
|
5
7
|
const CERTIFICATION = {
|
|
6
8
|
"todo.make-repeating": {
|
|
7
9
|
status: "lab-certified",
|
|
@@ -48,16 +50,59 @@ const CERTIFICATION = {
|
|
|
48
50
|
evidence: ["UI2-d", "UIC1-a", "HEADCERT1"],
|
|
49
51
|
},
|
|
50
52
|
"project.move-heading-to-project": {
|
|
51
|
-
//
|
|
52
|
-
//
|
|
53
|
-
// type the destination → Return
|
|
54
|
-
//
|
|
55
|
-
//
|
|
56
|
-
//
|
|
57
|
-
//
|
|
58
|
-
//
|
|
53
|
+
// HEADXPROJ (2026-07-27, bjhx-lab, Things 3.22.11) established the flow and the
|
|
54
|
+
// DB oracle with a hand-written driver: HID-click the "More. <title>" button →
|
|
55
|
+
// Move… → type the destination → Return, and heading `HXH`'s project FK
|
|
56
|
+
// rewritten HX-PA → HX-PB with both children following via their intact heading
|
|
57
|
+
// FK (project NULL, heading=HXH) — a single-row change, no index churn.
|
|
58
|
+
//
|
|
59
|
+
// HXPC1 (2026-08-25, hxpc1-lab, Things 3.23 / golden-v4) certified the SHIPPED
|
|
60
|
+
// recipe for the first time and corrected three of the four provisional paths:
|
|
61
|
+
// the "More. <title>" button is three levels below the content table (so the
|
|
62
|
+
// shipped one-level `whose` clause matched nothing and the drive never got past
|
|
63
|
+
// its first click), the picker is a detached `MovePopUpDialog-` window rather
|
|
64
|
+
// than a sheet of the main window, and the commit is a CLICK on the row whose
|
|
65
|
+
// title matches exactly — the blind Return could take the picker's
|
|
66
|
+
// `New Project "<typed>"` row whenever the destination was absent from it,
|
|
67
|
+
// which a completed or canceled destination is. 7/7 through the production CLI
|
|
68
|
+
// (clean match, prefix collision, completed-destination refusal with zero
|
|
69
|
+
// mutation). docs/lab/hxpc1-picker-assert.md.
|
|
59
70
|
status: "lab-certified",
|
|
60
|
-
evidence: ["HXPC1"],
|
|
71
|
+
evidence: ["HEADXPROJ", "HXPC1"],
|
|
72
|
+
},
|
|
73
|
+
"project.move-heading": {
|
|
74
|
+
// HEADORD1 (2026-08-25, headord1-lab, Things 3.23 / golden-v4) discovered and
|
|
75
|
+
// characterised the affordance: ⌘↑/⌘↓ = ±1 slot, ⌘⌥↑/⌘⌥↓ = to top/bottom on a
|
|
76
|
+
// selected heading row; a single-row `index` rewrite with no sibling renumber
|
|
77
|
+
// and children untouched behind their FK; a chord with nowhere to go declined
|
|
78
|
+
// with zero delta and one alert beep; System Events modifiers frontmost-only,
|
|
79
|
+
// `CGEventPostToPid` background-capable.
|
|
80
|
+
//
|
|
81
|
+
// CHORDMH1 (2026-08-25, chordmh1-lab, Things 3.23 / golden-v4) certified the
|
|
82
|
+
// SHIPPED op. Its delivery gate re-measured the whole gesture with Things
|
|
83
|
+
// never activated at all — `open -g` reveal, pure-AX row select, pid-posted
|
|
84
|
+
// chord — and Finder frontmost at every stage, so the op ships BACKGROUND
|
|
85
|
+
// delivery with no `activate` step (the least-disruptive tier any ordering op
|
|
86
|
+
// has reached). The certification arms drove the production CLI over
|
|
87
|
+
// 3-heading fixtures: ±1 up, ±1 down, to-top, to-bottom, a multi-hop, the
|
|
88
|
+
// already-in-position no-op, the dry run, and the ungated call — children
|
|
89
|
+
// byte-identical on every arm, sibling indexes byte-identical, zero beeps on
|
|
90
|
+
// the normal paths. docs/lab/chordmh1-move-heading-build.md.
|
|
91
|
+
//
|
|
92
|
+
// CHORDMH2 (2026-08-25, chordmh2-lab, Things 3.23 / golden-v4) lifted CHORDMH1's
|
|
93
|
+
// one deliberate capability cut — the whole-project refusal on any archived
|
|
94
|
+
// heading — after CHORD2 cell 7a′ measured that an archived heading renders no
|
|
95
|
+
// content row, takes no ordinal in the walk, and is skipped by a live heading's
|
|
96
|
+
// ±1. The fence stood in for an ordinal mismatch, so the three reads that feed
|
|
97
|
+
// the plan, the driver and the bare-placement anchor now return the RENDERED
|
|
98
|
+
// (`status = 0`) order. Certified through the production CLI: one chord carried
|
|
99
|
+
// a heading past an archived row's slot, that heading was the only row
|
|
100
|
+
// rewritten, the archived row was byte-untouched on status/index/stopDate/umd,
|
|
101
|
+
// children intact, zero beeps; an archived heading named as a movee or an
|
|
102
|
+
// anchor still refuses with zero mutation.
|
|
103
|
+
// docs/lab/chordmh2-archived-fence-lift.md.
|
|
104
|
+
status: "lab-certified",
|
|
105
|
+
evidence: ["HEADORD1", "CHORDMH1", "CHORDMH2"],
|
|
61
106
|
},
|
|
62
107
|
"project.dissolve-heading": {
|
|
63
108
|
// DISS1 (2026-07-28, bjhx-lab, Things 3.22.11): the ellipsis Delete recipe ran
|
|
@@ -66,8 +111,13 @@ const CERTIFICATION = {
|
|
|
66
111
|
// TMTask), its 3 children re-homed as DIRECT project children (heading→NULL,
|
|
67
112
|
// project→parent, index preserved: c1<c2<c3, trashed=0). NO confirm sheet.
|
|
68
113
|
// Popover items are AX-description-enumerable (the recipe resolves Delete by
|
|
69
|
-
// description, scoped to the popover)
|
|
70
|
-
//
|
|
114
|
+
// description, scoped to the popover) — the one provisional path HXPC1 measured
|
|
115
|
+
// CORRECT. Its sibling was not: the "More. <title>" button this drive opens the
|
|
116
|
+
// popover with was addressed one level too shallow, so it resolved nothing and
|
|
117
|
+
// the drive died at its first click on every host. HXPC1 (2026-08-25, Things
|
|
118
|
+
// 3.23) fixed the walk and certified it through the move-heading sibling, but
|
|
119
|
+
// this op was NOT driven end to end there — its next sitting should carry a cell
|
|
120
|
+
// (docs/lab/hxpc1-picker-assert.md §B0/§D). The DB oracle + flow are certified.
|
|
71
121
|
status: "lab-certified",
|
|
72
122
|
evidence: ["DISS1"],
|
|
73
123
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ui-certification.js","sourceRoot":"","sources":["../../../src/write/vectors/ui-certification.ts"],"names":[],"mappings":"AAqCA,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAYhD,kFAAkF;AAClF,MAAM,CAAC,MAAM,wBAAwB,GACnC,
|
|
1
|
+
{"version":3,"file":"ui-certification.js","sourceRoot":"","sources":["../../../src/write/vectors/ui-certification.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
import type { DatabaseSync } from "node:sqlite";
|
|
2
|
+
import type { UiCommand, UiRunner } from "./ui.ts";
|
|
3
|
+
/** The move a `chord-reorder` step performs, compiled from the pre-state. */
|
|
4
|
+
export interface HeadingChordSpec {
|
|
5
|
+
/** The project whose headings are being reordered. */
|
|
6
|
+
projectUuid: string;
|
|
7
|
+
/**
|
|
8
|
+
* Every LIVE (`status = 0`) heading of the project, in the order they must end
|
|
9
|
+
* up in — the full end state, not just the moved block. The driver places them
|
|
10
|
+
* left to right, so this doubles as the verification target. Archived headings
|
|
11
|
+
* are absent by construction: they render no row, so they are neither
|
|
12
|
+
* addressable nor displaced (CHORD2 cell 7a′).
|
|
13
|
+
*/
|
|
14
|
+
targetOrder: string[];
|
|
15
|
+
/**
|
|
16
|
+
* The headings the caller named. Only these may ever be chorded: if the
|
|
17
|
+
* driver's placement walk would have to move a heading the caller did not
|
|
18
|
+
* name, it refuses rather than touch a bystander.
|
|
19
|
+
*/
|
|
20
|
+
movees: string[];
|
|
21
|
+
/** The project view's content table (the recipe supplies the one path). */
|
|
22
|
+
tablePath: string;
|
|
23
|
+
}
|
|
24
|
+
/** The database read the driver asserts against between chords. */
|
|
25
|
+
export interface HeadingOrderState {
|
|
26
|
+
/**
|
|
27
|
+
* The project's LIVE (`status = 0`) headings in `index` order, with their raw
|
|
28
|
+
* index — the rows the project view actually renders, and therefore the rows
|
|
29
|
+
* the positional `select-heading-row` walk enumerates. An ARCHIVED heading is
|
|
30
|
+
* absent: it renders no row, takes no ordinal, and a live heading's ±1 chord
|
|
31
|
+
* skips its slot in one dispatch (CHORD2 cell 7a′). Filtering here is what
|
|
32
|
+
* keeps the driver's ordinals in step with the walk's.
|
|
33
|
+
*/
|
|
34
|
+
headings: {
|
|
35
|
+
uuid: string;
|
|
36
|
+
index: number;
|
|
37
|
+
}[];
|
|
38
|
+
/**
|
|
39
|
+
* Digest over every non-trashed child of those headings: `uuid:headingFK:index`.
|
|
40
|
+
* The chord law says children are untouched behind their FK — this is what
|
|
41
|
+
* proves it, and what catches the one measured hazard in the family (a row
|
|
42
|
+
* driven across a heading boundary has its heading FK rewritten, HEADORD1 §2
|
|
43
|
+
* cells 1h4/1i2; it cannot happen to a heading, and this asserts that).
|
|
44
|
+
*/
|
|
45
|
+
childDigest: string;
|
|
46
|
+
/** How many child rows the digest covers (reported in the failure text). */
|
|
47
|
+
childCount: number;
|
|
48
|
+
}
|
|
49
|
+
/** The database seam the chord driver reads its ground truth through. */
|
|
50
|
+
export type HeadingOrderReader = (projectUuid: string) => HeadingOrderState;
|
|
51
|
+
/**
|
|
52
|
+
* The client-side default: heading order + child containment, from the open DB.
|
|
53
|
+
*
|
|
54
|
+
* The heading read is filtered to `status = 0` so it returns the RENDERED order
|
|
55
|
+
* (CHORD2 cell 7a′). The child digest is deliberately NOT filtered — it covers
|
|
56
|
+
* every non-trashed child of every heading of the project, archived headings
|
|
57
|
+
* included, because no heading chord may disturb any of them.
|
|
58
|
+
*/
|
|
59
|
+
export declare function createHeadingOrderReader(db: DatabaseSync): HeadingOrderReader;
|
|
60
|
+
/**
|
|
61
|
+
* The four chords, as `(key code, CGEventFlags)` pairs. `126`/`125` are the
|
|
62
|
+
* arrow keys; `0x100000` is `kCGEventFlagMaskCommand` and `0x80000`
|
|
63
|
+
* `kCGEventFlagMaskAlternate`. Named rather than inlined so the recipe trace and
|
|
64
|
+
* the failure text can say which chord was posted.
|
|
65
|
+
*/
|
|
66
|
+
export type ChordId = "up-one" | "down-one" | "to-top" | "to-bottom";
|
|
67
|
+
export declare function chordGlyph(id: ChordId): string;
|
|
68
|
+
/**
|
|
69
|
+
* Post ONE modifier-bearing key event pair straight at the Things process
|
|
70
|
+
* (`CGEventPostToPid`), through the same JXA ObjC bridge every other synthetic
|
|
71
|
+
* input in this codebase rides.
|
|
72
|
+
*
|
|
73
|
+
* Why not System Events. The shipped `key` primitive emits `key code N` with no
|
|
74
|
+
* modifier support at all, and the System-Events spelling that DOES carry
|
|
75
|
+
* modifiers only lands while Things is FRONTMOST (HEADORD1 cell 1h2b: with
|
|
76
|
+
* Finder frontmost it produced no delta). `CGEventPostToPid` addresses the
|
|
77
|
+
* process rather than the focused surface, so the whole gesture — reveal,
|
|
78
|
+
* select, chord — runs with Things in the background and the user's focus
|
|
79
|
+
* untouched. Measured on Things 3.23 / golden-v4 (HEADORD1 1h2a; re-measured end
|
|
80
|
+
* to end, with Things never activated at all, by CHORDMH1's delivery gate).
|
|
81
|
+
*
|
|
82
|
+
* Note this is the KEYBOARD tap only. NATIVE1-e measured `CGEventPostToPid` as
|
|
83
|
+
* inert for Things' MOUSE hit-testing, which is why click synthesis still uses
|
|
84
|
+
* the HID tap and stays foreground-bound; keyboard events to the pid are a
|
|
85
|
+
* different path and do land.
|
|
86
|
+
*/
|
|
87
|
+
export declare function jxaChordScript(id: ChordId): string;
|
|
88
|
+
export declare function chordCommand(id: ChordId): UiCommand;
|
|
89
|
+
/** Select the Nth heading row of the revealed project view (the shipped primitive). */
|
|
90
|
+
export declare function chordSelectCommand(tablePath: string, ordinal: number, script: string): UiCommand;
|
|
91
|
+
export interface ChordDriveResult {
|
|
92
|
+
ok: boolean;
|
|
93
|
+
/** Human-readable outcome (chords posted) or the refusal reason. */
|
|
94
|
+
detail: string;
|
|
95
|
+
/** How many chords were posted before the outcome (partial-state honesty). */
|
|
96
|
+
chords: number;
|
|
97
|
+
}
|
|
98
|
+
/** One scheduled step: which heading to chord, with what, and where it must land. */
|
|
99
|
+
export interface ChordStep {
|
|
100
|
+
/** The heading to select and move — ALWAYS one the caller named. */
|
|
101
|
+
uuid: string;
|
|
102
|
+
chord: ChordId;
|
|
103
|
+
/** The position the heading must occupy afterwards (the progress assertion). */
|
|
104
|
+
landsAt: number;
|
|
105
|
+
}
|
|
106
|
+
/**
|
|
107
|
+
* The next chord that advances `order` towards `target`, or null when they
|
|
108
|
+
* already agree. `movees` is the only set of rows a chord may ever move.
|
|
109
|
+
*
|
|
110
|
+
* THE SCHEDULE, and why it is this one. The obvious walk — "put target[i] into
|
|
111
|
+
* slot i, left to right" — is WRONG here, because target[i] is very often a row
|
|
112
|
+
* the caller never named: asking to move heading A down one slot produces a
|
|
113
|
+
* target whose first element is the BYSTANDER B. Moving B is not an option (it
|
|
114
|
+
* would break the untouched-siblings law the whole vector rests on), and the
|
|
115
|
+
* equally obvious repair — "push whichever movee sits at slot i down" — thrashes
|
|
116
|
+
* forever when two movees sit side by side, each pushing the other back.
|
|
117
|
+
*
|
|
118
|
+
* So the rule fixes the first mismatched slot `i` from the row's own side:
|
|
119
|
+
*
|
|
120
|
+
* - target[i] IS a movee → it is necessarily BELOW slot i (everything above
|
|
121
|
+
* already matches), so step it UP; from slot 0 the one-dispatch ⌘⌥↑ takes it
|
|
122
|
+
* there directly.
|
|
123
|
+
* - target[i] is a bystander `R` → every row between slot i and R's current
|
|
124
|
+
* position is provably a movee (the non-movees keep their relative order, so
|
|
125
|
+
* R is the first non-movee at or below i), and pushing the ONE movee directly
|
|
126
|
+
* above R down past it moves R up by exactly one slot.
|
|
127
|
+
*
|
|
128
|
+
* Both branches strictly reduce a distance that cannot go below zero, so the
|
|
129
|
+
* schedule terminates, and every chord it emits moves a named heading by one
|
|
130
|
+
* slot. Two endpoint shortcuts run first, because they are the common single
|
|
131
|
+
* heading requests and each costs one dispatch instead of a walk: a movee whose
|
|
132
|
+
* target is the very top or the very bottom is sent there with ⌘⌥↑ / ⌘⌥↓.
|
|
133
|
+
*/
|
|
134
|
+
export declare function planChordStep(order: readonly string[], target: readonly string[], movees: ReadonlySet<string>): ChordStep | {
|
|
135
|
+
error: string;
|
|
136
|
+
} | null;
|
|
137
|
+
/**
|
|
138
|
+
* Drive a project's headings into `spec.targetOrder`, one verified chord at a
|
|
139
|
+
* time (see {@link planChordStep} for the schedule). Nothing here trusts the
|
|
140
|
+
* plan it made a moment ago: every step is re-derived from a fresh database
|
|
141
|
+
* read, and the step is only counted once the database says it landed where it
|
|
142
|
+
* was aimed with nothing else touched.
|
|
143
|
+
*/
|
|
144
|
+
export declare function driveHeadingChordReorder(spec: HeadingChordSpec, run: UiRunner, reader: HeadingOrderReader | undefined, selectScript: (ordinal: number) => string, sleep?: (ms: number) => Promise<void>): Promise<ChordDriveResult>;
|