@friggframework/admin-scripts 2.0.0--canary.517.559ad7e.0 → 2.0.0--canary.517.beaf080.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/README.md CHANGED
@@ -228,7 +228,7 @@ Scheduling requires `admin.enableScheduling: true` in the app definition (so the
228
228
 
229
229
  ## Script chaining
230
230
 
231
- Long or fan-out work can enqueue follow-up scripts. Continuations are tracked with `parentExecutionId` so you can trace the lineage:
231
+ A script can enqueue follow-up scripts via `queueScript()` / `queueScriptBatch()`. Each continuation runs **asynchronously** in the executor Lambda (trigger `QUEUE`) with its `parentExecutionId` set to the queuing execution, so you can trace the lineage (and query children by `parentExecutionId`).
232
232
 
233
233
  ```javascript
234
234
  async execute(params) {
@@ -240,6 +240,24 @@ async execute(params) {
240
240
  }
241
241
  ```
242
242
 
243
+ ### When to reach for it
244
+
245
+ Chaining is the escape hatch for work that doesn't fit a single execution. Use it to:
246
+
247
+ - **Beat the timeouts** — sync runs in the API Lambda (≈30s); async in the executor (15-min max). Split bigger jobs into children, each with its own 15-min budget.
248
+ - **Page / resume** — process one page, queue a continuation with the next cursor; a job of any length never hits the wall.
249
+ - **Fan out** — one child per item/batch runs concurrently (bounded by the queue) instead of one script grinding serially.
250
+ - **Isolate failures** — one bad item fails only that child's execution; siblings continue.
251
+ - **Stage pipelines** — script A finishes and queues script B with its output, each stage independently retried/timed.
252
+
253
+ For small, bounded, fast work — or when you need the result in the response — just use a single sync/async execution instead.
254
+
255
+ ### Caveats
256
+
257
+ - **Fire-and-forget** — you don't get a child's result back; correlate via `parentExecutionId`.
258
+ - **At-least-once delivery** — a child may run more than once (SQS redrive on crash). **Make child scripts idempotent.**
259
+ - **No depth guard** — a script that queues itself fans out unbounded. Keep continuation targets terminal, or bound the chain yourself.
260
+
243
261
  ---
244
262
 
245
263
  ## Execution modes & reliability
package/package.json CHANGED
@@ -1,19 +1,19 @@
1
1
  {
2
2
  "name": "@friggframework/admin-scripts",
3
3
  "prettier": "@friggframework/prettier-config",
4
- "version": "2.0.0--canary.517.559ad7e.0",
4
+ "version": "2.0.0--canary.517.beaf080.0",
5
5
  "description": "Admin Script Runner for Frigg - Execute maintenance and operational scripts in hosted environments",
6
6
  "dependencies": {
7
7
  "@aws-sdk/client-scheduler": "^3.588.0",
8
- "@friggframework/core": "2.0.0--canary.517.559ad7e.0",
8
+ "@friggframework/core": "2.0.0--canary.517.beaf080.0",
9
9
  "@hapi/boom": "^10.0.1",
10
10
  "express": "^4.18.2",
11
11
  "serverless-http": "^3.2.0"
12
12
  },
13
13
  "devDependencies": {
14
- "@friggframework/eslint-config": "2.0.0--canary.517.559ad7e.0",
15
- "@friggframework/prettier-config": "2.0.0--canary.517.559ad7e.0",
16
- "@friggframework/test": "2.0.0--canary.517.559ad7e.0",
14
+ "@friggframework/eslint-config": "2.0.0--canary.517.beaf080.0",
15
+ "@friggframework/prettier-config": "2.0.0--canary.517.beaf080.0",
16
+ "@friggframework/test": "2.0.0--canary.517.beaf080.0",
17
17
  "eslint": "^8.22.0",
18
18
  "jest": "^29.7.0",
19
19
  "prettier": "^2.7.1",
@@ -44,5 +44,5 @@
44
44
  "maintenance",
45
45
  "operations"
46
46
  ],
47
- "gitHead": "559ad7ed62bf320273a70e2bb9e30ec67a026355"
47
+ "gitHead": "beaf080b1337695f52525105e87e02c38d29b490"
48
48
  }
@@ -57,6 +57,24 @@ class AdminScriptContext {
57
57
 
58
58
  // ==================== QUEUE OPERATIONS ====================
59
59
 
60
+ /**
61
+ * Enqueue a follow-up script as an async continuation of this execution.
62
+ *
63
+ * Fire-and-forget: the child runs later in the executor Lambda (trigger
64
+ * `QUEUE`) with its `parentExecutionId` set to this execution — you do NOT
65
+ * get the child's result back here. Use it to split work that won't fit one
66
+ * execution (paging past the 15-min executor timeout, per-item fan-out,
67
+ * multi-stage pipelines).
68
+ *
69
+ * Caveats: delivery is at-least-once, so child scripts must be idempotent;
70
+ * and there is no recursion/depth guard, so a script that queues itself
71
+ * fans out unbounded — keep continuation targets terminal or bound the chain
72
+ * yourself.
73
+ *
74
+ * @param {string} scriptName - Registered name of the script to enqueue
75
+ * @param {Object} [params={}] - Params passed to the child's execute()
76
+ * @throws {Error} if ADMIN_SCRIPT_QUEUE_URL is not configured
77
+ */
60
78
  async queueScript(scriptName, params = {}) {
61
79
  const queueUrl = process.env.ADMIN_SCRIPT_QUEUE_URL;
62
80
  if (!queueUrl) {
@@ -78,6 +96,14 @@ class AdminScriptContext {
78
96
  this.log('info', `Queued continuation for ${scriptName}`, { params });
79
97
  }
80
98
 
99
+ /**
100
+ * Enqueue many follow-up scripts at once (batched to SQS). Same semantics
101
+ * and caveats as {@link queueScript} — each child runs async with this
102
+ * execution as its parent; make children idempotent and keep them terminal.
103
+ *
104
+ * @param {Array<{scriptName: string, params?: Object}>} entries - Scripts to enqueue
105
+ * @throws {Error} if ADMIN_SCRIPT_QUEUE_URL is not configured
106
+ */
81
107
  async queueScriptBatch(entries) {
82
108
  const queueUrl = process.env.ADMIN_SCRIPT_QUEUE_URL;
83
109
  if (!queueUrl) {