@voltro/cli 0.28.0 → 0.29.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +278 -0
- package/THIRD-PARTY-NOTICES.md +88 -2
- package/dist/{apiBuild-eUM32r1u.js → apiBuild-BESZbTjA.js} +3 -3
- package/dist/apiBuild-C8d74T6g.js +2 -0
- package/dist/bin.js +3 -3
- package/dist/checkCommand-BPAtyWs8.js +2420 -0
- package/dist/checkCommand-DBvZvCh1.js +2 -0
- package/dist/cliRuntime-Oh517vCV.js +96 -0
- package/dist/{commands-CSkrUI1h.js → commands-82BDEktg.js} +6803 -8191
- package/dist/dbCommand-CaIVTp-a.js +2 -0
- package/dist/{dbCommand-CpYgmSw4.js → dbCommand-bCBbk6tz.js} +2 -2
- package/dist/{dev-CEZwJhmb.js → dev-Cg4BKLmi.js} +1801 -1612
- package/dist/{dev-DlBWWnJQ.js → dev-DeEJj5T4.js} +1 -1
- package/dist/fileConventions-Cof68_BL.js +33 -0
- package/dist/{frameworkTableAssembly-BwHU9Euq.js → frameworkTableAssembly-4Db40V23.js} +2 -2
- package/dist/frameworkTableAssembly-BTNirAAk.js +2 -0
- package/dist/index.js +1 -1
- package/dist/{inspect-CUCCzw2I.js → inspect-BMvQpwqy.js} +211 -190
- package/dist/inspect-DHeaMZak.js +2 -0
- package/dist/{inspectMetrics-BU90mvJN.js → inspectMetrics-DHYygE4s.js} +999 -961
- package/dist/{manifestBuild-BnzAxp2O.js → manifestBuild-C4R1EdHn.js} +1 -1
- package/dist/manifestBuild-Ck_90gZy.js +2 -0
- package/dist/sdkgen-CW5NbYF0.js +582 -0
- package/dist/serveCommand-BXl8mhZD.js +1489 -0
- package/dist/serveEntry.js +2 -2
- package/dist/{start-BGXIf6zT.js → start-CsCIaW4-.js} +282 -269
- package/dist/startEntry.js +2 -2
- package/package.json +17 -17
- package/templates/AGENTS.md +2 -1
- package/templates/agent-docs/_index.md +2 -1
- package/templates/agent-docs/_manifest.json +10 -1
- package/templates/agent-docs/ai.md +135 -0
- package/templates/agent-docs/cli.md +124 -6
- package/templates/agent-docs/configuration.md +32 -0
- package/templates/agent-docs/data.md +282 -0
- package/templates/agent-docs/database/migrations.md +47 -0
- package/templates/agent-docs/database/misc.md +57 -0
- package/templates/agent-docs/database/schema.md +3 -1
- package/templates/agent-docs/internationalization.md +161 -1
- package/templates/agent-docs/local-first-mobile.md +414 -0
- package/templates/agent-docs/routing.md +93 -2
- package/templates/agent-docs/schema-driven-ui.md +12 -0
- package/templates/agent-docs/templates/apibackends.md +1 -1
- package/templates/agent-docs/whats-new.md +162 -181
- package/templates/agent-docs/workflows.md +11 -0
- package/templates/apps/api-ai/package.json +7 -7
- package/templates/apps/api-auth/package.json +8 -8
- package/templates/apps/api-backend/package.json +7 -7
- package/templates/apps/api-backend-deactivation/package.json +7 -7
- package/templates/apps/api-backend-mail/package.json +8 -8
- package/templates/apps/api-backend-mariadb/package.json +9 -9
- package/templates/apps/api-backend-sqlite/.env.example +19 -0
- package/templates/apps/api-backend-sqlite/README.md +38 -0
- package/templates/apps/api-backend-sqlite/app.config.ts +35 -0
- package/templates/apps/api-backend-sqlite/database/schema.ts +54 -0
- package/templates/apps/api-backend-sqlite/mutations/notes.create.mutation.server.ts +19 -0
- package/templates/apps/api-backend-sqlite/mutations/notes.create.mutation.ts +37 -0
- package/templates/apps/api-backend-sqlite/package.json +30 -0
- package/templates/apps/api-backend-sqlite/queries/notes.query.server.ts +14 -0
- package/templates/apps/api-backend-sqlite/queries/notes.query.ts +20 -0
- package/templates/apps/api-backend-sqlite/template.json +6 -0
- package/templates/apps/api-backend-sqlite/tests/notes.create.test.ts +50 -0
- package/templates/apps/api-backend-sqlite/tsconfig.json +5 -0
- package/templates/apps/api-backend-storage/package.json +8 -8
- package/templates/apps/api-cms/README.md +104 -0
- package/templates/apps/api-cms/actions/content.get.action.server.ts +27 -0
- package/templates/apps/api-cms/actions/content.get.action.ts +19 -0
- package/templates/apps/api-cms/actions/content.types.action.server.ts +26 -0
- package/templates/apps/api-cms/actions/content.types.action.ts +40 -0
- package/templates/apps/api-cms/actions/me.action.server.ts +18 -0
- package/templates/apps/api-cms/actions/me.action.ts +16 -0
- package/templates/apps/api-cms/app.config.ts +61 -0
- package/templates/apps/api-cms/content/blogPost.contentType.ts +39 -0
- package/templates/apps/api-cms/content/index.ts +18 -0
- package/templates/apps/api-cms/content/page.contentType.ts +24 -0
- package/templates/apps/api-cms/database/schema.ts +64 -0
- package/templates/apps/api-cms/mutations/content.publish.mutation.server.ts +19 -0
- package/templates/apps/api-cms/mutations/content.publish.mutation.ts +15 -0
- package/templates/apps/api-cms/mutations/content.saveDraft.mutation.server.ts +36 -0
- package/templates/apps/api-cms/mutations/content.saveDraft.mutation.ts +32 -0
- package/templates/apps/api-cms/mutations/content.unpublish.mutation.server.ts +19 -0
- package/templates/apps/api-cms/mutations/content.unpublish.mutation.ts +11 -0
- package/templates/apps/api-cms/package.json +32 -0
- package/templates/apps/api-cms/queries/content.list.query.server.ts +0 -0
- package/templates/apps/api-cms/queries/content.list.query.ts +27 -0
- package/templates/apps/api-cms/template.json +6 -0
- package/templates/apps/api-cms/tests/content.descriptors.test.ts +64 -0
- package/templates/apps/api-cms/tests/content.write.test.ts +85 -0
- package/templates/apps/api-cms/tsconfig.json +5 -0
- package/templates/apps/api-data-advanced/package.json +8 -8
- package/templates/apps/api-durable/package.json +8 -8
- package/templates/apps/api-feature-flags/package.json +9 -9
- package/templates/apps/api-governance/package.json +8 -8
- package/templates/apps/api-kv/package.json +8 -8
- package/templates/apps/api-moderation/package.json +8 -8
- package/templates/apps/api-observability/package.json +8 -8
- package/templates/apps/api-ratelimit/package.json +8 -8
- package/templates/apps/api-rbac/package.json +8 -8
- package/templates/apps/api-rest/package.json +7 -7
- package/templates/apps/api-saas/package.json +11 -11
- package/templates/apps/api-saas-starter/README.md +103 -0
- package/templates/apps/api-saas-starter/actions/me.action.server.ts +18 -0
- package/templates/apps/api-saas-starter/actions/me.action.ts +20 -0
- package/templates/apps/api-saas-starter/app.config.ts +87 -0
- package/templates/apps/api-saas-starter/database/schema.ts +57 -0
- package/templates/apps/api-saas-starter/mutations/invites.create.mutation.server.ts +26 -0
- package/templates/apps/api-saas-starter/mutations/invites.create.mutation.ts +18 -0
- package/templates/apps/api-saas-starter/mutations/projects.create.mutation.server.ts +29 -0
- package/templates/apps/api-saas-starter/mutations/projects.create.mutation.ts +18 -0
- package/templates/apps/api-saas-starter/package.json +32 -0
- package/templates/apps/api-saas-starter/queries/invites.list.query.server.ts +14 -0
- package/templates/apps/api-saas-starter/queries/invites.list.query.ts +17 -0
- package/templates/apps/api-saas-starter/queries/projects.list.query.server.ts +14 -0
- package/templates/apps/api-saas-starter/queries/projects.list.query.ts +18 -0
- package/templates/apps/api-saas-starter/template.json +6 -0
- package/templates/apps/api-saas-starter/tests/projects.create.test.ts +62 -0
- package/templates/apps/api-saas-starter/tests/session.test.ts +33 -0
- package/templates/apps/api-saas-starter/tsconfig.json +5 -0
- package/templates/apps/api-search/package.json +8 -8
- package/templates/apps/api-status/README.md +88 -0
- package/templates/apps/api-status/app.config.ts +36 -0
- package/templates/apps/api-status/authz.ts +33 -0
- package/templates/apps/api-status/database/schema.ts +70 -0
- package/templates/apps/api-status/mutations/components.create.mutation.server.ts +19 -0
- package/templates/apps/api-status/mutations/components.create.mutation.ts +16 -0
- package/templates/apps/api-status/mutations/incidents.create.mutation.server.ts +25 -0
- package/templates/apps/api-status/mutations/incidents.create.mutation.ts +22 -0
- package/templates/apps/api-status/mutations/incidents.resolve.mutation.server.ts +24 -0
- package/templates/apps/api-status/mutations/incidents.resolve.mutation.ts +19 -0
- package/templates/apps/api-status/mutations/incidents.update.mutation.server.ts +26 -0
- package/templates/apps/api-status/mutations/incidents.update.mutation.ts +21 -0
- package/templates/apps/api-status/package.json +30 -0
- package/templates/apps/api-status/queries/components.list.query.server.ts +14 -0
- package/templates/apps/api-status/queries/components.list.query.ts +13 -0
- package/templates/apps/api-status/queries/incidents.live.query.server.ts +14 -0
- package/templates/apps/api-status/queries/incidents.live.query.ts +20 -0
- package/templates/apps/api-status/queries/updates.list.query.server.ts +14 -0
- package/templates/apps/api-status/queries/updates.list.query.ts +17 -0
- package/templates/apps/api-status/template.json +6 -0
- package/templates/apps/api-status/tests/status.test.ts +70 -0
- package/templates/apps/api-status/tsconfig.json +5 -0
- package/templates/apps/api-versioning/package.json +8 -8
- package/templates/apps/api-webhooks/package.json +9 -9
- package/templates/apps/changelog/package.json +6 -6
- package/templates/apps/edge-functions/package.json +2 -2
- package/templates/apps/frontend-admin/package.json +8 -8
- package/templates/apps/frontend-app/package.json +8 -8
- package/templates/apps/frontend-auth/README.md +78 -0
- package/templates/apps/frontend-auth/app.config.ts +34 -0
- package/templates/apps/frontend-auth/package.json +32 -0
- package/templates/apps/frontend-auth/src/components/AuthShell.tsx +35 -0
- package/templates/apps/frontend-auth/src/components/PasswordStrength.tsx +33 -0
- package/templates/apps/frontend-auth/src/config.ts +11 -0
- package/templates/apps/frontend-auth/src/globals.css +105 -0
- package/templates/apps/frontend-auth/src/globals.d.ts +6 -0
- package/templates/apps/frontend-auth/src/lib/auth.ts +34 -0
- package/templates/apps/frontend-auth/src/lib/redirect.test.ts +24 -0
- package/templates/apps/frontend-auth/src/lib/redirect.ts +29 -0
- package/templates/apps/frontend-auth/src/locales/de.ts +66 -0
- package/templates/apps/frontend-auth/src/locales/en.ts +76 -0
- package/templates/apps/frontend-auth/src/locales/index.ts +14 -0
- package/templates/apps/frontend-auth/src/pages/forgot/page.tsx +51 -0
- package/templates/apps/frontend-auth/src/pages/layout.tsx +12 -0
- package/templates/apps/frontend-auth/src/pages/login/page.test.tsx +53 -0
- package/templates/apps/frontend-auth/src/pages/login/page.tsx +67 -0
- package/templates/apps/frontend-auth/src/pages/logout/page.tsx +28 -0
- package/templates/apps/frontend-auth/src/pages/magic/page.tsx +51 -0
- package/templates/apps/frontend-auth/src/pages/page.tsx +26 -0
- package/templates/apps/frontend-auth/src/pages/reset/page.test.tsx +51 -0
- package/templates/apps/frontend-auth/src/pages/reset/page.tsx +63 -0
- package/templates/apps/frontend-auth/src/pages/signup/page.tsx +60 -0
- package/templates/apps/frontend-auth/src/pages/verify/page.tsx +50 -0
- package/templates/apps/frontend-auth/template.json +6 -0
- package/templates/apps/frontend-auth/tsconfig.json +5 -0
- package/templates/apps/frontend-blank/package.json +7 -7
- package/templates/apps/frontend-cms/README.md +47 -0
- package/templates/apps/frontend-cms/app.config.ts +37 -0
- package/templates/apps/frontend-cms/package.json +33 -0
- package/templates/apps/frontend-cms/src/config.ts +8 -0
- package/templates/apps/frontend-cms/src/globals.css +105 -0
- package/templates/apps/frontend-cms/src/globals.d.ts +6 -0
- package/templates/apps/frontend-cms/src/lib/api.ts +58 -0
- package/templates/apps/frontend-cms/src/locales/de.ts +50 -0
- package/templates/apps/frontend-cms/src/locales/en.ts +55 -0
- package/templates/apps/frontend-cms/src/locales/index.ts +14 -0
- package/templates/apps/frontend-cms/src/pages/(app)/error.tsx +18 -0
- package/templates/apps/frontend-cms/src/pages/(app)/layout.test.tsx +31 -0
- package/templates/apps/frontend-cms/src/pages/(app)/layout.tsx +62 -0
- package/templates/apps/frontend-cms/src/pages/(app)/not-found.tsx +14 -0
- package/templates/apps/frontend-cms/src/pages/(app)/page.test.tsx +110 -0
- package/templates/apps/frontend-cms/src/pages/(app)/page.tsx +159 -0
- package/templates/apps/frontend-cms/src/pages/layout.tsx +12 -0
- package/templates/apps/frontend-cms/src/pages/login/page.test.tsx +58 -0
- package/templates/apps/frontend-cms/src/pages/login/page.tsx +93 -0
- package/templates/apps/frontend-cms/template.json +6 -0
- package/templates/apps/frontend-cms/tsconfig.json +5 -0
- package/templates/apps/frontend-contact/package.json +7 -7
- package/templates/apps/frontend-dashboard/package.json +7 -7
- package/templates/apps/frontend-docs/package.json +7 -7
- package/templates/apps/frontend-i18n/package.json +6 -6
- package/templates/apps/frontend-landing/package.json +7 -7
- package/templates/apps/frontend-portal/README.md +71 -0
- package/templates/apps/frontend-portal/app.config.ts +37 -0
- package/templates/apps/frontend-portal/package.json +32 -0
- package/templates/apps/frontend-portal/src/config.ts +8 -0
- package/templates/apps/frontend-portal/src/globals.css +93 -0
- package/templates/apps/frontend-portal/src/globals.d.ts +6 -0
- package/templates/apps/frontend-portal/src/lib/api.ts +62 -0
- package/templates/apps/frontend-portal/src/locales/de.ts +86 -0
- package/templates/apps/frontend-portal/src/locales/en.ts +93 -0
- package/templates/apps/frontend-portal/src/locales/index.ts +14 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/api-keys/page.test.tsx +71 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/api-keys/page.tsx +124 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/billing/page.test.tsx +86 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/billing/page.tsx +97 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/error.tsx +19 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/invoices/page.tsx +45 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/layout.test.tsx +31 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/layout.tsx +63 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/not-found.tsx +15 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/page.tsx +39 -0
- package/templates/apps/frontend-portal/src/pages/(portal)/profile/page.tsx +79 -0
- package/templates/apps/frontend-portal/src/pages/layout.tsx +12 -0
- package/templates/apps/frontend-portal/src/pages/login/page.test.tsx +58 -0
- package/templates/apps/frontend-portal/src/pages/login/page.tsx +96 -0
- package/templates/apps/frontend-portal/template.json +6 -0
- package/templates/apps/frontend-portal/tsconfig.json +5 -0
- package/templates/apps/frontend-saas/README.md +73 -0
- package/templates/apps/frontend-saas/app.config.ts +46 -0
- package/templates/apps/frontend-saas/package.json +32 -0
- package/templates/apps/frontend-saas/src/config.ts +8 -0
- package/templates/apps/frontend-saas/src/globals.css +85 -0
- package/templates/apps/frontend-saas/src/globals.d.ts +6 -0
- package/templates/apps/frontend-saas/src/lib/api.ts +47 -0
- package/templates/apps/frontend-saas/src/locales/de.ts +72 -0
- package/templates/apps/frontend-saas/src/locales/en.ts +81 -0
- package/templates/apps/frontend-saas/src/locales/index.ts +14 -0
- package/templates/apps/frontend-saas/src/pages/(marketing)/layout.tsx +30 -0
- package/templates/apps/frontend-saas/src/pages/(marketing)/login/page.test.tsx +58 -0
- package/templates/apps/frontend-saas/src/pages/(marketing)/login/page.tsx +96 -0
- package/templates/apps/frontend-saas/src/pages/(marketing)/page.tsx +27 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/billing/page.tsx +72 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/error.tsx +20 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/layout.test.tsx +32 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/layout.tsx +69 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/not-found.tsx +17 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/page.test.tsx +113 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/page.tsx +76 -0
- package/templates/apps/frontend-saas/src/pages/dashboard/team/page.tsx +73 -0
- package/templates/apps/frontend-saas/src/pages/layout.tsx +12 -0
- package/templates/apps/frontend-saas/template.json +6 -0
- package/templates/apps/frontend-saas/tsconfig.json +5 -0
- package/templates/apps/frontend-spa/package.json +7 -7
- package/templates/apps/frontend-ssr/package.json +7 -7
- package/templates/apps/frontend-ssr-api/package.json +8 -8
- package/templates/apps/frontend-static-blog/package.json +6 -6
- package/templates/apps/frontend-status/README.md +51 -0
- package/templates/apps/frontend-status/app.config.ts +39 -0
- package/templates/apps/frontend-status/package.json +32 -0
- package/templates/apps/frontend-status/src/config.ts +7 -0
- package/templates/apps/frontend-status/src/globals.css +70 -0
- package/templates/apps/frontend-status/src/globals.d.ts +6 -0
- package/templates/apps/frontend-status/src/lib/status.ts +81 -0
- package/templates/apps/frontend-status/src/locales/de.ts +41 -0
- package/templates/apps/frontend-status/src/locales/en.ts +45 -0
- package/templates/apps/frontend-status/src/locales/index.ts +13 -0
- package/templates/apps/frontend-status/src/pages/layout.tsx +27 -0
- package/templates/apps/frontend-status/src/pages/page.test.tsx +123 -0
- package/templates/apps/frontend-status/src/pages/page.tsx +136 -0
- package/templates/apps/frontend-status/template.json +6 -0
- package/templates/apps/frontend-status/tsconfig.json +11 -0
- package/templates/baselines/compose/docker-compose.prod.yml +15 -0
- package/templates/baselines/compose-mariadb/docker-compose.prod.yml +15 -0
- package/dist/apiBuild-DgBS9ayv.js +0 -2
- package/dist/dbCommand-DvguqlzF.js +0 -2
- package/dist/fileConventions-3bffWssN.js +0 -30
- package/dist/frameworkTableAssembly-lrjZtk0G.js +0 -2
- package/dist/inspect-gt8bq-Tz.js +0 -2
- package/dist/manifestBuild-ifczArzr.js +0 -2
- package/dist/serveCommand-ZTn-dPFa.js +0 -1425
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
// `/` — the public status page. `renderMode: 'ssr'`, fed by the sibling api:
|
|
2
|
+
// the loader bakes the current incidents + components + updates into the first
|
|
3
|
+
// paint (crawlable), then the component upgrades each to live with
|
|
4
|
+
// `useSubscription`, so a newly-declared or resolved incident lands on every
|
|
5
|
+
// open page within seconds — no polling.
|
|
6
|
+
import type { ReactNode } from 'react'
|
|
7
|
+
import { useLoaderData, type LoaderFn, type PageMeta } from '@voltro/web'
|
|
8
|
+
import { useSubscription } from '@voltro/client'
|
|
9
|
+
import { T } from '@voltro/i18n'
|
|
10
|
+
import { getCatalog } from '../locales'
|
|
11
|
+
import {
|
|
12
|
+
deriveOverall, uptimeGrid, uptimePercent,
|
|
13
|
+
type Incident, type Component, type Update,
|
|
14
|
+
} from '../lib/status'
|
|
15
|
+
|
|
16
|
+
interface PageData {
|
|
17
|
+
readonly incidents: ReadonlyArray<Incident>
|
|
18
|
+
readonly components: ReadonlyArray<Component>
|
|
19
|
+
readonly updates: ReadonlyArray<Update>
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
export const renderMode = 'ssr' as const
|
|
23
|
+
|
|
24
|
+
// `query` is present ONLY server-side. It invokes the api's rpc over POST /rpc;
|
|
25
|
+
// a streaming query is drained to its first snapshot. On a client navigation
|
|
26
|
+
// `query` is undefined and we start empty — the subscriptions fill in.
|
|
27
|
+
export const loader: LoaderFn<PageData> = async ({ query }) => ({
|
|
28
|
+
incidents: query ? await query<ReadonlyArray<Incident>>('incidents.live', {}) : [],
|
|
29
|
+
components: query ? await query<ReadonlyArray<Component>>('components.list', {}) : [],
|
|
30
|
+
updates: query ? await query<ReadonlyArray<Update>>('updates.list', {}) : [],
|
|
31
|
+
})
|
|
32
|
+
|
|
33
|
+
export const meta = ({ locale }: { readonly locale: string }): PageMeta => ({
|
|
34
|
+
title: getCatalog(locale)['meta.title'],
|
|
35
|
+
description: getCatalog(locale)['meta.description'],
|
|
36
|
+
})
|
|
37
|
+
|
|
38
|
+
const fmtDate = (v: string | Date | null): string =>
|
|
39
|
+
v == null ? '' : new Date(v).toLocaleString()
|
|
40
|
+
|
|
41
|
+
export default function StatusPage(): ReactNode {
|
|
42
|
+
const initial = useLoaderData<PageData>()
|
|
43
|
+
const { data: iLive } = useSubscription<ReadonlyArray<Incident>>('app', 'incidents.live')
|
|
44
|
+
const { data: cLive } = useSubscription<ReadonlyArray<Component>>('app', 'components.list')
|
|
45
|
+
const { data: uLive } = useSubscription<ReadonlyArray<Update>>('app', 'updates.list')
|
|
46
|
+
|
|
47
|
+
const incidents = iLive ?? initial.incidents
|
|
48
|
+
const components = cLive ?? initial.components
|
|
49
|
+
const updates = uLive ?? initial.updates
|
|
50
|
+
|
|
51
|
+
const overall = deriveOverall(incidents, components)
|
|
52
|
+
const grid = uptimeGrid(incidents)
|
|
53
|
+
const pct = uptimePercent(grid)
|
|
54
|
+
|
|
55
|
+
const updatesFor = (incidentId: string): ReadonlyArray<Update> =>
|
|
56
|
+
updates
|
|
57
|
+
.filter((u) => u.incidentId === incidentId)
|
|
58
|
+
.slice()
|
|
59
|
+
.sort((a, b) => new Date(a.createdAt).getTime() - new Date(b.createdAt).getTime())
|
|
60
|
+
|
|
61
|
+
return (
|
|
62
|
+
<main>
|
|
63
|
+
{/* Overall banner */}
|
|
64
|
+
<div className={`banner banner--${overall}`} role="status">
|
|
65
|
+
<span className="dot" aria-hidden="true" />
|
|
66
|
+
<strong><T id={`overall.${overall}`} /></strong>
|
|
67
|
+
</div>
|
|
68
|
+
|
|
69
|
+
{/* Uptime */}
|
|
70
|
+
<section>
|
|
71
|
+
<h2><T id="uptime.heading" values={{ days: String(grid.length) }} /></h2>
|
|
72
|
+
<div className="uptime" aria-hidden="true">
|
|
73
|
+
{grid.map((up, idx) => (
|
|
74
|
+
<span key={idx} className={up ? 'day up' : 'day down'} />
|
|
75
|
+
))}
|
|
76
|
+
</div>
|
|
77
|
+
<p className="muted"><T id="uptime.percent" values={{ percent: String(pct) }} /></p>
|
|
78
|
+
</section>
|
|
79
|
+
|
|
80
|
+
{/* Components */}
|
|
81
|
+
<section>
|
|
82
|
+
<h2><T id="components.heading" /></h2>
|
|
83
|
+
{components.length === 0 ? (
|
|
84
|
+
<p className="muted"><T id="components.empty" /></p>
|
|
85
|
+
) : (
|
|
86
|
+
<ul className="components">
|
|
87
|
+
{components.map((c) => (
|
|
88
|
+
<li key={c.id}>
|
|
89
|
+
<span>{c.name}</span>
|
|
90
|
+
<span className={`pill pill--${c.status}`}><T id={`comp.status.${c.status}`} /></span>
|
|
91
|
+
</li>
|
|
92
|
+
))}
|
|
93
|
+
</ul>
|
|
94
|
+
)}
|
|
95
|
+
</section>
|
|
96
|
+
|
|
97
|
+
{/* Incidents */}
|
|
98
|
+
<section>
|
|
99
|
+
<h2><T id="incidents.heading" /></h2>
|
|
100
|
+
{incidents.length === 0 ? (
|
|
101
|
+
<p className="muted"><T id="incidents.none" /></p>
|
|
102
|
+
) : (
|
|
103
|
+
<ul className="incidents">
|
|
104
|
+
{incidents.map((inc) => (
|
|
105
|
+
<li key={inc.id} className={`incident impact--${inc.impact}`}>
|
|
106
|
+
<div className="incident-head">
|
|
107
|
+
<strong>{inc.title}</strong>
|
|
108
|
+
<span className="pill"><T id={`impact.${inc.impact}`} /></span>
|
|
109
|
+
<span className="pill"><T id={`status.${inc.status}`} /></span>
|
|
110
|
+
</div>
|
|
111
|
+
<p className="muted">
|
|
112
|
+
<T id="incident.started" values={{ when: fmtDate(inc.startedAt) }} />
|
|
113
|
+
{' · '}
|
|
114
|
+
{inc.resolvedAt == null
|
|
115
|
+
? <T id="incident.ongoing" />
|
|
116
|
+
: <T id="incident.resolved" values={{ when: fmtDate(inc.resolvedAt) }} />}
|
|
117
|
+
</p>
|
|
118
|
+
{updatesFor(inc.id).length > 0 ? (
|
|
119
|
+
<ul className="timeline">
|
|
120
|
+
{updatesFor(inc.id).map((u) => (
|
|
121
|
+
<li key={u.id}>
|
|
122
|
+
<span className="ts">{fmtDate(u.createdAt)}</span>
|
|
123
|
+
<span className="pill"><T id={`status.${u.status}`} /></span>
|
|
124
|
+
<span>{u.body}</span>
|
|
125
|
+
</li>
|
|
126
|
+
))}
|
|
127
|
+
</ul>
|
|
128
|
+
) : null}
|
|
129
|
+
</li>
|
|
130
|
+
))}
|
|
131
|
+
</ul>
|
|
132
|
+
)}
|
|
133
|
+
</section>
|
|
134
|
+
</main>
|
|
135
|
+
)
|
|
136
|
+
}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
{
|
|
2
|
+
"id": "frontend-status",
|
|
3
|
+
"kind": "web",
|
|
4
|
+
"summary": "A public status page — a clean live-useSubscription showcase. An SSR shell bakes the current incidents + components into the first paint (crawlable), then upgrades to live: the banner, 90-day uptime grid and incident timeline update within seconds when an operator posts, with no polling. Pairs with the api-status backend. Bilingual (en/de), no auth (it must stay up when the product is down).",
|
|
5
|
+
"tags": ["web", "frontend", "status-page", "live", "useSubscription", "ssr", "uptime"]
|
|
6
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
{
|
|
2
|
+
"extends": "../../../tsconfig.base.json",
|
|
3
|
+
"compilerOptions": {
|
|
4
|
+
"jsx": "react-jsx",
|
|
5
|
+
"lib": ["ES2024", "DOM", "DOM.Iterable"],
|
|
6
|
+
"module": "ESNext",
|
|
7
|
+
"moduleResolution": "Bundler"
|
|
8
|
+
},
|
|
9
|
+
"include": ["src/**/*"],
|
|
10
|
+
"exclude": ["node_modules", "dist", ".framework"]
|
|
11
|
+
}
|
|
@@ -59,6 +59,21 @@ services:
|
|
|
59
59
|
NODE_ENV: production
|
|
60
60
|
DB_URL: postgres://{{projectNameSnake}}:${POSTGRES_PASSWORD:-change-me-in-prod}@postgres:5432/{{projectNameSnake}}
|
|
61
61
|
VOLTRO_SESSION_SECRET: ${VOLTRO_SESSION_SECRET:?must be set for prod compose}
|
|
62
|
+
# Only needed once an app turns on a plugin that encrypts columns at rest
|
|
63
|
+
# (`governance` with `fieldEncryption`, or any `.encrypted()` column). It
|
|
64
|
+
# is commented out because a generated file cannot know which plugins you
|
|
65
|
+
# will enable — and left here, named, because the alternative is finding
|
|
66
|
+
# out at `onActivate` in a container:
|
|
67
|
+
#
|
|
68
|
+
# governance: fieldEncryption is enabled but secret
|
|
69
|
+
# "VOLTRO_FIELD_ENCRYPTION_KEY" did not resolve
|
|
70
|
+
#
|
|
71
|
+
# Mint it with `voltro secret generate field-encryption` — same shape as
|
|
72
|
+
# `openssl rand -hex 32`, but it is the documented path and it cannot
|
|
73
|
+
# produce the wrong length. LOSE THE KEY, LOSE THE DATA: there is no
|
|
74
|
+
# recovery for a column encrypted under a key you no longer have, so back
|
|
75
|
+
# it up wherever you keep the session secret.
|
|
76
|
+
# VOLTRO_FIELD_ENCRYPTION_KEY: ${VOLTRO_FIELD_ENCRYPTION_KEY:?must be set once fieldEncryption is on}
|
|
62
77
|
ports:
|
|
63
78
|
- "4000:4000"
|
|
64
79
|
depends_on:
|
|
@@ -83,6 +83,21 @@ services:
|
|
|
83
83
|
S3_SECRET_ACCESS_KEY: ${S3_SECRET_ACCESS_KEY:-minioadmin}
|
|
84
84
|
S3_FORCE_PATH_STYLE: "1"
|
|
85
85
|
VOLTRO_SESSION_SECRET: ${VOLTRO_SESSION_SECRET:?must be set for prod compose}
|
|
86
|
+
# Only needed once an app turns on a plugin that encrypts columns at rest
|
|
87
|
+
# (`governance` with `fieldEncryption`, or any `.encrypted()` column). It
|
|
88
|
+
# is commented out because a generated file cannot know which plugins you
|
|
89
|
+
# will enable — and left here, named, because the alternative is finding
|
|
90
|
+
# out at `onActivate` in a container:
|
|
91
|
+
#
|
|
92
|
+
# governance: fieldEncryption is enabled but secret
|
|
93
|
+
# "VOLTRO_FIELD_ENCRYPTION_KEY" did not resolve
|
|
94
|
+
#
|
|
95
|
+
# Mint it with `voltro secret generate field-encryption` — same shape as
|
|
96
|
+
# `openssl rand -hex 32`, but it is the documented path and it cannot
|
|
97
|
+
# produce the wrong length. LOSE THE KEY, LOSE THE DATA: there is no
|
|
98
|
+
# recovery for a column encrypted under a key you no longer have, so back
|
|
99
|
+
# it up wherever you keep the session secret.
|
|
100
|
+
# VOLTRO_FIELD_ENCRYPTION_KEY: ${VOLTRO_FIELD_ENCRYPTION_KEY:?must be set once fieldEncryption is on}
|
|
86
101
|
ports:
|
|
87
102
|
- "4000:4000"
|
|
88
103
|
depends_on:
|
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
//#region src/fileConventions.ts
|
|
2
|
-
var e = /\.(query|mutation|action|stream)\.ts$/, t = /\.(query|mutation|action|stream)\.server\.ts$/, n = /\.event\.ts$/, r = /\.workflow\.tsx$/, i = /\.workflow\.server\.tsx$/, a = /\.workflow\.tsx?$/, o = /\.trigger\.tsx?$/, s = /\.cron\.tsx?$/, c = /\.webhook\.tsx?$/, l = /\.outbox\.tsx?$/, u = /\.subscribe\.tsx?$/, d = /\.reaction\.tsx?$/, f = /\.aggregate\.tsx?$/, p = /\.startup\.tsx?$/, m = /\.seed\.ts$/, h = /\.relations\.ts$/, g = /\.entity\.ts$|\.schema\.ts$|^schema\.ts$/, _ = (e) => a.test(e) && !r.test(e) && !i.test(e), v = /(?:^|\/)page\.tsx$/, y = /\.island\.tsx?$/, b = /\.component\.tsx$/, x = /\.component\.ui\.tsx$/, S = /\.hook\.tsx?$/, C = /\.internal\.tsx?$/, w = /\.types\.tsx?$/, T = /\.fixture\.tsx?$/, E = /\.tracking\.tsx?$/, D = /\.store\.tsx?$/, O = /\.client\.tsx?$/, k = /\.(test|spec)\.tsx?$/, A = [
|
|
3
|
-
e,
|
|
4
|
-
t,
|
|
5
|
-
a,
|
|
6
|
-
i,
|
|
7
|
-
o,
|
|
8
|
-
s,
|
|
9
|
-
c,
|
|
10
|
-
l,
|
|
11
|
-
u,
|
|
12
|
-
d,
|
|
13
|
-
f,
|
|
14
|
-
p,
|
|
15
|
-
m,
|
|
16
|
-
h,
|
|
17
|
-
g,
|
|
18
|
-
/\.route\.tsx?$/,
|
|
19
|
-
n,
|
|
20
|
-
D,
|
|
21
|
-
O,
|
|
22
|
-
/\.(agent|tool|email|connection|serverless|server|config|generated)\.tsx?$/
|
|
23
|
-
], j = (e) => A.some((t) => t.test(e)), M = /* @__PURE__ */ new Set([
|
|
24
|
-
"layout.tsx",
|
|
25
|
-
"error.tsx",
|
|
26
|
-
"loading.tsx",
|
|
27
|
-
"not-found.tsx"
|
|
28
|
-
]);
|
|
29
|
-
//#endregion
|
|
30
|
-
export { j as A, E as C, r as D, c as E, a as O, k as S, w as T, g as _, n as a, D as b, C as c, v as d, M as f, h as g, d as h, s as i, _ as j, i as k, y as l, t as m, b as n, T as o, e as p, x as r, S as s, f as t, l as u, m as v, o as w, u as x, p as y };
|
package/dist/inspect-gt8bq-Tz.js
DELETED