@enricai/barnacle 1.6.1 → 1.6.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (105) hide show
  1. package/README.md +36 -29
  2. package/dist/api/errors.d.ts +3 -3
  3. package/dist/api/errors.d.ts.map +1 -1
  4. package/dist/api/errors.js +4 -4
  5. package/dist/api/errors.js.map +1 -1
  6. package/dist/api/helpers/reply.d.ts +1 -1
  7. package/dist/api/helpers/reply.js +1 -1
  8. package/dist/cache/keyed-ttl-cache.d.ts +4 -4
  9. package/dist/cache/keyed-ttl-cache.js +2 -2
  10. package/dist/lib/applicant-payload.d.ts +4 -4
  11. package/dist/lib/applicant-payload.js +4 -4
  12. package/dist/lib/application-address.d.ts +3 -3
  13. package/dist/lib/application-address.js +5 -5
  14. package/dist/lib/application-address.js.map +1 -1
  15. package/dist/lib/application-resume.d.ts +4 -4
  16. package/dist/lib/application-resume.js +4 -4
  17. package/dist/lib/dispatch-metrics.js +1 -1
  18. package/dist/lib/llm/judges/verify-submit.d.ts +1 -1
  19. package/dist/lib/llm/judges/verify-submit.js +1 -1
  20. package/dist/lib/llm/schemas.js +3 -3
  21. package/dist/lib/phone.d.ts +1 -1
  22. package/dist/lib/phone.js +1 -1
  23. package/dist/lib/telemetry/call-types.d.ts +1 -1
  24. package/dist/lib/telemetry/call-types.js +1 -1
  25. package/dist/lib/tracking-click.d.ts +5 -3
  26. package/dist/lib/tracking-click.d.ts.map +1 -1
  27. package/dist/lib/tracking-click.js +5 -3
  28. package/dist/lib/tracking-click.js.map +1 -1
  29. package/dist/lib/us-states.d.ts +1 -1
  30. package/dist/lib/us-states.js +1 -1
  31. package/dist/plugins/loader.js +2 -2
  32. package/dist/scraper/cookie-jar.d.ts +2 -2
  33. package/dist/scraper/cookie-jar.js +2 -2
  34. package/dist/scraper/deep-query.d.ts +36 -0
  35. package/dist/scraper/deep-query.d.ts.map +1 -0
  36. package/dist/scraper/deep-query.js +87 -0
  37. package/dist/scraper/deep-query.js.map +1 -0
  38. package/dist/scraper/errors.d.ts +12 -14
  39. package/dist/scraper/errors.d.ts.map +1 -1
  40. package/dist/scraper/errors.js +12 -17
  41. package/dist/scraper/errors.js.map +1 -1
  42. package/dist/scraper/flow-runner.d.ts +97 -30
  43. package/dist/scraper/flow-runner.d.ts.map +1 -1
  44. package/dist/scraper/flow-runner.js +304 -104
  45. package/dist/scraper/flow-runner.js.map +1 -1
  46. package/dist/scraper/http-client.d.ts +11 -1
  47. package/dist/scraper/http-client.d.ts.map +1 -1
  48. package/dist/scraper/http-client.js +90 -3
  49. package/dist/scraper/http-client.js.map +1 -1
  50. package/dist/scraper/phantom-click.d.ts +45 -0
  51. package/dist/scraper/phantom-click.d.ts.map +1 -0
  52. package/dist/scraper/phantom-click.js +37 -0
  53. package/dist/scraper/phantom-click.js.map +1 -0
  54. package/dist/scraper/raw-fetch.d.ts +2 -2
  55. package/dist/scraper/raw-fetch.js +1 -1
  56. package/dist/scraper/require-response-field.d.ts +1 -1
  57. package/dist/scraper/require-response-field.js +1 -1
  58. package/dist/scraper/session-browserbase.d.ts +48 -0
  59. package/dist/scraper/session-browserbase.d.ts.map +1 -1
  60. package/dist/scraper/session-browserbase.js +10 -5
  61. package/dist/scraper/session-browserbase.js.map +1 -1
  62. package/dist/scraper/session-shared.d.ts +6 -0
  63. package/dist/scraper/session-shared.d.ts.map +1 -1
  64. package/dist/scraper/session-shared.js.map +1 -1
  65. package/dist/scraper/session-warmup.d.ts +1 -1
  66. package/dist/scraper/session-warmup.js +1 -1
  67. package/dist/scraper/submit-control.d.ts +51 -0
  68. package/dist/scraper/submit-control.d.ts.map +1 -0
  69. package/dist/scraper/submit-control.js +142 -0
  70. package/dist/scraper/submit-control.js.map +1 -0
  71. package/dist/scripts/migrate-telemetry-dir-names.d.ts +2 -2
  72. package/dist/scripts/migrate-telemetry-dir-names.d.ts.map +1 -1
  73. package/dist/scripts/migrate-telemetry-dir-names.js +1 -1
  74. package/dist/scripts/recon-browser.d.ts +25 -20
  75. package/dist/scripts/recon-browser.d.ts.map +1 -1
  76. package/dist/scripts/recon-browser.js +65 -56
  77. package/dist/scripts/recon-browser.js.map +1 -1
  78. package/dist/scripts/recon-generate.d.ts +52 -7
  79. package/dist/scripts/recon-generate.d.ts.map +1 -1
  80. package/dist/scripts/recon-generate.js +73 -31
  81. package/dist/scripts/recon-generate.js.map +1 -1
  82. package/dist/scripts/recon-http.d.ts +36 -5
  83. package/dist/scripts/recon-http.d.ts.map +1 -1
  84. package/dist/scripts/recon-http.js +77 -47
  85. package/dist/scripts/recon-http.js.map +1 -1
  86. package/dist/scripts/recon-replay-jobs.d.ts +32 -3
  87. package/dist/scripts/recon-replay-jobs.d.ts.map +1 -1
  88. package/dist/scripts/recon-replay-jobs.js +46 -29
  89. package/dist/scripts/recon-replay-jobs.js.map +1 -1
  90. package/dist/scripts/recon-shared.d.ts +45 -0
  91. package/dist/scripts/recon-shared.d.ts.map +1 -1
  92. package/dist/scripts/recon-shared.js +117 -0
  93. package/dist/scripts/recon-shared.js.map +1 -1
  94. package/dist/scripts/recon-summarize.d.ts +5 -1
  95. package/dist/scripts/recon-summarize.d.ts.map +1 -1
  96. package/dist/scripts/recon-summarize.js +19 -7
  97. package/dist/scripts/recon-summarize.js.map +1 -1
  98. package/dist/site-plugin.d.ts +4 -4
  99. package/dist/testing/persona-fixture.d.ts +4 -4
  100. package/dist/testing/persona-fixture.d.ts.map +1 -1
  101. package/dist/testing/persona-fixture.js +4 -4
  102. package/dist/testing/persona-fixture.js.map +1 -1
  103. package/dist/types/dispatch-metrics.d.ts +1 -1
  104. package/dist/types/dispatch-metrics.js +1 -1
  105. package/package.json +1 -1
package/README.md CHANGED
@@ -29,7 +29,7 @@ Human involvement is one recon run up front and a small PR when things change.
29
29
 
30
30
  | Phase | What runs | What you get |
31
31
  |-------|-----------|--------------|
32
- | **1 — Browser recon** | `pnpm run recon:browser` | Every API call the site makes, captured to `/tmp/recon/graphql/*.json` |
32
+ | **1 — Browser recon** | `pnpm run recon:browser` | Every API call the site makes, captured to `<run-dir>/graphql/*.json` |
33
33
  | **2–3 — HTTP replay + probing** | `pnpm run recon:http` | Proof each endpoint works without a browser; rate-limit ceiling; static fixtures |
34
34
  | **4 — Plugin generation** | `pnpm run recon:generate` | A complete plugin: Zod schemas, headers, Bottleneck config, hot-path client, Stagehand fallback |
35
35
  | **5+ — Runtime** | `pnpm start` | Direct HTTP hot path, automatic browser fallback, nightly smoke test, drift detection |
@@ -100,17 +100,19 @@ pnpm run recon:browser -- --url https://example.com
100
100
 
101
101
  Drives a real Stagehand + Steel browser through your flow. Captures are wired via a single CDP session-level listener (`page.getSessionForFrame().on(...)`) — Stagehand V3 enables the Network domain internally, so attaching our `Network.requestWillBeSent` / `responseReceived` / `loadingFinished` listeners on the main session catches every response, including the early ones that fire before any page-level handler could be wired.
102
102
 
103
- Captures every network call matching `/graph`, `/api/`, `/graphql`, `/v1/`, or `*.json` to `/tmp/recon/graphql/<NNN>-<phase>-<operationName>.json` — one file per call, diffable and greppable. Use `--capture-all` for sites with non-standard API paths; it captures every response, producing more noise but missing nothing. Omitting both `--flow` and `--flow-file` runs zero interaction steps and captures only the network activity that fires during page navigation — useful for pure GET-style SPAs that fetch everything they need on load.
103
+ Captures every network call matching `/graph`, `/api/`, `/graphql`, `/v1/`, or `*.json` to `<run-dir>/graphql/<NNN>-<phase>-<operationName>.json` — one file per call, diffable and greppable. Use `--capture-all` for sites with non-standard API paths; it captures every response, producing more noise but missing nothing. Omitting both `--flow` and `--flow-file` runs zero interaction steps and captures only the network activity that fires during page navigation — useful for pure GET-style SPAs that fetch everything they need on load.
104
104
 
105
- Each step runs through a self-healing cascade (`act` → `observe + act` → `observe + act` with `ignoreSelectors` → Anthropic-SDK rephrase) verified by network-counter delta or URL change. The script's `main()` attempts up to two global flow replans before giving up; terminal failures dump a diagnostic bundle to `/tmp/recon/step-failures/`. See [docs/playbook.md#1c--self-healing-cascade](./docs/playbook.md#1c--self-healing-cascade) for the full design.
105
+ Each step runs through a self-healing cascade (`act` → `observe + act` → `observe + act` with `ignoreSelectors` → Anthropic-SDK rephrase) verified by network-counter delta or URL change. The script's `main()` attempts up to two global flow replans before giving up; terminal failures dump a diagnostic bundle to `<run-dir>/step-failures/`. See [docs/playbook.md#1c--self-healing-cascade](./docs/playbook.md#1c--self-healing-cascade) for the full design.
106
106
 
107
107
  Total runtime: 20–40 minutes for a typical flow (longer if healing or replans fire), fully unattended.
108
108
 
109
+ Every artifact — captures, cookie-jar snapshots, step-failure dumps, DOM dumps — is rooted under one run-scoped directory resolved once at startup: `<run-dir>` defaults to `/tmp/recon/<runId>`, where `<runId>` is a timestamp + random suffix generated per process (e.g. `20260718-120326-a1b2`). Set `RECON_RUN_ID` to pin a deterministic runId (e.g. for tests or replaying a known run) and `RECON_OUT_DIR` to override the base directory runs are rooted under. This keeps concurrent or repeated runs from intermixing files — the startup log line prints both the resolved `runId` and `out=<run-dir>`.
110
+
109
111
  #### Cookie-jar snapshots
110
112
 
111
113
  Alongside the network captures, every run snapshots the browser's complete cookie jar (via CDP `Network.getAllCookies`, which returns the whole-browser jar regardless of the current page's URL — unlike `document.cookie` or `Page.getCookies`, it also sees HttpOnly cookies) at each phase boundary: the initial goto, immediately before each flow step (`pre-step`), immediately after each flow step completes (`post-step`), and once more at run completion (`run-complete`).
112
114
 
113
- Snapshots land in `/tmp/recon/cookies/<NNN>-<label>-<phase>.json` — one file per boundary, using the same zero-padded chronological index convention as the network captures. `<label>` is the boundary kind (`goto`, `pre-step`, `post-step`, `run-complete`); `<phase>` is the current step's slugified instruction (e.g. `click-the-apply-button`), or `home` before the first step starts.
115
+ Snapshots land in `<run-dir>/cookies/<NNN>-<label>-<phase>.json` — one file per boundary, using the same zero-padded chronological index convention as the network captures. `<label>` is the boundary kind (`goto`, `pre-step`, `post-step`, `run-complete`); `<phase>` is the current step's slugified instruction (e.g. `click-the-apply-button`), or `home` before the first step starts.
114
116
 
115
117
  Each file is a JSON object:
116
118
 
@@ -122,9 +124,9 @@ Each file is a JSON object:
122
124
  "timestamp": "2026-07-18T12:34:56.789Z",
123
125
  "cookies": [
124
126
  {
125
- "name": "_appcast_attr",
127
+ "name": "_acme_attr",
126
128
  "value": "abc123",
127
- "domain": ".appcast.io",
129
+ "domain": ".acme.example",
128
130
  "path": "/",
129
131
  "expires": 1234567890,
130
132
  "size": 20,
@@ -142,7 +144,7 @@ Field reference (mirrors CDP's `Network.Cookie` type verbatim — no remapping b
142
144
  | Field | Meaning |
143
145
  | --- | --- |
144
146
  | `name` / `value` | The cookie's name and value. |
145
- | `domain` | Scope, e.g. `.appcast.io` (all subdomains) vs. `apply.appcast.io` (exact host) — the detail needed to tell a click-domain cookie from an apply-domain cookie. |
147
+ | `domain` | Scope, e.g. `.acme.example` (all subdomains) vs. `apply.acme.example` (exact host) — the detail needed to tell a click-domain cookie from an apply-domain cookie. |
146
148
  | `path` | Cookie path scope. |
147
149
  | `expires` | Raw CDP epoch-seconds number; `-1` means a session cookie (also reflected in `session: true`). Not reformatted — read it as CDP reports it. |
148
150
  | `size` | Cookie size in bytes, as reported by CDP. |
@@ -152,14 +154,14 @@ Field reference (mirrors CDP's `Network.Cookie` type verbatim — no remapping b
152
154
 
153
155
  If the CDP call fails, the file still writes but with an empty `cookies` array and an `error` string field carrying the failure message — cookie telemetry is best-effort and never aborts the run.
154
156
 
155
- **Diffing what a phase established:** to isolate what a specific traversal (e.g. the click.appcast.io redirect) minted, diff its `post-step` snapshot against the `pre-step` snapshot for the *next* step — cookies present in the later file but absent from the earlier one were established during that step:
157
+ **Diffing what a phase established:** to isolate what a specific traversal (e.g. a tracking-click redirect) minted, diff its `post-step` snapshot against the `pre-step` snapshot for the *next* step — cookies present in the later file but absent from the earlier one were established during that step:
156
158
 
157
159
  ```bash
158
- diff <(jq -S .cookies /tmp/recon/cookies/004-post-step-click-the-apply-button.json) \
159
- <(jq -S .cookies /tmp/recon/cookies/005-pre-step-fill-in-your-name.json)
160
+ diff <(jq -S .cookies <run-dir>/cookies/004-post-step-click-the-apply-button.json) \
161
+ <(jq -S .cookies <run-dir>/cookies/005-pre-step-fill-in-your-name.json)
160
162
  ```
161
163
 
162
- **Cookies actually sent per request:** the jar snapshot shows what's *available*, not what's *sent*. Each network capture in `/tmp/recon/graphql/` separately carries the outgoing `Cookie` header in its `requestHeaders` (recovered via CDP's `Network.requestWillBeSentExtraInfo`, since `requestWillBeSent` omits it by design) — cross-reference that capture's `requestHeaders.Cookie` against a jar snapshot to see which of the available cookies a given request, e.g. the application submit, actually sent.
164
+ **Cookies actually sent per request:** the jar snapshot shows what's *available*, not what's *sent*. Each network capture in `<run-dir>/graphql/` separately carries the outgoing `Cookie` header in its `requestHeaders` (recovered via CDP's `Network.requestWillBeSentExtraInfo`, since `requestWillBeSent` omits it by design) — cross-reference that capture's `requestHeaders.Cookie` against a jar snapshot to see which of the available cookies a given request, e.g. the application submit, actually sent.
163
165
 
164
166
  **Caveat on `Set-Cookie`:** response captures fold `responseReceivedExtraInfo` headers (which is where `Set-Cookie` actually appears — `responseReceived` omits it) into `responseHeaders` as a flat `Record<string, string>`. CDP does not guarantee multiple `Set-Cookie` values on one response stay distinguishable once folded into that shape — if a single response mints more than one cookie, treat the jar snapshot (not the response capture's `Set-Cookie` header) as the source of truth for what actually landed.
165
167
 
@@ -169,7 +171,7 @@ diff <(jq -S .cookies /tmp/recon/cookies/004-post-step-click-the-apply-button.js
169
171
  pnpm run recon:http
170
172
  ```
171
173
 
172
- Replays every capture via plain `fetch()` — no browser, no AI — to prove endpoints work standalone. Every replay returning 200 proves the browser is unnecessary for production. Also runs GraphQL introspection, auxiliary fixture detection (static JSON to commit as fixtures), and a rate-limit probe at 1→3→5 rps (run last — if it triggers a ban, all captures are already saved). Results land in `/tmp/recon/replays/`.
174
+ Replays every capture via plain `fetch()` — no browser, no AI — to prove endpoints work standalone. Every replay returning 200 proves the browser is unnecessary for production. Also runs GraphQL introspection, auxiliary fixture detection (static JSON to commit as fixtures), and a rate-limit probe at 1→3→5 rps (run last — if it triggers a ban, all captures are already saved). Results land under the run-scoped root resolved by `resolveReconRunDir()` — `/tmp/recon/<runId>/replays/` by default, rooted elsewhere via `--out-dir <path>` or `RECON_OUT_DIR`.
173
175
 
174
176
  See [docs/playbook.md](./docs/playbook.md#interpreting-replay-failures) for the full troubleshooting decision matrix when replays fail.
175
177
 
@@ -179,7 +181,7 @@ See [docs/playbook.md](./docs/playbook.md#interpreting-replay-failures) for the
179
181
  pnpm run recon:generate -- --site-id my-site
180
182
  ```
181
183
 
182
- Reads every artifact from Phases 1–3 — `/tmp/recon/graphql/*.json` (captures), `/tmp/recon/replays/*.json` (replay results), `/tmp/recon/replays/rate-limit.json` (probe findings), `/tmp/recon/aux/*.json` (static fixtures), and `src/sites/my-site/recon-flow.json` — and writes a complete plugin to `src/sites/my-site/`:
184
+ Reads every artifact from Phases 1–3 — `<run-dir>/graphql/*.json` (captures), `<run-dir>/replays/*.json` (replay results), `<run-dir>/replays/rate-limit.json` (probe findings), `<run-dir>/aux/*.json` (static fixtures), and `src/sites/my-site/recon-flow.json` — and writes a complete plugin to `src/sites/my-site/`. Pass `--run-dir <path>` to read a specific run's artifacts instead of the most recently modified run root under `/tmp/recon` (or `RECON_OUT_DIR`, if set):
183
185
 
184
186
  - `contract.ts` — Zod schemas inferred from captured JSON, load-bearing headers, Bottleneck ceiling, and `executeHttp` / `execute` implementations
185
187
  - `flows/browser-flow.ts` — Stagehand fallback wired to your `recon-flow.json` steps
@@ -276,7 +278,7 @@ Optionally generate the human-readable findings doc alongside:
276
278
  pnpm run recon:summarize -- --site-id my-site
277
279
  ```
278
280
 
279
- Writes `docs/my-site-recon.md` with: endpoints found, replay status, rate-limit ceiling, header frequency table, and hazards (Akamai, Cloudflare). Without `--site-id`, the default output path is `docs/target-recon.md`.
281
+ Writes `docs/my-site-recon.md` with: endpoints found, replay status, rate-limit ceiling, header frequency table, and hazards (Akamai, Cloudflare). Without `--site-id`, the default output path is `docs/target-recon.md`. Accepts `--run-dir <path>` the same way `recon:generate` does.
280
282
 
281
283
  ### Phase 5 — Register the plugin
282
284
 
@@ -485,7 +487,7 @@ Add a step to `.github/workflows/smoke.yml`:
485
487
 
486
488
  ### Maintenance loop
487
489
 
488
- When the smoke test fails: re-run `pnpm run recon:browser` → diff `/tmp/recon/graphql/*<operationName>*.json` against `src/sites/<id>/contract.ts` → update query / headers / Zod schema → ship. See [docs/playbook.md](./docs/playbook.md#phase-6--drift-detection) for the full maintenance loop and change severity table.
490
+ When the smoke test fails: re-run `pnpm run recon:browser` → diff `<run-dir>/graphql/*<operationName>*.json` against `src/sites/<id>/contract.ts` → update query / headers / Zod schema → ship. See [docs/playbook.md](./docs/playbook.md#phase-6--drift-detection) for the full maintenance loop and change severity table.
489
491
 
490
492
  ## Runtime internals
491
493
 
@@ -499,8 +501,7 @@ When the smoke test fails: re-run `pnpm run recon:browser` → diff `/tmp/recon/
499
501
  | `HttpBotChallengeError` | 401 / 403 | **Yes** | Residential proxy IP may get through |
500
502
  | `HttpServerError` | 5xx | **Yes** | Server-side outage; recovery strategy is the same |
501
503
  | `HttpRateLimitError` | 429 | **No** | A 429 means the configured rps ceiling is too high. Routing to the browser path would just hit the same ceiling and waste a Steel session. The right response is to lower the Bottleneck `minTime` in `contract.ts` and re-deploy. |
502
- | `HttpUrlLockedError` | 429 | **No** | Oracle HCM returned `ORA_URL_LOCKED` — the requisition URL is locked at Oracle's end. Neither a retry nor a browser session can succeed; the caller must back off and surface a "retry later" state. |
503
- | `OracleTokenExpiredError` | Any | **No** | Oracle HCM returned a plain-text `ORA_IRC_TOKEN_EXPIRED` sentinel. Retryable so p-retry keeps retrying, but distinct from `UnknownScraperError` so the encompass http-flow can catch exactly this class and re-mint the AccessCode before retrying. |
504
+ | `HttpUrlLockedError` | 429 | **No** | A plugin's `classifyResponseBody` detected a terminal resource-lock sentinel — the URL is locked at the target's end. Neither a retry nor a browser session can succeed; the caller must back off and surface a "retry later" state. |
504
505
  | `UnknownScraperError` | Any | **No** | Transient network failure or unclassified non-JSON response. `createHttpClient` retries up to 2 times internally; if all attempts fail, the error propagates as `ScrapeFailureError`. |
505
506
 
506
507
  ### Cache deduplication
@@ -904,8 +905,8 @@ Every response — success or error — uses the same envelope shape so clients
904
905
  | 2003 | `SCRAPE_FAILURE` | Browser automation failed after retries |
905
906
  | 2004 | `CAPTCHA_ENCOUNTERED` | CAPTCHA challenge could not be resolved |
906
907
  | 2005 | `EMPTY_RESULTS` | Scrape succeeded but returned no data |
907
- | 2006 | `VERIFICATION_TRIGGER_FAILED` | OTP trigger to Oracle HCM failed |
908
- | 2007 | `RESUME_INVALID_OTP` | Provided OTP was rejected by Oracle HCM |
908
+ | 2006 | `VERIFICATION_TRIGGER_FAILED` | OTP trigger to the target site failed |
909
+ | 2007 | `RESUME_INVALID_OTP` | Provided OTP was rejected by the target site |
909
910
  | 2008 | `URL_LOCKED` | Upstream vendor locked the target URL; back off and retry later |
910
911
 
911
912
  Full definitions: `src/api/schemas/common.ts`.
@@ -926,16 +927,22 @@ Each registered plugin exposes a POST route following the default convention:
926
927
  answers are absent (e.g. Gender, Degree, EducationLevel, SignatureFullName) or
927
928
  a repeat-applicant OTP challenge, `/run` returns HTTP 200 with
928
929
  `{ needsUserInfo: true, missingFields: [{ field, question }], requiresOtp }`
929
- instead of a submission result, so Vivian can collect the gaps and hand back.
930
-
931
- Plugin-specific extra routes (registered via `meta.extraRoutes` in each plugin):
932
-
933
- Encompass Health:
934
- - `POST /v1/encompasshealth/trigger-otp` — body `{ offerId, email }`; triggers Oracle HCM to email an OTP to a repeat applicant; returns `{ success: true }` or a `2006 VERIFICATION_TRIGGER_FAILED` error envelope
935
- - `POST /v1/encompasshealth/resume` — body = the full original candidate payload plus `collectedData` and `otpCode`; re-runs the hot path with the collected answers and/or OTP; returns the same `{ verified }` envelope as `/run`, or `2007 RESUME_INVALID_OTP` if the OTP is rejected
936
-
937
- Appcast:
938
- - `POST /v1/appcast/resume` — body = the full original candidate payload plus `collectedData` (no `otpCode` — Appcast has no OTP challenge); re-runs the hot path with the chat-collected answers merged in; returns the same `{ verified, response }` envelope as `/run`
930
+ instead of a submission result, so the caller can collect the gaps and hand back.
931
+
932
+ Plugins declare their own extra routes via `meta.extraRoutes`, which core registers
933
+ uniformly — the engine has no per-site knowledge. Route paths are declared as
934
+ `:siteId` templates, so the concrete path is whatever the plugin's `siteId` is. Two
935
+ conventional shapes a plugin may add:
936
+
937
+ - `POST /v1/<siteId>/resume` — body = the full original candidate payload plus
938
+ `collectedData` (and `otpCode` where the site issues an OTP challenge); re-runs the
939
+ hot path with the collected answers merged in; returns the same `{ verified }`
940
+ envelope as `/run`, or `2007 RESUME_INVALID_OTP` if the OTP is rejected
941
+ - `POST /v1/<siteId>/trigger-otp` — body `{ offerId, email }`; asks the target site to
942
+ email an OTP to a repeat applicant; returns `{ success: true }` or a
943
+ `2006 VERIFICATION_TRIGGER_FAILED` error envelope
944
+
945
+ See `examples/plugins/acme-jobs.plugin.json` for a runnable declaration.
939
946
 
940
947
  Operational routes:
941
948
  - `GET /healthz` — liveness probe
@@ -71,9 +71,9 @@ export declare class EmptyResultsApiError extends ApiError {
71
71
  constructor(message?: string);
72
72
  }
73
73
  /**
74
- * The OTP a candidate supplied to /resume was rejected by Oracle HCM, which
75
- * surfaces as a 401/403 on the first AccessCode-authed call. Distinct from a
76
- * generic scrape failure so Vivian can re-prompt for the code rather than
74
+ * The OTP a candidate supplied to /resume was rejected by the target site, which
75
+ * typically surfaces as a 401/403 on the first authenticated call. Distinct from a
76
+ * generic scrape failure so the caller can re-prompt for the code rather than
77
77
  * treating the resume as terminally failed.
78
78
  */
79
79
  export declare class InvalidOtpError extends ApiError {
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/api/errors.ts"],"names":[],"mappings":"AAGA,OAAO,EAAwC,KAAK,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAE5F;;;;GAIG;AACH,UAAU,eAAe;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,eAAe,EAAE,MAAM,CAAC;IACxB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,UAAU,gBAAgB;IACxB,MAAM,EAAE;QACN,UAAU,EAAE,MAAM,CAAC;QACnB,QAAQ,EAAE,MAAM,CAAC;QACjB,OAAO,EAAE,eAAe,EAAE,CAAC;KAC5B,CAAC;CACH;AAED;;;;;;;;GAQG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,SAAS,GAAG,MAAM,CAgCzD;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAQvD;AAED;;;;GAIG;AACH,qBAAa,QAAS,SAAQ,KAAK;IACjC,SAAgB,IAAI,EAAE,SAAS,CAAC;IAChC,SAAgB,UAAU,EAAE,MAAM,CAAC;IAEnC,YAAY,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,EAAE,UAAU,SAAU,EAKjE;CACF;AAED,qBAAa,iBAAkB,SAAQ,QAAQ;IAC7C,YAAY,OAAO,SAA4C,EAE9D;CACF;AAED,qBAAa,mBAAoB,SAAQ,QAAQ;IAC/C,YAAY,OAAO,EAAE,MAAM,EAE1B;CACF;AAED,qBAAa,qBAAsB,SAAQ,QAAQ;IACjD,YAAY,OAAO,SAAwB,EAE1C;CACF;AAED;;;;GAIG;AACH,qBAAa,cAAe,SAAQ,QAAQ;IAC1C,YAAY,OAAO,SAA2D,EAE7E;CACF;AAED,qBAAa,kBAAmB,SAAQ,QAAQ;IAC9C,YAAY,OAAO,SAA0C,EAE5D;CACF;AAED,qBAAa,uBAAwB,SAAQ,QAAQ;IACnD,YAAY,OAAO,SAA2C,EAE7D;CACF;AAED,qBAAa,oBAAqB,SAAQ,QAAQ;IAChD,YAAY,OAAO,SAA6C,EAE/D;CACF;AAED;;;;;GAKG;AACH,qBAAa,eAAgB,SAAQ,QAAQ;IAC3C,YAAY,OAAO,SAA4C,EAE9D;CACF;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,SAAS,EACf,OAAO,EAAE,MAAM,EACf,UAAU,SAAU,GACnB,gBAAgB,CAgBlB"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/api/errors.ts"],"names":[],"mappings":"AAGA,OAAO,EAAwC,KAAK,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAE5F;;;;GAIG;AACH,UAAU,eAAe;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,eAAe,EAAE,MAAM,CAAC;IACxB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,UAAU,gBAAgB;IACxB,MAAM,EAAE;QACN,UAAU,EAAE,MAAM,CAAC;QACnB,QAAQ,EAAE,MAAM,CAAC;QACjB,OAAO,EAAE,eAAe,EAAE,CAAC;KAC5B,CAAC;CACH;AAED;;;;;;;;GAQG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,SAAS,GAAG,MAAM,CAgCzD;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAQvD;AAED;;;;GAIG;AACH,qBAAa,QAAS,SAAQ,KAAK;IACjC,SAAgB,IAAI,EAAE,SAAS,CAAC;IAChC,SAAgB,UAAU,EAAE,MAAM,CAAC;IAEnC,YAAY,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,EAAE,UAAU,SAAU,EAKjE;CACF;AAED,qBAAa,iBAAkB,SAAQ,QAAQ;IAC7C,YAAY,OAAO,SAA4C,EAE9D;CACF;AAED,qBAAa,mBAAoB,SAAQ,QAAQ;IAC/C,YAAY,OAAO,EAAE,MAAM,EAE1B;CACF;AAED,qBAAa,qBAAsB,SAAQ,QAAQ;IACjD,YAAY,OAAO,SAAwB,EAE1C;CACF;AAED;;;;GAIG;AACH,qBAAa,cAAe,SAAQ,QAAQ;IAC1C,YAAY,OAAO,SAA2D,EAE7E;CACF;AAED,qBAAa,kBAAmB,SAAQ,QAAQ;IAC9C,YAAY,OAAO,SAA0C,EAE5D;CACF;AAED,qBAAa,uBAAwB,SAAQ,QAAQ;IACnD,YAAY,OAAO,SAA2C,EAE7D;CACF;AAED,qBAAa,oBAAqB,SAAQ,QAAQ;IAChD,YAAY,OAAO,SAA6C,EAE/D;CACF;AAED;;;;;GAKG;AACH,qBAAa,eAAgB,SAAQ,QAAQ;IAC3C,YAAY,OAAO,SAAiD,EAEnE;CACF;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,SAAS,EACf,OAAO,EAAE,MAAM,EACf,UAAU,SAAU,GACnB,gBAAgB,CAgBlB"}
@@ -129,13 +129,13 @@ class EmptyResultsApiError extends ApiError {
129
129
  }
130
130
  exports.EmptyResultsApiError = EmptyResultsApiError;
131
131
  /**
132
- * The OTP a candidate supplied to /resume was rejected by Oracle HCM, which
133
- * surfaces as a 401/403 on the first AccessCode-authed call. Distinct from a
134
- * generic scrape failure so Vivian can re-prompt for the code rather than
132
+ * The OTP a candidate supplied to /resume was rejected by the target site, which
133
+ * typically surfaces as a 401/403 on the first authenticated call. Distinct from a
134
+ * generic scrape failure so the caller can re-prompt for the code rather than
135
135
  * treating the resume as terminally failed.
136
136
  */
137
137
  class InvalidOtpError extends ApiError {
138
- constructor(message = "provided OTP was rejected by Oracle HCM") {
138
+ constructor(message = "provided OTP was rejected by the target site") {
139
139
  super(common_1.ERROR_CODES.RESUME_INVALID_OTP, message);
140
140
  }
141
141
  }
@@ -1 +1 @@
1
- {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/api/errors.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../../src/api/errors.ts"],"names":[],"mappings":"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"}
@@ -3,7 +3,7 @@ import type { ErrorCode } from "../../api/schemas/common";
3
3
  import type { DispatchMetrics } from "../../types/dispatch-metrics";
4
4
  /**
5
5
  * Sends a standard error envelope on the given reply, optionally including
6
- * dispatch metrics so Vivian can forward step-level detail even on failures.
6
+ * dispatch metrics so the caller can forward step-level detail even on failures.
7
7
  */
8
8
  export declare function replyWithError(reply: FastifyReply, code: ErrorCode, message: string, detailType?: string, statusOverride?: number, metrics?: DispatchMetrics): void;
9
9
  //# sourceMappingURL=reply.d.ts.map
@@ -4,7 +4,7 @@ exports.replyWithError = replyWithError;
4
4
  const errors_1 = require("../../api/errors");
5
5
  /**
6
6
  * Sends a standard error envelope on the given reply, optionally including
7
- * dispatch metrics so Vivian can forward step-level detail even on failures.
7
+ * dispatch metrics so the caller can forward step-level detail even on failures.
8
8
  */
9
9
  function replyWithError(reply, code, message, detailType, statusOverride, metrics) {
10
10
  const envelope = (0, errors_1.buildErrorEnvelope)(code, message, detailType);
@@ -1,8 +1,8 @@
1
1
  /**
2
2
  * Generic per-key TTL cache factory with single-flight warmup coalescing.
3
3
  *
4
- * Why this exists: both `src/cache/response-cache.ts` and
5
- * `src/sites/appcast/tokens/cache.ts` independently hand-roll the same
4
+ * Why this exists: both `src/cache/response-cache.ts` and a plugin's
5
+ * `tokens/cache.ts` independently hand-roll the same
6
6
  * inFlight Map + LRUCache wiring. Any future site needing a per-key token
7
7
  * or session cache would copy it a third time. This factory captures the
8
8
  * shared invariant — promise registered synchronously before any yield so
@@ -33,8 +33,8 @@ export interface KeyedTtlCache<T extends object> {
33
33
  * in-flight promise is written to the map *synchronously* — before any
34
34
  * microtask yield — guaranteeing that every concurrent caller for the same
35
35
  * key awaits the same promise instead of kicking off a duplicate warmup.
36
- * See the same pattern at `response-cache.ts:108-111` and
37
- * `appcast/tokens/cache.ts:124-125`.
36
+ * See the same pattern at `response-cache.ts:108-111` and a plugin's
37
+ * `tokens/cache.ts:124-125`.
38
38
  *
39
39
  * `getOrWarm` returns `{ ...value }` (a shallow copy) to each caller so
40
40
  * that an in-place mutation of the master cache entry (e.g. rotating a
@@ -13,8 +13,8 @@ const lru_cache_1 = require("lru-cache");
13
13
  * in-flight promise is written to the map *synchronously* — before any
14
14
  * microtask yield — guaranteeing that every concurrent caller for the same
15
15
  * key awaits the same promise instead of kicking off a duplicate warmup.
16
- * See the same pattern at `response-cache.ts:108-111` and
17
- * `appcast/tokens/cache.ts:124-125`.
16
+ * See the same pattern at `response-cache.ts:108-111` and a plugin's
17
+ * `tokens/cache.ts:124-125`.
18
18
  *
19
19
  * `getOrWarm` returns `{ ...value }` (a shallow copy) to each caller so
20
20
  * that an in-place mutation of the master cache entry (e.g. rotating a
@@ -1,9 +1,9 @@
1
1
  /**
2
2
  * Shared Zod schema for the applicant identity, address, and resume fields
3
- * that AppCast-powered ATS plugins require on every submission. Both AppCast
4
- * and Encompass Health declare the same 13 fields; this module is the single
5
- * source of truth so a field-type change propagates to every AppCast-shaped
6
- * plugin from one place.
3
+ * that JSON-envelope ATS plugins require on every submission. Multiple
4
+ * production plugins declare the same 13 fields; this module is the single
5
+ * source of truth so a field-type change propagates to every plugin of this
6
+ * shape from one place.
7
7
  *
8
8
  * Diverging fields (Email, BaseUrl, ClickUrl, JobId, Answers) stay in each
9
9
  * plugin's own contract because their types or presence differ across plugins.
@@ -1,10 +1,10 @@
1
1
  "use strict";
2
2
  /**
3
3
  * Shared Zod schema for the applicant identity, address, and resume fields
4
- * that AppCast-powered ATS plugins require on every submission. Both AppCast
5
- * and Encompass Health declare the same 13 fields; this module is the single
6
- * source of truth so a field-type change propagates to every AppCast-shaped
7
- * plugin from one place.
4
+ * that JSON-envelope ATS plugins require on every submission. Multiple
5
+ * production plugins declare the same 13 fields; this module is the single
6
+ * source of truth so a field-type change propagates to every plugin of this
7
+ * shape from one place.
8
8
  *
9
9
  * Diverging fields (Email, BaseUrl, ClickUrl, JobId, Answers) stay in each
10
10
  * plugin's own contract because their types or presence differ across plugins.
@@ -1,7 +1,7 @@
1
1
  /**
2
- * Shared Zod fragment for the six address fields that AppCast-powered plugins
3
- * (AppCast, Encompass Health) require on every submission. Extracted so a
4
- * field-type change propagates from one place to every consumer.
2
+ * Shared Zod fragment for the six address fields that multiple production ATS
3
+ * plugins require on every submission. Extracted so a field-type change
4
+ * propagates from one place to every consumer.
5
5
  */
6
6
  import { z } from "zod/v4";
7
7
  export declare const ApplicantAddressSchema: z.ZodObject<{
@@ -1,8 +1,8 @@
1
1
  "use strict";
2
2
  /**
3
- * Shared Zod fragment for the six address fields that AppCast-powered plugins
4
- * (AppCast, Encompass Health) require on every submission. Extracted so a
5
- * field-type change propagates from one place to every consumer.
3
+ * Shared Zod fragment for the six address fields that multiple production ATS
4
+ * plugins require on every submission. Extracted so a field-type change
5
+ * propagates from one place to every consumer.
6
6
  */
7
7
  Object.defineProperty(exports, "__esModule", { value: true });
8
8
  exports.ApplicantAddressSchema = void 0;
@@ -13,8 +13,8 @@ exports.ApplicantAddressSchema = v4_1.z.object({
13
13
  State: v4_1.z.string().min(1),
14
14
  PostalCode: v4_1.z.string().min(1),
15
15
  Country: v4_1.z.string().min(1),
16
- /** Applicant's home county. Required by some tenants (Encompass Health and
17
- * similar) before submit unlocks. */
16
+ /** Applicant's home county. Required by some tenants before submit
17
+ * unlocks. */
18
18
  County: v4_1.z.string().min(1),
19
19
  });
20
20
  //# sourceMappingURL=application-address.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"application-address.js","sourceRoot":"","sources":["../../src/lib/application-address.ts"],"names":[],"mappings":";AAAA;;;;GAIG;;;AAEH,+BAA2B;AAEd,QAAA,sBAAsB,GAAG,MAAC,CAAC,MAAM,CAAC;IAC7C,WAAW,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC9B,IAAI,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IACvB,KAAK,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IACxB,UAAU,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC7B,OAAO,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC1B;yCACqC;IACrC,MAAM,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;CAC1B,CAAC,CAAC"}
1
+ {"version":3,"file":"application-address.js","sourceRoot":"","sources":["../../src/lib/application-address.ts"],"names":[],"mappings":";AAAA;;;;GAIG;;;AAEH,+BAA2B;AAEd,QAAA,sBAAsB,GAAG,MAAC,CAAC,MAAM,CAAC;IAC7C,WAAW,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC9B,IAAI,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IACvB,KAAK,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IACxB,UAAU,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC7B,OAAO,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC1B;kBACc;IACd,MAAM,EAAE,MAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;CAC1B,CAAC,CAAC"}
@@ -1,14 +1,14 @@
1
1
  /**
2
- * Shared Zod schema for the resume attachment block that AppCast-powered ATS
3
- * plugins require on every submission. AppCast and Encompass Health both declare
2
+ * Shared Zod schema for the resume attachment block that JSON-envelope ATS
3
+ * plugins require on every submission. Multiple production plugins declare
4
4
  * the same four fields; this fragment is extracted so the Buffer/instanceof
5
5
  * constraint and the base64 twin are defined once and propagate to every
6
- * AppCast-shaped plugin from one source of truth.
6
+ * plugin of this shape from one source of truth.
7
7
  *
8
8
  * `Resume` must be a real Node.js Buffer — multipart form builders call
9
9
  * `fd.append("Resume", payload.Resume, ...)` which requires an actual Buffer
10
10
  * instance, not a base64 string. `ResumeBase64` carries the same bytes
11
- * pre-encoded for JSON payloads (e.g. the AppCast `interruption_check` body).
11
+ * pre-encoded for JSON payloads (e.g. the `interruption_check` body).
12
12
  */
13
13
  import { z } from "zod/v4";
14
14
  export declare const ApplicantResumeSchema: z.ZodObject<{
@@ -1,15 +1,15 @@
1
1
  "use strict";
2
2
  /**
3
- * Shared Zod schema for the resume attachment block that AppCast-powered ATS
4
- * plugins require on every submission. AppCast and Encompass Health both declare
3
+ * Shared Zod schema for the resume attachment block that JSON-envelope ATS
4
+ * plugins require on every submission. Multiple production plugins declare
5
5
  * the same four fields; this fragment is extracted so the Buffer/instanceof
6
6
  * constraint and the base64 twin are defined once and propagate to every
7
- * AppCast-shaped plugin from one source of truth.
7
+ * plugin of this shape from one source of truth.
8
8
  *
9
9
  * `Resume` must be a real Node.js Buffer — multipart form builders call
10
10
  * `fd.append("Resume", payload.Resume, ...)` which requires an actual Buffer
11
11
  * instance, not a base64 string. `ResumeBase64` carries the same bytes
12
- * pre-encoded for JSON payloads (e.g. the AppCast `interruption_check` body).
12
+ * pre-encoded for JSON payloads (e.g. the `interruption_check` body).
13
13
  */
14
14
  Object.defineProperty(exports, "__esModule", { value: true });
15
15
  exports.ApplicantResumeSchema = void 0;
@@ -5,7 +5,7 @@ exports.MetricsCollector = void 0;
5
5
  * Lightweight step-timing accumulator for a single dispatch invocation.
6
6
  * Instantiated per-request in the dispatch layer, threaded through
7
7
  * SitePluginContext, and finalized into a DispatchMetrics payload that
8
- * ships in the response body for Vivian → Segment forwarding.
8
+ * ships in the response body for caller → Segment forwarding.
9
9
  */
10
10
  const date_fns_1 = require("date-fns");
11
11
  /** Accumulates step-level timing for a single dispatch, producing a DispatchMetrics payload for the response. */
@@ -7,7 +7,7 @@
7
7
  * Empirically validated 2026-06-11 on two production failure cases:
8
8
  * - Case A (was wrongly flagged as failure by the regex): verdict=true,
9
9
  * correctly identified dom_signal="uapp-universal-submitted-page" and
10
- * url_signal="/applyboard/applied".
10
+ * url_signal="/&lt;vendor&gt;/applied".
11
11
  * - Case B (genuinely stuck, 10 ng-invalid markers, no success DOM):
12
12
  * verdict=false with a coherent reason about why submission failed.
13
13
  *
@@ -8,7 +8,7 @@
8
8
  * Empirically validated 2026-06-11 on two production failure cases:
9
9
  * - Case A (was wrongly flagged as failure by the regex): verdict=true,
10
10
  * correctly identified dom_signal="uapp-universal-submitted-page" and
11
- * url_signal="/applyboard/applied".
11
+ * url_signal="/&lt;vendor&gt;/applied".
12
12
  * - Case B (genuinely stuck, 10 ng-invalid markers, no success DOM):
13
13
  * verdict=false with a coherent reason about why submission failed.
14
14
  *
@@ -38,9 +38,9 @@ exports.RECON_FLOW_STEP_SCHEMA = v4_1.z.union([
38
38
  * When true, the step is treated as the canonical submit click for the
39
39
  * `submitEndpointPattern` verifier even when its position in the flow
40
40
  * is not the last index. The pre-2026-06-15 implementation gated the
41
- * pre-submit DOM probe on `isFinalStep` only, but real AppCast flows
42
- * put the submit click in the middle of the step list (UVA Verona's
43
- * Submit was at index 55/328) and follow it with post-submit
41
+ * pre-submit DOM probe on `isFinalStep` only, but real production flows
42
+ * put the submit click in the middle of the step list (one measured
43
+ * tenant's Submit was at index 55/328) and follow it with post-submit
44
44
  * verification steps. With this flag set, the probe + verifier fire
45
45
  * at the actual submit click, not at the unrelated last step.
46
46
  */
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * Parses a US phone string into area code and subscriber number.
3
- * Oracle HCM requires the phone split into `areaCode` (first 3 digits) and
3
+ * Some ATS backends require the phone split into `areaCode` (first 3 digits) and
4
4
  * `number` (remaining digits). Inputs shorter than 10 digits get an empty
5
5
  * `areaCode` so the partial number is still submitted as-is.
6
6
  */
package/dist/lib/phone.js CHANGED
@@ -3,7 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.parsePhone = parsePhone;
4
4
  /**
5
5
  * Parses a US phone string into area code and subscriber number.
6
- * Oracle HCM requires the phone split into `areaCode` (first 3 digits) and
6
+ * Some ATS backends require the phone split into `areaCode` (first 3 digits) and
7
7
  * `number` (remaining digits). Inputs shorter than 10 digits get an empty
8
8
  * `areaCode` so the partial number is still submitted as-is.
9
9
  */
@@ -26,7 +26,7 @@ export declare const CALL_TYPE_STAGEHAND_EXTRACT = "stagehand-extract";
26
26
  /**
27
27
  * Haiku 4.5 judge for submit-success verification. Replaces the per-site
28
28
  * regex (`submitEndpointPattern`) that mislabeled successful submits as
29
- * failures whenever AppCast used a different POST URL than the regex
29
+ * failures whenever a site used a different POST URL than the regex
30
30
  * expected. The judge receives evidence (recent network captures, page
31
31
  * URL/title, unfocused observe, site criteria) and returns a discriminated
32
32
  * verdict — verified=true requires multi-signal corroboration to prevent
@@ -29,7 +29,7 @@ exports.CALL_TYPE_STAGEHAND_EXTRACT = "stagehand-extract";
29
29
  /**
30
30
  * Haiku 4.5 judge for submit-success verification. Replaces the per-site
31
31
  * regex (`submitEndpointPattern`) that mislabeled successful submits as
32
- * failures whenever AppCast used a different POST URL than the regex
32
+ * failures whenever a site used a different POST URL than the regex
33
33
  * expected. The judge receives evidence (recent network captures, page
34
34
  * URL/title, unfocused observe, site criteria) and returns a discriminated
35
35
  * verdict — verified=true requires multi-signal corroboration to prevent
@@ -1,9 +1,11 @@
1
1
  /**
2
- * Fire-and-forget background click for Appcast vivclid tracking URLs.
2
+ * Fire-and-forget background click for vendor click-tracking URLs.
3
3
  * After a successful submission, Barnacle navigates to the tracking URL
4
- * in a short-lived Browserbase session so Appcast records the Click event.
4
+ * in a short-lived Browserbase session so the tracking vendor records the
5
+ * Click event.
5
6
  *
6
- * Navigation pattern is proven against click.appcast.io with advancedStealth.
7
+ * Navigation pattern is proven against production click-tracking domains
8
+ * with advancedStealth.
7
9
  * No CDP behavioral signals are needed; those are only required when extracting
8
10
  * DataDome tokens for subsequent Node HTTP requests.
9
11
  */
@@ -1 +1 @@
1
- {"version":3,"file":"tracking-click.d.ts","sourceRoot":"","sources":["../../src/lib/tracking-click.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AA0DH;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI,CAK3E;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CAAC,SAAS,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAO3E"}
1
+ {"version":3,"file":"tracking-click.d.ts","sourceRoot":"","sources":["../../src/lib/tracking-click.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AA0DH;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,IAAI,CAK3E;AAED;;;GAGG;AACH,wBAAsB,mBAAmB,CAAC,SAAS,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,CAO3E"}
@@ -1,10 +1,12 @@
1
1
  "use strict";
2
2
  /**
3
- * Fire-and-forget background click for Appcast vivclid tracking URLs.
3
+ * Fire-and-forget background click for vendor click-tracking URLs.
4
4
  * After a successful submission, Barnacle navigates to the tracking URL
5
- * in a short-lived Browserbase session so Appcast records the Click event.
5
+ * in a short-lived Browserbase session so the tracking vendor records the
6
+ * Click event.
6
7
  *
7
- * Navigation pattern is proven against click.appcast.io with advancedStealth.
8
+ * Navigation pattern is proven against production click-tracking domains
9
+ * with advancedStealth.
8
10
  * No CDP behavioral signals are needed; those are only required when extracting
9
11
  * DataDome tokens for subsequent Node HTTP requests.
10
12
  */
@@ -1 +1 @@
1
- {"version":3,"file":"tracking-click.js","sourceRoot":"","sources":["../../src/lib/tracking-click.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"tracking-click.js","sourceRoot":"","sources":["../../src/lib/tracking-click.ts"],"names":[],"mappings":"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"}
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * Shared US state and territory name→abbreviation map. Extracted from
3
- * site-specific copies in appcast and encompasshealth so any plugin can
3
+ * site-specific copies in multiple plugins so any plugin can
4
4
  * resolve a full state name (or a 2-letter code) to an uppercase abbreviation
5
5
  * without duplicating this data.
6
6
  *
@@ -1,7 +1,7 @@
1
1
  "use strict";
2
2
  /**
3
3
  * Shared US state and territory name→abbreviation map. Extracted from
4
- * site-specific copies in appcast and encompasshealth so any plugin can
4
+ * site-specific copies in multiple plugins so any plugin can
5
5
  * resolve a full state name (or a 2-letter code) to an uppercase abbreviation
6
6
  * without duplicating this data.
7
7
  *
@@ -278,8 +278,8 @@ async function registerRoutes(app, cfg, plugins) {
278
278
  }
279
279
  /**
280
280
  * Fastify registers each `method+url` exactly once, but several plugins declare
281
- * the SAME parameterized extra route (e.g. `POST /v1/:siteId/resume` for both
282
- * appcast and encompasshealth). Registering per-plugin throws
281
+ * the SAME parameterized extra route (e.g. `POST /v1/:siteId/resume` for two
282
+ * or more sibling plugins). Registering per-plugin throws
283
283
  * `FST_ERR_DUPLICATED_ROUTE` and crashes boot.
284
284
  *
285
285
  * We group extra routes by `method+path` and register each unique path once.
@@ -2,8 +2,8 @@
2
2
  * Cookie-jar snapshot capture via CDP `Network.getAllCookies`. `document.cookie`
3
3
  * and Stagehand's own cookie helpers can't see HttpOnly cookies, and
4
4
  * `Page.getCookies`/`Network.getCookies` only return cookies scoped to the
5
- * current frame's URLs — a journey that navigated click.appcast.io ->
6
- * apply.appcast.io would miss the click-domain cookies once on the apply
5
+ * current frame's URLs — a journey that navigated a click-tracking domain ->
6
+ * an apply domain would miss the click-domain cookies once on the apply
7
7
  * page. `Network.getAllCookies` returns the whole-browser jar regardless of
8
8
  * the page's current URL, which is what attribution analysis needs.
9
9
  */
@@ -3,8 +3,8 @@
3
3
  * Cookie-jar snapshot capture via CDP `Network.getAllCookies`. `document.cookie`
4
4
  * and Stagehand's own cookie helpers can't see HttpOnly cookies, and
5
5
  * `Page.getCookies`/`Network.getCookies` only return cookies scoped to the
6
- * current frame's URLs — a journey that navigated click.appcast.io ->
7
- * apply.appcast.io would miss the click-domain cookies once on the apply
6
+ * current frame's URLs — a journey that navigated a click-tracking domain ->
7
+ * an apply domain would miss the click-domain cookies once on the apply
8
8
  * page. `Network.getAllCookies` returns the whole-browser jar regardless of
9
9
  * the page's current URL, which is what attribution analysis needs.
10
10
  */