Community deals and discussions
DynoStatic can run the interactive backend for a deal site or discussion forum while an Astro site and Cloudflare Worker deliver its public pages. The optional Deals and Discussions presets reuse collections, contributor accounts and forms, publication jobs, boards, comments, uploads and signed voting.
Set up through an agent or the owner interface
An agent can provision the same presets using a website Automation token with workspace:read and workspace:write. Its creator must still be an active website owner or installation administrator. Discover automation.capabilities first, then send the exact installed request:
POST /api/?action=automation.community.setup&site=SITE_ULID
Authorization: Bearer YOUR_AUTOMATION_TOKEN
Content-Type: application/json
{"format":"dynostatic.community-setup","version":1,"presets":["deals","discussions"]}
The response contains the board/workflow IDs, owned Comments widgets, a stable suggested Comments ID and the installation's Comments defaults. Exact retries reuse the presets. Concurrent setup is serialized; customized schemas and workflows return a conflict instead of being replaced. Authority is rechecked inside each mutation, without creating a browser session.
The installed setup script discovers this action, preserves existing widgets and creates/publishes missing Comments through the ordinary widget change-set API. Run it privately from the website directory with DYNOSTATIC_URL, DYNOSTATIC_SITE_ID and SITE_ORIGIN set. It reads a token from DYNOSTATIC_BUILD_TOKEN or .secrets/.dynostatic-api; keep both that file and .local/ ignored. It saves resumable operation IDs before writing and public connection IDs under .local/dynostatic-setup/. Resolve any reported customization or widget-selection conflict before retrying. It does not configure mail, Turnstile, hosting or CI credentials. site:publish is separately required for build coordination.
The equivalent owner interface is:
- Open Boards for the website and choose Add Deals board or Add Discussions board. Each preset creates a collection, an account-only contributor workflow and a board. Create both for a combined community.
- Publish a Comments widget for that website. The reference uses its existing editor, replies, anti-spam controls and signed votes. Configure mail so members can verify their addresses.
- Install the Astro/Worker reference, select the website and Comments widget IDs, and register the website's HTTPS origin in DynoStatic.
- Configure the separate build dispatcher and CI credentials described below. A static frontend by itself cannot safely run this workflow.
The collections contain ordinary editable fields. Deals include title, body, category, merchant link, store, price, currency, previous price, coupon and up to six photos. Discussions include title, body and category. Change category options through the existing collection schema and board tools. The presets are resumable; customized schemas or workflows are left for the owner to reconcile rather than overwritten.
What happens when someone posts
A member signs in and verifies their email. Their account owns the draft and its uploads. Submitting an eligible draft runs the existing automatic editorial and publication admission, then attempts publication immediately. The durable publication job remains available for retries. Until delivery succeeds, the author sees Publishing.
Publishing ordinary cms.entry resources alone does not create community posts.
The contributor flow binds the verified author, submission, board, canonical page
and discussion identity in one transaction. Use that flow for an initial community
import as well. Label historical workbook examples and avoid presenting their
recorded prices as current offers.
Member verification requires outbound mail enabled on the DynoStatic installation;
the frontend Worker's separate contact/alert SMTP settings do not enable it. The
installed email return path is /contributor/account/email/verify. The website must
render its account UI there with the query intact, prevent referrer disclosure and
let the official client consume the challenge. Verification revokes the old account
session: remove it locally and request a fresh sign-in before further participation.
Once published, the Worker can render the post from DynoStatic's current public projection. It retains the same canonical URL and discussion identity when a later static build takes over. The reference shares its render functions between Astro and the Worker.
Replies and votes use the existing Comments engine. Authors can change a post's status from My posts; owners/moderators retain the existing board progress tools. These interactions do not request static builds. The reference keeps an opt-in account session in first-party sessionStorage, scoped to website and API origin; the existing generic contributor form keeps its original memory-only behavior. Sign-out clears the shared community session. No website Automation credential belongs in browser code.
Moderation remains authoritative
Reading is public; posting, voting and reporting require an active verified account. Downvotes affect ranking only.
By default, reports from five distinct active accounts whose email was verified at least seven days earlier temporarily hide a publication. Newer verified accounts can report, but their reports go to moderators without contributing to automatic hiding. Owners can adjust the threshold on Boards. The community report queue shows current published content and supports audited restore/remove decisions with revision checks. Hidden and removed posts keeps resolved removals available for later restoration.
A report is unique per account and publication revision. Retries do not add votes to the threshold. Resolving reports prevents those same reports from immediately hiding the unchanged publication again. A changed publication has a new report revision.
All community HTML must run through the Worker first, including aliases, /index.html, lists, search and previews. Visibility evidence contains origin-issued issued_at and expires_at; the maximum absolute age is 60 seconds. Cache hits never extend it. Once it expires, an unavailable backend produces an unavailable page, not stale protected content. The reference also guards copied community photos. Do not configure a CDN rule, service worker, Pages fallback or alternate static hostname that bypasses this Worker.
Static build and actual deployment
The default publication batch interval is two minutes. One renewable build lease per website prevents overlapping builds. Changes during a build remain dirty for a follow-up build. Expired leases cannot complete or overwrite the current build receipt.
The Automation action automation.community.build requires a website-bound site:publish token (or an explicitly selected website with an owner token). Use the physical gateway:
POST /api/?action=automation.community.build&site=SITE_ULID
Authorization: Bearer YOUR_BUILD_TOKEN
Content-Type: application/json
| Operation | Body fields in addition to operation |
Result |
|---|---|---|
claim |
operation_id (new ULID; reuse it after an uncertain response) |
idle, waiting, busy, or a leased immutable manifest |
renew |
build_id |
Extends a still-current lease by 15 minutes |
complete |
build_id, manifest_sha256, provider_deployment_id |
Confirms actual deployed website proof and records deployment |
fail |
build_id, manifest_sha256 |
Ends the failed build and retains dirty content |
The deployment must serve /.well-known/dynostatic-community-deployment over the website's configured HTTPS origin with the exact build ID and manifest SHA-256. DynoStatic fetches that proof before accepting complete. Producing files or receiving a successful CI status alone is insufficient. The public Worker uses static HTML only when its bundled manifest, the confirmed deployment and the current publication match. Otherwise it renders the current public post dynamically.
The reference dispatcher runs every minute, claims only due work, and dispatches the repository workflow. Keep its GitHub dispatch token and DynoStatic build token in the separate dispatcher, with the build token and Cloudflare deployment token also available only in CI. The public website Worker has no administrative secret.
The reference intentionally bounds a full capture to 10,000 posts and 16 MiB of post data. Larger archives need a partitioned build adapter; it fails explicitly instead of silently omitting posts. Existing built-in site releases and immutable board revision formats remain unchanged.
Product suggestions and photos
In a Deals draft, Import product details accepts a public HTTPS product URL. It suggests a title, store, price and currency for review. Version 1 profiles recognize product paths for Amazon, AliExpress, Walmart, Best Buy, CVS, Home Depot, Sam's Club, Costco, and Outdoor Supply Hardware (osh.com redirects to the latter). Generic stores can supply primary Product JSON-LD or product OpenGraph metadata. A profile identifies URLs; it does not guarantee that a merchant will allow access or provide useful data.
The importer performs at most three HTTPS requests with a 12-second transfer budget, bounded response sizes, fresh DNS validation and a pinned public destination for every hop. It does not execute JavaScript, crawl categories, copy cookies or bypass blocks. Successful metadata is cached for 24 hours and failures for ten minutes. Account and merchant-domain limits bound repeated attempts. Expired preview/cache records are purged by the existing maintenance worker.
Image suggestions are opaque choices bound to the current verified account and editable draft. Confirm permission to publish before importing a photo. The selected bytes must be JPEG, PNG or WebP, at least 120 pixels on each side, at most 40 million pixels and 8 MiB. They enter private contributor upload storage; submission pins the upload revision and publication promotes it into CMS media. The reference copies verified published bytes to guarded Worker assets. A raw image URL or preview ID from another draft grants no upload authority. Keep manual entry/upload available when a store blocks requests or changes markup.
Discover the installed contract
integration.php includes community, merchant profile versions, public route mappings, freshness limits and the build action/scope. Public adapters use community.view at /api/?action=community.view&site=SITE_ULID&path=/deals, with the website's registered Origin. Contributor product preview/import and author status routes use the existing identity and browser-proof headers. The browser adapter maps installed public routes to the explicit api/index.php physical gateway and calls DynoStatic directly using its registered-Origin CORS policy. Use the explicit PHP filename for browser requests: nginx can reject OPTIONS on the directory URL api/ before PHP receives it. Hosting rewrites are unnecessary. This preserves visitor IP admission; Cloudflare cross-zone Worker proxies can replace visitor IPs with a shared address. The Worker handles page delivery without an administrative secret. See Cloudflare’s subrequest header behavior.
See the community OpenAPI contract, contributor forms, browser API, and Automation API. Backups preserve boards, reports and visibility decisions but clear import previews, caches, build leases and deployment receipts. A restored installation cannot claim an earlier live deployment.
The reference shares the contributor account within the first-party browser tab. Before mounting Comments, it exchanges the account token and browser proof at contributor.public.community.discussion-session for a short-lived token scoped to this website’s published Comments widget. The exchange requires a current visible community post and verified active account. The placement token stays in memory and is renewed while the page is open; widget isolation and normal account revocation checks remain in force. A shared widget from another website cannot use this exchange.