feat: docs for PRs #1663/#1664 + automated schema sync pipeline#1667
feat: docs for PRs #1663/#1664 + automated schema sync pipeline#1667jaypatrick merged 8 commits intomainfrom
Conversation
Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/5ca913d3-e1be-4411-8221-2f610ae6ddaf Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/5ca913d3-e1be-4411-8221-2f610ae6ddaf Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
|
@copilot Fix ci |
…ts string literals Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/eed80bfb-95aa-42ab-ab14-449dca99d3b4 Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
Fixed in 9ed1d9c. The CI failures ( The fix:
|
|
@copilot Fix CI |
…ds SSE stream test) Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/cd693534-0d79-46b1-ac7b-6256200d301d Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
Fixed in 5ed85a5. The |
|
@copilot apply changes based on the comments in this thread |
Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/7bd8b89b-8b07-43b3-9224-bf37ca088a84 Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
…o max_batch_timeout Agent-Logs-Url: https://github.com/jaypatrick/adblock-compiler/sessions/7bd8b89b-8b07-43b3-9224-bf37ca088a84 Co-authored-by: jaypatrick <1800595+jaypatrick@users.noreply.github.com>
Applied all changes from the review thread in ba762c9:
|
Description
Closes the three post-merge gaps from PRs #1663 (Sentry DO/Workflow instrumentation) and #1664 (extensible EmailService): missing
/docscoverage, missing security section for web-asset sync, and the absence of an end-to-endgenerate → validate → uploadautomation task.Changes
Documentation — PR #1663 (Sentry Durable Objects & Workflows)
docs/observability/SENTRY_DURABLE_OBJECTS.md— why DO/Workflow isolates need their own Sentry client (not shared withwithSentryWorker),sequenceDiagramof main Worker vs DO vs Workflow Sentry flows,captureExceptionInIsolatestep-by-step internals, call-site table,state.waitUntilrationale, config steps, retry-on-import-failure behaviour, ZTA notes; correctedwithSentryWorkerdescription to accurately describeSentry.withSentry(() => config, handler)wrapper pattern (not a directSentry.init()call)Documentation — PR #1664 (EmailService)
docs/cloudflare/EMAIL_SERVICE.md—flowchart TDof provider selection (Queue → CF Email Worker → MailChannels → Null) and the queue → Workflow → D1/KV path, provider priority table, full config steps (bindings, secrets, vars, D1 migrations), fire-and-forgetctx.waitUntilusage pattern, admin API reference, idempotency viarequestIdoption (key derived internally asemail-${requestId ?? uuid}), ZTA notes, troubleshooting table; correctedwrangler.tomlsnippet to match actual config (max_batch_size=5,max_retries=3,dead_letter_queue, noEMAIL_DLQproducer, noscript_name;destination_addressnoted as optional); fixedrenderCompilationCompleteexample to match actual{ configName, ruleCount, durationMs, requestId }signature; flowchart updated to usecreateEmailService(env, { useQueue: false })and corrected receipt nodes (KV METRICS + D1, not Neon)docs/cloudflare/EMAIL_DELIVERY_WORKFLOW.md— why a Workflow over a plain queue consumer (step checkpointing = no duplicate sends on restart),stateDiagram-v2of the validate → deliver → receipt flow with retry/DLQ paths, corrected retry config defaults (delay: '10 seconds', exponential backoff matchingEmailDeliveryWorkflow.ts), corrected Step 3 (writes to D1email_log_edge+email_idempotency_keys+ KV METRICS, not Neon), and whycreateEmailService(env, { useQueue: false })is used instead ofcreateEmailService(env)(prevents queue→workflow→queue recursion)Automated schema/web-asset sync
scripts/sync-api-assets.ts— new Deno script that runs the full pipeline in one command:cloudflare-schema.yamlfromopenapi.yaml(filter localhost servers +x-*extensions, validate$refs)openapi.yamlby delegating toscripts/validate-openapi.tsas a subprocess (avoids validation drift — runs the full canonical validator includingoperationIdchecks and best-practice warnings)CloudflareApiService— zero-downtime upsert (upload → enable validation → delete old schema);--skip-if-unchangedskips no-op uploads by hash comparison; when hash matches but validation is disabled, enables validation and deletes any other previously-active schema (mirrorsupload-cloudflare-schema.ts)Response is SSE streamassertion fortext/event-streamresponses, matching the canonicalgenerate-postman-collection.tsoutputFlags:
--dry-run(simulate all steps, no writes/API calls),--skip-upload(generate + validate only),--skip-if-unchanged(defaulttrue). Env vars (CLOUDFLARE_ZONE_ID,CLOUDFLARE_API_SHIELD_TOKEN) Zod-validated before any API call.deno.json— three new tasks:docs/security/API_SHIELD_WEB_ASSETS.md—flowchart LRof the sync pipeline, task reference table with when-to-run guidance, env var requirements,--skip-if-unchangedsemantics, zero-downtime upsert explanationdocs/SUMMARY.md[Sentry Durable Objects & Workflows]under Observability[Email Service]and[Email Delivery Workflow]under Cloudflare Integration[Automated Web Asset Sync]under SecurityCI drift fix
sync-api-assets.tsstring literals to exactly match the canonicalgenerate-cloudflare-schema.tsandgenerate-postman-collection.tsscripts (header regeneration hint, Postman variable descriptions,_postman_exported_usingfield)docs/postman/postman-collection.jsonto its canonical pre-PR state — a locally installed Deno version produced output missing theResponse is SSE streamtest assertion that CI's Deno generates; restoring from git ensures byte-for-byte agreement with whatdeno task schema:generateproduces in CIdocs/api/cloudflare-schema.yamlanddocs/postman/postman-environment.jsonconfirmed at canonical stateTesting
schema:sync --dry-runandschema:sync --skip-uploadboth exit 0 with correct output;deno fmt,deno lint,deno checkall pass on new scriptZero Trust Architecture Checklist
Worker / Backend
*) on write/authenticated endpoints — N/A[vars]) — documented:SENTRY_DSN,DKIM_PRIVATE_KEYare Worker Secretssync-api-assets.tsZod-validates env vars before upload step.prepare().bind()(no string interpolation) — N/A (no new queries)Frontend / Angular
CanActivateFnauth guards — N/AlocalStorage) — N/AAPI Shield / Vulnerability Scanner
operationIdinopenapi.yaml— N/A (no new endpoints)/{id}path parameters) include asecurity:annotation — N/AWHERE user_id = ?) — N/A (no new queries)404(not403) — N/Acloudflare-schema.yamlregenerated ifopenapi.yamlchanged — restored to canonical pre-PR state; confirmed clean againstdeno task schema:generateOriginal prompt
Overview
Three separate gaps need to be closed following the merge of PRs #1663 and #1664:
/docsdocumentation — both PRs were merged without thorough documentation (architecture diagrams, configuration steps, usage guides).docs/security/has no coverage of the Cloudflare web-asset surface (API Shield schema, OpenAPI) or how those assets stay in sync.cloudflare-schema.yamlandopenapi.yamlmust be regenerated and uploaded to Cloudflare API Shield automatically whenever API endpoints change. The upload currently requires a manualdeno task schema:upload. There is no script that orchestrates the full generate → validate → upload pipeline, and there is nodeno taskwired to run it end-to-end.PR #1663 — Sentry Durable Object & Workflow Instrumentation
What was shipped:
worker/services/sentry-isolate-init.ts— sharedcaptureExceptionInIsolate(env, error)helper that lazy-loads@sentry/cloudflareonly whenSENTRY_DSNis present, initialises aCloudflareClientonce per isolate, and callscaptureException.captureExceptionInIsolatewired into every Durable Object (RateLimiterDO,CompilationCoordinator,WsHibernationDO) and every Workflow (CompilationWorkflow,BatchCompilationWorkflow,CacheWarmingWorkflow,HealthMonitoringWorkflow).Required documentation — create
docs/observability/SENTRY_DURABLE_OBJECTS.md:withSentryWorker) is not shared with DO/Workflow isolates. Any unhandled exception thrown inside a DO or Workflow is silently dropped by the Sentry SDK unless the DO/Workflow explicitly initialises its own client.sequenceDiagramshowing:withSentryWorker(main isolate) → Sentry DSNalarm()catch →captureExceptionInIsolate→ lazy import →CloudflareClientinit → Sentry DSNrun()catch →captureExceptionInIsolate→ lazy import →CloudflareClientinit → Sentry DSNSENTRY_DSNmust be set as a Worker Secret (wrangler secret put SENTRY_DSN). The helper is a no-op when the binding is absent.SENTRY_RELEASE(version tag) andENVIRONMENT(e.g.,production) — both fall back gracefully.wrangler.tomlchanges required; existing bindings are reused.state.waitUntilis used inWsHibernationDO.webSocketError()to avoid blocking WebSocket teardown.SENTRY_DSNis a Worker Secret only; no data is leaked via Sentry because the helper only forwardsErrorobjects.docs/SUMMARY.mdto add[Sentry Durable Objects & Workflows](observability/SENTRY_DURABLE_OBJECTS.md)under theObservabilitysection.PR #1664 — Extensible EmailService
What was shipped:
worker/services/email-service.ts— provider-agnosticIEmailServicewith four implementations:QueuedEmailService— highest priority; enqueues toEMAIL_QUEUE→EmailDeliveryWorkflow(durable, retryable).CfEmailWorkerService— routes through theadblock-emailCF Email Workers binding (SEND_EMAIL); builds RFC 5322 MIME messages.MailChannelsEmailService— MailChannels HTTP API fallback whenFROM_EMAILis set.NullEmailService— graceful no-op.createEmailService(env)/createDirectEmailService(env)factories.worker/workflows/EmailDeliveryWorkflow.ts— step-checkpointed Cloudflare Workflow with D1 + Neon delivery receipts.worker/handlers/email-queue.ts—EMAIL_QUEUEconsumer.worker/handlers/admin-email.ts—GET /admin/email/configandPOST /admin/email/test.EmailTemplate,EmailLog,EmailNotificationPreference(Neon) andEmailLogEdge,EmailIdempotencyKey(D1).wrangler.tomladditions:[[send_email]],[[queues.producers/consumers]],[[workflows]].Required documentation — create the following files:
docs/cloudflare/EMAIL_SERVICE.mdflowchart TD:createEmailService(env)→ priority selection →QueuedEmailService/CfEmailWorkerService/MailChannelsEmailService/NullEmailServiceQueuedEmailService→EMAIL_QUEUE→email-queue.tshandler →EmailDeliveryWorkflow→ delivery receipt → D1 + NeonEmailDeliveryWorkflow→ `createDirectEmailSer...This pull request was created from Copilot chat.