@wringer/core 0.1.0 → 0.1.2

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.
Files changed (258) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +71 -2
  3. package/dist/answer-supervisor-connection.d.ts +8 -0
  4. package/dist/app-machine.d.ts +76 -0
  5. package/dist/append-run-event.d.ts +16 -0
  6. package/dist/bind-drivers.d.ts +9 -0
  7. package/dist/build-commands.d.ts +5 -0
  8. package/dist/build-envelope-json-schema.d.ts +1 -0
  9. package/dist/build-envelope.d.ts +16 -0
  10. package/dist/build-launch-guard.d.ts +1 -0
  11. package/dist/build-manifest-write.d.ts +6 -0
  12. package/dist/build-promised-object-reads.d.ts +7 -0
  13. package/dist/build-report.d.ts +10 -0
  14. package/dist/build-run-handle.d.ts +2 -0
  15. package/dist/build-run-view.d.ts +29 -0
  16. package/dist/build-service-key.d.ts +1 -0
  17. package/dist/build-shut-down-steps.d.ts +14 -0
  18. package/dist/build-skip-worktree-marks.d.ts +7 -0
  19. package/dist/build-spawn-error.d.ts +2 -0
  20. package/dist/build-state-paths.d.ts +21 -0
  21. package/dist/build-submodule-adds.d.ts +7 -0
  22. package/dist/builtins/build-doctor-command.d.ts +2 -0
  23. package/dist/builtins/build-exec-command.d.ts +2 -0
  24. package/dist/builtins/build-lifecycle-commands.d.ts +3 -0
  25. package/dist/builtins/build-state-commands.d.ts +2 -0
  26. package/dist/builtins/build-use-pointers.d.ts +9 -0
  27. package/dist/builtins/build-verdict-commands.d.ts +2 -0
  28. package/dist/builtins/call-run-supervisor.d.ts +5 -0
  29. package/dist/builtins/pick-doctor-outcome.d.ts +13 -0
  30. package/dist/builtins/pick-start-action.d.ts +10 -0
  31. package/dist/builtins/pick-stop-plan.d.ts +14 -0
  32. package/dist/builtins/start-run.d.ts +22 -0
  33. package/dist/builtins/stop-data-schema.d.ts +6 -0
  34. package/dist/builtins/stop-run.d.ts +3 -0
  35. package/dist/call-supervisor.d.ts +10 -0
  36. package/dist/cap-data.d.ts +17 -0
  37. package/dist/collect-driver-configs.d.ts +7 -0
  38. package/dist/create-directory.d.ts +1 -0
  39. package/dist/create-evidence-writer.d.ts +13 -0
  40. package/dist/create-file-state.d.ts +36 -0
  41. package/dist/create-log-writer.d.ts +5 -0
  42. package/dist/create-node-repo-host.d.ts +2 -0
  43. package/dist/create-node-state-file-system.d.ts +10 -0
  44. package/dist/create-repo-state.d.ts +2 -0
  45. package/dist/create-socket-folder.d.ts +1 -0
  46. package/dist/create-wringer.d.ts +17 -0
  47. package/dist/decide-guard.d.ts +12 -0
  48. package/dist/define-driver.d.ts +13 -0
  49. package/dist/dispatch.d.ts +10 -0
  50. package/dist/envelope.d.ts +63 -0
  51. package/dist/error-codes.d.ts +25 -0
  52. package/dist/find-cancel-failure.d.ts +2 -0
  53. package/dist/find-colliding-service-key.d.ts +5 -0
  54. package/dist/find-own-value.d.ts +1 -0
  55. package/dist/find-remote-stop-failure.d.ts +2 -0
  56. package/dist/find-verdict-refusal.d.ts +3 -0
  57. package/dist/follow-process.d.ts +10 -0
  58. package/dist/get-lock-value.d.ts +2 -0
  59. package/dist/get-target.d.ts +2 -0
  60. package/dist/host.d.ts +19 -0
  61. package/dist/index.d.ts +60 -0
  62. package/dist/is-error-code.d.ts +1 -0
  63. package/dist/keep-cancelled-call.d.ts +1 -0
  64. package/dist/kill-process-group.d.ts +1 -0
  65. package/dist/launch-line-schema.d.ts +3 -0
  66. package/dist/listen-supervisor-socket.d.ts +8 -0
  67. package/dist/local.d.ts +2 -0
  68. package/dist/make-fence.d.ts +8 -0
  69. package/dist/make-fenced-exec.d.ts +10 -0
  70. package/dist/make-process-supervisor-port.d.ts +7 -0
  71. package/dist/open-drive.d.ts +23 -0
  72. package/dist/open-runless-drive.d.ts +17 -0
  73. package/dist/parse-launch-line.d.ts +2 -0
  74. package/dist/parse-patch-id.d.ts +2 -0
  75. package/dist/parse-report-block.d.ts +9 -0
  76. package/dist/parse-run-log.d.ts +2 -0
  77. package/dist/pick-access-refusal.d.ts +12 -0
  78. package/dist/pick-command-needs.d.ts +15 -0
  79. package/dist/pick-command-plan.d.ts +23 -0
  80. package/dist/pick-context-target.d.ts +7 -0
  81. package/dist/pick-drive-kind.d.ts +8 -0
  82. package/dist/pick-envelope-context.d.ts +1 -0
  83. package/dist/pick-envelope-payload.d.ts +12 -0
  84. package/dist/pick-envelope-run.d.ts +6 -0
  85. package/dist/pick-envelope-target.d.ts +4 -0
  86. package/dist/pick-late-failure-write.d.ts +13 -0
  87. package/dist/pick-log-refusal.d.ts +4 -0
  88. package/dist/pick-merge-base-failure.d.ts +2 -0
  89. package/dist/pick-merge-base-steps.d.ts +13 -0
  90. package/dist/pick-pending-cleanups.d.ts +10 -0
  91. package/dist/pick-submodule-refusal.d.ts +2 -0
  92. package/dist/pick-supervisor-operation.d.ts +16 -0
  93. package/dist/prepare-args.d.ts +3 -0
  94. package/dist/probe-process.d.ts +1 -0
  95. package/dist/quote-shell-word.d.ts +1 -0
  96. package/dist/race-deadline.d.ts +1 -0
  97. package/dist/read-changed-paths.d.ts +7 -0
  98. package/dist/read-default-base.d.ts +2 -0
  99. package/dist/read-fingerprint.d.ts +13 -0
  100. package/dist/read-head-sha.d.ts +2 -0
  101. package/dist/read-launch-host.d.ts +26 -0
  102. package/dist/read-pid-namespace.d.ts +1 -0
  103. package/dist/read-stream-line-batches.d.ts +2 -0
  104. package/dist/read-stream-lines.d.ts +2 -0
  105. package/dist/read-text.d.ts +1 -0
  106. package/dist/read-verdicts.d.ts +5 -0
  107. package/dist/remove-directory.d.ts +1 -0
  108. package/dist/remove-file.d.ts +1 -0
  109. package/dist/render-report-markdown.d.ts +4 -0
  110. package/dist/report-schema.d.ts +51 -0
  111. package/dist/run-events.d.ts +129 -0
  112. package/dist/run-git.d.ts +9 -0
  113. package/dist/run-process.d.ts +19 -0
  114. package/dist/run-supervisor-process.d.ts +2 -0
  115. package/dist/run-supervisor.d.ts +16 -0
  116. package/dist/settle-dispatch-answer.d.ts +9 -0
  117. package/dist/settle-envelope.d.ts +16 -0
  118. package/dist/ssh.d.ts +12 -0
  119. package/dist/start-launch.d.ts +20 -0
  120. package/dist/start-services.d.ts +16 -0
  121. package/dist/supervisor-machine.d.ts +78 -0
  122. package/dist/supervisor-protocol.d.ts +43 -0
  123. package/dist/to-wringer-error.d.ts +2 -0
  124. package/dist/types.d.ts +353 -0
  125. package/dist/wait-for-cancelled-calls.d.ts +2 -0
  126. package/dist/wringer-error.d.ts +12 -0
  127. package/dist/write-envelope-log.d.ts +11 -0
  128. package/dist/write-late-failure.d.ts +11 -0
  129. package/dist/write-new-file.d.ts +1 -0
  130. package/envelope.schema.json +175 -0
  131. package/package.json +21 -5
  132. package/src/answer-supervisor-connection.ts +117 -0
  133. package/src/app-machine.ts +174 -0
  134. package/src/append-run-event.ts +131 -0
  135. package/src/bind-drivers.ts +33 -0
  136. package/src/build-commands.ts +104 -0
  137. package/src/build-envelope-json-schema.ts +34 -0
  138. package/src/build-envelope.ts +40 -0
  139. package/src/build-launch-guard.ts +5 -0
  140. package/src/build-manifest-write.ts +26 -0
  141. package/src/build-promised-object-reads.ts +48 -0
  142. package/src/build-report.ts +55 -0
  143. package/src/build-run-handle.ts +13 -0
  144. package/src/build-run-view.ts +120 -0
  145. package/src/build-service-key.ts +4 -0
  146. package/src/build-shut-down-steps.ts +54 -0
  147. package/src/build-skip-worktree-marks.ts +36 -0
  148. package/src/build-spawn-error.ts +12 -0
  149. package/src/build-state-paths.ts +53 -0
  150. package/src/build-submodule-adds.ts +64 -0
  151. package/src/builtins/build-doctor-command.ts +163 -0
  152. package/src/builtins/build-exec-command.ts +41 -0
  153. package/src/builtins/build-lifecycle-commands.ts +115 -0
  154. package/src/builtins/build-state-commands.ts +152 -0
  155. package/src/builtins/build-use-pointers.ts +26 -0
  156. package/src/builtins/build-verdict-commands.ts +266 -0
  157. package/src/builtins/call-run-supervisor.ts +40 -0
  158. package/src/builtins/pick-doctor-outcome.ts +32 -0
  159. package/src/builtins/pick-start-action.ts +35 -0
  160. package/src/builtins/pick-stop-plan.ts +32 -0
  161. package/src/builtins/start-run.ts +281 -0
  162. package/src/builtins/stop-data-schema.ts +8 -0
  163. package/src/builtins/stop-run.ts +49 -0
  164. package/src/call-supervisor.ts +109 -0
  165. package/src/cap-data.ts +43 -0
  166. package/src/collect-driver-configs.ts +36 -0
  167. package/src/create-directory.ts +6 -0
  168. package/src/create-evidence-writer.ts +82 -0
  169. package/src/create-file-state.ts +193 -0
  170. package/src/create-log-writer.ts +38 -0
  171. package/src/create-node-repo-host.ts +20 -0
  172. package/src/create-node-state-file-system.ts +52 -0
  173. package/src/create-repo-state.ts +15 -0
  174. package/src/create-socket-folder.ts +24 -0
  175. package/src/create-wringer.ts +169 -0
  176. package/src/decide-guard.ts +47 -0
  177. package/src/define-driver.ts +165 -0
  178. package/src/dispatch.ts +589 -0
  179. package/src/envelope.ts +57 -0
  180. package/src/error-codes.ts +39 -0
  181. package/src/find-cancel-failure.ts +7 -0
  182. package/src/find-colliding-service-key.ts +16 -0
  183. package/src/find-own-value.ts +8 -0
  184. package/src/find-remote-stop-failure.ts +19 -0
  185. package/src/find-verdict-refusal.ts +26 -0
  186. package/src/follow-process.ts +147 -0
  187. package/src/get-lock-value.ts +17 -0
  188. package/src/get-target.ts +15 -0
  189. package/src/host.ts +26 -0
  190. package/src/index.ts +75 -0
  191. package/src/is-error-code.ts +3 -0
  192. package/src/keep-cancelled-call.ts +21 -0
  193. package/src/kill-process-group.ts +13 -0
  194. package/src/launch-line-schema.ts +6 -0
  195. package/src/listen-supervisor-socket.ts +75 -0
  196. package/src/local.ts +20 -0
  197. package/src/make-fence.ts +27 -0
  198. package/src/make-fenced-exec.ts +52 -0
  199. package/src/make-process-supervisor-port.ts +65 -0
  200. package/src/open-drive.ts +151 -0
  201. package/src/open-runless-drive.ts +71 -0
  202. package/src/parse-launch-line.ts +19 -0
  203. package/src/parse-patch-id.ts +8 -0
  204. package/src/parse-report-block.ts +39 -0
  205. package/src/parse-run-log.ts +34 -0
  206. package/src/pick-access-refusal.ts +32 -0
  207. package/src/pick-command-needs.ts +29 -0
  208. package/src/pick-command-plan.ts +51 -0
  209. package/src/pick-context-target.ts +22 -0
  210. package/src/pick-drive-kind.ts +23 -0
  211. package/src/pick-envelope-context.ts +10 -0
  212. package/src/pick-envelope-payload.ts +28 -0
  213. package/src/pick-envelope-run.ts +25 -0
  214. package/src/pick-envelope-target.ts +10 -0
  215. package/src/pick-late-failure-write.ts +44 -0
  216. package/src/pick-log-refusal.ts +18 -0
  217. package/src/pick-merge-base-failure.ts +15 -0
  218. package/src/pick-merge-base-steps.ts +37 -0
  219. package/src/pick-pending-cleanups.ts +23 -0
  220. package/src/pick-submodule-refusal.ts +46 -0
  221. package/src/pick-supervisor-operation.ts +52 -0
  222. package/src/prepare-args.ts +22 -0
  223. package/src/probe-process.ts +16 -0
  224. package/src/quote-shell-word.ts +9 -0
  225. package/src/race-deadline.ts +23 -0
  226. package/src/read-changed-paths.ts +39 -0
  227. package/src/read-default-base.ts +21 -0
  228. package/src/read-fingerprint.ts +271 -0
  229. package/src/read-head-sha.ts +23 -0
  230. package/src/read-launch-host.ts +64 -0
  231. package/src/read-pid-namespace.ts +18 -0
  232. package/src/read-stream-line-batches.ts +28 -0
  233. package/src/read-stream-lines.ts +11 -0
  234. package/src/read-text.ts +5 -0
  235. package/src/read-verdicts.ts +57 -0
  236. package/src/remove-directory.ts +6 -0
  237. package/src/remove-file.ts +6 -0
  238. package/src/render-report-markdown.ts +53 -0
  239. package/src/report-schema.ts +37 -0
  240. package/src/run-events.ts +71 -0
  241. package/src/run-git.ts +49 -0
  242. package/src/run-process.ts +168 -0
  243. package/src/run-supervisor-process.ts +51 -0
  244. package/src/run-supervisor.ts +327 -0
  245. package/src/settle-dispatch-answer.ts +26 -0
  246. package/src/settle-envelope.ts +34 -0
  247. package/src/ssh.ts +211 -0
  248. package/src/start-launch.ts +327 -0
  249. package/src/start-services.ts +108 -0
  250. package/src/supervisor-machine.ts +169 -0
  251. package/src/supervisor-protocol.ts +42 -0
  252. package/src/to-wringer-error.ts +20 -0
  253. package/src/types.ts +476 -0
  254. package/src/wait-for-cancelled-calls.ts +37 -0
  255. package/src/wringer-error.ts +25 -0
  256. package/src/write-envelope-log.ts +72 -0
  257. package/src/write-late-failure.ts +40 -0
  258. package/src/write-new-file.ts +17 -0
package/LICENSE CHANGED
@@ -1,6 +1,6 @@
1
1
  MIT License
2
2
 
3
- Copyright (c) 2026 the wringer authors
3
+ Copyright (c) 2026 Geoff Whatley
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
package/README.md CHANGED
@@ -9,8 +9,9 @@
9
9
 
10
10
  The core of wringer, a verification framework that each repo wraps in its own CLI.
11
11
 
12
- Every wringer command writes one JSON envelope. The package exports the envelope's version number,
13
- which a consumer checks before it reads the rest of the envelope.
12
+ Every wringer command writes one JSON envelope, and a streaming command writes NDJSON events before
13
+ it. The envelope carries `wringer: 1`, so a consumer checks the version before it reads the rest.
14
+ The package publishes the envelope's JSON Schema as `@wringer/core/envelope.schema.json`.
14
15
 
15
16
  ## Install
16
17
 
@@ -19,3 +20,71 @@ bun add @wringer/core
19
20
  ```
20
21
 
21
22
  The package runs on [Bun](https://bun.sh) 1.3 or newer.
23
+
24
+ ## Usage
25
+
26
+ A repo builds its registry with the typed builder, then hands it to a CLI adapter:
27
+
28
+ ```ts
29
+ import { createWringer, local } from '@wringer/core';
30
+
31
+ export const registry = createWringer({ name: 'shop' })
32
+ .target('local', {
33
+ mode: 'launch',
34
+ access: 'read-write',
35
+ host: local(),
36
+ launch: () => ({
37
+ command: ['bun', 'run', 'dev'],
38
+ ready: (line) => (line['event'] === 'listening' ? { web: 'http://127.0.0.1:3000' } : null),
39
+ }),
40
+ })
41
+ .feature({ name: 'checkout', summary: 'Pay for the cart', paths: ['src/checkout/**'] })
42
+ .build();
43
+ ```
44
+
45
+ Add drivers with `.use(...)`. `bindDrivers(drivers)` returns `defineAction`, `defineTarget`,
46
+ `defineCommand` and `defineCheck`, typed against those drivers, so a repo can define each one in its
47
+ own file.
48
+
49
+ ## Features
50
+
51
+ - The typed builder. Each action and command declares `effect: 'read' | 'write'`, and is a write
52
+ unless it says otherwise.
53
+ - Read-only targets: each driver client and exec refuses a write there with `read-only` and the
54
+ target's hint. A target's driver config lists the writes it grants.
55
+ - One supervisor process per run, which owns the app and every driver service.
56
+ - The built-in commands, from `up` and `doctor` to `done`, `report` and `gate`.
57
+ - The envelope's zod schema, and the JSON Schema built from it.
58
+ - A closed set of error codes, each mapped to one exit code.
59
+ - Run state on disk: `state.json` holds pointers, and each run's `log.ndjson` holds its events.
60
+ - The fingerprint: `git patch-id --verbatim` of the working tree against the merge base, which stays
61
+ the same across a commit and across a clean rebase that leaves the 3 lines around each change as
62
+ they were. A rebase that changes those lines changes the fingerprint, because the hash keeps the
63
+ diff's context. It needs git 2.39 or later. Only the tracked files and git's defaults shape it:
64
+ the config, attributes and ignore files of the clone, the user and the system never apply, so the
65
+ same change gets the same fingerprint in any clone. A clone whose config converts a file as git
66
+ adds it, such as `core.autocrlf` or a clean filter, can get another fingerprint once the change is
67
+ committed; the verdict then reads as stale, never as fresh. A sparse checkout, a linked worktree,
68
+ a shallow or partial clone and a detached HEAD get the fingerprint of the same change in a full
69
+ clone, and a file on disk that the index marks skip-worktree counts as any other. A repo with no
70
+ commit, a shallow clone that lacks the merge base, and a submodule that holds work it has not
71
+ committed fail with an `environment` error.
72
+ - Two hosts for exec: `local()`, and `ssh()` with an argv prefix in layers, quoted once per shell
73
+ layer. Each host also follows a long-running command, such as `tail -F`, line by line.
74
+
75
+ ## Error codes
76
+
77
+ A command that passes exits `0`. A command that fails puts one of these in the envelope's
78
+ `error.code`, and exits with its exit code:
79
+
80
+ | Code | Exit | Meaning |
81
+ | -------------------- | ---- | ---------------------------------------------- |
82
+ | `check-failed` | 1 | A check or an assertion failed. |
83
+ | `usage` | 2 | The command or its arguments are not valid. |
84
+ | `read-only` | 3 | A read-only target refused a write. |
85
+ | `doctor-required` | 3 | The doctor has not passed on the current run. |
86
+ | `not-running` | 3 | The target has no running run. |
87
+ | `target-not-allowed` | 3 | The command does not run on this target. |
88
+ | `environment` | 4 | A tool, a host or the network failed. |
89
+ | `internal` | 4 | wringer failed; the stack is in the run's log. |
90
+ | `timeout` | 5 | The command ran past its deadline. |
@@ -0,0 +1,8 @@
1
+ import type { Duplex } from 'node:stream';
2
+ import type { SupervisorRequest } from './supervisor-protocol.ts';
3
+ export type SupervisorRequestHandler = (request: SupervisorRequest, signal: AbortSignal) => Promise<unknown>;
4
+ export interface SupervisorConnectionOptions {
5
+ readonly answerRequest: SupervisorRequestHandler;
6
+ readonly onTransportError: (error: unknown) => void;
7
+ }
8
+ export declare function answerSupervisorConnection(connection: Duplex, options: SupervisorConnectionOptions, closing: AbortSignal): Promise<void>;
@@ -0,0 +1,76 @@
1
+ import type { Endpoints } from './run-events.ts';
2
+ import { WringerError } from './wringer-error.ts';
3
+ interface AppMachineInput {
4
+ readonly readyTimeoutMs: number;
5
+ readonly reportCrash: (reason: string) => void;
6
+ readonly killGroup: () => void;
7
+ readonly stopApp: () => Promise<void>;
8
+ }
9
+ export type AppStart = {
10
+ readonly kind: 'pending';
11
+ } | {
12
+ readonly kind: 'ready';
13
+ readonly endpoints: Endpoints;
14
+ } | {
15
+ readonly kind: 'failed';
16
+ readonly failure: WringerError;
17
+ };
18
+ interface AppContext extends AppMachineInput {
19
+ readonly start: AppStart;
20
+ readonly logFailure: string | null;
21
+ readonly stopFailure: WringerError | null;
22
+ }
23
+ type AppEvent = {
24
+ readonly type: 'ready';
25
+ readonly endpoints: Endpoints;
26
+ } | {
27
+ readonly type: 'exited';
28
+ readonly exitCode: number;
29
+ } | {
30
+ readonly type: 'log.failed';
31
+ readonly reason: string;
32
+ } | {
33
+ readonly type: 'abort';
34
+ } | {
35
+ readonly type: 'stop';
36
+ };
37
+ export declare const appMachine: import("xstate").StateMachine<AppContext, AppEvent, {
38
+ [x: string]: import("xstate").ActorRefFromLogic<import("xstate").PromiseActorLogic<null, {
39
+ readonly run: () => Promise<void>;
40
+ }, import("xstate").EventObject>> | undefined;
41
+ }, {
42
+ src: "stopApp";
43
+ logic: import("xstate").PromiseActorLogic<null, {
44
+ readonly run: () => Promise<void>;
45
+ }, import("xstate").EventObject>;
46
+ id: string | undefined;
47
+ }, {
48
+ type: "failStart";
49
+ params: import("xstate").NonReducibleUnknown;
50
+ } | {
51
+ type: "failStartOnTimeout";
52
+ params: import("xstate").NonReducibleUnknown;
53
+ } | {
54
+ type: "keepEndpoints";
55
+ params: import("xstate").NonReducibleUnknown;
56
+ } | {
57
+ type: "keepLogFailure";
58
+ params: import("xstate").NonReducibleUnknown;
59
+ } | {
60
+ type: "killGroup";
61
+ params: unknown;
62
+ } | {
63
+ type: "reportCrash";
64
+ params: unknown;
65
+ }, never, "readyTimeout", "crashed" | "failingStart" | "running" | "startFailed" | "starting" | "stopped" | "stopping", string, AppMachineInput, import("xstate").NonReducibleUnknown, import("xstate").EventObject, import("xstate").MetaObject, {
66
+ states: {
67
+ readonly starting: {};
68
+ readonly failingStart: {};
69
+ readonly startFailed: {};
70
+ readonly running: {};
71
+ readonly crashed: {};
72
+ readonly stopping: {};
73
+ readonly stopped: {};
74
+ };
75
+ }, import("xstate").MetaObject>;
76
+ export {};
@@ -0,0 +1,16 @@
1
+ import type { StateFileSystem } from './create-node-state-file-system.ts';
2
+ import type { RunEvent, RunEventType } from './run-events.ts';
3
+ import { WringerError } from './wringer-error.ts';
4
+ export interface AppendRunEventRequest {
5
+ readonly fs: StateFileSystem;
6
+ readonly logPath: string;
7
+ readonly lockPath: string;
8
+ readonly lockTimeoutMs: number;
9
+ readonly line: string;
10
+ readonly event: RunEvent;
11
+ readonly refuse: ((events: readonly RunEvent[]) => WringerError | null) | null;
12
+ }
13
+ export declare function appendRunEvent(request: AppendRunEventRequest): Promise<boolean>;
14
+ export type RunStatus = 'starting' | 'running' | 'crashed' | 'ended';
15
+ export declare function findRunStatusMove(eventType: RunEventType): RunStatus | null;
16
+ export declare function canMoveRunStatus(from: RunStatus, to: RunStatus): boolean;
@@ -0,0 +1,9 @@
1
+ import type { ActionDefinition, AnyDrivers, CheckDefinition, CommandSpec, TargetDefinition } from './types.ts';
2
+ export interface BoundHelpers<Ds extends AnyDrivers> {
3
+ readonly drivers: Ds;
4
+ readonly defineAction: <Input, Data>(action: ActionDefinition<Input, Data, Ds>) => ActionDefinition<Input, Data, Ds>;
5
+ readonly defineTarget: <Target extends TargetDefinition<Ds>>(target: Target) => Target;
6
+ readonly defineCommand: <Args, Data>(spec: CommandSpec<Args, Data, Ds>) => CommandSpec<Args, Data, Ds>;
7
+ readonly defineCheck: <Input, Data>(check: CheckDefinition<Input, Data, Ds>) => CheckDefinition<Input, Data, Ds>;
8
+ }
9
+ export declare function bindDrivers<const Ds extends AnyDrivers>(drivers: Ds): BoundHelpers<Ds>;
@@ -0,0 +1,5 @@
1
+ import type { ActionDefinition, AnyDrivers, BuiltinCommandSpec, CheckDefinition, CommandSpec, RegisteredCommand, RunnableRepoCheck } from './types.ts';
2
+ export declare function buildBuiltinCommand<Args, Data>(spec: BuiltinCommandSpec<Args, Data>): RegisteredCommand;
3
+ export declare function buildRepoCommand<Args, Data, Ds extends AnyDrivers>(spec: CommandSpec<Args, Data, Ds>, targets: readonly string[] | undefined, driverNames: readonly string[]): RegisteredCommand;
4
+ export declare function buildActionCommand<Input, Data, Ds extends AnyDrivers>(action: ActionDefinition<Input, Data, Ds>, driverNames: readonly string[]): RegisteredCommand;
5
+ export declare function buildRepoCheck<Input, Data, Ds extends AnyDrivers>(check: CheckDefinition<Input, Data, Ds>, driverNames: readonly string[]): RunnableRepoCheck;
@@ -0,0 +1 @@
1
+ export declare function buildEnvelopeJSONSchema(): Record<string, unknown>;
@@ -0,0 +1,16 @@
1
+ import type { Envelope, Evidence } from './envelope.ts';
2
+ import type { WringerError } from './wringer-error.ts';
3
+ export interface EnvelopeInput {
4
+ readonly command: string;
5
+ readonly target: string | null;
6
+ readonly instance: string | null;
7
+ readonly feature: string | null;
8
+ readonly sha: string | null;
9
+ readonly durationMs: number;
10
+ readonly data: unknown;
11
+ readonly evidence: readonly Evidence[];
12
+ readonly cursors: Readonly<Record<string, number>>;
13
+ readonly truncatedPath: string | null;
14
+ readonly error: WringerError | null;
15
+ }
16
+ export declare function buildEnvelope(input: EnvelopeInput): Envelope;
@@ -0,0 +1 @@
1
+ export declare function buildLaunchGuard(setprivPath: string | null): readonly string[];
@@ -0,0 +1,6 @@
1
+ import type { RunView } from './build-run-view.ts';
2
+ export interface ManifestWrite {
3
+ readonly path: string;
4
+ readonly text: string;
5
+ }
6
+ export declare function buildManifestWrite(path: string, view: RunView | undefined): ManifestWrite | null;
@@ -0,0 +1,7 @@
1
+ import type { GitRequest } from './run-git.ts';
2
+ export interface PromisedObjectReadInput {
3
+ readonly root: string;
4
+ readonly mergeBase: string;
5
+ readonly configList: string;
6
+ }
7
+ export declare function buildPromisedObjectReads(input: PromisedObjectReadInput): GitRequest[];
@@ -0,0 +1,10 @@
1
+ import type { Report, Verdict } from './report-schema.ts';
2
+ import type { FeatureDefinition } from './types.ts';
3
+ export interface ReportInput {
4
+ readonly base: string;
5
+ readonly fingerprint: string;
6
+ readonly features: readonly FeatureDefinition[];
7
+ readonly changedPaths: readonly string[];
8
+ readonly verdicts: ReadonlyMap<string, Verdict>;
9
+ }
10
+ export declare function buildReport(input: ReportInput): Report;
@@ -0,0 +1,2 @@
1
+ import type { RunHandle } from './types.ts';
2
+ export declare function buildRunHandle(stateDir: string, runID: string): RunHandle;
@@ -0,0 +1,29 @@
1
+ import type { RunStatus } from './append-run-event.ts';
2
+ import type { Envelope } from './envelope.ts';
3
+ import type { CheckResult, Endpoints, Mode, RunEvent, RunID } from './run-events.ts';
4
+ export type DoctorState = 'none' | 'passed' | 'failed';
5
+ export interface SupervisorInfo {
6
+ readonly pid: number;
7
+ readonly socket: string;
8
+ }
9
+ export interface RunView {
10
+ readonly runID: RunID;
11
+ readonly target: string;
12
+ readonly mode: Mode;
13
+ readonly fingerprint: string;
14
+ readonly status: RunStatus;
15
+ readonly startedAt: string;
16
+ readonly endedAt: string | null;
17
+ readonly crashReason: string | null;
18
+ readonly endpoints: Endpoints;
19
+ readonly services: readonly string[];
20
+ readonly supervisor: SupervisorInfo | null;
21
+ readonly doctor: DoctorState;
22
+ readonly doctorResults: readonly CheckResult[];
23
+ readonly drivesAfterDoctor: readonly Envelope[];
24
+ }
25
+ export interface BuildRunViewInput {
26
+ readonly runID: RunID;
27
+ readonly events: readonly RunEvent[];
28
+ }
29
+ export declare function buildRunView(input: BuildRunViewInput): RunView | undefined;
@@ -0,0 +1 @@
1
+ export declare function buildServiceKey(driver: string, service: string): string;
@@ -0,0 +1,14 @@
1
+ import type { RunEvent } from './run-events.ts';
2
+ import { WringerError } from './wringer-error.ts';
3
+ export interface ShutDownFacts {
4
+ readonly crashReason: string | null;
5
+ readonly gaveUpOnStartup: boolean;
6
+ readonly failures: readonly string[];
7
+ readonly at: string;
8
+ }
9
+ export interface ShutDownSteps {
10
+ readonly abortCommands: boolean;
11
+ readonly events: readonly RunEvent[];
12
+ readonly failure: WringerError | null;
13
+ }
14
+ export declare function buildShutDownSteps(facts: ShutDownFacts): ShutDownSteps;
@@ -0,0 +1,7 @@
1
+ import type { GitRequest } from './run-git.ts';
2
+ export interface SkipWorktreeMarkInput {
3
+ readonly root: string;
4
+ readonly env: Readonly<Record<string, string>>;
5
+ readonly taggedEntries: Uint8Array;
6
+ }
7
+ export declare function buildSkipWorktreeMarks(input: SkipWorktreeMarkInput): GitRequest[];
@@ -0,0 +1,2 @@
1
+ import { WringerError } from './wringer-error.ts';
2
+ export declare function buildSpawnError(command: string, error: unknown): WringerError;
@@ -0,0 +1,21 @@
1
+ import type { RunID } from './run-events.ts';
2
+ export interface StatePaths {
3
+ readonly root: string;
4
+ readonly state: string;
5
+ readonly locks: string;
6
+ readonly runs: string;
7
+ readonly lateFailures: string;
8
+ }
9
+ export declare function buildStatePaths(stateDir: string): StatePaths;
10
+ export interface RunPaths {
11
+ readonly directory: string;
12
+ readonly manifest: string;
13
+ readonly log: string;
14
+ readonly socket: string;
15
+ readonly supervisorLog: string;
16
+ readonly streams: string;
17
+ readonly children: string;
18
+ readonly features: string;
19
+ readonly lock: string;
20
+ }
21
+ export declare function buildRunPaths(stateDir: string, runID: RunID): RunPaths;
@@ -0,0 +1,7 @@
1
+ import type { GitRequest } from './run-git.ts';
2
+ export interface SubmoduleAddInput {
3
+ readonly root: string;
4
+ readonly env: Readonly<Record<string, string>>;
5
+ readonly stagedEntries: Uint8Array;
6
+ }
7
+ export declare function buildSubmoduleAdds(input: SubmoduleAddInput): GitRequest[];
@@ -0,0 +1,2 @@
1
+ import type { RegisteredCommand } from '../types.ts';
2
+ export declare function buildDoctorCommand(): RegisteredCommand;
@@ -0,0 +1,2 @@
1
+ import type { RegisteredCommand } from '../types.ts';
2
+ export declare function buildExecCommand(): RegisteredCommand;
@@ -0,0 +1,3 @@
1
+ import type { RegisteredCommand } from '../types.ts';
2
+ export declare const launchReadyTimeoutMs = 120000;
3
+ export declare function buildLifecycleCommands(): readonly RegisteredCommand[];
@@ -0,0 +1,2 @@
1
+ import type { RegisteredCommand } from '../types.ts';
2
+ export declare function buildStateCommands(): readonly RegisteredCommand[];
@@ -0,0 +1,9 @@
1
+ import type { Pointers } from '../create-file-state.ts';
2
+ import type { RunID } from '../run-events.ts';
3
+ export interface UseChange {
4
+ readonly target: string | undefined;
5
+ readonly feature: string | undefined;
6
+ readonly cursors: Readonly<Record<string, number>>;
7
+ readonly runID: RunID | undefined;
8
+ }
9
+ export declare function buildUsePointers(current: Pointers, change: UseChange): Pointers;
@@ -0,0 +1,2 @@
1
+ import type { RegisteredCommand } from '../types.ts';
2
+ export declare function buildVerdictCommands(): readonly RegisteredCommand[];
@@ -0,0 +1,5 @@
1
+ import type { RunView } from '../build-run-view.ts';
2
+ import type { SupervisorPort } from '../types.ts';
3
+ export type SupervisorReach = 'answered' | 'gone';
4
+ export declare function callRunSupervisor(supervisor: SupervisorPort, run: RunView, method: 'ping' | 'stop', signal: AbortSignal): Promise<SupervisorReach>;
5
+ export declare function isSupervisorGone(error: unknown): boolean;
@@ -0,0 +1,13 @@
1
+ import type { CheckResult, RunEvent } from '../run-events.ts';
2
+ import { WringerError } from '../wringer-error.ts';
3
+ interface DoctorData {
4
+ readonly passed: boolean;
5
+ readonly results: CheckResult[];
6
+ }
7
+ export interface DoctorOutcome {
8
+ readonly event: RunEvent;
9
+ readonly data: DoctorData;
10
+ readonly failure: WringerError | null;
11
+ }
12
+ export declare function pickDoctorOutcome(results: readonly CheckResult[], at: string): DoctorOutcome;
13
+ export {};
@@ -0,0 +1,10 @@
1
+ import type { RunStatus } from '../append-run-event.ts';
2
+ import type { SupervisorReach } from './call-run-supervisor.ts';
3
+ export interface StartFacts {
4
+ readonly status: RunStatus | null;
5
+ readonly restart: boolean;
6
+ readonly ping: SupervisorReach | null;
7
+ readonly stop: SupervisorReach | null;
8
+ }
9
+ export type StartAction = 'ping' | 'stop' | 'reuse' | 'mark-crashed' | 'start';
10
+ export declare function pickStartAction(facts: StartFacts): StartAction;
@@ -0,0 +1,14 @@
1
+ import type { RunView } from '../build-run-view.ts';
2
+ import type { SupervisorReach } from './call-run-supervisor.ts';
3
+ import type { StopData } from './stop-data-schema.ts';
4
+ export interface StopInput {
5
+ readonly runID: string | undefined;
6
+ readonly status: RunView['status'] | undefined;
7
+ readonly reach: SupervisorReach;
8
+ }
9
+ export interface StopPlan {
10
+ readonly data: StopData;
11
+ readonly markCrashed: boolean;
12
+ readonly clearPointer: boolean;
13
+ }
14
+ export declare function pickStopPlan(input: StopInput): StopPlan;
@@ -0,0 +1,22 @@
1
+ import { z } from 'zod';
2
+ import type { BuiltinContext } from '../types.ts';
3
+ export declare const runDataSchema: z.ZodObject<{
4
+ run: z.ZodString;
5
+ target: z.ZodString;
6
+ status: z.ZodEnum<{
7
+ crashed: "crashed";
8
+ ended: "ended";
9
+ running: "running";
10
+ starting: "starting";
11
+ }>;
12
+ endpoints: z.ZodRecord<z.ZodString, z.ZodString>;
13
+ services: z.ZodArray<z.ZodString>;
14
+ reused: z.ZodBoolean;
15
+ }, z.core.$strict>;
16
+ export type RunData = z.infer<typeof runDataSchema>;
17
+ export interface StartRunRequest {
18
+ readonly command: 'up' | 'attach';
19
+ readonly restart: boolean;
20
+ readonly readyTimeoutMs: number;
21
+ }
22
+ export declare function startRun(ctx: BuiltinContext, request: StartRunRequest): Promise<RunData>;
@@ -0,0 +1,6 @@
1
+ import { z } from 'zod';
2
+ export declare const stopDataSchema: z.ZodObject<{
3
+ run: z.ZodNullable<z.ZodString>;
4
+ stopped: z.ZodBoolean;
5
+ }, z.core.$strict>;
6
+ export type StopData = z.infer<typeof stopDataSchema>;
@@ -0,0 +1,3 @@
1
+ import type { BuiltinContext } from '../types.ts';
2
+ import type { StopData } from './stop-data-schema.ts';
3
+ export declare function stopRun(ctx: BuiltinContext): Promise<StopData>;
@@ -0,0 +1,10 @@
1
+ import type { SupervisorRequest } from './supervisor-protocol.ts';
2
+ import { WringerError } from './wringer-error.ts';
3
+ export interface SupervisorCall {
4
+ readonly socket: string;
5
+ readonly request: SupervisorRequest;
6
+ readonly signal: AbortSignal;
7
+ }
8
+ export declare function callSupervisor(call: SupervisorCall): Promise<unknown>;
9
+ export declare const supervisorCancelWaitMs = 2000;
10
+ export declare function buildUnconfirmedError(): WringerError;
@@ -0,0 +1,17 @@
1
+ import type { Evidence } from './envelope.ts';
2
+ import type { EvidenceFiles } from './types.ts';
3
+ import type { WringerError } from './wringer-error.ts';
4
+ export declare const dataCapBytes: number;
5
+ export interface CapRequest {
6
+ readonly root: string;
7
+ readonly directory: string;
8
+ readonly now: () => Date;
9
+ readonly files: EvidenceFiles;
10
+ }
11
+ export interface CappedData {
12
+ readonly data: unknown;
13
+ readonly evidence: readonly Evidence[];
14
+ readonly truncatedPath: string | null;
15
+ readonly failure: WringerError | null;
16
+ }
17
+ export declare function capData(data: unknown, request: CapRequest): Promise<CappedData>;
@@ -0,0 +1,7 @@
1
+ import type { ConfiguredDriver, DriverConfigContext, TargetDefinition, Wringer } from './types.ts';
2
+ export interface ConfiguredEntry {
3
+ readonly name: string;
4
+ readonly serviceNames: readonly string[];
5
+ readonly configured: ConfiguredDriver;
6
+ }
7
+ export declare function collectDriverConfigs(wringer: Wringer, target: TargetDefinition, ctx: DriverConfigContext): readonly ConfiguredEntry[];
@@ -0,0 +1 @@
1
+ export declare function createDirectory(path: string): Promise<void>;
@@ -0,0 +1,13 @@
1
+ import type { Evidence } from './envelope.ts';
2
+ import type { EvidenceFiles, EvidenceWriter } from './types.ts';
3
+ export interface EvidenceWriterOptions {
4
+ readonly root: string;
5
+ readonly directory: string;
6
+ readonly now: () => Date;
7
+ readonly files: EvidenceFiles;
8
+ }
9
+ export interface CollectingEvidenceWriter {
10
+ readonly writer: EvidenceWriter;
11
+ readonly collected: readonly Evidence[];
12
+ }
13
+ export declare function createEvidenceWriter(options: EvidenceWriterOptions): CollectingEvidenceWriter;
@@ -0,0 +1,36 @@
1
+ import { z } from 'zod';
2
+ import type { RunView } from './build-run-view.ts';
3
+ import type { StatePaths } from './build-state-paths.ts';
4
+ import type { StateFileSystem } from './create-node-state-file-system.ts';
5
+ import type { LateFailureEvent, RunEvent, RunID } from './run-events.ts';
6
+ import { WringerError } from './wringer-error.ts';
7
+ export declare const pointersSchema: z.ZodObject<{
8
+ currentRun: z.ZodRecord<z.ZodString, z.ZodString>;
9
+ target: z.ZodOptional<z.ZodString>;
10
+ feature: z.ZodOptional<z.ZodString>;
11
+ cursors: z.ZodRecord<z.ZodString, z.ZodNumber>;
12
+ cursorsRun: z.ZodOptional<z.ZodString>;
13
+ }, z.core.$strict>;
14
+ export type Pointers = z.infer<typeof pointersSchema>;
15
+ export type RunViewRefusal = (run: RunView | undefined) => WringerError | null;
16
+ export interface StatePort {
17
+ readonly paths: StatePaths;
18
+ readonly readPointers: () => Promise<Pointers>;
19
+ readonly withTargetLock: <T>(target: string, work: () => Promise<T>) => Promise<T>;
20
+ readonly writePointers: (change: (current: Pointers) => Pointers) => Promise<Pointers>;
21
+ readonly appendEvent: (runID: RunID, event: RunEvent) => Promise<void>;
22
+ readonly appendEventUnless: (runID: RunID, event: RunEvent, refuse: RunViewRefusal) => Promise<void>;
23
+ readonly appendLateFailure: (event: LateFailureEvent) => Promise<void>;
24
+ readonly readRunEvents: (runID: RunID) => Promise<readonly RunEvent[]>;
25
+ readonly readRun: (runID: RunID) => Promise<RunView | undefined>;
26
+ readonly listRuns: () => Promise<readonly RunID[]>;
27
+ readonly writeManifest: (runID: RunID) => Promise<void>;
28
+ readonly readCursors: (runID: RunID) => Promise<Record<string, number>>;
29
+ }
30
+ export interface FileStateOptions {
31
+ readonly stateDir: string;
32
+ readonly lockTimeoutMs: number;
33
+ readonly fs: StateFileSystem;
34
+ }
35
+ export declare const eventSizeCapBytes: number;
36
+ export declare function createFileState(options: FileStateOptions): StatePort;
@@ -0,0 +1,5 @@
1
+ export interface LogWriter {
2
+ readonly append: (text: string) => Promise<void>;
3
+ readonly close: () => Promise<void>;
4
+ }
5
+ export declare function createLogWriter(appendLog: (text: string) => Promise<void>): LogWriter;
@@ -0,0 +1,2 @@
1
+ import type { RepoHost } from './types.ts';
2
+ export declare function createNodeRepoHost(): RepoHost;
@@ -0,0 +1,10 @@
1
+ export interface StateFileSystem {
2
+ readonly readText: (path: string) => Promise<string | null>;
3
+ readonly listNames: (directory: string) => Promise<readonly string[]>;
4
+ readonly readFileSize: (path: string) => Promise<number>;
5
+ readonly createDirectory: (path: string) => Promise<void>;
6
+ readonly appendText: (path: string, text: string) => Promise<void>;
7
+ readonly truncateFile: (path: string, length: number) => Promise<void>;
8
+ readonly writeTextAtomic: (path: string, text: string) => Promise<void>;
9
+ }
10
+ export declare function createNodeStateFileSystem(): StateFileSystem;
@@ -0,0 +1,2 @@
1
+ import type { StatePort } from './create-file-state.ts';
2
+ export declare function createRepoState(root: string, stateDir: string): StatePort;
@@ -0,0 +1 @@
1
+ export declare function createSocketFolder(preferredSocket: string): Promise<string>;
@@ -0,0 +1,17 @@
1
+ import type { ActionDefinition, AnyDriver, AnyDrivers, CheckDefinition, CommandSpec, FeatureDefinition, HookHandlers, TargetDefinition, Wringer } from './types.ts';
2
+ export interface WringerOptions {
3
+ readonly name: string;
4
+ readonly stateDir?: string | undefined;
5
+ }
6
+ export interface WringerBuilder<Ds extends AnyDrivers> {
7
+ readonly use: <const Added extends readonly AnyDriver[]>(...drivers: Added) => WringerBuilder<readonly [...Ds, ...Added]>;
8
+ readonly target: (name: string, target: TargetDefinition<Ds>) => WringerBuilder<Ds>;
9
+ readonly command: <Args, Data>(spec: CommandSpec<Args, Data, Ds>) => WringerBuilder<Ds>;
10
+ readonly action: <Input, Data>(action: ActionDefinition<Input, Data, Ds>) => WringerBuilder<Ds>;
11
+ readonly check: <Input, Data>(check: CheckDefinition<Input, Data, Ds>) => WringerBuilder<Ds>;
12
+ readonly feature: (...features: readonly FeatureDefinition[]) => WringerBuilder<Ds>;
13
+ readonly hook: <Name extends keyof HookHandlers>(name: Name, handler: HookHandlers[Name]) => WringerBuilder<Ds>;
14
+ readonly build: () => Wringer;
15
+ }
16
+ export declare function createWringer(options: WringerOptions): WringerBuilder<readonly []>;
17
+ export declare const defaultStateDir = ".wringer";