@nuetzliches/croniq-runner 0.3.0 → 0.6.0

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/dist/logger.js CHANGED
@@ -1,3 +1,4 @@
1
+ import { escapeControlChars } from './sanitize.js';
1
2
  const ORDER = {
2
3
  trace: 0,
3
4
  debug: 1,
@@ -19,9 +20,16 @@ export function consoleLogger(minLevel = 'warn', prefix) {
19
20
  const emit = (level, message, fields) => {
20
21
  if (ORDER[level] < threshold)
21
22
  return;
23
+ // The message is escaped before it reaches the console: it is the one part
24
+ // of a record that is plain text, and a handler's exception message — or,
25
+ // before #441, a server-supplied identifier — can carry CRLF or ANSI
26
+ // escapes. `fields` needs no such treatment because JSON.stringify already
27
+ // escapes the C0 range, ESC included. This mirrors Go, whose slog handlers
28
+ // escape control characters in every rendered value.
29
+ const safe = escapeControlChars(message);
22
30
  const line = fields && Object.keys(fields).length > 0
23
- ? `${tag}${level}: ${message} ${JSON.stringify(fields)}`
24
- : `${tag}${level}: ${message}`;
31
+ ? `${tag}${level}: ${safe} ${JSON.stringify(fields)}`
32
+ : `${tag}${level}: ${safe}`;
25
33
  // Map to console method, but funnel everything to stderr for warn/error
26
34
  // so application stdout stays clean for actual job output.
27
35
  // eslint-disable-next-line no-console
@@ -1 +1 @@
1
- {"version":3,"file":"logger.js","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../src/logger.ts"],"names":[],"mappings":"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"}
package/dist/options.d.ts CHANGED
@@ -19,8 +19,22 @@ export interface ResolvedLogWriterOptions {
19
19
  shutdownTimeoutMs: number;
20
20
  }
21
21
  export interface CroniqRunnerOptions {
22
- /** Base URL of the Croniq server, e.g. `http://localhost:4000`. */
22
+ /**
23
+ * Base URL of the Croniq server, e.g. `http://localhost:4000`.
24
+ *
25
+ * `https://` is required unless the host is loopback (`localhost`,
26
+ * `127.0.0.0/8`, `::1`) — the API key rides along on every request and would
27
+ * otherwise travel in cleartext. See {@link allowInsecureHttp}.
28
+ */
23
29
  serverUrl: string;
30
+ /**
31
+ * Opt in to a cleartext `http://` {@link serverUrl} on a non-loopback host.
32
+ *
33
+ * Off by default: without it such a URL is rejected by `resolveOptions`.
34
+ * With it, the SDK still emits one loud startup warning — the API key then
35
+ * travels in cleartext on every poll. Default `false`.
36
+ */
37
+ allowInsecureHttp?: boolean;
24
38
  /**
25
39
  * Stable runner identifier. If omitted, the SDK resolves it via
26
40
  * `RUNNER_ID` env var → state file under {@link runnerDataDir} →
@@ -62,6 +76,30 @@ export interface CroniqRunnerOptions {
62
76
  pollRetryDelayMs?: number;
63
77
  /** Idle delay when the runner is at `maxInflight` capacity. Default 500 ms. */
64
78
  capacityBackoffMs?: number;
79
+ /**
80
+ * How many consecutive `409 Conflict` responses from `POST /v1/work/poll`
81
+ * the runner tolerates before `run()` rejects with a
82
+ * `PollInstanceConflictError`. Default 3, range [1, 100].
83
+ *
84
+ * A sustained 409 means a second process is registered under the same
85
+ * `runnerId` and no amount of retrying fixes that. The counter resets on a
86
+ * successful poll or on any non-409 failure (5xx, network, timeout), which
87
+ * say nothing about instance ownership.
88
+ */
89
+ maxConsecutivePollConflicts?: number;
90
+ /**
91
+ * How many consecutive `401 Unauthorized` responses from
92
+ * `POST /v1/work/poll` the runner tolerates before `run()` rejects with an
93
+ * `AuthFailedError`. Default 3, range [1, 100].
94
+ *
95
+ * The API key is read once and never re-read, so a rejected credential
96
+ * cannot fix itself; retrying only produces an idle-looking process that
97
+ * never exits. Not fatal on the first 401 — rotation hands over through an
98
+ * expiry window (server issue #471) and a race around it should not kill a
99
+ * healthy runner. The counter resets on a successful poll and on any other
100
+ * failure: a 5xx says nothing about whether the key is valid.
101
+ */
102
+ maxConsecutiveAuthFailures?: number;
65
103
  /** Streaming log-writer tunables. */
66
104
  logWriter?: LogWriterOptions;
67
105
  /** Optional logger for SDK-level diagnostics. Defaults to a console logger that emits warn/error only. */
@@ -69,6 +107,7 @@ export interface CroniqRunnerOptions {
69
107
  }
70
108
  export interface ResolvedRunnerOptions {
71
109
  serverUrl: string;
110
+ allowInsecureHttp: boolean;
72
111
  runnerId: string | undefined;
73
112
  runnerIdPrefix: string;
74
113
  runnerDataDir: string | undefined;
@@ -82,6 +121,8 @@ export interface ResolvedRunnerOptions {
82
121
  drainTimeoutMs: number;
83
122
  pollRetryDelayMs: number;
84
123
  capacityBackoffMs: number;
124
+ maxConsecutivePollConflicts: number;
125
+ maxConsecutiveAuthFailures: number;
85
126
  logWriter: ResolvedLogWriterOptions;
86
127
  logger: Logger;
87
128
  }
@@ -1 +1 @@
1
- {"version":3,"file":"options.d.ts","sourceRoot":"","sources":["../src/options.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAG1C,MAAM,WAAW,gBAAgB;IAC/B,4EAA4E;IAC5E,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,gEAAgE;IAChE,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,2FAA2F;IAC3F,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,0DAA0D;IAC1D,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,wGAAwG;IACxG,iBAAiB,CAAC,EAAE,MAAM,CAAC;CAC5B;AAED,MAAM,WAAW,wBAAwB;IACvC,eAAe,EAAE,MAAM,CAAC;IACxB,kBAAkB,EAAE,MAAM,CAAC;IAC3B,oBAAoB,EAAE,MAAM,CAAC;IAC7B,eAAe,EAAE,MAAM,CAAC;IACxB,iBAAiB,EAAE,MAAM,CAAC;CAC3B;AAED,MAAM,WAAW,mBAAmB;IAClC,mEAAmE;IACnE,SAAS,EAAE,MAAM,CAAC;IAElB;;;;OAIG;IACH,QAAQ,CAAC,EAAE,MAAM,CAAC;IAElB,yEAAyE;IACzE,cAAc,CAAC,EAAE,MAAM,CAAC;IAExB;;;;OAIG;IACH,aAAa,CAAC,EAAE,MAAM,CAAC;IAEvB,iGAAiG;IACjG,MAAM,CAAC,EAAE,MAAM,CAAC;IAEhB,6DAA6D;IAC7D,WAAW,CAAC,EAAE,MAAM,CAAC;IAErB;;;OAGG;IACH,YAAY,CAAC,EAAE,MAAM,EAAE,CAAC;IAExB;;;;OAIG;IACH,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAEhB,2EAA2E;IAC3E,WAAW,CAAC,EAAE,MAAM,CAAC;IAErB,8EAA8E;IAC9E,aAAa,CAAC,EAAE,MAAM,CAAC;IAEvB,sFAAsF;IACtF,eAAe,CAAC,EAAE,MAAM,CAAC;IAEzB,wGAAwG;IACxG,cAAc,CAAC,EAAE,MAAM,CAAC;IAExB,6DAA6D;IAC7D,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAE1B,+EAA+E;IAC/E,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAE3B,qCAAqC;IACrC,SAAS,CAAC,EAAE,gBAAgB,CAAC;IAE7B,0GAA0G;IAC1G,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,qBAAqB;IACpC,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,GAAG,SAAS,CAAC;IAC7B,cAAc,EAAE,MAAM,CAAC;IACvB,aAAa,EAAE,MAAM,GAAG,SAAS,CAAC;IAClC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;IAC3B,WAAW,EAAE,MAAM,GAAG,SAAS,CAAC;IAChC,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,IAAI,EAAE,MAAM,EAAE,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,eAAe,EAAE,MAAM,CAAC;IACxB,cAAc,EAAE,MAAM,CAAC;IACvB,gBAAgB,EAAE,MAAM,CAAC;IACzB,iBAAiB,EAAE,MAAM,CAAC;IAC1B,SAAS,EAAE,wBAAwB,CAAC;IACpC,MAAM,EAAE,MAAM,CAAC;CAChB;AAUD,wBAAgB,cAAc,CAAC,KAAK,EAAE,mBAAmB,EAAE,aAAa,EAAE,MAAM,GAAG,qBAAqB,CA0CvG"}
1
+ {"version":3,"file":"options.d.ts","sourceRoot":"","sources":["../src/options.ts"],"names":[],"mappings":"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"}
package/dist/options.js CHANGED
@@ -1,3 +1,4 @@
1
+ import { assertSecureServerUrl } from './security.js';
1
2
  import { trimTrailingSlashes } from './url.js';
2
3
  const DEFAULT_LOG_WRITER = {
3
4
  channelCapacity: 256,
@@ -17,10 +18,26 @@ export function resolveOptions(input, defaultLogger) {
17
18
  catch {
18
19
  throw new TypeError(`CroniqRunnerOptions.serverUrl is not a valid URL: ${input.serverUrl}`);
19
20
  }
21
+ const logger = input.logger ?? defaultLogger;
22
+ // Fail fast on a cleartext base URL that would leak the API key (#440).
23
+ const allowInsecureHttp = input.allowInsecureHttp ?? false;
24
+ assertSecureServerUrl(input.serverUrl, allowInsecureHttp, 'CroniqRunnerOptions.serverUrl', logger);
20
25
  const maxInflight = input.maxInflight ?? 5;
21
26
  if (!Number.isInteger(maxInflight) || maxInflight < 1 || maxInflight > 1024) {
22
27
  throw new RangeError(`CroniqRunnerOptions.maxInflight must be an integer in [1, 1024], got ${maxInflight}`);
23
28
  }
29
+ const maxConsecutivePollConflicts = input.maxConsecutivePollConflicts ?? 3;
30
+ if (!Number.isInteger(maxConsecutivePollConflicts) ||
31
+ maxConsecutivePollConflicts < 1 ||
32
+ maxConsecutivePollConflicts > 100) {
33
+ throw new RangeError(`CroniqRunnerOptions.maxConsecutivePollConflicts must be an integer in [1, 100], got ${maxConsecutivePollConflicts}`);
34
+ }
35
+ const maxConsecutiveAuthFailures = input.maxConsecutiveAuthFailures ?? 3;
36
+ if (!Number.isInteger(maxConsecutiveAuthFailures) ||
37
+ maxConsecutiveAuthFailures < 1 ||
38
+ maxConsecutiveAuthFailures > 100) {
39
+ throw new RangeError(`CroniqRunnerOptions.maxConsecutiveAuthFailures must be an integer in [1, 100], got ${maxConsecutiveAuthFailures}`);
40
+ }
24
41
  const logWriter = {
25
42
  channelCapacity: input.logWriter?.channelCapacity ?? DEFAULT_LOG_WRITER.channelCapacity,
26
43
  batchSizeThreshold: input.logWriter?.batchSizeThreshold ?? DEFAULT_LOG_WRITER.batchSizeThreshold,
@@ -30,6 +47,7 @@ export function resolveOptions(input, defaultLogger) {
30
47
  };
31
48
  return {
32
49
  serverUrl: trimTrailingSlashes(input.serverUrl),
50
+ allowInsecureHttp,
33
51
  runnerId: input.runnerId,
34
52
  runnerIdPrefix: input.runnerIdPrefix ?? 'runner',
35
53
  runnerDataDir: input.runnerDataDir,
@@ -43,8 +61,10 @@ export function resolveOptions(input, defaultLogger) {
43
61
  drainTimeoutMs: input.drainTimeoutMs ?? 30_000,
44
62
  pollRetryDelayMs: input.pollRetryDelayMs ?? 5_000,
45
63
  capacityBackoffMs: input.capacityBackoffMs ?? 500,
64
+ maxConsecutivePollConflicts,
65
+ maxConsecutiveAuthFailures,
46
66
  logWriter,
47
- logger: input.logger ?? defaultLogger,
67
+ logger,
48
68
  };
49
69
  }
50
70
  //# sourceMappingURL=options.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"options.js","sourceRoot":"","sources":["../src/options.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,mBAAmB,EAAE,MAAM,UAAU,CAAC;AA2G/C,MAAM,kBAAkB,GAA6B;IACnD,eAAe,EAAE,GAAG;IACpB,kBAAkB,EAAE,EAAE;IACtB,oBAAoB,EAAE,GAAG;IACzB,eAAe,EAAE,GAAG;IACpB,iBAAiB,EAAE,KAAK;CACzB,CAAC;AAEF,MAAM,UAAU,cAAc,CAAC,KAA0B,EAAE,aAAqB;IAC9E,IAAI,CAAC,KAAK,CAAC,SAAS,IAAI,OAAO,KAAK,CAAC,SAAS,KAAK,QAAQ,EAAE,CAAC;QAC5D,MAAM,IAAI,SAAS,CAAC,2CAA2C,CAAC,CAAC;IACnE,CAAC;IACD,IAAI,CAAC;QACH,kCAAkC;QAClC,IAAI,GAAG,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACP,MAAM,IAAI,SAAS,CAAC,qDAAqD,KAAK,CAAC,SAAS,EAAE,CAAC,CAAC;IAC9F,CAAC;IAED,MAAM,WAAW,GAAG,KAAK,CAAC,WAAW,IAAI,CAAC,CAAC;IAC3C,IAAI,CAAC,MAAM,CAAC,SAAS,CAAC,WAAW,CAAC,IAAI,WAAW,GAAG,CAAC,IAAI,WAAW,GAAG,IAAI,EAAE,CAAC;QAC5E,MAAM,IAAI,UAAU,CAAC,wEAAwE,WAAW,EAAE,CAAC,CAAC;IAC9G,CAAC;IAED,MAAM,SAAS,GAA6B;QAC1C,eAAe,EAAE,KAAK,CAAC,SAAS,EAAE,eAAe,IAAI,kBAAkB,CAAC,eAAe;QACvF,kBAAkB,EAAE,KAAK,CAAC,SAAS,EAAE,kBAAkB,IAAI,kBAAkB,CAAC,kBAAkB;QAChG,oBAAoB,EAAE,KAAK,CAAC,SAAS,EAAE,oBAAoB,IAAI,kBAAkB,CAAC,oBAAoB;QACtG,eAAe,EAAE,KAAK,CAAC,SAAS,EAAE,eAAe,IAAI,kBAAkB,CAAC,eAAe;QACvF,iBAAiB,EAAE,KAAK,CAAC,SAAS,EAAE,iBAAiB,IAAI,kBAAkB,CAAC,iBAAiB;KAC9F,CAAC;IAEF,OAAO;QACL,SAAS,EAAE,mBAAmB,CAAC,KAAK,CAAC,SAAS,CAAC;QAC/C,QAAQ,EAAE,KAAK,CAAC,QAAQ;QACxB,cAAc,EAAE,KAAK,CAAC,cAAc,IAAI,QAAQ;QAChD,aAAa,EAAE,KAAK,CAAC,aAAa;QAClC,MAAM,EAAE,KAAK,CAAC,MAAM;QACpB,WAAW,EAAE,KAAK,CAAC,WAAW;QAC9B,YAAY,EAAE,CAAC,GAAG,CAAC,KAAK,CAAC,YAAY,IAAI,EAAE,CAAC,CAAC;QAC7C,IAAI,EAAE,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,IAAI,EAAE,CAAC,CAAC;QAC7B,WAAW;QACX,aAAa,EAAE,KAAK,CAAC,aAAa,IAAI,MAAM;QAC5C,eAAe,EAAE,KAAK,CAAC,eAAe,IAAI,MAAM;QAChD,cAAc,EAAE,KAAK,CAAC,cAAc,IAAI,MAAM;QAC9C,gBAAgB,EAAE,KAAK,CAAC,gBAAgB,IAAI,KAAK;QACjD,iBAAiB,EAAE,KAAK,CAAC,iBAAiB,IAAI,GAAG;QACjD,SAAS;QACT,MAAM,EAAE,KAAK,CAAC,MAAM,IAAI,aAAa;KACtC,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"options.js","sourceRoot":"","sources":["../src/options.ts"],"names":[],"mappings":"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"}
@@ -71,12 +71,14 @@ export interface TriggerRequest {
71
71
  }
72
72
  /**
73
73
  * Wire response of `POST /v1/trigger`. `deduplicated` is sent by servers that
74
- * support trigger idempotency keys (#279); older servers omit it and the
75
- * client defaults it to `false`.
74
+ * support trigger idempotency keys (#279) and `coalesced` by servers that
75
+ * support the `coalesce` job directive (#759); older servers omit either and
76
+ * the client defaults it to `false`.
76
77
  */
77
78
  export interface TriggerResponse {
78
79
  execution_id: string;
79
80
  queued: number;
80
81
  deduplicated?: boolean;
82
+ coalesced?: boolean;
81
83
  }
82
84
  //# sourceMappingURL=protocol.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"protocol.d.ts","sourceRoot":"","sources":["../src/protocol.ts"],"names":[],"mappings":"AAOA,MAAM,WAAW,WAAW;IAC1B,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,YAAY,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,IAAI,EAAE,MAAM,EAAE,CAAC;CAChB;AAED,MAAM,WAAW,cAAc;IAC7B,YAAY,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB;;;OAGG;IACH,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,OAAO,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,cAAc,EAAE,CAAC;IACvB,MAAM,EAAE,MAAM,EAAE,CAAC;CAClB;AAED,MAAM,MAAM,SAAS,GAAG,SAAS,GAAG,SAAS,CAAC;AAE9C,MAAM,WAAW,UAAU;IACzB,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,EAAE,SAAS,CAAC;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,YAAY;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,kBAAkB;IACjC,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,mBAAmB;IAClC,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,YAAY,GAAG,wBAAwB,CAAC;CAClD;AAED,MAAM,MAAM,cAAc,GAAG,OAAO,GAAG,OAAO,GAAG,MAAM,GAAG,MAAM,GAAG,OAAO,CAAC;AAE3E,MAAM,WAAW,SAAS;IACxB,KAAK,CAAC,EAAE,cAAc,CAAC;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACjC;AAED;;;;GAIG;AACH,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACnC,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;GAIG;AACH,MAAM,WAAW,eAAe;IAC9B,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,CAAC,EAAE,OAAO,CAAC;CACxB"}
1
+ {"version":3,"file":"protocol.d.ts","sourceRoot":"","sources":["../src/protocol.ts"],"names":[],"mappings":"AAOA,MAAM,WAAW,WAAW;IAC1B,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,YAAY,EAAE,MAAM,CAAC;IACrB,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,IAAI,EAAE,MAAM,EAAE,CAAC;CAChB;AAED,MAAM,WAAW,cAAc;IAC7B,YAAY,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB;;;OAGG;IACH,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,OAAO,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,cAAc,EAAE,CAAC;IACvB,MAAM,EAAE,MAAM,EAAE,CAAC;CAClB;AAED,MAAM,MAAM,SAAS,GAAG,SAAS,GAAG,SAAS,CAAC;AAE9C,MAAM,WAAW,UAAU;IACzB,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,EAAE,SAAS,CAAC;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,YAAY;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,kBAAkB;IACjC,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,EAAE,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,mBAAmB;IAClC,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,MAAM,CAAC,EAAE,YAAY,GAAG,wBAAwB,CAAC;CAClD;AAED,MAAM,MAAM,cAAc,GAAG,OAAO,GAAG,OAAO,GAAG,MAAM,GAAG,MAAM,GAAG,OAAO,CAAC;AAE3E,MAAM,WAAW,SAAS;IACxB,KAAK,CAAC,EAAE,cAAc,CAAC;IACvB,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACjC;AAED;;;;GAIG;AACH,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACnC,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,EAAE,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,eAAe,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;GAKG;AACH,MAAM,WAAW,eAAe;IAC9B,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB"}
@@ -1 +1 @@
1
- {"version":3,"file":"runner.d.ts","sourceRoot":"","sources":["../src/runner.ts"],"names":[],"mappings":"AAOA,OAAO,EAEL,KAAK,UAAU,EACf,KAAK,sBAAsB,EAC5B,MAAM,cAAc,CAAC;AAGtB,OAAO,EAAkB,KAAK,mBAAmB,EAA8B,MAAM,cAAc,CAAC;AAGpG;;;;;;;GAOG;AACH,qBAAa,YAAY;;gBAaX,OAAO,EAAE,mBAAmB;IAYxC;;;;OAIG;IACH,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,IAAI,CAAC,EAAE,sBAAsB,GAAG,IAAI;IAKhF,gFAAgF;IAChF,iBAAiB,CAAC,OAAO,EAAE,UAAU,GAAG,IAAI;IAK5C,qEAAqE;IACrE,IAAI,QAAQ,IAAI,MAAM,CAGrB;IAED,sEAAsE;IACtE,IAAI,QAAQ,IAAI,SAAS,MAAM,EAAE,CAEhC;IAED;;;;OAIG;IACG,GAAG,CAAC,MAAM,GAAE,WAA0C,GAAG,OAAO,CAAC,IAAI,CAAC;IA4C5E;;;OAGG;IACH,YAAY,IAAI,IAAI;CA4HrB;AAED,sEAAsE;AACtE,wBAAgB,YAAY,CAAC,OAAO,EAAE,mBAAmB,GAAG,YAAY,CAEvE"}
1
+ {"version":3,"file":"runner.d.ts","sourceRoot":"","sources":["../src/runner.ts"],"names":[],"mappings":"AAgBA,OAAO,EAEL,KAAK,UAAU,EACf,KAAK,sBAAsB,EAC5B,MAAM,cAAc,CAAC;AAGtB,OAAO,EAAkB,KAAK,mBAAmB,EAA8B,MAAM,cAAc,CAAC;AAepG;;;;;;;GAOG;AACH,qBAAa,YAAY;;gBAaX,OAAO,EAAE,mBAAmB;IAYxC;;;;OAIG;IACH,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,IAAI,CAAC,EAAE,sBAAsB,GAAG,IAAI;IAKhF,gFAAgF;IAChF,iBAAiB,CAAC,OAAO,EAAE,UAAU,GAAG,IAAI;IAK5C,qEAAqE;IACrE,IAAI,QAAQ,IAAI,MAAM,CAGrB;IAED,sEAAsE;IACtE,IAAI,QAAQ,IAAI,SAAS,MAAM,EAAE,CAEhC;IAED;;;;OAIG;IACG,GAAG,CAAC,MAAM,GAAE,WAA0C,GAAG,OAAO,CAAC,IAAI,CAAC;IA4C5E;;;OAGG;IACH,YAAY,IAAI,IAAI;CA0RrB;AAED,sEAAsE;AACtE,wBAAgB,YAAY,CAAC,OAAO,EAAE,mBAAmB,GAAG,YAAY,CAEvE"}
package/dist/runner.js CHANGED
@@ -1,13 +1,14 @@
1
1
  import { randomBytes } from 'node:crypto';
2
2
  import { setMaxListeners } from 'node:events';
3
3
  import { anySignal } from './abort.js';
4
- import { CroniqClient, HttpError } from './client.js';
4
+ import { CroniqClient, HttpError, AuthFailedError, PollInstanceConflictError, RunnerOwnershipDeniedError, isInstanceConflict, isOwnershipDenied, isUnauthorized, } from './client.js';
5
5
  import { sleep } from './deferred.js';
6
6
  import { ExecutionDispatcher } from './dispatcher.js';
7
7
  import { HandlerRegistry, } from './handler.js';
8
8
  import { resolveRunnerId } from './identity.js';
9
9
  import { consoleLogger } from './logger.js';
10
10
  import { resolveOptions } from './options.js';
11
+ import { isSafeExecutionId, previewForLog, rejectAssignmentReason, rejectionAckError, } from './sanitize.js';
11
12
  /**
12
13
  * The Croniq runner: polls the server for work, dispatches handlers
13
14
  * concurrently up to {@link CroniqRunnerOptions.maxInflight}, renews leases
@@ -134,6 +135,13 @@ export class CroniqRunner {
134
135
  }
135
136
  }
136
137
  async #pollLoop(signal) {
138
+ // Consecutive 409 Conflict responses on poll. Reset by a successful poll
139
+ // or by any non-409 failure — see `maxConsecutivePollConflicts`.
140
+ let consecutiveConflicts = 0;
141
+ // Consecutive 401s, tracked separately: a run of conflicts must not
142
+ // spend the auth budget, or a duplicate deployment would be reported
143
+ // as an authentication failure.
144
+ let consecutiveAuthFailures = 0;
137
145
  while (!signal.aborted) {
138
146
  // Control-slot polling (issue #176): even at capacity we still poll
139
147
  // so the server can deliver cancels via PollResponse.cancel. The
@@ -155,10 +163,74 @@ export class CroniqRunner {
155
163
  catch (err) {
156
164
  if (signal.aborted)
157
165
  return;
158
- const detail = err instanceof HttpError
159
- ? { status: err.status, status_text: err.statusText }
160
- : { error: String(err) };
161
- this.#logger.warn(`poll failed — backing off ${this.#options.pollRetryDelayMs}ms`, detail);
166
+ // A 403 is permanent (issue #437): the credential is bound to
167
+ // another runner_id, so the next poll fails identically. Stop with
168
+ // an actionable error instead of retrying on the poll interval,
169
+ // which makes a fenced-out runner look merely idle.
170
+ if (isOwnershipDenied(err)) {
171
+ this.#logger.error('fatal: poll refused with 403 Forbidden — this runner\'s credential does not own ' +
172
+ 'runner_id. Give the runner its own runner_id, or release the existing binding ' +
173
+ 'with DELETE /v1/runners/{id}', { runner_id: this.#runnerId });
174
+ throw new RunnerOwnershipDeniedError(this.#runnerId);
175
+ }
176
+ // A 401 says the key was rejected, and the client never re-reads
177
+ // it, so every later poll presents the same dead credential.
178
+ // Budgeted rather than fatal at once: rotation hands over through an
179
+ // expiry window (server issue #471) and a race around it should not
180
+ // kill a healthy runner (issue #473).
181
+ if (isUnauthorized(err)) {
182
+ consecutiveAuthFailures += 1;
183
+ if (consecutiveAuthFailures >= this.#options.maxConsecutiveAuthFailures) {
184
+ this.#logger.error(`fatal: poll refused with 401 Unauthorized ${consecutiveAuthFailures} times in ` +
185
+ 'a row — the API key was rejected. It may have been revoked, or its rotation ' +
186
+ 'grace window may have elapsed. Restart the runner with the current key', { runner_id: this.#runnerId });
187
+ throw new AuthFailedError(consecutiveAuthFailures);
188
+ }
189
+ this.#logger.warn(`poll returned 401 Unauthorized (${consecutiveAuthFailures}/` +
190
+ `${this.#options.maxConsecutiveAuthFailures}) — the API key was rejected; ` +
191
+ `retrying after ${this.#options.pollRetryDelayMs}ms`, { runner_id: this.#runnerId });
192
+ // A 401 is not a 409, so it clears the conflict budget just like
193
+ // any other non-409 failure. This branch returns before reaching
194
+ // the reset below, so it has to do it here (issue #508).
195
+ consecutiveConflicts = 0;
196
+ try {
197
+ await sleep(this.#options.pollRetryDelayMs, signal);
198
+ }
199
+ catch {
200
+ return;
201
+ }
202
+ continue;
203
+ }
204
+ // Anything that is not a 401 clears the auth budget: a 5xx or a
205
+ // timeout says nothing about whether the credential is valid.
206
+ consecutiveAuthFailures = 0;
207
+ // A 409 means a newer instance has taken this runner_id over
208
+ // (fencing, issue #374). One is transient — the deposed instance may
209
+ // win it back — so we back off and retry. A streak of them is a
210
+ // duplicate deployment, and retrying forever hides it behind a
211
+ // warning that scrolls past (issue #134 sub-item 1).
212
+ if (isInstanceConflict(err)) {
213
+ consecutiveConflicts += 1;
214
+ if (consecutiveConflicts >= this.#options.maxConsecutivePollConflicts) {
215
+ this.#logger.error(`fatal: poll refused with 409 Conflict ${consecutiveConflicts} times in a row — ` +
216
+ 'another runner is registered with this runner_id. Stop the duplicate process ' +
217
+ 'or rotate the runner_id', { runner_id: this.#runnerId });
218
+ throw new PollInstanceConflictError(this.#runnerId, consecutiveConflicts);
219
+ }
220
+ this.#logger.warn(`poll returned 409 Conflict (${consecutiveConflicts}/` +
221
+ `${this.#options.maxConsecutivePollConflicts}) — another runner instance may be ` +
222
+ `active; retrying after ${this.#options.pollRetryDelayMs}ms`, { runner_id: this.#runnerId });
223
+ }
224
+ else {
225
+ // Non-409 transient (5xx, network, timeout) — unrelated to instance
226
+ // ownership, so a recovered outage must not accumulate with later
227
+ // conflicts.
228
+ consecutiveConflicts = 0;
229
+ const detail = err instanceof HttpError
230
+ ? { status: err.status, status_text: err.statusText }
231
+ : { error: String(err) };
232
+ this.#logger.warn(`poll failed — backing off ${this.#options.pollRetryDelayMs}ms`, detail);
233
+ }
162
234
  try {
163
235
  await sleep(this.#options.pollRetryDelayMs, signal);
164
236
  }
@@ -167,6 +239,13 @@ export class CroniqRunner {
167
239
  }
168
240
  continue;
169
241
  }
242
+ // Poll succeeded — the other instance must have died or released the
243
+ // identity, so the conflict streak starts over. The auth budget starts
244
+ // over with it: the credential just worked, so an earlier 401 must not
245
+ // still count against a runner that has been healthy since (issue
246
+ // #507).
247
+ consecutiveConflicts = 0;
248
+ consecutiveAuthFailures = 0;
170
249
  this.#handleCancellations(response.cancel);
171
250
  if (atCapacity) {
172
251
  // Work is always empty in this branch (server-side capacity
@@ -180,6 +259,14 @@ export class CroniqRunner {
180
259
  continue;
181
260
  }
182
261
  for (const assignment of response.work) {
262
+ // Ingest guard: an assignment carrying a control character in either
263
+ // identifier never reaches a handler, a log record or a telemetry
264
+ // attribute. See sanitize.ts for the rule and why it is a denylist.
265
+ const rejected = rejectAssignmentReason(assignment.execution_id, assignment.job_key);
266
+ if (rejected !== undefined) {
267
+ await this.#rejectAssignment(assignment, rejected, signal);
268
+ continue;
269
+ }
183
270
  if (this.#inflight.has(assignment.execution_id))
184
271
  continue;
185
272
  const ac = new AbortController();
@@ -193,13 +280,65 @@ export class CroniqRunner {
193
280
  }
194
281
  }
195
282
  }
283
+ /**
284
+ * Handle a work assignment refused by the ingest guard.
285
+ *
286
+ * The two cases differ in what the runner can still tell the server:
287
+ *
288
+ * - **Unsafe `execution_id`** — nothing. That value is what addresses an ack
289
+ * or renew, so there is no way to report anything about this execution.
290
+ * The assignment is dropped and the server's lease expires.
291
+ * - **Unsafe `job_key`, valid `execution_id`** — a failure ack. The handler
292
+ * never runs, but the execution completes with an error naming the
293
+ * offending field, so the operator sees a dead-lettered execution instead
294
+ * of an execution that is silently requeued by the stale-claim reaper and
295
+ * refused again on every later poll.
296
+ *
297
+ * Awaited rather than fire-and-forget: this path only triggers on malformed
298
+ * input, so pausing the loop for one small POST costs nothing and keeps the
299
+ * ordering observable.
300
+ */
301
+ async #rejectAssignment(assignment, field, signal) {
302
+ // Escaped and truncated explicitly: this is the one place a refused value
303
+ // is rendered, and it is hostile by definition.
304
+ const preview = previewForLog(assignment[field]);
305
+ const ackable = field === 'job_key';
306
+ this.#logger.warn('rejected work assignment with unsafe identifier', {
307
+ field,
308
+ value: preview,
309
+ acked: ackable,
310
+ });
311
+ if (!ackable)
312
+ return;
313
+ try {
314
+ await this.#client.ack({
315
+ runner_id: this.#runnerId,
316
+ execution_id: assignment.execution_id,
317
+ status: 'failure',
318
+ attempt: assignment.attempt,
319
+ duration_ms: 0,
320
+ error: rejectionAckError(field, assignment[field]),
321
+ }, signal);
322
+ }
323
+ catch (err) {
324
+ this.#logger.warn('failed to ack a rejected work assignment', {
325
+ execution_id: assignment.execution_id,
326
+ error: String(err),
327
+ });
328
+ }
329
+ }
196
330
  #handleCancellations(cancelIds) {
197
331
  if (cancelIds.length === 0)
198
332
  return;
199
333
  for (const id of cancelIds) {
334
+ // Cancel ids are server-supplied too. An unsafe one can never match an
335
+ // in-flight key (those were validated on ingest), but checking here
336
+ // keeps the value out of the log line below on any code path.
337
+ if (!isSafeExecutionId(id))
338
+ continue;
200
339
  const ac = this.#inflight.get(id);
201
340
  if (ac && !ac.signal.aborted) {
202
- this.#logger.info(`server requested cancellation of execution ${id}`, { execution_id: id });
341
+ this.#logger.info('server requested cancellation', { execution_id: id });
203
342
  ac.abort();
204
343
  }
205
344
  }
@@ -1 +1 @@
1
- {"version":3,"file":"runner.js","sourceRoot":"","sources":["../src/runner.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"runner.js","sourceRoot":"","sources":["../src/runner.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,82 @@
1
+ /**
2
+ * Hygiene for server-supplied strings.
3
+ *
4
+ * `job_key` and `execution_id` arrive from the Croniq server and are echoed
5
+ * into logs and telemetry. The threat actor is a malicious or compromised
6
+ * server — but not only: in a multi-tenant deployment anyone who can name a
7
+ * job key in the Croniqfile controls a string that round-trips to every
8
+ * runner unchanged. A value carrying CRLF forges log records; one carrying
9
+ * ANSI escapes repaints the operator's terminal.
10
+ *
11
+ * Two layers defend against that:
12
+ *
13
+ * 1. {@link assertSafeAssignmentIdentifiers} rejects an assignment whose
14
+ * identifiers fall outside the shape Croniq itself defines, so hostile
15
+ * values never enter the SDK.
16
+ * 2. {@link escapeControlChars} escapes anything a terminal would interpret,
17
+ * applied wherever this SDK renders text itself (see `logger.ts`).
18
+ */
19
+ /**
20
+ * Maximum accepted `job_key` length, counted in Unicode scalar values.
21
+ *
22
+ * The server stores job keys in an unbounded `TEXT` column
23
+ * (`crates/croniq-store/src/migrations/001_initial.sql`), so this bound is the
24
+ * SDK's own. 256 is far above any plausible `namespace:name:variant` while
25
+ * still bounding what a single log line can be made to hold.
26
+ */
27
+ export declare const MAX_JOB_KEY_LENGTH = 256;
28
+ /**
29
+ * Maximum accepted `execution_id` length. The server always emits a v4 UUID
30
+ * (36 characters); 64 leaves room for the shorter opaque ids used by mock
31
+ * servers and the conformance suite.
32
+ */
33
+ export declare const MAX_EXECUTION_ID_LENGTH = 64;
34
+ /**
35
+ * Escape every character a terminal interprets rather than prints: the C0
36
+ * range (including ESC, `0x1B`, which introduces every ANSI sequence), DEL,
37
+ * and the C1 range.
38
+ *
39
+ * This mirrors what Go's `slog` handlers do for attribute values, and is
40
+ * applied here because this SDK's console logger writes the message itself.
41
+ * Field maps do not need it — they are rendered with `JSON.stringify`, which
42
+ * already escapes these.
43
+ */
44
+ export declare function escapeControlChars(value: string): string;
45
+ /**
46
+ * Render a rejected value for a diagnostic: escaped so it cannot forge a
47
+ * record, and truncated so an over-long value cannot flood the log either.
48
+ */
49
+ export declare function previewForLog(value: unknown, maxLength?: number): string;
50
+ /**
51
+ * True when `value` is a job key this runner is willing to act on: non-empty,
52
+ * within {@link MAX_JOB_KEY_LENGTH} scalar values, and free of control
53
+ * characters. Iteration is over scalar values (`for…of`), not UTF-16 code
54
+ * units, so an astral character counts once and a surrogate pair is never
55
+ * inspected half at a time.
56
+ */
57
+ export declare function isSafeJobKey(value: unknown): value is string;
58
+ /** True when `value` is an execution id this runner is willing to act on. */
59
+ export declare function isSafeExecutionId(value: unknown): value is string;
60
+ /** The identifier that makes a work assignment unacceptable. */
61
+ export type RejectedField = 'execution_id' | 'job_key';
62
+ /**
63
+ * Names the identifier that makes a work assignment unacceptable, or
64
+ * `undefined` when both pass. Only the field name is returned — the offending
65
+ * value is reported separately, escaped, so the diagnostic cannot itself become
66
+ * the injection vector.
67
+ *
68
+ * The two outcomes are handled differently by the caller, and the order here
69
+ * is what makes that possible. An unsafe `execution_id` leaves nothing to
70
+ * address the server with, so the assignment is dropped silently. An unsafe
71
+ * `job_key` with a *valid* `execution_id` can still be acked as a failure, so
72
+ * the operator gets a dead-lettered execution naming the problem instead of a
73
+ * silent requeue loop.
74
+ */
75
+ export declare function rejectAssignmentReason(executionId: unknown, jobKey: unknown): RejectedField | undefined;
76
+ /**
77
+ * The `error` string acked for an assignment rejected on `job_key`. Names the
78
+ * field and shows the offending value escaped, so the dead-letter row explains
79
+ * itself without carrying a live payload.
80
+ */
81
+ export declare function rejectionAckError(field: RejectedField, value: unknown): string;
82
+ //# sourceMappingURL=sanitize.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sanitize.d.ts","sourceRoot":"","sources":["../src/sanitize.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AAEH;;;;;;;GAOG;AACH,eAAO,MAAM,kBAAkB,MAAM,CAAC;AAEtC;;;;GAIG;AACH,eAAO,MAAM,uBAAuB,KAAK,CAAC;AAkC1C;;;;;;;;;GASG;AACH,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAcxD;AAED;;;GAGG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,OAAO,EAAE,SAAS,SAAM,GAAG,MAAM,CASrE;AAED;;;;;;GAMG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,MAAM,CAQ5D;AAED,6EAA6E;AAC7E,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,MAAM,CAOjE;AAED,gEAAgE;AAChE,MAAM,MAAM,aAAa,GAAG,cAAc,GAAG,SAAS,CAAC;AAEvD;;;;;;;;;;;;GAYG;AACH,wBAAgB,sBAAsB,CACpC,WAAW,EAAE,OAAO,EACpB,MAAM,EAAE,OAAO,GACd,aAAa,GAAG,SAAS,CAI3B;AAED;;;;GAIG;AACH,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,aAAa,EAAE,KAAK,EAAE,OAAO,GAAG,MAAM,CAE9E"}