@riddledc/riddle-proof 0.7.24 → 0.7.25
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 +10 -0
- package/dist/{chunk-5KOHSE4V.js → chunk-7PSWK57T.js} +98 -5
- package/dist/cli.cjs +127 -8
- package/dist/cli.js +30 -4
- package/dist/index.cjs +98 -5
- package/dist/index.d.cts +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/proof-run-engine.d.cts +3 -3
- package/dist/proof-run-engine.d.ts +3 -3
- package/dist/riddle-client.cjs +98 -5
- package/dist/riddle-client.d.cts +29 -11
- package/dist/riddle-client.d.ts +29 -11
- package/dist/riddle-client.js +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -339,6 +339,16 @@ that performs the interaction. If proof is weak, keep the diagnostics history in
|
|
|
339
339
|
the run state so the next agent can see the last route, tool status, artifact
|
|
340
340
|
shape, and errors without rerunning blind.
|
|
341
341
|
|
|
342
|
+
### Riddle Job Polling
|
|
343
|
+
|
|
344
|
+
`riddle-proof-loop riddle-poll <job-id> --wait` keeps stdout as JSON and writes
|
|
345
|
+
human progress lines to stderr while waiting. The JSON result includes
|
|
346
|
+
`poll.timed_out`, `poll.elapsed_ms`, `poll.queue_elapsed_ms`, and
|
|
347
|
+
`poll.running_without_submission` so delayed dispatch is distinguishable from a
|
|
348
|
+
terminal proof failure. If `--wait` exhausts its attempts before a terminal job
|
|
349
|
+
status, the command exits non-zero and the result explains the last observed
|
|
350
|
+
status and `submitted_at` state.
|
|
351
|
+
|
|
342
352
|
## OpenClaw Adapter Boundary
|
|
343
353
|
|
|
344
354
|
`@riddledc/riddle-proof/openclaw` translates OpenClaw Riddle Proof tool params
|
|
@@ -196,21 +196,109 @@ async function runRiddleScript(config, input) {
|
|
|
196
196
|
function isTerminalRiddleJobStatus(status) {
|
|
197
197
|
return ["completed", "complete", "completed_error", "completed_timeout", "failed"].includes(String(status || ""));
|
|
198
198
|
}
|
|
199
|
+
function stringField(record, key) {
|
|
200
|
+
const value = record?.[key];
|
|
201
|
+
return typeof value === "string" && value.trim() ? value.trim() : null;
|
|
202
|
+
}
|
|
203
|
+
function parseTimestampMs(value) {
|
|
204
|
+
if (!value) return null;
|
|
205
|
+
const parsed = Date.parse(value);
|
|
206
|
+
return Number.isFinite(parsed) ? parsed : null;
|
|
207
|
+
}
|
|
208
|
+
function buildPollSnapshot(jobId, job, input) {
|
|
209
|
+
const status = job?.status ? String(job.status) : null;
|
|
210
|
+
const terminal = isTerminalRiddleJobStatus(status);
|
|
211
|
+
const createdAt = stringField(job, "created_at");
|
|
212
|
+
const submittedAt = stringField(job, "submitted_at");
|
|
213
|
+
const completedAt = stringField(job, "completed_at");
|
|
214
|
+
const createdMs = parseTimestampMs(createdAt);
|
|
215
|
+
const submittedMs = parseTimestampMs(submittedAt);
|
|
216
|
+
let queueElapsedMs = null;
|
|
217
|
+
if (createdMs !== null && submittedMs !== null) {
|
|
218
|
+
queueElapsedMs = Math.max(0, submittedMs - createdMs);
|
|
219
|
+
} else if (createdMs !== null && !submittedAt && !terminal) {
|
|
220
|
+
queueElapsedMs = Math.max(0, input.observedAt - createdMs);
|
|
221
|
+
}
|
|
222
|
+
return {
|
|
223
|
+
job_id: jobId,
|
|
224
|
+
status,
|
|
225
|
+
terminal,
|
|
226
|
+
attempt: input.attempt,
|
|
227
|
+
attempts: input.attempts,
|
|
228
|
+
elapsed_ms: Math.max(0, input.observedAt - input.startedAt),
|
|
229
|
+
created_at: createdAt,
|
|
230
|
+
submitted_at: submittedAt,
|
|
231
|
+
completed_at: completedAt,
|
|
232
|
+
queue_elapsed_ms: queueElapsedMs,
|
|
233
|
+
running_without_submission: Boolean(status && !terminal && !submittedAt)
|
|
234
|
+
};
|
|
235
|
+
}
|
|
236
|
+
function pollMessage(snapshot, timedOut) {
|
|
237
|
+
if (!timedOut) return void 0;
|
|
238
|
+
const submitted = snapshot.submitted_at || "not submitted";
|
|
239
|
+
const queue = snapshot.queue_elapsed_ms !== null ? ` queue_elapsed_ms=${snapshot.queue_elapsed_ms}` : "";
|
|
240
|
+
return `Riddle job ${snapshot.job_id} did not reach a terminal status after ${snapshot.attempt} poll attempts; status=${snapshot.status || "unknown"} submitted_at=${submitted}.${queue}`;
|
|
241
|
+
}
|
|
199
242
|
async function pollRiddleJob(config, jobId, options = {}) {
|
|
200
243
|
if (!jobId?.trim()) throw new Error("jobId is required");
|
|
201
|
-
const attempts = options.attempts
|
|
202
|
-
const intervalMs = options.intervalMs
|
|
244
|
+
const attempts = Math.max(1, Math.floor(options.attempts ?? (options.wait ? 300 : 1)));
|
|
245
|
+
const intervalMs = Math.max(0, Math.floor(options.intervalMs ?? 2e3));
|
|
246
|
+
const progressEveryMs = Math.max(0, Math.floor(options.progressEveryMs ?? 1e4));
|
|
247
|
+
const startedAt = Date.now();
|
|
203
248
|
let job = null;
|
|
249
|
+
let lastSnapshot = null;
|
|
250
|
+
let lastProgressAt = 0;
|
|
251
|
+
let lastProgressKey = "";
|
|
204
252
|
for (let index = 0; index < attempts; index += 1) {
|
|
205
253
|
job = await riddleRequestJson(config, `/v1/jobs/${jobId}`);
|
|
206
|
-
|
|
254
|
+
const observedAt = Date.now();
|
|
255
|
+
lastSnapshot = buildPollSnapshot(jobId, job, {
|
|
256
|
+
attempt: index + 1,
|
|
257
|
+
attempts,
|
|
258
|
+
startedAt,
|
|
259
|
+
observedAt
|
|
260
|
+
});
|
|
261
|
+
const progressKey = [
|
|
262
|
+
lastSnapshot.status || "unknown",
|
|
263
|
+
lastSnapshot.terminal ? "terminal" : "nonterminal",
|
|
264
|
+
lastSnapshot.submitted_at ? "submitted" : "unsubmitted"
|
|
265
|
+
].join(":");
|
|
266
|
+
if (options.onProgress) {
|
|
267
|
+
const shouldReport = index === 0 || lastSnapshot.terminal || progressKey !== lastProgressKey || observedAt - lastProgressAt >= progressEveryMs;
|
|
268
|
+
if (shouldReport) {
|
|
269
|
+
lastProgressAt = observedAt;
|
|
270
|
+
lastProgressKey = progressKey;
|
|
271
|
+
await options.onProgress(lastSnapshot);
|
|
272
|
+
}
|
|
273
|
+
}
|
|
274
|
+
if (lastSnapshot.terminal) break;
|
|
207
275
|
if (index + 1 < attempts) {
|
|
208
276
|
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
209
277
|
}
|
|
210
278
|
}
|
|
211
279
|
const status = job?.status ? String(job.status) : null;
|
|
280
|
+
const fallbackObservedAt = Date.now();
|
|
281
|
+
const snapshot = lastSnapshot || buildPollSnapshot(jobId, job, {
|
|
282
|
+
attempt: 0,
|
|
283
|
+
attempts,
|
|
284
|
+
startedAt,
|
|
285
|
+
observedAt: fallbackObservedAt
|
|
286
|
+
});
|
|
212
287
|
if (!isTerminalRiddleJobStatus(status)) {
|
|
213
|
-
|
|
288
|
+
const timedOut = Boolean(options.wait);
|
|
289
|
+
return {
|
|
290
|
+
ok: !timedOut,
|
|
291
|
+
job_id: jobId,
|
|
292
|
+
status,
|
|
293
|
+
terminal: false,
|
|
294
|
+
job,
|
|
295
|
+
poll: {
|
|
296
|
+
...snapshot,
|
|
297
|
+
timed_out: timedOut,
|
|
298
|
+
interval_ms: intervalMs,
|
|
299
|
+
message: pollMessage(snapshot, timedOut)
|
|
300
|
+
}
|
|
301
|
+
};
|
|
214
302
|
}
|
|
215
303
|
const artifacts = await riddleRequestJson(config, `/v1/jobs/${jobId}/artifacts`);
|
|
216
304
|
return {
|
|
@@ -219,7 +307,12 @@ async function pollRiddleJob(config, jobId, options = {}) {
|
|
|
219
307
|
status,
|
|
220
308
|
terminal: true,
|
|
221
309
|
job,
|
|
222
|
-
artifacts
|
|
310
|
+
artifacts,
|
|
311
|
+
poll: {
|
|
312
|
+
...snapshot,
|
|
313
|
+
timed_out: false,
|
|
314
|
+
interval_ms: intervalMs
|
|
315
|
+
}
|
|
223
316
|
};
|
|
224
317
|
}
|
|
225
318
|
function createRiddleApiClient(config = {}) {
|
package/dist/cli.cjs
CHANGED
|
@@ -6743,21 +6743,109 @@ async function runRiddleScript(config, input) {
|
|
|
6743
6743
|
function isTerminalRiddleJobStatus(status) {
|
|
6744
6744
|
return ["completed", "complete", "completed_error", "completed_timeout", "failed"].includes(String(status || ""));
|
|
6745
6745
|
}
|
|
6746
|
+
function stringField(record, key) {
|
|
6747
|
+
const value = record?.[key];
|
|
6748
|
+
return typeof value === "string" && value.trim() ? value.trim() : null;
|
|
6749
|
+
}
|
|
6750
|
+
function parseTimestampMs(value) {
|
|
6751
|
+
if (!value) return null;
|
|
6752
|
+
const parsed = Date.parse(value);
|
|
6753
|
+
return Number.isFinite(parsed) ? parsed : null;
|
|
6754
|
+
}
|
|
6755
|
+
function buildPollSnapshot(jobId, job, input) {
|
|
6756
|
+
const status = job?.status ? String(job.status) : null;
|
|
6757
|
+
const terminal = isTerminalRiddleJobStatus(status);
|
|
6758
|
+
const createdAt = stringField(job, "created_at");
|
|
6759
|
+
const submittedAt = stringField(job, "submitted_at");
|
|
6760
|
+
const completedAt = stringField(job, "completed_at");
|
|
6761
|
+
const createdMs = parseTimestampMs(createdAt);
|
|
6762
|
+
const submittedMs = parseTimestampMs(submittedAt);
|
|
6763
|
+
let queueElapsedMs = null;
|
|
6764
|
+
if (createdMs !== null && submittedMs !== null) {
|
|
6765
|
+
queueElapsedMs = Math.max(0, submittedMs - createdMs);
|
|
6766
|
+
} else if (createdMs !== null && !submittedAt && !terminal) {
|
|
6767
|
+
queueElapsedMs = Math.max(0, input.observedAt - createdMs);
|
|
6768
|
+
}
|
|
6769
|
+
return {
|
|
6770
|
+
job_id: jobId,
|
|
6771
|
+
status,
|
|
6772
|
+
terminal,
|
|
6773
|
+
attempt: input.attempt,
|
|
6774
|
+
attempts: input.attempts,
|
|
6775
|
+
elapsed_ms: Math.max(0, input.observedAt - input.startedAt),
|
|
6776
|
+
created_at: createdAt,
|
|
6777
|
+
submitted_at: submittedAt,
|
|
6778
|
+
completed_at: completedAt,
|
|
6779
|
+
queue_elapsed_ms: queueElapsedMs,
|
|
6780
|
+
running_without_submission: Boolean(status && !terminal && !submittedAt)
|
|
6781
|
+
};
|
|
6782
|
+
}
|
|
6783
|
+
function pollMessage(snapshot, timedOut) {
|
|
6784
|
+
if (!timedOut) return void 0;
|
|
6785
|
+
const submitted = snapshot.submitted_at || "not submitted";
|
|
6786
|
+
const queue = snapshot.queue_elapsed_ms !== null ? ` queue_elapsed_ms=${snapshot.queue_elapsed_ms}` : "";
|
|
6787
|
+
return `Riddle job ${snapshot.job_id} did not reach a terminal status after ${snapshot.attempt} poll attempts; status=${snapshot.status || "unknown"} submitted_at=${submitted}.${queue}`;
|
|
6788
|
+
}
|
|
6746
6789
|
async function pollRiddleJob(config, jobId, options = {}) {
|
|
6747
6790
|
if (!jobId?.trim()) throw new Error("jobId is required");
|
|
6748
|
-
const attempts = options.attempts
|
|
6749
|
-
const intervalMs = options.intervalMs
|
|
6791
|
+
const attempts = Math.max(1, Math.floor(options.attempts ?? (options.wait ? 300 : 1)));
|
|
6792
|
+
const intervalMs = Math.max(0, Math.floor(options.intervalMs ?? 2e3));
|
|
6793
|
+
const progressEveryMs = Math.max(0, Math.floor(options.progressEveryMs ?? 1e4));
|
|
6794
|
+
const startedAt = Date.now();
|
|
6750
6795
|
let job = null;
|
|
6796
|
+
let lastSnapshot = null;
|
|
6797
|
+
let lastProgressAt = 0;
|
|
6798
|
+
let lastProgressKey = "";
|
|
6751
6799
|
for (let index = 0; index < attempts; index += 1) {
|
|
6752
6800
|
job = await riddleRequestJson(config, `/v1/jobs/${jobId}`);
|
|
6753
|
-
|
|
6801
|
+
const observedAt = Date.now();
|
|
6802
|
+
lastSnapshot = buildPollSnapshot(jobId, job, {
|
|
6803
|
+
attempt: index + 1,
|
|
6804
|
+
attempts,
|
|
6805
|
+
startedAt,
|
|
6806
|
+
observedAt
|
|
6807
|
+
});
|
|
6808
|
+
const progressKey = [
|
|
6809
|
+
lastSnapshot.status || "unknown",
|
|
6810
|
+
lastSnapshot.terminal ? "terminal" : "nonterminal",
|
|
6811
|
+
lastSnapshot.submitted_at ? "submitted" : "unsubmitted"
|
|
6812
|
+
].join(":");
|
|
6813
|
+
if (options.onProgress) {
|
|
6814
|
+
const shouldReport = index === 0 || lastSnapshot.terminal || progressKey !== lastProgressKey || observedAt - lastProgressAt >= progressEveryMs;
|
|
6815
|
+
if (shouldReport) {
|
|
6816
|
+
lastProgressAt = observedAt;
|
|
6817
|
+
lastProgressKey = progressKey;
|
|
6818
|
+
await options.onProgress(lastSnapshot);
|
|
6819
|
+
}
|
|
6820
|
+
}
|
|
6821
|
+
if (lastSnapshot.terminal) break;
|
|
6754
6822
|
if (index + 1 < attempts) {
|
|
6755
6823
|
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
6756
6824
|
}
|
|
6757
6825
|
}
|
|
6758
6826
|
const status = job?.status ? String(job.status) : null;
|
|
6827
|
+
const fallbackObservedAt = Date.now();
|
|
6828
|
+
const snapshot = lastSnapshot || buildPollSnapshot(jobId, job, {
|
|
6829
|
+
attempt: 0,
|
|
6830
|
+
attempts,
|
|
6831
|
+
startedAt,
|
|
6832
|
+
observedAt: fallbackObservedAt
|
|
6833
|
+
});
|
|
6759
6834
|
if (!isTerminalRiddleJobStatus(status)) {
|
|
6760
|
-
|
|
6835
|
+
const timedOut = Boolean(options.wait);
|
|
6836
|
+
return {
|
|
6837
|
+
ok: !timedOut,
|
|
6838
|
+
job_id: jobId,
|
|
6839
|
+
status,
|
|
6840
|
+
terminal: false,
|
|
6841
|
+
job,
|
|
6842
|
+
poll: {
|
|
6843
|
+
...snapshot,
|
|
6844
|
+
timed_out: timedOut,
|
|
6845
|
+
interval_ms: intervalMs,
|
|
6846
|
+
message: pollMessage(snapshot, timedOut)
|
|
6847
|
+
}
|
|
6848
|
+
};
|
|
6761
6849
|
}
|
|
6762
6850
|
const artifacts = await riddleRequestJson(config, `/v1/jobs/${jobId}/artifacts`);
|
|
6763
6851
|
return {
|
|
@@ -6766,7 +6854,12 @@ async function pollRiddleJob(config, jobId, options = {}) {
|
|
|
6766
6854
|
status,
|
|
6767
6855
|
terminal: true,
|
|
6768
6856
|
job,
|
|
6769
|
-
artifacts
|
|
6857
|
+
artifacts,
|
|
6858
|
+
poll: {
|
|
6859
|
+
...snapshot,
|
|
6860
|
+
timed_out: false,
|
|
6861
|
+
interval_ms: intervalMs
|
|
6862
|
+
}
|
|
6770
6863
|
};
|
|
6771
6864
|
}
|
|
6772
6865
|
function createRiddleApiClient(config = {}) {
|
|
@@ -8156,7 +8249,7 @@ function usage() {
|
|
|
8156
8249
|
" riddle-proof-loop riddle-preview-deploy <build-dir> <label>",
|
|
8157
8250
|
" riddle-proof-loop riddle-server-preview <directory> --script-file <file> [--path /route] [--wait-for-selector selector]",
|
|
8158
8251
|
" riddle-proof-loop riddle-run-script --url <url> --script-file <file> [--viewport 1280x720]",
|
|
8159
|
-
" riddle-proof-loop riddle-poll <job-id> [--wait]",
|
|
8252
|
+
" riddle-proof-loop riddle-poll <job-id> [--wait] [--attempts n] [--quiet]",
|
|
8160
8253
|
" riddle-proof-loop doctor local [--codex-command <path>]",
|
|
8161
8254
|
"",
|
|
8162
8255
|
"The default CLI run mode is checkpoint-mode=yield unless --agent local is used.",
|
|
@@ -8190,6 +8283,26 @@ function optionString(options, key) {
|
|
|
8190
8283
|
function readStdin() {
|
|
8191
8284
|
return (0, import_node_fs6.readFileSync)(0, "utf-8");
|
|
8192
8285
|
}
|
|
8286
|
+
function formatPollDuration(ms) {
|
|
8287
|
+
if (typeof ms !== "number" || !Number.isFinite(ms)) return "n/a";
|
|
8288
|
+
const seconds = Math.max(0, Math.round(ms / 1e3));
|
|
8289
|
+
const minutes = Math.floor(seconds / 60);
|
|
8290
|
+
const remainder = seconds % 60;
|
|
8291
|
+
return minutes > 0 ? `${minutes}m${String(remainder).padStart(2, "0")}s` : `${seconds}s`;
|
|
8292
|
+
}
|
|
8293
|
+
function riddlePollProgressLine(snapshot) {
|
|
8294
|
+
const submittedAt = snapshot.submitted_at || "not-submitted";
|
|
8295
|
+
const queuePart = snapshot.running_without_submission ? ` queued_for=${formatPollDuration(snapshot.queue_elapsed_ms)}` : snapshot.queue_elapsed_ms !== null ? ` queue=${formatPollDuration(snapshot.queue_elapsed_ms)}` : "";
|
|
8296
|
+
const terminalPart = snapshot.terminal ? " terminal=true" : "";
|
|
8297
|
+
return [
|
|
8298
|
+
"[riddle-poll]",
|
|
8299
|
+
snapshot.job_id,
|
|
8300
|
+
`status=${snapshot.status || "unknown"}`,
|
|
8301
|
+
`attempt=${snapshot.attempt}/${snapshot.attempts}`,
|
|
8302
|
+
`elapsed=${formatPollDuration(snapshot.elapsed_ms)}`,
|
|
8303
|
+
`submitted_at=${submittedAt}${queuePart}${terminalPart}`
|
|
8304
|
+
].join(" ");
|
|
8305
|
+
}
|
|
8193
8306
|
function readJsonValue(value, label) {
|
|
8194
8307
|
if (!value) throw new Error(`${label} is required.`);
|
|
8195
8308
|
const raw = value === "-" ? readStdin() : (0, import_node_fs6.existsSync)(value) ? (0, import_node_fs6.readFileSync)(value, "utf-8") : value;
|
|
@@ -8621,10 +8734,16 @@ async function main() {
|
|
|
8621
8734
|
if (command === "riddle-poll") {
|
|
8622
8735
|
const jobId = positional[1];
|
|
8623
8736
|
if (!jobId) throw new Error("riddle-poll requires <job-id>.");
|
|
8737
|
+
const wait = options.wait === true;
|
|
8624
8738
|
const result = await createRiddleApiClient(riddleClientConfig(options)).pollJob(jobId, {
|
|
8625
|
-
wait
|
|
8739
|
+
wait,
|
|
8626
8740
|
attempts: optionString(options, "attempts") ? Number(optionString(options, "attempts")) : void 0,
|
|
8627
|
-
intervalMs: optionString(options, "intervalMs") ? Number(optionString(options, "intervalMs")) : void 0
|
|
8741
|
+
intervalMs: optionString(options, "intervalMs") ? Number(optionString(options, "intervalMs")) : void 0,
|
|
8742
|
+
progressEveryMs: optionString(options, "progressEveryMs") ? Number(optionString(options, "progressEveryMs")) : void 0,
|
|
8743
|
+
onProgress: wait && options.quiet !== true ? (snapshot) => {
|
|
8744
|
+
process.stderr.write(`${riddlePollProgressLine(snapshot)}
|
|
8745
|
+
`);
|
|
8746
|
+
} : void 0
|
|
8628
8747
|
});
|
|
8629
8748
|
process.stdout.write(`${JSON.stringify(result, null, 2)}
|
|
8630
8749
|
`);
|
package/dist/cli.js
CHANGED
|
@@ -14,7 +14,7 @@ import {
|
|
|
14
14
|
import {
|
|
15
15
|
createRiddleApiClient,
|
|
16
16
|
parseRiddleViewport
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-7PSWK57T.js";
|
|
18
18
|
import {
|
|
19
19
|
createDisabledRiddleProofAgentAdapter,
|
|
20
20
|
readRiddleProofRunStatus,
|
|
@@ -48,7 +48,7 @@ function usage() {
|
|
|
48
48
|
" riddle-proof-loop riddle-preview-deploy <build-dir> <label>",
|
|
49
49
|
" riddle-proof-loop riddle-server-preview <directory> --script-file <file> [--path /route] [--wait-for-selector selector]",
|
|
50
50
|
" riddle-proof-loop riddle-run-script --url <url> --script-file <file> [--viewport 1280x720]",
|
|
51
|
-
" riddle-proof-loop riddle-poll <job-id> [--wait]",
|
|
51
|
+
" riddle-proof-loop riddle-poll <job-id> [--wait] [--attempts n] [--quiet]",
|
|
52
52
|
" riddle-proof-loop doctor local [--codex-command <path>]",
|
|
53
53
|
"",
|
|
54
54
|
"The default CLI run mode is checkpoint-mode=yield unless --agent local is used.",
|
|
@@ -82,6 +82,26 @@ function optionString(options, key) {
|
|
|
82
82
|
function readStdin() {
|
|
83
83
|
return readFileSync(0, "utf-8");
|
|
84
84
|
}
|
|
85
|
+
function formatPollDuration(ms) {
|
|
86
|
+
if (typeof ms !== "number" || !Number.isFinite(ms)) return "n/a";
|
|
87
|
+
const seconds = Math.max(0, Math.round(ms / 1e3));
|
|
88
|
+
const minutes = Math.floor(seconds / 60);
|
|
89
|
+
const remainder = seconds % 60;
|
|
90
|
+
return minutes > 0 ? `${minutes}m${String(remainder).padStart(2, "0")}s` : `${seconds}s`;
|
|
91
|
+
}
|
|
92
|
+
function riddlePollProgressLine(snapshot) {
|
|
93
|
+
const submittedAt = snapshot.submitted_at || "not-submitted";
|
|
94
|
+
const queuePart = snapshot.running_without_submission ? ` queued_for=${formatPollDuration(snapshot.queue_elapsed_ms)}` : snapshot.queue_elapsed_ms !== null ? ` queue=${formatPollDuration(snapshot.queue_elapsed_ms)}` : "";
|
|
95
|
+
const terminalPart = snapshot.terminal ? " terminal=true" : "";
|
|
96
|
+
return [
|
|
97
|
+
"[riddle-poll]",
|
|
98
|
+
snapshot.job_id,
|
|
99
|
+
`status=${snapshot.status || "unknown"}`,
|
|
100
|
+
`attempt=${snapshot.attempt}/${snapshot.attempts}`,
|
|
101
|
+
`elapsed=${formatPollDuration(snapshot.elapsed_ms)}`,
|
|
102
|
+
`submitted_at=${submittedAt}${queuePart}${terminalPart}`
|
|
103
|
+
].join(" ");
|
|
104
|
+
}
|
|
85
105
|
function readJsonValue(value, label) {
|
|
86
106
|
if (!value) throw new Error(`${label} is required.`);
|
|
87
107
|
const raw = value === "-" ? readStdin() : existsSync(value) ? readFileSync(value, "utf-8") : value;
|
|
@@ -513,10 +533,16 @@ async function main() {
|
|
|
513
533
|
if (command === "riddle-poll") {
|
|
514
534
|
const jobId = positional[1];
|
|
515
535
|
if (!jobId) throw new Error("riddle-poll requires <job-id>.");
|
|
536
|
+
const wait = options.wait === true;
|
|
516
537
|
const result = await createRiddleApiClient(riddleClientConfig(options)).pollJob(jobId, {
|
|
517
|
-
wait
|
|
538
|
+
wait,
|
|
518
539
|
attempts: optionString(options, "attempts") ? Number(optionString(options, "attempts")) : void 0,
|
|
519
|
-
intervalMs: optionString(options, "intervalMs") ? Number(optionString(options, "intervalMs")) : void 0
|
|
540
|
+
intervalMs: optionString(options, "intervalMs") ? Number(optionString(options, "intervalMs")) : void 0,
|
|
541
|
+
progressEveryMs: optionString(options, "progressEveryMs") ? Number(optionString(options, "progressEveryMs")) : void 0,
|
|
542
|
+
onProgress: wait && options.quiet !== true ? (snapshot) => {
|
|
543
|
+
process.stderr.write(`${riddlePollProgressLine(snapshot)}
|
|
544
|
+
`);
|
|
545
|
+
} : void 0
|
|
520
546
|
});
|
|
521
547
|
process.stdout.write(`${JSON.stringify(result, null, 2)}
|
|
522
548
|
`);
|
package/dist/index.cjs
CHANGED
|
@@ -10291,21 +10291,109 @@ async function runRiddleScript(config, input) {
|
|
|
10291
10291
|
function isTerminalRiddleJobStatus(status) {
|
|
10292
10292
|
return ["completed", "complete", "completed_error", "completed_timeout", "failed"].includes(String(status || ""));
|
|
10293
10293
|
}
|
|
10294
|
+
function stringField(record, key) {
|
|
10295
|
+
const value = record?.[key];
|
|
10296
|
+
return typeof value === "string" && value.trim() ? value.trim() : null;
|
|
10297
|
+
}
|
|
10298
|
+
function parseTimestampMs(value) {
|
|
10299
|
+
if (!value) return null;
|
|
10300
|
+
const parsed = Date.parse(value);
|
|
10301
|
+
return Number.isFinite(parsed) ? parsed : null;
|
|
10302
|
+
}
|
|
10303
|
+
function buildPollSnapshot(jobId, job, input) {
|
|
10304
|
+
const status = job?.status ? String(job.status) : null;
|
|
10305
|
+
const terminal = isTerminalRiddleJobStatus(status);
|
|
10306
|
+
const createdAt = stringField(job, "created_at");
|
|
10307
|
+
const submittedAt = stringField(job, "submitted_at");
|
|
10308
|
+
const completedAt = stringField(job, "completed_at");
|
|
10309
|
+
const createdMs = parseTimestampMs(createdAt);
|
|
10310
|
+
const submittedMs = parseTimestampMs(submittedAt);
|
|
10311
|
+
let queueElapsedMs = null;
|
|
10312
|
+
if (createdMs !== null && submittedMs !== null) {
|
|
10313
|
+
queueElapsedMs = Math.max(0, submittedMs - createdMs);
|
|
10314
|
+
} else if (createdMs !== null && !submittedAt && !terminal) {
|
|
10315
|
+
queueElapsedMs = Math.max(0, input.observedAt - createdMs);
|
|
10316
|
+
}
|
|
10317
|
+
return {
|
|
10318
|
+
job_id: jobId,
|
|
10319
|
+
status,
|
|
10320
|
+
terminal,
|
|
10321
|
+
attempt: input.attempt,
|
|
10322
|
+
attempts: input.attempts,
|
|
10323
|
+
elapsed_ms: Math.max(0, input.observedAt - input.startedAt),
|
|
10324
|
+
created_at: createdAt,
|
|
10325
|
+
submitted_at: submittedAt,
|
|
10326
|
+
completed_at: completedAt,
|
|
10327
|
+
queue_elapsed_ms: queueElapsedMs,
|
|
10328
|
+
running_without_submission: Boolean(status && !terminal && !submittedAt)
|
|
10329
|
+
};
|
|
10330
|
+
}
|
|
10331
|
+
function pollMessage(snapshot, timedOut) {
|
|
10332
|
+
if (!timedOut) return void 0;
|
|
10333
|
+
const submitted = snapshot.submitted_at || "not submitted";
|
|
10334
|
+
const queue = snapshot.queue_elapsed_ms !== null ? ` queue_elapsed_ms=${snapshot.queue_elapsed_ms}` : "";
|
|
10335
|
+
return `Riddle job ${snapshot.job_id} did not reach a terminal status after ${snapshot.attempt} poll attempts; status=${snapshot.status || "unknown"} submitted_at=${submitted}.${queue}`;
|
|
10336
|
+
}
|
|
10294
10337
|
async function pollRiddleJob(config, jobId, options = {}) {
|
|
10295
10338
|
if (!jobId?.trim()) throw new Error("jobId is required");
|
|
10296
|
-
const attempts = options.attempts
|
|
10297
|
-
const intervalMs = options.intervalMs
|
|
10339
|
+
const attempts = Math.max(1, Math.floor(options.attempts ?? (options.wait ? 300 : 1)));
|
|
10340
|
+
const intervalMs = Math.max(0, Math.floor(options.intervalMs ?? 2e3));
|
|
10341
|
+
const progressEveryMs = Math.max(0, Math.floor(options.progressEveryMs ?? 1e4));
|
|
10342
|
+
const startedAt = Date.now();
|
|
10298
10343
|
let job = null;
|
|
10344
|
+
let lastSnapshot = null;
|
|
10345
|
+
let lastProgressAt = 0;
|
|
10346
|
+
let lastProgressKey = "";
|
|
10299
10347
|
for (let index = 0; index < attempts; index += 1) {
|
|
10300
10348
|
job = await riddleRequestJson(config, `/v1/jobs/${jobId}`);
|
|
10301
|
-
|
|
10349
|
+
const observedAt = Date.now();
|
|
10350
|
+
lastSnapshot = buildPollSnapshot(jobId, job, {
|
|
10351
|
+
attempt: index + 1,
|
|
10352
|
+
attempts,
|
|
10353
|
+
startedAt,
|
|
10354
|
+
observedAt
|
|
10355
|
+
});
|
|
10356
|
+
const progressKey = [
|
|
10357
|
+
lastSnapshot.status || "unknown",
|
|
10358
|
+
lastSnapshot.terminal ? "terminal" : "nonterminal",
|
|
10359
|
+
lastSnapshot.submitted_at ? "submitted" : "unsubmitted"
|
|
10360
|
+
].join(":");
|
|
10361
|
+
if (options.onProgress) {
|
|
10362
|
+
const shouldReport = index === 0 || lastSnapshot.terminal || progressKey !== lastProgressKey || observedAt - lastProgressAt >= progressEveryMs;
|
|
10363
|
+
if (shouldReport) {
|
|
10364
|
+
lastProgressAt = observedAt;
|
|
10365
|
+
lastProgressKey = progressKey;
|
|
10366
|
+
await options.onProgress(lastSnapshot);
|
|
10367
|
+
}
|
|
10368
|
+
}
|
|
10369
|
+
if (lastSnapshot.terminal) break;
|
|
10302
10370
|
if (index + 1 < attempts) {
|
|
10303
10371
|
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
10304
10372
|
}
|
|
10305
10373
|
}
|
|
10306
10374
|
const status = job?.status ? String(job.status) : null;
|
|
10375
|
+
const fallbackObservedAt = Date.now();
|
|
10376
|
+
const snapshot = lastSnapshot || buildPollSnapshot(jobId, job, {
|
|
10377
|
+
attempt: 0,
|
|
10378
|
+
attempts,
|
|
10379
|
+
startedAt,
|
|
10380
|
+
observedAt: fallbackObservedAt
|
|
10381
|
+
});
|
|
10307
10382
|
if (!isTerminalRiddleJobStatus(status)) {
|
|
10308
|
-
|
|
10383
|
+
const timedOut = Boolean(options.wait);
|
|
10384
|
+
return {
|
|
10385
|
+
ok: !timedOut,
|
|
10386
|
+
job_id: jobId,
|
|
10387
|
+
status,
|
|
10388
|
+
terminal: false,
|
|
10389
|
+
job,
|
|
10390
|
+
poll: {
|
|
10391
|
+
...snapshot,
|
|
10392
|
+
timed_out: timedOut,
|
|
10393
|
+
interval_ms: intervalMs,
|
|
10394
|
+
message: pollMessage(snapshot, timedOut)
|
|
10395
|
+
}
|
|
10396
|
+
};
|
|
10309
10397
|
}
|
|
10310
10398
|
const artifacts = await riddleRequestJson(config, `/v1/jobs/${jobId}/artifacts`);
|
|
10311
10399
|
return {
|
|
@@ -10314,7 +10402,12 @@ async function pollRiddleJob(config, jobId, options = {}) {
|
|
|
10314
10402
|
status,
|
|
10315
10403
|
terminal: true,
|
|
10316
10404
|
job,
|
|
10317
|
-
artifacts
|
|
10405
|
+
artifacts,
|
|
10406
|
+
poll: {
|
|
10407
|
+
...snapshot,
|
|
10408
|
+
timed_out: false,
|
|
10409
|
+
interval_ms: intervalMs
|
|
10410
|
+
}
|
|
10318
10411
|
};
|
|
10319
10412
|
}
|
|
10320
10413
|
function createRiddleApiClient(config = {}) {
|
package/dist/index.d.cts
CHANGED
|
@@ -11,4 +11,4 @@ export { BuildVisualProofSessionInput, RIDDLE_PROOF_VISUAL_SESSION_FINGERPRINT_V
|
|
|
11
11
|
export { AssessPlayabilityOptions, RIDDLE_PROOF_PLAYABILITY_ASSESSMENT_VERSION, RIDDLE_PROOF_PLAYABILITY_VERSION, RiddleProofPlayabilityAssessment, RiddleProofPlayabilityEvidence, assessPlayabilityEvidence, extractPlayabilityEvidence, isRiddleProofPlayabilityMode } from './playability.cjs';
|
|
12
12
|
export { AssessBasicGameplayOptions, AttachBasicGameplayArtifactOptions, BASIC_GAMEPLAY_ACTION_TYPES, BASIC_GAMEPLAY_PROGRESS_CHECK_TYPES, BasicGameplayActionResult, BasicGameplayActionType, BasicGameplayArtifactResolution, BasicGameplayAssessmentSummary, BasicGameplayBoundsOffender, BasicGameplayCanvasState, BasicGameplayCatchRecord, BasicGameplayChangeSummary, BasicGameplayFailureCode, BasicGameplayFixReference, BasicGameplayMetric, BasicGameplayMobileEvidence, BasicGameplayProgressCheckType, BasicGameplayProgressionCheck, BasicGameplayProofArtifact, BasicGameplayResponsiveViewportEvidence, BasicGameplayRouteReference, BasicGameplaySnapshot, BasicGameplaySuiteFailure, BasicGameplayWarningCode, CreateBasicGameplayCatchSummaryInput, RIDDLE_PROOF_BASIC_GAMEPLAY_ASSESSMENT_VERSION, RIDDLE_PROOF_BASIC_GAMEPLAY_CATCH_VERSION, RIDDLE_PROOF_BASIC_GAMEPLAY_VERSION, RiddleProofBasicGameplayAssessment, RiddleProofBasicGameplayCatchSummary, RiddleProofBasicGameplayEvidence, RiddleProofBasicGameplayRouteAssessment, RiddleProofBasicGameplayRouteEvidence, assessBasicGameplayEvidence, assessBasicGameplayProgressionCheck, assessBasicGameplayProgressionChecks, assessBasicGameplayRoute, attachBasicGameplayArtifactScreenshotHashes, augmentBasicGameplayAssessmentWithProgressionChecks, compactBasicGameplayText, createBasicGameplayCatchRecords, createBasicGameplayCatchSummary, extractBasicGameplayEvidence, resolveBasicGameplayProgressionCheckWithArtifactScreenshots, sanitizeBasicGameplayJsonString } from './basic-gameplay.cjs';
|
|
13
13
|
export { NormalizeRiddleProofProfileOptions, RIDDLE_PROOF_PROFILE_CHECK_TYPES, RIDDLE_PROOF_PROFILE_EVIDENCE_VERSION, RIDDLE_PROOF_PROFILE_RESULT_VERSION, RIDDLE_PROOF_PROFILE_SETUP_ACTION_TYPES, RIDDLE_PROOF_PROFILE_STATUSES, RIDDLE_PROOF_PROFILE_VERSION, RiddleProofProfile, RiddleProofProfileArtifactRef, RiddleProofProfileBaselinePolicy, RiddleProofProfileBoundsOffender, RiddleProofProfileCheck, RiddleProofProfileCheckResult, RiddleProofProfileCheckType, RiddleProofProfileEvidence, RiddleProofProfileFailureAction, RiddleProofProfileResult, RiddleProofProfileRouteEvidence, RiddleProofProfileRunner, RiddleProofProfileSetupAction, RiddleProofProfileSetupActionType, RiddleProofProfileStatus, RiddleProofProfileTarget, RiddleProofProfileViewport, RiddleProofProfileViewportEvidence, assessRiddleProofProfileEvidence, buildRiddleProofProfileScript, collectRiddleProfileArtifactRefs, createRiddleProofProfileConfigurationError, createRiddleProofProfileEnvironmentBlockedResult, createRiddleProofProfileInsufficientResult, extractRiddleProofProfileResult, normalizeRiddleProofProfile, profileStatusExitCode, resolveRiddleProofProfileRouteUrl, resolveRiddleProofProfileTargetUrl, resolveRiddleProofProfileTimeoutSec, slugifyRiddleProofProfileName, summarizeRiddleProofProfileResult } from './profile.cjs';
|
|
14
|
-
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, RiddleClientConfig, RiddleFetch, RiddlePollJobResult, RiddlePreviewDeployResult, RiddleRunScriptInput, RiddleServerPreviewInput, RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview } from './riddle-client.cjs';
|
|
14
|
+
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, RiddleClientConfig, RiddleFetch, RiddlePollJobOptions, RiddlePollJobResult, RiddlePollProgressSnapshot, RiddlePollSummary, RiddlePreviewDeployResult, RiddleRunScriptInput, RiddleServerPreviewInput, RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview } from './riddle-client.cjs';
|
package/dist/index.d.ts
CHANGED
|
@@ -11,4 +11,4 @@ export { BuildVisualProofSessionInput, RIDDLE_PROOF_VISUAL_SESSION_FINGERPRINT_V
|
|
|
11
11
|
export { AssessPlayabilityOptions, RIDDLE_PROOF_PLAYABILITY_ASSESSMENT_VERSION, RIDDLE_PROOF_PLAYABILITY_VERSION, RiddleProofPlayabilityAssessment, RiddleProofPlayabilityEvidence, assessPlayabilityEvidence, extractPlayabilityEvidence, isRiddleProofPlayabilityMode } from './playability.js';
|
|
12
12
|
export { AssessBasicGameplayOptions, AttachBasicGameplayArtifactOptions, BASIC_GAMEPLAY_ACTION_TYPES, BASIC_GAMEPLAY_PROGRESS_CHECK_TYPES, BasicGameplayActionResult, BasicGameplayActionType, BasicGameplayArtifactResolution, BasicGameplayAssessmentSummary, BasicGameplayBoundsOffender, BasicGameplayCanvasState, BasicGameplayCatchRecord, BasicGameplayChangeSummary, BasicGameplayFailureCode, BasicGameplayFixReference, BasicGameplayMetric, BasicGameplayMobileEvidence, BasicGameplayProgressCheckType, BasicGameplayProgressionCheck, BasicGameplayProofArtifact, BasicGameplayResponsiveViewportEvidence, BasicGameplayRouteReference, BasicGameplaySnapshot, BasicGameplaySuiteFailure, BasicGameplayWarningCode, CreateBasicGameplayCatchSummaryInput, RIDDLE_PROOF_BASIC_GAMEPLAY_ASSESSMENT_VERSION, RIDDLE_PROOF_BASIC_GAMEPLAY_CATCH_VERSION, RIDDLE_PROOF_BASIC_GAMEPLAY_VERSION, RiddleProofBasicGameplayAssessment, RiddleProofBasicGameplayCatchSummary, RiddleProofBasicGameplayEvidence, RiddleProofBasicGameplayRouteAssessment, RiddleProofBasicGameplayRouteEvidence, assessBasicGameplayEvidence, assessBasicGameplayProgressionCheck, assessBasicGameplayProgressionChecks, assessBasicGameplayRoute, attachBasicGameplayArtifactScreenshotHashes, augmentBasicGameplayAssessmentWithProgressionChecks, compactBasicGameplayText, createBasicGameplayCatchRecords, createBasicGameplayCatchSummary, extractBasicGameplayEvidence, resolveBasicGameplayProgressionCheckWithArtifactScreenshots, sanitizeBasicGameplayJsonString } from './basic-gameplay.js';
|
|
13
13
|
export { NormalizeRiddleProofProfileOptions, RIDDLE_PROOF_PROFILE_CHECK_TYPES, RIDDLE_PROOF_PROFILE_EVIDENCE_VERSION, RIDDLE_PROOF_PROFILE_RESULT_VERSION, RIDDLE_PROOF_PROFILE_SETUP_ACTION_TYPES, RIDDLE_PROOF_PROFILE_STATUSES, RIDDLE_PROOF_PROFILE_VERSION, RiddleProofProfile, RiddleProofProfileArtifactRef, RiddleProofProfileBaselinePolicy, RiddleProofProfileBoundsOffender, RiddleProofProfileCheck, RiddleProofProfileCheckResult, RiddleProofProfileCheckType, RiddleProofProfileEvidence, RiddleProofProfileFailureAction, RiddleProofProfileResult, RiddleProofProfileRouteEvidence, RiddleProofProfileRunner, RiddleProofProfileSetupAction, RiddleProofProfileSetupActionType, RiddleProofProfileStatus, RiddleProofProfileTarget, RiddleProofProfileViewport, RiddleProofProfileViewportEvidence, assessRiddleProofProfileEvidence, buildRiddleProofProfileScript, collectRiddleProfileArtifactRefs, createRiddleProofProfileConfigurationError, createRiddleProofProfileEnvironmentBlockedResult, createRiddleProofProfileInsufficientResult, extractRiddleProofProfileResult, normalizeRiddleProofProfile, profileStatusExitCode, resolveRiddleProofProfileRouteUrl, resolveRiddleProofProfileTargetUrl, resolveRiddleProofProfileTimeoutSec, slugifyRiddleProofProfileName, summarizeRiddleProofProfileResult } from './profile.js';
|
|
14
|
-
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, RiddleClientConfig, RiddleFetch, RiddlePollJobResult, RiddlePreviewDeployResult, RiddleRunScriptInput, RiddleServerPreviewInput, RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview } from './riddle-client.js';
|
|
14
|
+
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, RiddleClientConfig, RiddleFetch, RiddlePollJobOptions, RiddlePollJobResult, RiddlePollProgressSnapshot, RiddlePollSummary, RiddlePreviewDeployResult, RiddleRunScriptInput, RiddleServerPreviewInput, RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview } from './riddle-client.js';
|
package/dist/index.js
CHANGED
|
@@ -292,7 +292,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
292
292
|
blocking?: boolean;
|
|
293
293
|
details?: Record<string, unknown>;
|
|
294
294
|
ok: boolean;
|
|
295
|
-
action: "
|
|
295
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
296
296
|
state_path: string;
|
|
297
297
|
stage: any;
|
|
298
298
|
summary: string;
|
|
@@ -382,7 +382,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
382
382
|
continueWithStage?: WorkflowStage | null;
|
|
383
383
|
blocking?: boolean;
|
|
384
384
|
details?: Record<string, unknown>;
|
|
385
|
-
action: "
|
|
385
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
386
386
|
state_path: string;
|
|
387
387
|
stage: any;
|
|
388
388
|
checkpoint: string;
|
|
@@ -659,7 +659,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
659
659
|
error?: undefined;
|
|
660
660
|
} | {
|
|
661
661
|
ok: boolean;
|
|
662
|
-
action: "
|
|
662
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
663
663
|
state_path: string;
|
|
664
664
|
stage: any;
|
|
665
665
|
summary: string;
|
|
@@ -292,7 +292,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
292
292
|
blocking?: boolean;
|
|
293
293
|
details?: Record<string, unknown>;
|
|
294
294
|
ok: boolean;
|
|
295
|
-
action: "
|
|
295
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
296
296
|
state_path: string;
|
|
297
297
|
stage: any;
|
|
298
298
|
summary: string;
|
|
@@ -382,7 +382,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
382
382
|
continueWithStage?: WorkflowStage | null;
|
|
383
383
|
blocking?: boolean;
|
|
384
384
|
details?: Record<string, unknown>;
|
|
385
|
-
action: "
|
|
385
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
386
386
|
state_path: string;
|
|
387
387
|
stage: any;
|
|
388
388
|
checkpoint: string;
|
|
@@ -659,7 +659,7 @@ declare function executeWorkflow(params: WorkflowParams, pluginConfig: any, reso
|
|
|
659
659
|
error?: undefined;
|
|
660
660
|
} | {
|
|
661
661
|
ok: boolean;
|
|
662
|
-
action: "
|
|
662
|
+
action: "author" | "recon" | "ship" | "implement" | "verify" | "setup" | "run";
|
|
663
663
|
state_path: string;
|
|
664
664
|
stage: any;
|
|
665
665
|
summary: string;
|
package/dist/riddle-client.cjs
CHANGED
|
@@ -241,21 +241,109 @@ async function runRiddleScript(config, input) {
|
|
|
241
241
|
function isTerminalRiddleJobStatus(status) {
|
|
242
242
|
return ["completed", "complete", "completed_error", "completed_timeout", "failed"].includes(String(status || ""));
|
|
243
243
|
}
|
|
244
|
+
function stringField(record, key) {
|
|
245
|
+
const value = record?.[key];
|
|
246
|
+
return typeof value === "string" && value.trim() ? value.trim() : null;
|
|
247
|
+
}
|
|
248
|
+
function parseTimestampMs(value) {
|
|
249
|
+
if (!value) return null;
|
|
250
|
+
const parsed = Date.parse(value);
|
|
251
|
+
return Number.isFinite(parsed) ? parsed : null;
|
|
252
|
+
}
|
|
253
|
+
function buildPollSnapshot(jobId, job, input) {
|
|
254
|
+
const status = job?.status ? String(job.status) : null;
|
|
255
|
+
const terminal = isTerminalRiddleJobStatus(status);
|
|
256
|
+
const createdAt = stringField(job, "created_at");
|
|
257
|
+
const submittedAt = stringField(job, "submitted_at");
|
|
258
|
+
const completedAt = stringField(job, "completed_at");
|
|
259
|
+
const createdMs = parseTimestampMs(createdAt);
|
|
260
|
+
const submittedMs = parseTimestampMs(submittedAt);
|
|
261
|
+
let queueElapsedMs = null;
|
|
262
|
+
if (createdMs !== null && submittedMs !== null) {
|
|
263
|
+
queueElapsedMs = Math.max(0, submittedMs - createdMs);
|
|
264
|
+
} else if (createdMs !== null && !submittedAt && !terminal) {
|
|
265
|
+
queueElapsedMs = Math.max(0, input.observedAt - createdMs);
|
|
266
|
+
}
|
|
267
|
+
return {
|
|
268
|
+
job_id: jobId,
|
|
269
|
+
status,
|
|
270
|
+
terminal,
|
|
271
|
+
attempt: input.attempt,
|
|
272
|
+
attempts: input.attempts,
|
|
273
|
+
elapsed_ms: Math.max(0, input.observedAt - input.startedAt),
|
|
274
|
+
created_at: createdAt,
|
|
275
|
+
submitted_at: submittedAt,
|
|
276
|
+
completed_at: completedAt,
|
|
277
|
+
queue_elapsed_ms: queueElapsedMs,
|
|
278
|
+
running_without_submission: Boolean(status && !terminal && !submittedAt)
|
|
279
|
+
};
|
|
280
|
+
}
|
|
281
|
+
function pollMessage(snapshot, timedOut) {
|
|
282
|
+
if (!timedOut) return void 0;
|
|
283
|
+
const submitted = snapshot.submitted_at || "not submitted";
|
|
284
|
+
const queue = snapshot.queue_elapsed_ms !== null ? ` queue_elapsed_ms=${snapshot.queue_elapsed_ms}` : "";
|
|
285
|
+
return `Riddle job ${snapshot.job_id} did not reach a terminal status after ${snapshot.attempt} poll attempts; status=${snapshot.status || "unknown"} submitted_at=${submitted}.${queue}`;
|
|
286
|
+
}
|
|
244
287
|
async function pollRiddleJob(config, jobId, options = {}) {
|
|
245
288
|
if (!jobId?.trim()) throw new Error("jobId is required");
|
|
246
|
-
const attempts = options.attempts
|
|
247
|
-
const intervalMs = options.intervalMs
|
|
289
|
+
const attempts = Math.max(1, Math.floor(options.attempts ?? (options.wait ? 300 : 1)));
|
|
290
|
+
const intervalMs = Math.max(0, Math.floor(options.intervalMs ?? 2e3));
|
|
291
|
+
const progressEveryMs = Math.max(0, Math.floor(options.progressEveryMs ?? 1e4));
|
|
292
|
+
const startedAt = Date.now();
|
|
248
293
|
let job = null;
|
|
294
|
+
let lastSnapshot = null;
|
|
295
|
+
let lastProgressAt = 0;
|
|
296
|
+
let lastProgressKey = "";
|
|
249
297
|
for (let index = 0; index < attempts; index += 1) {
|
|
250
298
|
job = await riddleRequestJson(config, `/v1/jobs/${jobId}`);
|
|
251
|
-
|
|
299
|
+
const observedAt = Date.now();
|
|
300
|
+
lastSnapshot = buildPollSnapshot(jobId, job, {
|
|
301
|
+
attempt: index + 1,
|
|
302
|
+
attempts,
|
|
303
|
+
startedAt,
|
|
304
|
+
observedAt
|
|
305
|
+
});
|
|
306
|
+
const progressKey = [
|
|
307
|
+
lastSnapshot.status || "unknown",
|
|
308
|
+
lastSnapshot.terminal ? "terminal" : "nonterminal",
|
|
309
|
+
lastSnapshot.submitted_at ? "submitted" : "unsubmitted"
|
|
310
|
+
].join(":");
|
|
311
|
+
if (options.onProgress) {
|
|
312
|
+
const shouldReport = index === 0 || lastSnapshot.terminal || progressKey !== lastProgressKey || observedAt - lastProgressAt >= progressEveryMs;
|
|
313
|
+
if (shouldReport) {
|
|
314
|
+
lastProgressAt = observedAt;
|
|
315
|
+
lastProgressKey = progressKey;
|
|
316
|
+
await options.onProgress(lastSnapshot);
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
if (lastSnapshot.terminal) break;
|
|
252
320
|
if (index + 1 < attempts) {
|
|
253
321
|
await new Promise((resolve) => setTimeout(resolve, intervalMs));
|
|
254
322
|
}
|
|
255
323
|
}
|
|
256
324
|
const status = job?.status ? String(job.status) : null;
|
|
325
|
+
const fallbackObservedAt = Date.now();
|
|
326
|
+
const snapshot = lastSnapshot || buildPollSnapshot(jobId, job, {
|
|
327
|
+
attempt: 0,
|
|
328
|
+
attempts,
|
|
329
|
+
startedAt,
|
|
330
|
+
observedAt: fallbackObservedAt
|
|
331
|
+
});
|
|
257
332
|
if (!isTerminalRiddleJobStatus(status)) {
|
|
258
|
-
|
|
333
|
+
const timedOut = Boolean(options.wait);
|
|
334
|
+
return {
|
|
335
|
+
ok: !timedOut,
|
|
336
|
+
job_id: jobId,
|
|
337
|
+
status,
|
|
338
|
+
terminal: false,
|
|
339
|
+
job,
|
|
340
|
+
poll: {
|
|
341
|
+
...snapshot,
|
|
342
|
+
timed_out: timedOut,
|
|
343
|
+
interval_ms: intervalMs,
|
|
344
|
+
message: pollMessage(snapshot, timedOut)
|
|
345
|
+
}
|
|
346
|
+
};
|
|
259
347
|
}
|
|
260
348
|
const artifacts = await riddleRequestJson(config, `/v1/jobs/${jobId}/artifacts`);
|
|
261
349
|
return {
|
|
@@ -264,7 +352,12 @@ async function pollRiddleJob(config, jobId, options = {}) {
|
|
|
264
352
|
status,
|
|
265
353
|
terminal: true,
|
|
266
354
|
job,
|
|
267
|
-
artifacts
|
|
355
|
+
artifacts,
|
|
356
|
+
poll: {
|
|
357
|
+
...snapshot,
|
|
358
|
+
timed_out: false,
|
|
359
|
+
interval_ms: intervalMs
|
|
360
|
+
}
|
|
268
361
|
};
|
|
269
362
|
}
|
|
270
363
|
function createRiddleApiClient(config = {}) {
|
package/dist/riddle-client.d.cts
CHANGED
|
@@ -7,6 +7,31 @@ interface RiddleClientConfig {
|
|
|
7
7
|
apiBaseUrl?: string;
|
|
8
8
|
fetchImpl?: RiddleFetch;
|
|
9
9
|
}
|
|
10
|
+
interface RiddlePollProgressSnapshot {
|
|
11
|
+
job_id: string;
|
|
12
|
+
status: string | null;
|
|
13
|
+
terminal: boolean;
|
|
14
|
+
attempt: number;
|
|
15
|
+
attempts: number;
|
|
16
|
+
elapsed_ms: number;
|
|
17
|
+
created_at: string | null;
|
|
18
|
+
submitted_at: string | null;
|
|
19
|
+
completed_at: string | null;
|
|
20
|
+
queue_elapsed_ms: number | null;
|
|
21
|
+
running_without_submission: boolean;
|
|
22
|
+
}
|
|
23
|
+
interface RiddlePollSummary extends RiddlePollProgressSnapshot {
|
|
24
|
+
timed_out: boolean;
|
|
25
|
+
interval_ms: number;
|
|
26
|
+
message?: string;
|
|
27
|
+
}
|
|
28
|
+
interface RiddlePollJobOptions {
|
|
29
|
+
wait?: boolean;
|
|
30
|
+
attempts?: number;
|
|
31
|
+
intervalMs?: number;
|
|
32
|
+
progressEveryMs?: number;
|
|
33
|
+
onProgress?: (snapshot: RiddlePollProgressSnapshot) => void | Promise<void>;
|
|
34
|
+
}
|
|
10
35
|
interface RiddlePreviewDeployResult {
|
|
11
36
|
ok: true;
|
|
12
37
|
id: string;
|
|
@@ -58,6 +83,7 @@ interface RiddlePollJobResult {
|
|
|
58
83
|
terminal: boolean;
|
|
59
84
|
job: Record<string, unknown> | null;
|
|
60
85
|
artifacts?: Record<string, unknown> | null;
|
|
86
|
+
poll?: RiddlePollSummary;
|
|
61
87
|
}
|
|
62
88
|
interface RiddleServerPreviewResult {
|
|
63
89
|
ok: boolean;
|
|
@@ -83,21 +109,13 @@ declare function parseRiddleViewport(value?: string): {
|
|
|
83
109
|
declare function runRiddleServerPreview(config: RiddleClientConfig, input: RiddleServerPreviewInput): Promise<RiddleServerPreviewResult>;
|
|
84
110
|
declare function runRiddleScript(config: RiddleClientConfig, input: RiddleRunScriptInput): Promise<Record<string, unknown>>;
|
|
85
111
|
declare function isTerminalRiddleJobStatus(status: unknown): boolean;
|
|
86
|
-
declare function pollRiddleJob(config: RiddleClientConfig, jobId: string, options?:
|
|
87
|
-
wait?: boolean;
|
|
88
|
-
attempts?: number;
|
|
89
|
-
intervalMs?: number;
|
|
90
|
-
}): Promise<RiddlePollJobResult>;
|
|
112
|
+
declare function pollRiddleJob(config: RiddleClientConfig, jobId: string, options?: RiddlePollJobOptions): Promise<RiddlePollJobResult>;
|
|
91
113
|
declare function createRiddleApiClient(config?: RiddleClientConfig): {
|
|
92
114
|
requestJson: <T = unknown>(pathname: string, init?: RequestInit) => Promise<T>;
|
|
93
115
|
deployStaticPreview: (directory: string, label: string) => Promise<RiddlePreviewDeployResult>;
|
|
94
116
|
runScript: (input: RiddleRunScriptInput) => Promise<Record<string, unknown>>;
|
|
95
117
|
runServerPreview: (input: RiddleServerPreviewInput) => Promise<RiddleServerPreviewResult>;
|
|
96
|
-
pollJob: (jobId: string, options?:
|
|
97
|
-
wait?: boolean;
|
|
98
|
-
attempts?: number;
|
|
99
|
-
intervalMs?: number;
|
|
100
|
-
}) => Promise<RiddlePollJobResult>;
|
|
118
|
+
pollJob: (jobId: string, options?: RiddlePollJobOptions) => Promise<RiddlePollJobResult>;
|
|
101
119
|
};
|
|
102
120
|
|
|
103
|
-
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, type RiddleClientConfig, type RiddleFetch, type RiddlePollJobResult, type RiddlePreviewDeployResult, type RiddleRunScriptInput, type RiddleServerPreviewInput, type RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview };
|
|
121
|
+
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, type RiddleClientConfig, type RiddleFetch, type RiddlePollJobOptions, type RiddlePollJobResult, type RiddlePollProgressSnapshot, type RiddlePollSummary, type RiddlePreviewDeployResult, type RiddleRunScriptInput, type RiddleServerPreviewInput, type RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview };
|
package/dist/riddle-client.d.ts
CHANGED
|
@@ -7,6 +7,31 @@ interface RiddleClientConfig {
|
|
|
7
7
|
apiBaseUrl?: string;
|
|
8
8
|
fetchImpl?: RiddleFetch;
|
|
9
9
|
}
|
|
10
|
+
interface RiddlePollProgressSnapshot {
|
|
11
|
+
job_id: string;
|
|
12
|
+
status: string | null;
|
|
13
|
+
terminal: boolean;
|
|
14
|
+
attempt: number;
|
|
15
|
+
attempts: number;
|
|
16
|
+
elapsed_ms: number;
|
|
17
|
+
created_at: string | null;
|
|
18
|
+
submitted_at: string | null;
|
|
19
|
+
completed_at: string | null;
|
|
20
|
+
queue_elapsed_ms: number | null;
|
|
21
|
+
running_without_submission: boolean;
|
|
22
|
+
}
|
|
23
|
+
interface RiddlePollSummary extends RiddlePollProgressSnapshot {
|
|
24
|
+
timed_out: boolean;
|
|
25
|
+
interval_ms: number;
|
|
26
|
+
message?: string;
|
|
27
|
+
}
|
|
28
|
+
interface RiddlePollJobOptions {
|
|
29
|
+
wait?: boolean;
|
|
30
|
+
attempts?: number;
|
|
31
|
+
intervalMs?: number;
|
|
32
|
+
progressEveryMs?: number;
|
|
33
|
+
onProgress?: (snapshot: RiddlePollProgressSnapshot) => void | Promise<void>;
|
|
34
|
+
}
|
|
10
35
|
interface RiddlePreviewDeployResult {
|
|
11
36
|
ok: true;
|
|
12
37
|
id: string;
|
|
@@ -58,6 +83,7 @@ interface RiddlePollJobResult {
|
|
|
58
83
|
terminal: boolean;
|
|
59
84
|
job: Record<string, unknown> | null;
|
|
60
85
|
artifacts?: Record<string, unknown> | null;
|
|
86
|
+
poll?: RiddlePollSummary;
|
|
61
87
|
}
|
|
62
88
|
interface RiddleServerPreviewResult {
|
|
63
89
|
ok: boolean;
|
|
@@ -83,21 +109,13 @@ declare function parseRiddleViewport(value?: string): {
|
|
|
83
109
|
declare function runRiddleServerPreview(config: RiddleClientConfig, input: RiddleServerPreviewInput): Promise<RiddleServerPreviewResult>;
|
|
84
110
|
declare function runRiddleScript(config: RiddleClientConfig, input: RiddleRunScriptInput): Promise<Record<string, unknown>>;
|
|
85
111
|
declare function isTerminalRiddleJobStatus(status: unknown): boolean;
|
|
86
|
-
declare function pollRiddleJob(config: RiddleClientConfig, jobId: string, options?:
|
|
87
|
-
wait?: boolean;
|
|
88
|
-
attempts?: number;
|
|
89
|
-
intervalMs?: number;
|
|
90
|
-
}): Promise<RiddlePollJobResult>;
|
|
112
|
+
declare function pollRiddleJob(config: RiddleClientConfig, jobId: string, options?: RiddlePollJobOptions): Promise<RiddlePollJobResult>;
|
|
91
113
|
declare function createRiddleApiClient(config?: RiddleClientConfig): {
|
|
92
114
|
requestJson: <T = unknown>(pathname: string, init?: RequestInit) => Promise<T>;
|
|
93
115
|
deployStaticPreview: (directory: string, label: string) => Promise<RiddlePreviewDeployResult>;
|
|
94
116
|
runScript: (input: RiddleRunScriptInput) => Promise<Record<string, unknown>>;
|
|
95
117
|
runServerPreview: (input: RiddleServerPreviewInput) => Promise<RiddleServerPreviewResult>;
|
|
96
|
-
pollJob: (jobId: string, options?:
|
|
97
|
-
wait?: boolean;
|
|
98
|
-
attempts?: number;
|
|
99
|
-
intervalMs?: number;
|
|
100
|
-
}) => Promise<RiddlePollJobResult>;
|
|
118
|
+
pollJob: (jobId: string, options?: RiddlePollJobOptions) => Promise<RiddlePollJobResult>;
|
|
101
119
|
};
|
|
102
120
|
|
|
103
|
-
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, type RiddleClientConfig, type RiddleFetch, type RiddlePollJobResult, type RiddlePreviewDeployResult, type RiddleRunScriptInput, type RiddleServerPreviewInput, type RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview };
|
|
121
|
+
export { DEFAULT_RIDDLE_API_BASE_URL, DEFAULT_RIDDLE_API_KEY_FILE, RiddleApiError, type RiddleClientConfig, type RiddleFetch, type RiddlePollJobOptions, type RiddlePollJobResult, type RiddlePollProgressSnapshot, type RiddlePollSummary, type RiddlePreviewDeployResult, type RiddleRunScriptInput, type RiddleServerPreviewInput, type RiddleServerPreviewResult, createRiddleApiClient, deployRiddleStaticPreview, isTerminalRiddleJobStatus, parseRiddleViewport, pollRiddleJob, resolveRiddleApiKey, riddleRequestJson, runRiddleScript, runRiddleServerPreview };
|
package/dist/riddle-client.js
CHANGED