{
 "source": "data/recipes.json",
 "data_generated": "2026-10-28T17:17:33+01:00",
 "rows": 211,
 "note": "One row per test scenario, from the latest published result file for each recipe. Results come from mock servers unless mock_or_live says otherwise. Earlier failed and flaky runs are not in this file; see https://mainstreetskills.com/how-we-test.",
 "columns": [
  "recipe",
  "trade",
  "scenario_id",
  "scenario",
  "result",
  "run_date",
  "mock_or_live",
  "result_file",
  "limitations"
 ],
 "scenarios": [
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S1",
   "scenario": "Answered call is ignored",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S2",
   "scenario": "Missed call during business hours gets a call-back text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S3",
   "scenario": "After-hours no-cool call becomes a Jobber request over 2 texts",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S4",
   "scenario": "Burst pipe at 2am Saturday pages on-call",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S5",
   "scenario": "Gas smell gets safety instructions, no booking",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S6",
   "scenario": "Same caller twice within 12h only gets one text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S7",
   "scenario": "Blocked / anonymous caller is skipped",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S8",
   "scenario": "A text after the request is logged goes to the office, not back into intake",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S9",
   "scenario": "Plain-English opt-out ('please stop texting me') is honored: one confirmation, no more auto-texts; later texts go to the office",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S10",
   "scenario": "'Won't stop' about a leak is NOT treated as an opt-out",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "missed-call-text-back",
   "trade": "hvac-plumbing",
   "scenario_id": "S11",
   "scenario": "Carrier keyword STOP: no reply from the workflow (Twilio confirms), and no text-back on the next missed call",
   "result": "pass",
   "run_date": "2026-10-28T17:13:22+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/missed-call-text-back/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | The after-hours greeting is 2 SMS segments, so it costs twice a short text. The business-hours greeting fits in 1 segment with a business name up to about 30 characters. | Plain-English opt-outs are matched against a phrase list (stop texting, don't text me, remove me, unsubscribe, opt out, leave me alone and similar). Unusual wordings can slip through, so skim replies now and then. Twilio's own keyword handling (STOP, END, CANCEL and so on) still applies; confirm your Messaging Service opt-out settings. | Housecall Pro and ServiceTitan versions are not built; we could not verify their API docs."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D1",
   "scenario": "First daily run: three quotes due a first check-in, one too fresh, one too old to cold-text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D1b",
   "scenario": "Same day re-run (e.g. n8n restarted): must not double-text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D2",
   "scenario": "Next day: drain-camera quote reaches day 2",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D3",
   "scenario": "Day 5+ quotes get the AI-written second touch",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D4",
   "scenario": "Furnace quote approved in Jobber overnight: its sequence stops; mini-split gets the close-out text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "R1",
   "scenario": "Marcus (water heater) replies by text: his sequence pauses and the reply goes to the office",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D5",
   "scenario": "A week later: drain-camera close-out; water heater skipped (customer replied); mini-split (3 texts, no reply, 22 days) goes to the owner",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "quote-follow-up",
   "trade": "hvac-plumbing",
   "scenario_id": "D6",
   "scenario": "Quiet day: nothing due, owner not re-alerted",
   "result": "pass",
   "run_date": "2026-10-28T17:13:39+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/quote-follow-up/test/results.json",
   "limitations": "Built for Jobber only. Housecall Pro's API is on its MAX plan and we could not open its API docs; ServiceTitan not checked. | A small model wrote touch 2 in our tests; one early draft swapped the customer and company roles before we added a guardrail for it. Review a few real drafts before trusting it. | The first text includes the quote link, so it's 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W1",
   "scenario": "Jobber INVOICE_CREATE (signed) for today's water-heater job -> Stripe link for $489.00 -> text to customer",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W2",
   "scenario": "Jobber retries the same delivery (at-least-once): no second text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W3",
   "scenario": "Forged call with a wrong signature: ignored, Jobber not even queried",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W4",
   "scenario": "Webhook for an invoice that is already paid: no text",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S1",
   "scenario": "Daily sweep Oct 27: first reminders on 3/7/14-day-old invoices (partial payment billed at its $150 balance), 21-day one to owner, paid + opted-out skipped",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S1b",
   "scenario": "Sweep re-run the same day: nothing sent twice",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S2",
   "scenario": "Oct 30: tankless invoice paid in the meantime (stops); today's invoice gets reminder 1 reusing its link; 7+ day ones get reminder 2",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S3",
   "scenario": "Nov 3: customer paid part of #2201 by check (balance $200): new link for the new balance; #2188 hits day 21 -> owner, no more texts",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S4",
   "scenario": "Nov 10: last automatic reminders; #2195 reaches day 21 -> owner",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S5",
   "scenario": "Invoice #2210 is voided in Jobber (status added in API version 2026-05-12): the sweep never chases it again",
   "result": "pass",
   "run_date": "2026-10-28T17:13:44+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W1",
   "scenario": "Jobber INVOICE_CREATE (signed) for today's water-heater job -> Stripe link for $489.00 -> text to customer",
   "result": "pass",
   "run_date": "2026-10-28T16:58:42+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results-jobber.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W2",
   "scenario": "Jobber retries the same delivery (at-least-once): no second text",
   "result": "pass",
   "run_date": "2026-10-28T16:58:42+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results-jobber.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "W3",
   "scenario": "Forged call with a wrong signature: ignored, Jobber not even queried",
   "result": "pass",
   "run_date": "2026-10-28T16:58:42+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results-jobber.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S1",
   "scenario": "Daily sweep Oct 27: first reminders on 3/7/14-day-old invoices (partial payment billed at its $150 balance), 21-day one to owner, paid + opted-out skipped",
   "result": "pass",
   "run_date": "2026-10-28T16:58:42+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results-jobber.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "S2",
   "scenario": "Oct 30: tankless invoice paid in the meantime (stops); today's invoice gets reminder 1 reusing its link; 7+ day ones get reminder 2",
   "result": "pass",
   "run_date": "2026-10-28T16:58:42+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/invoice-payment-reminders/test/results-jobber.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L1",
   "scenario": "invoice created -> real test-mode payment link",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L2",
   "scenario": "paid with test card 4242 on the real Checkout page",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L3",
   "scenario": "sweep S1 (2026-10-27)",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L3",
   "scenario": "sweep S1b (2026-10-27)",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L3",
   "scenario": "sweep S2 (2026-10-30)",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L3",
   "scenario": "sweep S3 (2026-11-03)",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L3",
   "scenario": "sweep S4 (2026-11-10)",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "invoice-payment-reminders",
   "trade": "hvac-plumbing",
   "scenario_id": "L4",
   "scenario": "owner told once that #2210 was paid by Stripe link",
   "result": "pass",
   "run_date": "2026-10-27T15:40:37+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/invoice-payment-reminders/test/results-live-stripe.json",
   "limitations": "Stripe paid detection reads up to 100 completed checkouts from the last 35 days per sweep; a busier account needs pagination. It was tested with a USD card payment only (Stripe may show customers abroad their local currency). | Texts include a link, so each is 2 SMS segments."
  },
  {
   "recipe": "voice-memo-to-invoice",
   "trade": "hvac-plumbing",
   "scenario_id": "M1",
   "scenario": "Memo: \"Okay, this is job fifty five twelve, the Raman house. Furnace was locking out on flame failure. Pulled the...\"",
   "result": "pass",
   "run_date": "2026-10-28T17:14:36+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/voice-memo-to-invoice/test/results.json",
   "limitations": "The AI step is an extractor; matching and prices are plain code. A price book with very different names will need more aliases. | It writes a draft note, not invoice line items, on purpose: a person should approve before billing. | The small test model sometimes mixed up who the customer was in the summary; prompts now tell it the customer is not the tech, but review summaries. | Tested with clean synthetic voices; real job sites are noisier."
  },
  {
   "recipe": "voice-memo-to-invoice",
   "trade": "hvac-plumbing",
   "scenario_id": "M2",
   "scenario": "Memo: \"Kitchen sink leak at the Baptiste job. The leak was at the P trap, the old trap was cracked, so I put in a...\"",
   "result": "pass",
   "run_date": "2026-10-28T17:14:36+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/voice-memo-to-invoice/test/results.json",
   "limitations": "The AI step is an extractor; matching and prices are plain code. A price book with very different names will need more aliases. | It writes a draft note, not invoice line items, on purpose: a person should approve before billing. | The small test model sometimes mixed up who the customer was in the summary; prompts now tell it the customer is not the tech, but review summaries. | Tested with clean synthetic voices; real job sites are noisier."
  },
  {
   "recipe": "voice-memo-to-invoice",
   "trade": "hvac-plumbing",
   "scenario_id": "M3",
   "scenario": "Memo: \"Kevin Tran, annual water heater maintenance. Flushed the tank, lots of sediment came out. The anode rod was...\"",
   "result": "pass",
   "run_date": "2026-10-28T17:14:36+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/voice-memo-to-invoice/test/results.json",
   "limitations": "The AI step is an extractor; matching and prices are plain code. A price book with very different names will need more aliases. | It writes a draft note, not invoice line items, on purpose: a person should approve before billing. | The small test model sometimes mixed up who the customer was in the summary; prompts now tell it the customer is not the tech, but review summaries. | Tested with clean synthetic voices; real job sites are noisier."
  },
  {
   "recipe": "voice-memo-to-invoice",
   "trade": "hvac-plumbing",
   "scenario_id": "M4",
   "scenario": "Memo: \"AC not cooling at the Novak place. Capacitor was bulged, replaced it with a forty five five MFD run...\"",
   "result": "pass",
   "run_date": "2026-10-28T17:14:36+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/voice-memo-to-invoice/test/results.json",
   "limitations": "The AI step is an extractor; matching and prices are plain code. A price book with very different names will need more aliases. | It writes a draft note, not invoice line items, on purpose: a person should approve before billing. | The small test model sometimes mixed up who the customer was in the summary; prompts now tell it the customer is not the tech, but review summaries. | Tested with clean synthetic voices; real job sites are noisier."
  },
  {
   "recipe": "voice-memo-to-invoice",
   "trade": "hvac-plumbing",
   "scenario_id": "M5-silence",
   "scenario": "Silent recording: workflow must stop and write nothing",
   "result": "pass",
   "run_date": "2026-10-28T17:14:36+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/voice-memo-to-invoice/test/results.json",
   "limitations": "The AI step is an extractor; matching and prices are plain code. A price book with very different names will need more aliases. | It writes a draft note, not invoice line items, on purpose: a person should approve before billing. | The small test model sometimes mixed up who the customer was in the summary; prompts now tell it the customer is not the tech, but review summaries. | Tested with clean synthetic voices; real job sites are noisier."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "C1",
   "scenario": "Good call: all info captured, time offered, asked for the booking, booked",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "C2",
   "scenario": "Price shopper: CSR quotes the fee, never offers a time or asks to book",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "C3",
   "scenario": "CSR asks for the booking, customer declines (wants to talk to spouse)",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "C4",
   "scenario": "Offers a time but never actually asks; customer says they'll call back",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "N1-forged-signature",
   "scenario": "N1-forged-signature",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "N2-duplicate-callback",
   "scenario": "N2-duplicate-callback",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "N3-short-hangup",
   "scenario": "N3-short-hangup",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "call-scorecard",
   "trade": "hvac-plumbing",
   "scenario_id": "W1-weekly-summary",
   "scenario": "W1-weekly-summary",
   "result": "pass",
   "run_date": "2026-10-28T16:53:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/call-scorecard/test/results.json",
   "limitations": "No speaker labels: the model infers who is the CSR. Dual-channel recording would make this more reliable. | 4 test calls is a small sample, and the small local model missed 'caller described the problem' on some runs; treat scores as a conversation starter, not a performance review. | Recording and transcribing calls has legal requirements; check yours."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I1",
   "scenario": "New family-law inquiry gets the intake form + booking link in seconds, and a Clio Grow lead",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I2",
   "scenario": "Eviction hearing this week: reply says call now, attorney gets an URGENT alert",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I3",
   "scenario": "Practice area the firm doesn't handle gets a polite decline + bar referral, no booking link",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I4",
   "scenario": "Existing client using the web form is routed to the attorney, not into intake",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I5",
   "scenario": "Bot submission (honeypot filled) is dropped silently",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I6",
   "scenario": "Same person submits twice in 10 minutes: one reply only",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I7",
   "scenario": "Clio rate-limits the contact lookup (429): the workflow waits, retries and still replies",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I8",
   "scenario": "Calendly booking (valid signature) lands on the Clio calendar + attorney heads-up",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I9",
   "scenario": "Forged Calendly call (bad signature) is ignored",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I10",
   "scenario": "Calendly re-delivers the same booking: no duplicate calendar entry",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-inquiry-intake",
   "trade": "law-firms",
   "scenario_id": "I11",
   "scenario": "Bot submission with the hidden company_website (honeypot) field filled gets no reply, no attorney alert and no Clio Grow lead",
   "result": "pass",
   "run_date": "2026-10-28T16:54:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-inquiry-intake/test/results.json",
   "limitations": "The urgency check is a keyword list, not AI. It will miss urgent inquiries phrased differently, and the attorney should still read every new inquiry. | No conflict check is run. The reply says so and invites no confidential details, but someone must run conflicts before the consult. | The workflow keeps its 'already replied' memory in n8n's workflow data; if you re-import the workflow, that memory resets. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B1",
   "scenario": "First sweep: 7-days-late invoice gets a Stripe link, trust request gets the LawPay trust link, 31-days-late invoice goes to the attorney",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B2",
   "scenario": "Second run the same day sends nothing new",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B3",
   "scenario": "A week later: reminder #2 reuses the same link, the newly overdue invoice gets one, and a low trust balance triggers a top-up request",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B4",
   "scenario": "Paid invoice stops; others move one step; top-up re-sent after 7 days",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B5",
   "scenario": "Partial payment: the old single-use link is switched off and the last reminder carries a new link for the new balance",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B6",
   "scenario": "Clio answers 429 (rate limit): the run waits, retries and finishes; T-0007 reaches 30+ days and goes to the attorney",
   "result": "pass",
   "run_date": "2026-10-28T16:54:07+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-invoice-retainer/test/results.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-invoice-retainer-reminders",
   "trade": "law-firms",
   "scenario_id": "B1",
   "scenario": "First sweep: 7-days-late invoice gets a Stripe link, trust request gets the LawPay trust link, 31-days-late invoice goes to the attorney",
   "result": "pass",
   "run_date": "2026-10-27T16:50:17+01:00",
   "mock_or_live": "live Stripe API in test mode; other services mocked",
   "result_file": "recipes/law-invoice-retainer/test/results-live-stripe.json",
   "limitations": "Clio already has its own bill reminders: automated bill reminders, and bill-reminder Workflows (these need Clio Payments). Clio warns those two can double-send, and turning this recipe on as well can mean a client gets the same reminder two or three times. Pick one: switch Clio's reminders off if you use this recipe. | If you use Clio Payments and only need reminders for unpaid bills, Clio's built-in reminders are enough and you don't need this recipe. It adds a 30-day hand-off to the attorney, low-retainer top-up alerts and Stripe links for firms not on Clio Payments. | LawPay payments no longer sync to Clio since the integration ended on Aug 31, 2026; whoever keeps the books has to record them in Clio. | Never send a Stripe link for a retainer or any unearned fee. Stripe takes its fee out of the payment, which most state rules forbid for trust money. | Trust rules differ by state. This is not legal or accounting advice; check your state bar's guidance. | The low-balance threshold is one number for all matters; edit the code node if you need per-matter thresholds."
  },
  {
   "recipe": "law-firm-time-capture",
   "trade": "law-firms",
   "scenario_id": "T1",
   "scenario": "Busy Tuesday: 2 meetings + 2 client emails become draft entries; UTBMS matter, unmatched and internal email are handled safely",
   "result": "pass",
   "run_date": "2026-10-28T16:54:11+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-time-capture/test/results.json",
   "limitations": "Clio has no 'draft' state for time entries. Entries are created unbilled and labeled '[Auto-draft - review before billing]'; review or delete them before you bill. | Email time is a flat amount per message, not the time you actually spent. Adjust EMAIL_MINUTES or edit entries. | It reads up to 200 events, emails and matters per day (one page each); larger firms need pagination. | Phone calls, document drafting and research outside email and calendar are not captured. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-time-capture",
   "trade": "law-firms",
   "scenario_id": "T2",
   "scenario": "Re-running the same day creates no duplicates and sends no email",
   "result": "pass",
   "run_date": "2026-10-28T16:54:11+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-time-capture/test/results.json",
   "limitations": "Clio has no 'draft' state for time entries. Entries are created unbilled and labeled '[Auto-draft - review before billing]'; review or delete them before you bill. | Email time is a flat amount per message, not the time you actually spent. Adjust EMAIL_MINUTES or edit entries. | It reads up to 200 events, emails and matters per day (one page each); larger firms need pagination. | Phone calls, document drafting and research outside email and calendar are not captured. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-time-capture",
   "trade": "law-firms",
   "scenario_id": "T3",
   "scenario": "Monday: 24-minute call rounds up to 0.4 h but its matter needs UTBMS, so it goes to review; the evening email is drafted",
   "result": "pass",
   "run_date": "2026-10-28T16:54:11+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-time-capture/test/results.json",
   "limitations": "Clio has no 'draft' state for time entries. Entries are created unbilled and labeled '[Auto-draft - review before billing]'; review or delete them before you bill. | Email time is a flat amount per message, not the time you actually spent. Adjust EMAIL_MINUTES or edit entries. | It reads up to 200 events, emails and matters per day (one page each); larger firms need pagination. | Phone calls, document drafting and research outside email and calendar are not captured. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-time-capture",
   "trade": "law-firms",
   "scenario_id": "T4",
   "scenario": "Clio rate-limits a call (429): the run retries and finishes; an empty day sends nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:54:11+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-time-capture/test/results.json",
   "limitations": "Clio has no 'draft' state for time entries. Entries are created unbilled and labeled '[Auto-draft - review before billing]'; review or delete them before you bill. | Email time is a flat amount per message, not the time you actually spent. Adjust EMAIL_MINUTES or edit entries. | It reads up to 200 events, emails and matters per day (one page each); larger firms need pagination. | Phone calls, document drafting and research outside email and calendar are not captured. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-time-capture",
   "trade": "law-firms",
   "scenario_id": "T5",
   "scenario": "Client with two open matters: the email is NOT guessed onto one, it is listed for review",
   "result": "pass",
   "run_date": "2026-10-28T16:54:11+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-time-capture/test/results.json",
   "limitations": "Clio has no 'draft' state for time entries. Entries are created unbilled and labeled '[Auto-draft - review before billing]'; review or delete them before you bill. | Email time is a flat amount per message, not the time you actually spent. Adjust EMAIL_MINUTES or edit entries. | It reads up to 200 events, emails and matters per day (one page each); larger firms need pagination. | Phone calls, document drafting and research outside email and calendar are not captured. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-client-status-updates",
   "trade": "law-firms",
   "scenario_id": "U1",
   "scenario": "First run only records where every matter stands - no emails",
   "result": "pass",
   "run_date": "2026-10-28T16:54:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-matter-updates/test/results.json",
   "limitations": "Clio's Core plan and up now advertise AI-drafted client updates. If you already use that, you may not need this. | Emails say only the stage name and a fixed sentence. Anything specific to the case should come from the attorney. | The workflow's memory of what it already sent lives in n8n's workflow data; re-importing the workflow resets it (the next run is a silent baseline again). | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-client-status-updates",
   "trade": "law-firms",
   "scenario_id": "U2",
   "scenario": "Paralegal moves Gonzalez to Settlement drafting: client gets a plain-language update, Clio gets a note",
   "result": "pass",
   "run_date": "2026-10-28T16:54:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-matter-updates/test/results.json",
   "limitations": "Clio's Core plan and up now advertise AI-drafted client updates. If you already use that, you may not need this. | Emails say only the stage name and a fixed sentence. Anything specific to the case should come from the attorney. | The workflow's memory of what it already sent lives in n8n's workflow data; re-importing the workflow resets it (the next run is a silent baseline again). | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-client-status-updates",
   "trade": "law-firms",
   "scenario_id": "U3",
   "scenario": "Nothing changed: no repeat email",
   "result": "pass",
   "run_date": "2026-10-28T16:54:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-matter-updates/test/results.json",
   "limitations": "Clio's Core plan and up now advertise AI-drafted client updates. If you already use that, you may not need this. | Emails say only the stage name and a fixed sentence. Anything specific to the case should come from the attorney. | The workflow's memory of what it already sent lives in n8n's workflow data; re-importing the workflow resets it (the next run is a silent baseline again). | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-client-status-updates",
   "trade": "law-firms",
   "scenario_id": "U4",
   "scenario": "Three weeks of silence: 'still working on it' check-ins to the quiet matters only (Gonzalez was updated 20 days ago)",
   "result": "pass",
   "run_date": "2026-10-28T16:54:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-matter-updates/test/results.json",
   "limitations": "Clio's Core plan and up now advertise AI-drafted client updates. If you already use that, you may not need this. | Emails say only the stage name and a fixed sentence. Anything specific to the case should come from the attorney. | The workflow's memory of what it already sent lives in n8n's workflow data; re-importing the workflow resets it (the next run is a silent baseline again). | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-client-status-updates",
   "trade": "law-firms",
   "scenario_id": "U5",
   "scenario": "Next day: Gonzalez now hits 21 quiet days and gets her check-in; nobody gets a repeat; a Clio 429 mid-run is retried",
   "result": "pass",
   "run_date": "2026-10-28T16:54:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-matter-updates/test/results.json",
   "limitations": "Clio's Core plan and up now advertise AI-drafted client updates. If you already use that, you may not need this. | Emails say only the stage name and a fixed sentence. Anything specific to the case should come from the attorney. | The workflow's memory of what it already sent lives in n8n's workflow data; re-importing the workflow resets it (the next run is a silent baseline again). | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M1",
   "scenario": "Answered call is ignored",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M2",
   "scenario": "Existing client misses us during office hours: personal text (no case details), attorney email, call logged on her open matter in Clio",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M3",
   "scenario": "Same client calls again 2 hours later: no second text",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M4",
   "scenario": "New caller after hours: intake form + booking link, 'don't text details about your case', STOP line; nothing logged in Clio",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M5",
   "scenario": "Silent recording: workflow must stop and write nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M6",
   "scenario": "Anonymous / blocked caller ID is skipped",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M7",
   "scenario": "Caller replies with a question: forwarded to the attorney's phone, no bot answer",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M8",
   "scenario": "Plain-English opt-out ('please stop texting me'): one confirmation, then no text after the next missed call",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M9",
   "scenario": "STOP keyword: no extra confirmation from us (Twilio sends it); START re-subscribes and texts resume",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "law-firm-missed-call-text-back",
   "trade": "law-firms",
   "scenario_id": "M10",
   "scenario": "Clio rate limit (429) during the lookup is retried; the client still gets the text and the call is logged",
   "result": "pass",
   "run_date": "2026-10-28T16:54:26+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/law-missed-call/test/results.json",
   "limitations": "Twilio's X-Twilio-Signature is checked against PUBLIC_WEBHOOK_BASE plus the webhook path. That value must match the public URL you give Twilio exactly (scheme, host, path, no trailing slash), or every real callback is rejected as forged. | Texting clients may be subject to your state's advertising and confidentiality rules; keep texts free of case details, as this workflow does. | The new-caller text is 2 SMS segments, so it costs twice a 1-segment text. | These workflows are tools, not legal advice. Check your state's rules on advertising, client communication, trust accounting and texting before you turn one on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T1",
   "scenario": "New caller, office hours: generic text with booking link, callback row, no Open Dental write",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T2",
   "scenario": "Family number after hours (mom's cell, kids' home phone): same generic text, emergency line, no names; commlog on guarantor",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T3",
   "scenario": "Same caller again 1 h later: no second text (one per 12 h)",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T4",
   "scenario": "Patient who opted out of texts (TxtMsgOk = No): no text, call-only callback row, phone commlog",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T5",
   "scenario": "Answered call: nothing happens",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T6",
   "scenario": "STOP keyword: TxtMsgOk = No on every chart with that number (3 family members); no extra confirmation (Twilio sends it)",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T7",
   "scenario": "Plain-English opt-out: Open Dental updated and one confirmation text",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T8",
   "scenario": "Ordinary reply: stored in the replies sheet; staff ping carries no message content",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T9",
   "scenario": "Forged webhook (bad X-Twilio-Signature): ignored, nothing sent or read",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-missed-call-text-back",
   "trade": "dental",
   "scenario_id": "T10",
   "scenario": "Open Dental rate limit (429 + Retry-After) during lookup: waits and finishes",
   "result": "pass",
   "run_date": "2026-10-28T16:54:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-missed-call-text-back/test/results.json",
   "limitations": "The text never says who the practice thinks called. If staff want to call back, they look the number up in Open Dental themselves. | Opt-out phrases are matched from a list; unusual wordings can slip through, so skim the replies Sheet. Twilio's own keyword handling (STOP, END, CANCEL...) always applies. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-unscheduled-treatment-follow-up",
   "trade": "dental",
   "scenario_id": "U1",
   "scenario": "First weekly run: call list for every unbooked plan; generic text only to TxtMsgOk = Yes; patients with a future visit, inactive and just-presented plans skipped",
   "result": "pass",
   "run_date": "2026-10-28T16:54:43+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-unscheduled-treatment-follow-up/test/results.json",
   "limitations": "The call list is the main output: a text is a reminder to book, not a treatment conversation. Fees and codes appear only in the staff Sheet. | Insurance-driven delays (waiting for the new benefit year) are not detected; the coordinator should mark those plans. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-unscheduled-treatment-follow-up",
   "trade": "dental",
   "scenario_id": "U2",
   "scenario": "A week later: visits on Nov 5 are past but the plan is still open -> those patients join the list; already-texted wait 30 days",
   "result": "pass",
   "run_date": "2026-10-28T16:54:43+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-unscheduled-treatment-follow-up/test/results.json",
   "limitations": "The call list is the main output: a text is a reminder to book, not a treatment conversation. Fees and codes appear only in the staff Sheet. | Insurance-driven delays (waiting for the new benefit year) are not detected; the coordinator should mark those plans. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-unscheduled-treatment-follow-up",
   "trade": "dental",
   "scenario_id": "U3",
   "scenario": "Dec 3: patient who booked drops off; patient who replied is call-only; plans whose visit passed or that aged past 14 days get a first text; second text to the rest",
   "result": "pass",
   "run_date": "2026-10-28T16:54:43+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-unscheduled-treatment-follow-up/test/results.json",
   "limitations": "The call list is the main output: a text is a reminder to book, not a treatment conversation. Fees and codes appear only in the staff Sheet. | Insurance-driven delays (waiting for the new benefit year) are not detected; the coordinator should mark those plans. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-unscheduled-treatment-follow-up",
   "trade": "dental",
   "scenario_id": "U4",
   "scenario": "Jan 4: after two texts it is call only, never a third text",
   "result": "pass",
   "run_date": "2026-10-28T16:54:43+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-unscheduled-treatment-follow-up/test/results.json",
   "limitations": "The call list is the main output: a text is a reminder to book, not a treatment conversation. Fees and codes appear only in the staff Sheet. | Insurance-driven delays (waiting for the new benefit year) are not detected; the coordinator should mark those plans. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-unscheduled-treatment-follow-up",
   "trade": "dental",
   "scenario_id": "U5",
   "scenario": "Frequency cap shared with the other recipes (missed-call text 2 h earlier) + Open Dental 429 handled",
   "result": "pass",
   "run_date": "2026-10-28T16:54:43+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-unscheduled-treatment-follow-up/test/results.json",
   "limitations": "The call list is the main output: a text is a reminder to book, not a treatment conversation. Fees and codes appear only in the staff Sheet. | Insurance-driven delays (waiting for the new benefit year) are not detected; the coordinator should mark those plans. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-overdue-recall-reactivation",
   "trade": "dental",
   "scenario_id": "R1",
   "scenario": "Overdue recalls: one text per family phone (two kids, one number), call list for no-consent / 3-reminder patients, booked and recently reminded skipped",
   "result": "pass",
   "run_date": "2026-10-28T16:54:50+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-overdue-recall-reactivation/test/results.json",
   "limitations": "Reactivation texts to patients who have not been in for a long time may be closer to marketing than to a treatment reminder. Your compliance officer should decide the lookback window. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-overdue-recall-reactivation",
   "trade": "dental",
   "scenario_id": "R2",
   "scenario": "Next day: nothing new (14-day gap, daily cap)",
   "result": "pass",
   "run_date": "2026-10-28T16:54:50+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-overdue-recall-reactivation/test/results.json",
   "limitations": "Reactivation texts to patients who have not been in for a long time may be closer to marketing than to a treatment reminder. Your compliance officer should decide the lookback window. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-overdue-recall-reactivation",
   "trade": "dental",
   "scenario_id": "R3",
   "scenario": "Two weeks on: family texted STOP (Open Dental TxtMsgOk = No) -> call only; patient who replied -> call only; 2nd reminder to others",
   "result": "pass",
   "run_date": "2026-10-28T16:54:50+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-overdue-recall-reactivation/test/results.json",
   "limitations": "Reactivation texts to patients who have not been in for a long time may be closer to marketing than to a treatment reminder. Your compliance officer should decide the lookback window. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-overdue-recall-reactivation",
   "trade": "dental",
   "scenario_id": "R4",
   "scenario": "Patient books (appointment added): drops off the list; 429 from Open Dental handled",
   "result": "pass",
   "run_date": "2026-10-28T16:54:50+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-overdue-recall-reactivation/test/results.json",
   "limitations": "Reactivation texts to patients who have not been in for a long time may be closer to marketing than to a treatment reminder. Your compliance officer should decide the lookback window. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V1",
   "scenario": "End of day: everyone with a completed visit and text consent gets the same generic request (no pre-screen, no incentive); no consent -> not asked",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V2",
   "scenario": "Same day re-run: nobody asked twice",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V3",
   "scenario": "Two kids on one parent's number: one text; returning patient within a year: not asked again",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V4",
   "scenario": "1-star review + risky staff draft: privacy-safe template, every risky phrase flagged, emailed to the office manager; Open Dental never queried",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V5",
   "scenario": "5-star review, safe draft: thank-you template, draft passes",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-review-request-and-response-guard",
   "trade": "dental",
   "scenario_id": "V6",
   "scenario": "Review webhook without the shared-secret header: ignored",
   "result": "pass",
   "run_date": "2026-10-28T16:54:53+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-review-request-and-response-guard/test/results.json",
   "limitations": "The phrase check is a list of patterns, not a privacy review. It catches common slips (your visit, your crown, a date, an amount, the reviewer's name) and will miss others. A person must read every reply before posting. | Nothing is posted to Google or any site; the office manager posts by hand. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-insurance-verification-prep",
   "trade": "dental",
   "scenario_id": "I1",
   "scenario": "Monday 7 am, visits on Thursday: active, low remaining maximum, inactive, payer error (bad member ID), no insurance",
   "result": "pass",
   "run_date": "2026-10-28T16:54:58+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-insurance-verification-prep/test/results.json",
   "limitations": "No patient cost text. A cost estimate is billing information (PHI) and isn't one of the TCPA's exempted healthcare messages, so estimates stay a staff conversation. (Our keyword plan described this as a no-payer-call checklist; we chose a real eligibility check through Stedi instead, mocked in our tests.) | An eligibility response is not a guarantee of payment. Payers can still deny a claim. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-insurance-verification-prep",
   "trade": "dental",
   "scenario_id": "I2",
   "scenario": "Re-run the same morning: no second (billable) eligibility call",
   "result": "pass",
   "run_date": "2026-10-28T16:54:58+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-insurance-verification-prep/test/results.json",
   "limitations": "No patient cost text. A cost estimate is billing information (PHI) and isn't one of the TCPA's exempted healthcare messages, so estimates stay a staff conversation. (Our keyword plan described this as a no-payer-call checklist; we chose a real eligibility check through Stedi instead, mocked in our tests.) | An eligibility response is not a guarantee of payment. Payers can still deny a claim. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-insurance-verification-prep",
   "trade": "dental",
   "scenario_id": "I3",
   "scenario": "Child on a parent's plan: request carries the subscriber's member ID + a dependent block",
   "result": "pass",
   "run_date": "2026-10-28T16:54:58+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-insurance-verification-prep/test/results.json",
   "limitations": "No patient cost text. A cost estimate is billing information (PHI) and isn't one of the TCPA's exempted healthcare messages, so estimates stay a staff conversation. (Our keyword plan described this as a no-payer-call checklist; we chose a real eligibility check through Stedi instead, mocked in our tests.) | An eligibility response is not a guarantee of payment. Payers can still deny a claim. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "dental-insurance-verification-prep",
   "trade": "dental",
   "scenario_id": "I4",
   "scenario": "Missing birth date -> Stedi 400 shown as 'check failed' (no crash, nothing marked verified); Open Dental 429 retried",
   "result": "pass",
   "run_date": "2026-10-28T16:54:58+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/dental-insurance-verification-prep/test/results.json",
   "limitations": "No patient cost text. A cost estimate is billing information (PHI) and isn't one of the TCPA's exempted healthcare messages, so estimates stay a staff conversation. (Our keyword plan described this as a no-payer-call checklist; we chose a real eligibility check through Stedi instead, mocked in our tests.) | An eligibility response is not a guarantee of payment. Payers can still deny a claim. | Built for Open Dental only. Dentrix, Eaglesoft, Curve and NexHealth versions are not built, and we make no claim that this works with them. | Business associate agreements are your job: self-host n8n on infrastructure covered by a BAA (we found no BAA for n8n Cloud: its Trust Center doesn't list HIPAA, and the forum reply saying there is none came from a community Top Supporter, not n8n staff), accept Google's Workspace BAA before any patient name goes into a Sheet, and ask your compliance officer whether your texting setup needs Twilio's HIPAA offering (Security or Enterprise Edition plus a BAA, sales-quoted). Patient replies can contain health details even when our texts do not. | Not a compliance guarantee. We designed around HIPAA and the TCPA (generic texts with no treatment, fee or name; consent from Open Dental; staff lists kept in BAA-covered Google Workspace), but whether your setup is compliant depends on your contracts, your server and how your staff use it. Check with your compliance officer or counsel and your state dental board before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L1",
   "scenario": "New lead with recorded text consent (TX, 10:00): email + text naming agent and brokerage, agent alert, FUB note",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L2",
   "scenario": "New lead without text consent: email only; the agent alert says why no text",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L4",
   "scenario": "Forged FUB-Signature is dropped; the same signed event delivered twice (FUB retries) is handled once",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L5",
   "scenario": "STOP from a lead: opt-out ledger row, FUB tag Do Not Text (mergeTags=true), note; no extra confirmation text. A normal reply alerts the agent",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L8",
   "scenario": "Forged X-Twilio-Signature on an inbound text: ignored",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L7",
   "scenario": "FUB rate limit (429 + Retry-After) on the read: waits and retries. Bulk-imported old lead (created 3 days ago) gets no auto-reply",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L3",
   "scenario": "California lead at 10:30 pm Central (8:30 pm Pacific): email now, text held for quiet hours; still held at 8:00 Central (6:00 Pacific)",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L6",
   "scenario": "Next day: Cara's held text goes out at 11:15 Central; Ana (no contact, opted out of texts) gets one follow-up email + agent nudge + FUB call task; Ben (contacted), Dee (replied) and Eve (agent texted) get nothing more; Cara gets her one follow-up 24 h after the first touch",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-lead-auto-reply",
   "trade": "real-estate",
   "scenario_id": "L9",
   "scenario": "Visitor created by the open-house recipe (source 'Open House'): no second auto-reply from this workflow",
   "result": "pass",
   "run_date": "2026-10-28T16:55:13+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lead-auto-reply/test/results.json",
   "limitations": "It replies with fixed wording: it doesn't answer questions about a property. The point is to acknowledge fast and get you on the phone. | Consent is only as good as your form. Leads bought from third parties often arrive without consent you can rely on; they get email only unless your consent field is set. | The time zone comes from the lead's state; for states with two zones it waits until it is 8 am in both. A lead with no state uses your own time zone. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C2",
   "scenario": "dotloop loop id without confirmation: reads the loop (token expired -> refresh -> retry), emails the TC the dates to check with a pre-filled link; no calendar writes",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C1",
   "scenario": "Confirmed manual entry: 7 all-day events (email 3 days + popup 1 day before, agent + TC invited, sendUpdates=all), summary + .ics; Saturday and Thanksgiving flagged but not moved",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C3",
   "scenario": "Bad input: inspection after closing, an unparseable date, and no 'confirmed' tick: nothing written, one email listing every problem",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C4",
   "scenario": "Amendment moves closing to Dec 18: one PATCH of the existing event (no duplicate), summary shows old -> new",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C5",
   "scenario": "Same form submitted again: no calendar calls, 'no changes' email",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C6",
   "scenario": "Honeypot filled, then wrong form key: both ignored",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C7",
   "scenario": "Daily digest Nov 10: lists inspection (Nov 12) only; second run the same day sends nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-contract-deadline-calendar",
   "trade": "real-estate",
   "scenario_id": "C8",
   "scenario": "Deal terminated: all 7 events deleted with sendUpdates=all; later digests skip it",
   "result": "pass",
   "run_date": "2026-10-28T16:55:19+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-contract-deadline-calendar/test/results.json",
   "limitations": "It never reads dates out of a contract by itself: a person types or confirms every date. That is deliberate; a misread date is worse than none. | Holiday and weekend handling differs by state form and contract. We flag those dates; we don't move them. Check your contract's definition of days. | Built for Google Calendar. Outlook, SkySlope and other transaction tools are not built. | Not legal advice. Your contract and your broker decide what each deadline means."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S1",
   "scenario": "Tuesday: one status request per open transaction and party ([TX-id] in subject, reply-to the receiving address, TC cc'd); closed and past-closing files skipped",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S2",
   "scenario": "Tuesday run again: nothing re-sent",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S3",
   "scenario": "Lender replies 'clear to close' above the quoted request: verified, body fetched, quote stripped, row saved, agent texted",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S4",
   "scenario": "Forged Svix signature: dropped before any fetch. Valid webhook from an address not on file: not recorded, agent told",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S5",
   "scenario": "Thursday: nudge only parties with no reply (title on both files, not the lender), plus one agent summary",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S6",
   "scenario": "Title replies that closing may be pushed: delay alert text to the agent",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-lender-title-status-chase",
   "trade": "real-estate",
   "scenario_id": "S7",
   "scenario": "Friday: one client-update DRAFT per file to the agent only (client not emailed); draft has fixed-phrase status + wire-fraud reminder, lender wording kept separate",
   "result": "pass",
   "run_date": "2026-10-28T16:55:33+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-lender-title-status-chase/test/results.json",
   "limitations": "Status words are matched from a list ('clear to close', 'delay', 'pushed'...). It can miss unusual wording, so skim the replies Sheet. | Never put wiring instructions or account numbers in these emails, and never act on wiring instructions received by email; call a known number to confirm. | Lenders' and title companies' own portals may already give you this status; this recipe is for the ones that answer only by email. | Not legal advice. Your broker's policies decide what you may share with clients."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O1",
   "scenario": "Four sign-ins become Follow Up Boss 'Visited Open House' events; consent recorded only when the box was ticked; nothing sent yet",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O2",
   "scenario": "Honeypot, wrong form key, wrong-day sign-in and a double tap: all dropped",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O3",
   "scenario": "Before 2 h nothing; at 2 h: thank-you emails to all four, a text only to Ana (consent, no agent); Ben gets an agent-respectful note",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O4",
   "scenario": "Late sign-in at 18:30 (Eve, consent): thank-you email at 20:30, text held by quiet hours (TX spans Central and Mountain, so 9 am Mountain = 10 am Central): not at 9:05, sent at 10:05 Sunday",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O5",
   "scenario": "Monday 10 am follow-up: Ana email only (texted STOP), Cy and Eve follow up, Dee skipped (agent made contact), Ben nothing; call tasks added",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-open-house-follow-up",
   "trade": "real-estate",
   "scenario_id": "O6",
   "scenario": "Later ticks: nothing more (max two touches)",
   "result": "pass",
   "run_date": "2026-10-28T16:55:29+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-open-house-follow-up/test/results.json",
   "limitations": "A visitor who says they already work with an agent gets one thank-you email and nothing more. Don't change that to solicit them; see NAR Standard of Practice 16-13 and your local rules. | The tablet form needs internet at the house. Paper sign-ins must be typed in later. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A1",
   "scenario": "Nov 9: 5-year email to Pat (with text: consent on file), Uma email only (no consent); Quinn opted out, Lou not a past client, Ty closed this year; Rae's call task 3 days early; 112 people paged",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A2",
   "scenario": "Run again the same day: nothing repeated",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A3",
   "scenario": "Unsubscribe: GET only shows a confirm button (safe against link scanners); POST tags Email Opt-Out with mergeTags; forged token changes nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A4",
   "scenario": "Nov 12: Rae's 6-year email",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A5",
   "scenario": "Leap day: Sol (closed Feb 29, 2024) gets a task on Feb 25 and the email on Feb 28, 2027; nothing on Mar 1",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "real-estate-past-client-anniversary",
   "trade": "real-estate",
   "scenario_id": "A6",
   "scenario": "Next year: Pat (unsubscribed) gets no email; Uma still does; Ty now reaches year 1",
   "result": "pass",
   "run_date": "2026-10-28T16:55:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/real-estate-past-client-anniversary/test/results.json",
   "limitations": "The message is the same short template for everyone. It's a reason for you to call, not a substitute for it. | If an email contains an offer (like a home-value check), the FTC may treat it as commercial email; ask your broker whether you need an ad label. | Built for Follow Up Boss only. kvCORE/BoldTrail, Lofty, Sierra and other CRMs are not built, and we make no claim that this works with them. | Not legal advice and not a compliance guarantee. We designed around the TCPA (texts only with recorded written consent, 8 am-9 pm in the lead's time zone, STOP honored at once), CAN-SPAM and state advertising rules (every message names you and your brokerage), but whether your use is lawful depends on your consent wording, your lead sources, your state and your broker's policies. Have your broker or a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C1",
   "scenario": "Day 0: one email per client listing every missing item, portal link only, account number masked; paused client skipped; client with no email -> preparer told",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C2",
   "scenario": "Same day again: nothing re-sent",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C3",
   "scenario": "Day 3: Ben uploaded his only item -> nothing to Ben; Ava gets reminder 2",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C4",
   "scenario": "Missed days are not bunched: run on day 10 sends ONE reminder listing only the item still missing",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C5",
   "scenario": "Day 14: final reminder + preparer escalation + Karbon note on the work item (Karbon 429 first: Retry-After honored)",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C6",
   "scenario": "After the ladder: no more client email; when the last item arrives the preparer gets one 'all received' note",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-document-chase-ladder",
   "trade": "accounting-bookkeeping",
   "scenario_id": "C7",
   "scenario": "TaxDome source (read-only API v4, page size 1 -> cursor paging, one 429): pending checklist items only, uploaded ones left out, contact email used",
   "result": "pass",
   "run_date": "2026-10-28T16:55:48+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-document-chase-ladder/test/results.json",
   "limitations": "It only knows what's on the list. Someone at the firm still marks items received (or TaxDome does when the client uploads). | If Karbon or TaxDome client requests already remind your clients, turn one of them off so clients don't get two sets of reminders. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q1",
   "scenario": "Monday: expired QuickBooks token refreshed by n8n's OAuth2 credential, one 429 retried, paged queries; ONE client email with the 5 suspense lines (split line only), old txn out, card number masked",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q2",
   "scenario": "Same week again: nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q3",
   "scenario": "Form link: tampered token -> 403; real link -> form with 5 questions, bank memo HTML-escaped",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q4",
   "scenario": "Client answers 3 of 5: bookkeeper emailed, Karbon note on the client organization, thank-you page; QuickBooks untouched; posting twice does not resend",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q5",
   "scenario": "Next Monday: only the 2 unanswered + 1 new transaction are asked; answered ones are not",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "bookkeeping-uncategorized-transactions-questions",
   "trade": "accounting-bookkeeping",
   "scenario_id": "Q6",
   "scenario": "Lines recategorized in QuickBooks drop out; after 3 unanswered asks the bookkeeper is told instead of nagging the client again",
   "result": "pass",
   "run_date": "2026-10-28T16:56:01+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/bookkeeping-uncategorized-transactions-questions/test/results.json",
   "limitations": "It looks at expenses (Purchase) and deposits only, not journal entries, transfers or bank-feed items you haven't added yet ('For review'). Those still need the bank-feed screen. | It doesn't suggest a category. The bookkeeper decides, using the client's answer. | One workflow copy per client company (QuickBooks connects one company per credential). | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "tax-organizer-checklist-from-prior-year",
   "trade": "accounting-bookkeeping",
   "scenario_id": "O1",
   "scenario": "Jan 10: one 2026 checklist per client from last year's documents (account number hidden), life-change questions, rows added for the chase ladder; Karbon work item opened only where none exists (one 429 retried)",
   "result": "pass",
   "run_date": "2026-10-28T16:56:04+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/tax-organizer-checklist-from-prior-year/test/results.json",
   "limitations": "It only expects what the client sent last year. New income (a new job, crypto, a home sale) relies on the client answering the life-change questions. | Rule-based, no AI: the document type names are matched from a fixed list, so unusual labels show as you typed them. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "tax-organizer-checklist-from-prior-year",
   "trade": "accounting-bookkeeping",
   "scenario_id": "O2",
   "scenario": "Run again: nothing duplicated",
   "result": "pass",
   "run_date": "2026-10-28T16:56:04+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/tax-organizer-checklist-from-prior-year/test/results.json",
   "limitations": "It only expects what the client sent last year. New income (a new job, crypto, a home sale) relies on the client answering the life-change questions. | Rule-based, no AI: the document type names are matched from a fixed list, so unusual labels show as you typed them. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "tax-organizer-checklist-from-prior-year",
   "trade": "accounting-bookkeeping",
   "scenario_id": "O3",
   "scenario": "Hand-off: the document chase ladder (recipe 1) picks the new rows up the next weekday",
   "result": "pass",
   "run_date": "2026-10-28T16:56:04+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/tax-organizer-checklist-from-prior-year/test/results.json",
   "limitations": "It only expects what the client sent last year. New income (a new job, crypto, a home sale) relies on the client answering the life-change questions. | Rule-based, no AI: the document type names are matched from a fixed list, so unusual labels show as you typed them. | Emails ask for documents through your client portal, never as attachments. Before client-supplied text goes into an email, a Karbon note or a work item, this recipe applies the same rule as our chase ladder, uncategorized-transactions, organizer and digest recipes: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) are replaced with [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766; an SSN typed without dashes shows as its last 4). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. That is a safety net, not a guarantee: n8n's own execution log still keeps the unmasked rows it read (14 days by default). Keep those numbers out of the Google Sheet too. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I1",
   "scenario": "Nov 3: expired token refreshed, one 429 retried, paged query; 3-day reminder with QuickBooks pay link (Ava), 10-day reminder showing partial payment (Fernway), reply-to-pay wording when online pay is off (Delta Dental Lab); paid and not-yet-due invoices untouched",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I2",
   "scenario": "Same day again: nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I3",
   "scenario": "Nov 10: invoice paused in the sheet (dispute) skipped; Ava 10-day; Fernway day 21 -> final reminder (one email, not bunched)",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I4",
   "scenario": "Nov 12: overdue invoice with no billing email -> partner told once, no customer email",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I5",
   "scenario": "Nov 20: Fernway 31 days -> partner alert once, no more customer email; Ava day 20 final reminder; next day nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I6",
   "scenario": "Invoice paid in QuickBooks (balance 0): drops out of the query, nothing sent",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-invoice-reminders",
   "trade": "accounting-bookkeeping",
   "scenario_id": "I7",
   "scenario": "Customer name in QuickBooks carries an SSN-style number and an account number: masked in the client reminder and in the partner alert (same scrub rule as every accounting recipe)",
   "result": "pass",
   "run_date": "2026-10-28T16:56:14+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-invoice-reminders/test/results.json",
   "limitations": "Reads QuickBooks only. If you bill from Karbon, TaxDome or another tool, its own reminders are the place to start. | It doesn't add late fees, pause work or send anything your engagement letter doesn't already allow. What you do at 30 days is the partner's call. | Email only. Texting clients would need TCPA consent, which this recipe doesn't collect. | Customer names from QuickBooks are masked before they go into a reminder or the partner alert: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-waiting-on-client-digest",
   "trade": "accounting-bookkeeping",
   "scenario_id": "W1",
   "scenario": "Monday: Karbon 'Waiting' work items (OData filter, $top 2 + @odata.nextLink paging, one 429) + outstanding documents -> one digest per person, oldest first, near deadlines flagged; partner summary; no client email",
   "result": "pass",
   "run_date": "2026-10-28T16:56:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-waiting-on-client-digest/test/results.json",
   "limitations": "It reports; it doesn't chase. Client reminders come from the chase ladder recipe or your practice-management tool. | Built for Karbon work items. Financial Cents, Canopy and other tools are not built. | The digest contains client names and open items, so send it only to firm addresses with MFA on. Each outstanding document item is masked before it goes into a digest: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). Client names and Karbon work item titles are shown as they are in Karbon. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-waiting-on-client-digest",
   "trade": "accounting-bookkeeping",
   "scenario_id": "W2",
   "scenario": "Same week again: nothing",
   "result": "pass",
   "run_date": "2026-10-28T16:56:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-waiting-on-client-digest/test/results.json",
   "limitations": "It reports; it doesn't chase. Client reminders come from the chase ladder recipe or your practice-management tool. | Built for Karbon work items. Financial Cents, Canopy and other tools are not built. | The digest contains client names and open items, so send it only to firm addresses with MFA on. Each outstanding document item is masked before it goes into a digest: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). Client names and Karbon work item titles are shown as they are in Karbon. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "accounting-waiting-on-client-digest",
   "trade": "accounting-bookkeeping",
   "scenario_id": "W3",
   "scenario": "TaxDome as the document source (read-only, cursor paging): pending checklist items grouped under the assigned employee",
   "result": "pass",
   "run_date": "2026-10-28T16:56:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/accounting-waiting-on-client-digest/test/results.json",
   "limitations": "It reports; it doesn't chase. Client reminders come from the chase ladder recipe or your practice-management tool. | Built for Karbon work items. Financial Cents, Canopy and other tools are not built. | The digest contains client names and open items, so send it only to firm addresses with MFA on. Each outstanding document item is masked before it goes into a digest: numbers written like an SSN or ITIN (123-45-6789 or 123 45 6789) or an EIN (12-3456789) become [removed], and any other unbroken run of 5 or more digits is cut to its last 4 (99887766 becomes *7766). Runs of 4 digits or fewer, such as years and form numbers, are left as they are. It's the same rule (and the same code) as the chase ladder, uncategorized-transactions and organizer recipes. A safety net, not a guarantee: n8n's own execution log still keeps the unmasked data it read (14 days by default). Client names and Karbon work item titles are shown as they are in Karbon. | Not legal or professional-standards advice, and not a compliance guarantee. Tax preparers are covered by the FTC Safeguards Rule (16 CFR 314), which asks for encryption in transit and at rest (314.4(c)(3)), multi-factor authentication for anyone accessing an information system (314.4(c)(5)) and oversight of service providers (314.4(f)); n8n, its server, Resend, Google and Karbon/TaxDome are service providers to list in your written information security plan (IRS Pub 4557 and 5708). Section 7216 limits how you use and disclose tax return information. Check with counsel and your state board before you turn this on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F1",
   "scenario": "Due but outside 8 a.m.-9 p.m. homeowner time (9:30 p.m. Missouri): nothing goes to homeowners; the job with no phone or email becomes a rep task (internal, any hour)",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F2",
   "scenario": "Day 2 at 9 a.m. (JobNimbus answers 429 twice first): text to the consented homeowner, emails to the others, late import gets only its latest due touch, no duplicate rep task, one JobNimbus note per message",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F3",
   "scenario": "Next run 15 minutes later: nothing is sent twice",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F4",
   "scenario": "Ortiz replies (office alerted, JobNimbus note); Natarajan texts 'stop texting me' (opt-out row, consent field set to No, one confirmation); forged signature ignored",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F5",
   "scenario": "Day 7: replied, opted-out and status-changed jobs stop; only Henning gets email #2",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F6",
   "scenario": "Message lint: a rep's custom line promising to cover the deductible blocks the text; office alerted, JobNimbus note explains",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-estimate-follow-up",
   "trade": "roofing",
   "scenario_id": "F7",
   "scenario": "Day 14 then day 21: Henning gets email #3, then a JobNimbus task for the rep; no 4th message",
   "result": "pass",
   "run_date": "2026-10-28T17:05:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-estimate-follow-up/test/results.json",
   "limitations": "Fixed wording only. It doesn't answer questions about the estimate; the point is to get the homeowner talking to the rep. | It can't tell why a homeowner went quiet. A homeowner who signed on paper but whose job status wasn't updated will still get the next touch, so keep statuses current. | Time zones come from the job's state; a state with two time zones waits until it is 8 a.m. in both. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S1",
   "scenario": "Missed call (no-answer): one text asking for address, ZIP and the word LEAK; missed-call row; wording passes the lint",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S2",
   "scenario": "Answered call: nothing. Same caller missed again within 12 hours: logged, no second text. Forged signature: dropped",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S3",
   "scenario": "New caller replies with address, ZIP and a leak: JobNimbus contact (Lead) + ACTIVE LEAK task, on-call phone texted, caller acknowledged, not queued",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S4",
   "scenario": "Existing JobNimbus customer (Ortiz) misses us and replies without a leak: no duplicate contact, notes on her jobs, callback task, queued by ZIP",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S5",
   "scenario": "Another new caller (JobNimbus answers 429 once), then the hourly digest emails the office the queue grouped by ZIP; next digest sends nothing",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-storm-missed-call-text-back",
   "trade": "roofing",
   "scenario_id": "S6",
   "scenario": "STOP from a caller: opt-out row, no confirmation text; a later missed call from that number gets no text. A later message from a queued caller goes to the office",
   "result": "pass",
   "run_date": "2026-10-28T17:04:38+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-storm-missed-call-text-back/test/results.json",
   "limitations": "It doesn't diagnose anything or promise a time. The texts only collect an address and whether water is coming in. | Callers who don't text back still need a call; the missed-call Sheet lists them. | Plain-English opt-outs ('stop texting me') are also recorded, but the TCPA lets people revoke consent in any reasonable way; train the office to log spoken requests too. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-companycam-inspection-report",
   "trade": "roofing",
   "scenario_id": "R1",
   "scenario": "Wrong form key: nothing is read or sent",
   "result": "pass",
   "run_date": "2026-10-28T17:04:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-companycam-inspection-report/test/results.json",
   "limitations": "It is not an estimate, a coverage opinion or a damage determination, and it doesn't write supplements or Xactimate line items. | Sharing documentation with an insurer can touch state public-adjuster rules (for example Texas Insurance Code 4102.163 and Florida Statutes 489.147). The packet's footer says so; share it only when the homeowner asks and your state allows it. | Photo order depends on your tags. Untagged photos go in an 'Other photos' section at the end. | The packet is a plain-text email with photo links, not a PDF. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-companycam-inspection-report",
   "trade": "roofing",
   "scenario_id": "R2",
   "scenario": "Delgado hail job, Oct 18-28 (CompanyCam answers 429 once, 4 photos per page): packet emailed to the office only, sections in order, internal photo and September photo left out, risky caption and rep note held for review, disclaimer, JobNimbus note and CompanyCam comment",
   "result": "pass",
   "run_date": "2026-10-28T17:04:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-companycam-inspection-report/test/results.json",
   "limitations": "It is not an estimate, a coverage opinion or a damage determination, and it doesn't write supplements or Xactimate line items. | Sharing documentation with an insurer can touch state public-adjuster rules (for example Texas Insurance Code 4102.163 and Florida Statutes 489.147). The packet's footer says so; share it only when the homeowner asks and your state allows it. | Photo order depends on your tags. Untagged photos go in an 'Other photos' section at the end. | The packet is a plain-text email with photo links, not a PDF. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-companycam-inspection-report",
   "trade": "roofing",
   "scenario_id": "R3",
   "scenario": "Job with no photos in range (Becker, project 90002): office told why, no note, no comment",
   "result": "pass",
   "run_date": "2026-10-28T17:04:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-companycam-inspection-report/test/results.json",
   "limitations": "It is not an estimate, a coverage opinion or a damage determination, and it doesn't write supplements or Xactimate line items. | Sharing documentation with an insurer can touch state public-adjuster rules (for example Texas Insurance Code 4102.163 and Florida Statutes 489.147). The packet's footer says so; share it only when the homeowner asks and your state allows it. | Photo order depends on your tags. Untagged photos go in an 'Other photos' section at the end. | The packet is a plain-text email with photo links, not a PDF. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-companycam-inspection-report",
   "trade": "roofing",
   "scenario_id": "R4",
   "scenario": "Job without a CompanyCam Project ID (Ortiz estimate): office told which field to fill, CompanyCam never called",
   "result": "pass",
   "run_date": "2026-10-28T17:04:41+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-companycam-inspection-report/test/results.json",
   "limitations": "It is not an estimate, a coverage opinion or a damage determination, and it doesn't write supplements or Xactimate line items. | Sharing documentation with an insurer can touch state public-adjuster rules (for example Texas Insurance Code 4102.163 and Florida Statutes 489.147). The packet's footer says so; share it only when the homeowner asks and your state allows it. | Photo order depends on your tags. Untagged photos go in an 'Other photos' section at the end. | The packet is a plain-text email with photo links, not a PDF. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M1",
   "scenario": "Webhook with the wrong URL key: AccuLynx is never called, nothing sent",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M2",
   "scenario": "Fenn job completed (AccuLynx answers 429 once): milestone re-read, completion text to her mobile, logged on the AccuLynx job; the same eventId again does nothing",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M3",
   "scenario": "Stale event (says Completed, AccuLynx says Approved) is ignored; real Approved event at 10 p.m. waits for 8 a.m.",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M4",
   "scenario": "Hale (home phone only) gets the completion update by email; Vogel (no mobile, no email) becomes an office alert",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M5",
   "scenario": "Silent recording: workflow must stop and write nothing",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-milestone-updates-review-request",
   "trade": "roofing",
   "scenario_id": "M6",
   "scenario": "Park opts out by text, job completed: update goes by email; then the job is reopened before day 2, so no review request",
   "result": "pass",
   "run_date": "2026-10-28T17:05:09+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-milestone-updates-review-request/test/results.json",
   "limitations": "Only Approved and Completed send homeowner updates. Other milestones are ignored unless you add wording for them. | The FTC's rule on consumer reviews (16 CFR 465) bans, among other things, incentives tied to a positive review and suppressing negative ones. This recipe sends the same request to every finished job and offers nothing for a review; don't add a filter that only asks happy customers. | Built for AccuLynx. JobNimbus and Roofr versions are not built. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent. | Not legal advice and not a compliance guarantee. We designed around 47 CFR 64.1200 (texts only with consent you record, 8 a.m. to 9 p.m. in the homeowner's time zone, opt-out words honored) and around state rules that bar contractors from acting as public adjusters, but whether your use is lawful depends on your consent wording, your state and your city. Have a lawyer review the wording before you turn it on."
  },
  {
   "recipe": "roofing-crew-daily-photo-log",
   "trade": "roofing",
   "scenario_id": "P1",
   "scenario": "CompanyCam webhook with a bad signature: ignored",
   "result": "pass",
   "run_date": "2026-10-28T17:07:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-crew-daily-photo-log/test/results.json",
   "limitations": "Captions are checked against a word list. It can miss unusual wording, so the office should still skim updates for the first weeks. | Homeowner emails link to CompanyCam photo URLs; check your CompanyCam sharing settings before turning updates on. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-crew-daily-photo-log",
   "trade": "roofing",
   "scenario_id": "P2",
   "scenario": "First photo on the Ortiz garage job (9:15 a.m.): one 'crew on site' JobNimbus note; duplicate delivery and later photos add nothing",
   "result": "pass",
   "run_date": "2026-10-28T17:07:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-crew-daily-photo-log/test/results.json",
   "limitations": "Captions are checked against a word list. It can miss unusual wording, so the office should still skim updates for the first weeks. | Homeowner emails link to CompanyCam photo URLs; check your CompanyCam sharing settings before turning updates on. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-crew-daily-photo-log",
   "trade": "roofing",
   "scenario_id": "P3",
   "scenario": "6 p.m. run (CompanyCam answers 429 once, 4 photos per page; one caption says insurance will pay): JobNimbus log with all 8 photos, homeowner email with 6 (internal photo and risky caption left out), office told about the caption and about Becker's job with no photos",
   "result": "pass",
   "run_date": "2026-10-28T17:07:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-crew-daily-photo-log/test/results.json",
   "limitations": "Captions are checked against a word list. It can miss unusual wording, so the office should still skim updates for the first weeks. | Homeowner emails link to CompanyCam photo URLs; check your CompanyCam sharing settings before turning updates on. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  },
  {
   "recipe": "roofing-crew-daily-photo-log",
   "trade": "roofing",
   "scenario_id": "P4",
   "scenario": "Second run the same evening: nothing sent",
   "result": "pass",
   "run_date": "2026-10-28T17:07:16+01:00",
   "mock_or_live": "mock",
   "result_file": "recipes/roofing-crew-daily-photo-log/test/results.json",
   "limitations": "Captions are checked against a word list. It can miss unusual wording, so the office should still skim updates for the first weeks. | Homeowner emails link to CompanyCam photo URLs; check your CompanyCam sharing settings before turning updates on. | Built for JobNimbus. AccuLynx, Roofr and other CRMs are not built for this recipe, and we make no claim that it works with them. | No message says anything about deductibles, coverage or filing a claim, and none goes to an insurer or adjuster. Several states bar contractors from acting as public adjusters or interpreting policies (for example Texas Insurance Code 4102.163, Florida Statutes 489.147, Minnesota 325E.66, Colorado 6-22-105); check your state's rules. A message lint blocks a list of claim and deductible words before anything is sent."
  }
 ]
}