@growth-labs/cms 0.7.0 → 0.8.1
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/dist/engine/fronts-publish-intent.d.ts +25 -1
- package/dist/engine/fronts-publish-intent.d.ts.map +1 -1
- package/dist/engine/fronts-publish-intent.js +64 -11
- package/dist/engine/fronts-publish-intent.js.map +1 -1
- package/dist/engine/index.d.ts +1 -0
- package/dist/engine/index.d.ts.map +1 -1
- package/dist/engine/index.js +1 -0
- package/dist/engine/index.js.map +1 -1
- package/dist/engine/video-source.d.ts +26 -0
- package/dist/engine/video-source.d.ts.map +1 -0
- package/dist/engine/video-source.js +31 -0
- package/dist/engine/video-source.js.map +1 -0
- package/dist/providers/types.d.ts +40 -3
- package/dist/providers/types.d.ts.map +1 -1
- package/dist/providers/types.js +17 -0
- package/dist/providers/types.js.map +1 -1
- package/dist/routes/calendar.d.ts +26 -0
- package/dist/routes/calendar.d.ts.map +1 -1
- package/dist/routes/calendar.js +41 -0
- package/dist/routes/calendar.js.map +1 -1
- package/dist/routes/content.d.ts +2 -0
- package/dist/routes/content.d.ts.map +1 -1
- package/dist/routes/content.js.map +1 -1
- package/dist/routes/fronts-publish.d.ts.map +1 -1
- package/dist/routes/fronts-publish.js +1 -0
- package/dist/routes/fronts-publish.js.map +1 -1
- package/dist/ui/api/_content-config.d.ts.map +1 -1
- package/dist/ui/api/_content-config.js +1 -0
- package/dist/ui/api/_content-config.js.map +1 -1
- package/dist/ui/api/calendar.d.ts.map +1 -1
- package/dist/ui/api/calendar.js +5 -1
- package/dist/ui/api/calendar.js.map +1 -1
- package/dist/ui/screens/CalendarScreen.d.ts.map +1 -1
- package/dist/ui/screens/CalendarScreen.js +10 -1
- package/dist/ui/screens/CalendarScreen.js.map +1 -1
- package/dist/ui/screens/calendar-data.d.ts +3 -0
- package/dist/ui/screens/calendar-data.d.ts.map +1 -1
- package/dist/ui/screens/calendar-data.js.map +1 -1
- package/dist/ui/screens/go-publish-badge.d.ts +11 -0
- package/dist/ui/screens/go-publish-badge.d.ts.map +1 -0
- package/dist/ui/screens/go-publish-badge.js +47 -0
- package/dist/ui/screens/go-publish-badge.js.map +1 -0
- package/package.json +1 -1
- package/src/engine/fronts-publish-intent.ts +104 -15
- package/src/engine/index.ts +5 -0
- package/src/engine/video-source.ts +45 -0
- package/src/providers/types.ts +51 -1
- package/src/routes/calendar.ts +72 -0
- package/src/routes/content.ts +2 -0
- package/src/routes/fronts-publish.ts +1 -0
- package/src/ui/api/_content-config.ts +2 -0
- package/src/ui/api/calendar.ts +5 -1
- package/src/ui/screens/CalendarScreen.tsx +22 -0
- package/src/ui/screens/calendar-data.ts +4 -0
- package/src/ui/screens/go-publish-badge.ts +55 -0
package/src/ui/api/calendar.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
// src/ui/api/calendar.ts — Astro endpoint adapter for GET /admin/api/calendar.
|
|
2
2
|
// Maps the APIContext onto a RouteContext and delegates to createCalendarRoutes().month.
|
|
3
|
-
// The calendar is first-party D1
|
|
3
|
+
// The calendar is first-party D1; the host's Foundry provider (locals.cmsHooks.foundryVideo)
|
|
4
|
+
// adds the Go publish badge state to scheduled media items when present (W1-08b).
|
|
4
5
|
|
|
5
6
|
import type { APIContext } from 'astro'
|
|
6
7
|
import { type CalendarRouteConfig, createCalendarRoutes } from '../../routes/calendar.js'
|
|
@@ -13,8 +14,11 @@ function toCtx(c: APIContext): RouteContext {
|
|
|
13
14
|
}
|
|
14
15
|
|
|
15
16
|
function calendarConfig(c: APIContext): CalendarRouteConfig {
|
|
17
|
+
const hooks = (c.locals as { cmsHooks?: { foundryVideo?: CalendarRouteConfig['foundryVideo'] } })
|
|
18
|
+
.cmsHooks
|
|
16
19
|
return {
|
|
17
20
|
authz: buildSiteAuthz(c),
|
|
21
|
+
foundryVideo: hooks?.foundryVideo,
|
|
18
22
|
}
|
|
19
23
|
}
|
|
20
24
|
|
|
@@ -18,6 +18,7 @@
|
|
|
18
18
|
import { useCallback, useEffect, useReducer, useState } from 'react'
|
|
19
19
|
import { Icon } from '../icons.js'
|
|
20
20
|
import { buildCalendarMonth, type CalendarCell, type CalendarItem } from './calendar-data.js'
|
|
21
|
+
import { goPublishBadge } from './go-publish-badge.js'
|
|
21
22
|
|
|
22
23
|
// ---------------------------------------------------------------------------
|
|
23
24
|
// Props
|
|
@@ -483,6 +484,10 @@ function CalendarItemChip({
|
|
|
483
484
|
const border = TYPE_COLOR[item.type] ?? 'var(--accent)'
|
|
484
485
|
const statusIcon = STATUS_ICON[item.status]
|
|
485
486
|
const statusColor = STATUS_ICON_COLOR[item.status] ?? 'var(--ink-faint)'
|
|
487
|
+
// W1-08b: the Go publish state of a scheduled media item, from the
|
|
488
|
+
// host's receipts (route: goPublish). Hover shows the receipt and the
|
|
489
|
+
// correlation id; the pill vocabulary is the Foundry tab's.
|
|
490
|
+
const badge = goPublishBadge(item.goPublish)
|
|
486
491
|
|
|
487
492
|
return (
|
|
488
493
|
<div
|
|
@@ -520,6 +525,23 @@ function CalendarItemChip({
|
|
|
520
525
|
>
|
|
521
526
|
{item.title || '(Untitled)'}
|
|
522
527
|
</button>
|
|
528
|
+
{badge && (
|
|
529
|
+
<span
|
|
530
|
+
className={
|
|
531
|
+
badge.pill === 'ready'
|
|
532
|
+
? 'pill published'
|
|
533
|
+
: badge.pill === 'failed'
|
|
534
|
+
? 'pill review'
|
|
535
|
+
: 'pill processing'
|
|
536
|
+
}
|
|
537
|
+
title={badge.tooltip}
|
|
538
|
+
data-go-publish={item.goPublish?.state}
|
|
539
|
+
style={{ flex: 'none', fontSize: 9, padding: '1px 5px', whiteSpace: 'nowrap' }}
|
|
540
|
+
>
|
|
541
|
+
<span className="pdot" />
|
|
542
|
+
{badge.label}
|
|
543
|
+
</span>
|
|
544
|
+
)}
|
|
523
545
|
{statusIcon &&
|
|
524
546
|
(item.status === 'scheduled' ? (
|
|
525
547
|
<button
|
|
@@ -13,6 +13,8 @@
|
|
|
13
13
|
// Types
|
|
14
14
|
// ---------------------------------------------------------------------------
|
|
15
15
|
|
|
16
|
+
import type { CalendarGoPublish } from '../../routes/calendar.js'
|
|
17
|
+
|
|
16
18
|
/**
|
|
17
19
|
* A dated content item as returned by the `/admin/api/calendar?from=&to=` route.
|
|
18
20
|
* `date` is an ISO-8601 string (date-only or with time component, UTC-assumed).
|
|
@@ -24,6 +26,8 @@ export interface CalendarItem {
|
|
|
24
26
|
slug: string
|
|
25
27
|
title: string
|
|
26
28
|
date: string
|
|
29
|
+
/** Go publish state of a scheduled video/podcast item (W1-08b); see go-publish-badge.ts. */
|
|
30
|
+
goPublish?: CalendarGoPublish | null
|
|
27
31
|
}
|
|
28
32
|
|
|
29
33
|
/** A leading blank cell before the first day of the month. */
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
// src/ui/screens/go-publish-badge.ts — pure badge model for a scheduled media
|
|
2
|
+
// item's Go publish state (W1-08b).
|
|
3
|
+
//
|
|
4
|
+
// goPublishBadge(goPublish) → { label, pill, tooltip } | null
|
|
5
|
+
// label — the word the chip shows ("Captured", "Processing", …)
|
|
6
|
+
// pill — the FoundryPillState bucket the broadsheet pill classes render
|
|
7
|
+
// (working / ready / failed), reused from foundry-stages
|
|
8
|
+
// tooltip — the hover text: label, the newest receipt and its time, the
|
|
9
|
+
// correlation id, and the blocked reason when there is one
|
|
10
|
+
//
|
|
11
|
+
// Pure — no DOM, no React, fully vitest-testable.
|
|
12
|
+
|
|
13
|
+
import type { CalendarGoPublish } from '../../routes/calendar.js'
|
|
14
|
+
import type { FoundryPillState } from '../inspector/foundry-stages.js'
|
|
15
|
+
|
|
16
|
+
export interface GoPublishBadge {
|
|
17
|
+
label: string
|
|
18
|
+
pill: FoundryPillState
|
|
19
|
+
tooltip: string
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
const LABELS: Record<string, { label: string; pill: FoundryPillState }> = {
|
|
23
|
+
pending: { label: 'Not captured', pill: 'working' },
|
|
24
|
+
captured: { label: 'Captured', pill: 'working' },
|
|
25
|
+
processing: { label: 'Processing', pill: 'working' },
|
|
26
|
+
media_ready: { label: 'Media ready', pill: 'ready' },
|
|
27
|
+
publishing: { label: 'Publishing', pill: 'working' },
|
|
28
|
+
published: { label: 'Published', pill: 'ready' },
|
|
29
|
+
late: { label: 'Late', pill: 'failed' },
|
|
30
|
+
failed: { label: 'Blocked', pill: 'failed' },
|
|
31
|
+
unavailable: { label: 'State unavailable', pill: 'failed' },
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
/** Format a unix-second receipt time for the tooltip (UTC, to the minute). */
|
|
35
|
+
export function formatReceiptTime(unixSeconds: number): string {
|
|
36
|
+
return `${new Date(unixSeconds * 1000).toISOString().slice(0, 16).replace('T', ' ')} UTC`
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export function goPublishBadge(
|
|
40
|
+
goPublish: CalendarGoPublish | null | undefined,
|
|
41
|
+
): GoPublishBadge | null {
|
|
42
|
+
if (!goPublish) return null
|
|
43
|
+
const entry = LABELS[goPublish.state] ?? { label: goPublish.state, pill: 'working' as const }
|
|
44
|
+
const lines = [`Go publish: ${entry.label}`]
|
|
45
|
+
if (goPublish.eventKind && goPublish.receiptAt !== null) {
|
|
46
|
+
lines.push(`Last receipt: ${goPublish.eventKind} at ${formatReceiptTime(goPublish.receiptAt)}`)
|
|
47
|
+
} else if (goPublish.eventKind) {
|
|
48
|
+
lines.push(`Last receipt: ${goPublish.eventKind}`)
|
|
49
|
+
} else {
|
|
50
|
+
lines.push('No receipt yet')
|
|
51
|
+
}
|
|
52
|
+
if (goPublish.correlationId) lines.push(`Correlation: ${goPublish.correlationId}`)
|
|
53
|
+
if (goPublish.blockedReason) lines.push(`Reason: ${goPublish.blockedReason}`)
|
|
54
|
+
return { label: entry.label, pill: entry.pill, tooltip: lines.join('\n') }
|
|
55
|
+
}
|