@smart-cloud/publisher-exporter 1.1.59 → 1.1.61

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
@@ -171,6 +171,38 @@ Archived files are gzip-compressed per file and listed in `job.json`. WordPress
171
171
 
172
172
  Prune old archive directories with `publisher-exporter prune-logs --runtime-dir /srv/site/runtime --older-than-days 30`. Add that command to daily cron or another retention scheduler that matches your log policy.
173
173
 
174
+ ## Optional Lambda workers
175
+
176
+ The exporter includes protocol-v1 building blocks for delegating bounded
177
+ render, text-rewrite, and S3 deploy-copy tasks to container-image Lambda
178
+ functions. Large payloads do not travel in the Lambda response: workers write
179
+ HTML and detailed results below a configured S3 workspace prefix and return a
180
+ small `resultKey` pointer. Reusing the same job/task ID is idempotent.
181
+
182
+ The companion CDK application is in the repository `infrastructure/`
183
+ directory. Its deploy script emits a `remote-workers.json` containing the
184
+ versioned Lambda alias ARNs, workspace bucket/prefix, region, and generated
185
+ assumable role. The file contains no static AWS access keys.
186
+
187
+ Copy that output to the exporter host with owner-only permissions and validate
188
+ the role, aliases, and function runtimes:
189
+
190
+ ```bash
191
+ publisher-exporter remote-worker-health \
192
+ --config /etc/wpsuite/remote-workers.json
193
+ ```
194
+
195
+ Protocol v1 accepts 1-20 same-origin URLs per render task. Start with one URL
196
+ per invocation so retries stay small and Lambda concurrency supplies the
197
+ parallelism. The Lambda response is not the rendered body; read the returned
198
+ S3 result object using the same temporary role credentials.
199
+
200
+ This change establishes the deployable workers, client, health check, and S3
201
+ contract. The normal `crawl`, `rewrite`, and `deploy` commands retain their
202
+ local behavior until their coordinator paths are explicitly configured to
203
+ delegate work. There is deliberately no automatic local fallback after a
204
+ remote worker error.
205
+
174
206
  ## Troubleshooting
175
207
 
176
208
  - If exported HTML still contains old rewritten URLs after a rewrite fix, run `crawl --resume-rewrite`. This reprocesses every text file in the current output tree and does not depend on earlier `rewriteComplete: true` entries in `crawl-manifest.json`.
package/dist/cli.js CHANGED
@@ -1,23 +1,25 @@
1
1
  #!/usr/bin/env node
2
- import {spawn}from'child_process';import {existsSync,readFileSync}from'fs';import o from'path';import {fileURLToPath}from'url';var p=o.dirname(fileURLToPath(import.meta.url)),l=o.resolve(p,"..");function f(){try{let n=readFileSync(o.join(l,"package.json"),"utf8"),e=JSON.parse(n);if(typeof e.version=="string"&&e.version.trim())return e.version.trim()}catch{}return "unknown"}function g(){console.log(`publisher-exporter <command> [args]
2
+ import {spawn}from'child_process';import {existsSync,readFileSync}from'fs';import o from'path';import {fileURLToPath}from'url';var p=o.dirname(fileURLToPath(import.meta.url)),l=o.resolve(p,"..");function f(){try{let e=readFileSync(o.join(l,"package.json"),"utf8"),n=JSON.parse(e);if(typeof n.version=="string"&&n.version.trim())return n.version.trim()}catch{}return "unknown"}function g(){console.log(`publisher-exporter <command> [args]
3
3
 
4
4
  Commands:
5
- crawl Run the crawl phase
6
- deploy Deploy the prepared output
7
- invalidate Request CloudFront invalidation
8
- publish Run crawl, deploy, then invalidate
9
- content-sync Run an internal claimed content-sync job
10
- queue-runner Process queued jobs from runtime JSON
11
- prune-logs Delete archived log directories older than a retention window
12
- install-browsers Install Playwright Chromium into the current/shared browsers path
13
- version Show the installed CLI version
14
- help Show this help
5
+ crawl Run the crawl phase
6
+ deploy Deploy the prepared output
7
+ invalidate Request CloudFront invalidation
8
+ publish Run crawl, deploy, then invalidate
9
+ content-sync Run an internal claimed content-sync job
10
+ queue-runner Process queued jobs from runtime JSON
11
+ prune-logs Delete archived log directories older than a retention window
12
+ remote-worker-health Invoke health checks on all configured Lambda workers
13
+ install-browsers Install Playwright Chromium into the current/shared browsers path
14
+ version Show the installed CLI version
15
+ help Show this help
15
16
 
16
17
  Examples:
17
18
  publisher-exporter crawl --crawl-mode incremental
18
19
  publisher-exporter deploy --profile prod
19
20
  publisher-exporter queue-runner --runtime-dir /srv/site/runtime --max-jobs 1
20
21
  publisher-exporter prune-logs --runtime-dir /srv/site/runtime --older-than-days 30
22
+ publisher-exporter remote-worker-health --config ./remote-workers.json
21
23
  publisher-exporter install-browsers
22
24
  publisher-exporter --version
23
- `);}function v(){console.log(f());}function a(n){let e=o.join(p,`${n}.js`);if(!existsSync(e))throw new Error(`Missing CLI entrypoint: ${e}`);return e}function y(){let n=[o.join(l,"node_modules","playwright","cli.js"),o.join(l,"node_modules","playwright-core","cli.js")];for(let e of n)if(existsSync(e))return e;throw new Error("Playwright CLI was not found under this package. Run `npm install` first.")}function i(n,e){return new Promise((r,s)=>{let t=spawn(process.execPath,[n,...e],{cwd:l,env:process.env,stdio:"inherit"});t.on("error",s),t.on("close",(d,c)=>{if(c){s(new Error(`Command terminated by signal ${c}.`));return}r(d??1);});})}async function b(n){let e=`direct-publish-${Date.now()}`,r=await i(a("content-sync"),["--capture-baseline-cutoffs",e]);if(r!==0)return r;for(let s of ["crawl","deploy","invalidate"]){let t=await i(a(s),n);if(t!==0)return t}return i(a("content-sync"),["--establish-baselines",e])}async function x(){let[n="help",...e]=process.argv.slice(2);if(["version","--version","-v"].includes(n)){v();return}if(["help","--help","-h"].includes(n)){g();return}if(n==="publish"){process.exitCode=await b(e);return}if(n==="install-browsers"){let r=e.length>0?e:["install","chromium"];process.exitCode=await i(y(),r);return}if(n==="crawl"||n==="deploy"||n==="invalidate"||n==="queue-runner"||n==="prune-logs"||n==="content-sync"){process.exitCode=await i(a(n),e);return}throw new Error(`Unknown command: ${n}`)}x().catch(n=>{console.error(n instanceof Error?n.message:String(n)),process.exit(1);});
25
+ `);}function v(){console.log(f());}function a(e){let n=o.join(p,`${e}.js`);if(!existsSync(n))throw new Error(`Missing CLI entrypoint: ${n}`);return n}function y(){let e=[o.join(l,"node_modules","playwright","cli.js"),o.join(l,"node_modules","playwright-core","cli.js")];for(let n of e)if(existsSync(n))return n;throw new Error("Playwright CLI was not found under this package. Run `npm install` first.")}function i(e,n){return new Promise((r,s)=>{let t=spawn(process.execPath,[e,...n],{cwd:l,env:process.env,stdio:"inherit"});t.on("error",s),t.on("close",(d,c)=>{if(c){s(new Error(`Command terminated by signal ${c}.`));return}r(d??1);});})}async function b(e){let n=`direct-publish-${Date.now()}`,r=await i(a("content-sync"),["--capture-baseline-cutoffs",n]);if(r!==0)return r;for(let s of ["crawl","deploy","invalidate"]){let t=await i(a(s),e);if(t!==0)return t}return i(a("content-sync"),["--establish-baselines",n])}async function x(){let[e="help",...n]=process.argv.slice(2);if(["version","--version","-v"].includes(e)){v();return}if(["help","--help","-h"].includes(e)){g();return}if(e==="publish"){process.exitCode=await b(n);return}if(e==="install-browsers"){let r=n.length>0?n:["install","chromium"];process.exitCode=await i(y(),r);return}if(e==="crawl"||e==="deploy"||e==="invalidate"||e==="queue-runner"||e==="prune-logs"||e==="remote-worker-health"||e==="content-sync"){process.exitCode=await i(a(e),n);return}throw new Error(`Unknown command: ${e}`)}x().catch(e=>{console.error(e instanceof Error?e.message:String(e)),process.exit(1);});