feat(legal): host the privacy policy and EULA at /privacy/ and /eula/
CI / changes (pull_request) Successful in 2s
CI / unit (pull_request) Successful in 11s
CI / integration (pull_request) Successful in 22s
CI / ui (pull_request) Successful in 1m14s
CI / conformance (pull_request) Successful in 10s
CI / gate (pull_request) Successful in 0s
CI / deploy (pull_request) Failing after 40s
CI / changes (pull_request) Successful in 2s
CI / unit (pull_request) Successful in 11s
CI / integration (pull_request) Successful in 22s
CI / ui (pull_request) Successful in 1m14s
CI / conformance (pull_request) Successful in 10s
CI / gate (pull_request) Successful in 0s
CI / deploy (pull_request) Failing after 40s
Author ui/legal/{privacy,eula}_ru.md, reworked from the source documents: the seller INN is unified (290210610742), contacts unified to the Telegram bot + email + postal address, the EULA governing-law clause leads with Russian law + jurisdiction as residence tiers, the single-binding-language clause is dropped, data collection is scoped to voluntary/support provision, and "Компания" is no longer shout-cased.
Serve both as static pages through the render sidecar, reusing a shared renderLegalHtml generalised from renderOfferHtml: new GET /privacy/ and GET /eula/ (301 from the slashless form), the markdown baked into the image, no backend fetch. Route them at the edge via the @legal caddy matcher with a CI probe asserting each page's canonical URL + the seller INN, so a missing route cannot silently fall through to the landing. Add the two links to the landing footer.
Docs baked in: ARCHITECTURE (renderer legal pages + edge routing), FUNCTIONAL (+_ru) footer, renderer/README routes. Tests: renderer legal.test.mjs, ui renderLegalHtml unit, landing footer e2e.
This commit is contained in:
+10
-7
@@ -967,10 +967,12 @@ finished journal on each GET. The only degraded platform is a legacy Telegram cl
|
||||
predating `downloadFile`, where the GCG falls back to the old clipboard copy and the
|
||||
image option is not offered.
|
||||
|
||||
The same sidecar also serves the **public offer page** at `/offer/` — the one edge-exposed
|
||||
route on it (caddy routes `/offer/` here; its `/render` stays internal). It reuses the shared
|
||||
`ui/src/lib/offer.ts` renderer (again one renderer, no drift) over the owner-edited
|
||||
`ui/legal/offer_ru.md`, baked into the image, splicing in the **live price list** (§4.4): it
|
||||
The same sidecar also serves the **public legal pages** — the offer at `/offer/`, the privacy
|
||||
policy at `/privacy/` and the EULA at `/eula/` — the edge-exposed routes on it (caddy routes them
|
||||
here; its `/render` stays internal). All three reuse the shared `ui/src/lib/offer.ts`
|
||||
`renderLegalHtml` (one renderer, no drift) over their owner-edited `ui/legal/*_ru.md`, baked into
|
||||
the image. `/privacy/` and `/eula/` are static; the offer additionally splices in the **live price
|
||||
list** (§4.4): it
|
||||
fetches the two catalog tables as markdown from the backend's internal
|
||||
`/api/v1/internal/offer/pricing` at the `<#pricing_template#>` marker, then renders the page. The
|
||||
backend projects the tables from the active catalog through `payments.Money` (no float reaches the
|
||||
@@ -1446,9 +1448,10 @@ in-process (the distroless image has no `/etc/mime.types`). Hash-named `/assets/
|
||||
in-compose **caddy** is the contour's edge: it owns a single `/_gm` Basic-Auth and
|
||||
routes `/_gm/grafana/*` to **Grafana** (anonymous-admin, so the one shared login gates
|
||||
it with no per-user Grafana accounts) and the rest of `/_gm/*` to the backend-rendered
|
||||
**admin console**; `/app/`, `/telegram/`, `/vk/` and the Connect path go to the gateway; `/offer/`
|
||||
(the public offer, rendered by the `renderer` sidecar with the live catalog price list spliced in)
|
||||
goes to the render sidecar; and the catch-all — notably the landing at `/` — goes to the landing
|
||||
**admin console**; `/app/`, `/telegram/`, `/vk/` and the Connect path go to the gateway; the public
|
||||
legal pages `/offer/`, `/privacy/` and `/eula/` (rendered by the `renderer` sidecar — the offer with
|
||||
the live catalog price list spliced in) go to the render sidecar; and the catch-all — notably the
|
||||
landing at `/` — goes to the landing
|
||||
container. The
|
||||
**Telegram validator** runs as a separate container with **no public ingress**,
|
||||
answering only internal gRPC (HMAC, no Telegram egress). The **Telegram bot** holds
|
||||
|
||||
Reference in New Issue
Block a user