@openrails/contentkit-ui 0.104.0-rc.1 → 0.104.0-rc.3
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/README.md +6 -6
- package/dist/client/beacons.js +4 -1
- package/dist/client/beacons.js.map +1 -1
- package/dist/client/contents.d.ts +9 -1
- package/dist/client/contents.js +73 -55
- package/dist/client/contents.js.map +1 -1
- package/dist/client/discovery.d.ts +6 -2
- package/dist/client/discovery.js +1 -1
- package/dist/client/discovery.js.map +1 -1
- package/dist/client/generated/error-codes.d.ts +1 -1
- package/dist/client/generated/error-codes.js +4 -0
- package/dist/client/generated/error-codes.js.map +1 -1
- package/dist/client/generated/routes.d.ts +43 -30
- package/dist/client/generated/routes.js +70 -63
- package/dist/client/generated/routes.js.map +1 -1
- package/dist/client/generated/wire.d.ts +36 -74
- package/dist/client/generated/wire.js.map +1 -1
- package/dist/client/index.d.ts +1 -1
- package/dist/client/media/windows.d.ts +2 -0
- package/dist/client/media/windows.js +4 -1
- package/dist/client/media/windows.js.map +1 -1
- package/dist/client/stats.d.ts +4 -20
- package/dist/client/stats.js +0 -11
- package/dist/client/stats.js.map +1 -1
- package/dist/client/versions.d.ts +8 -6
- package/dist/client/versions.js +15 -10
- package/dist/client/versions.js.map +1 -1
- package/dist/components/admin/bulk-drafts.d.ts +17 -0
- package/dist/components/admin/bulk-drafts.js +41 -0
- package/dist/components/admin/bulk-drafts.js.map +1 -0
- package/dist/components/admin/content-admin.d.ts +1 -1
- package/dist/components/admin/content-admin.js.map +1 -1
- package/dist/components/admin/content-manager.d.ts +11 -3
- package/dist/components/admin/content-manager.js +739 -380
- package/dist/components/admin/content-manager.js.map +1 -1
- package/dist/components/admin/group-manager.d.ts +8 -3
- package/dist/components/admin/group-manager.js +218 -146
- package/dist/components/admin/group-manager.js.map +1 -1
- package/dist/components/admin/page-notices.d.ts +16 -0
- package/dist/components/admin/page-notices.js +113 -0
- package/dist/components/admin/page-notices.js.map +1 -0
- package/dist/components/admin/page-picker.d.ts +38 -0
- package/dist/components/admin/page-picker.js +159 -0
- package/dist/components/admin/page-picker.js.map +1 -0
- package/dist/components/admin/reader-content-editor.js +537 -500
- package/dist/components/admin/reader-content-editor.js.map +1 -1
- package/dist/components/admin/reader-manifest.js +181 -179
- package/dist/components/admin/reader-manifest.js.map +1 -1
- package/dist/components/admin/shell.d.ts +10 -2
- package/dist/components/admin/shell.js +114 -42
- package/dist/components/admin/shell.js.map +1 -1
- package/dist/components/admin/stats-dashboard.d.ts +4 -9
- package/dist/components/admin/stats-dashboard.js +300 -202
- package/dist/components/admin/stats-dashboard.js.map +1 -1
- package/dist/components/admin/upload-queue.d.ts +14 -0
- package/dist/components/admin/upload-queue.js +115 -98
- package/dist/components/admin/upload-queue.js.map +1 -1
- package/dist/components/content/card.d.ts +31 -3
- package/dist/components/content/card.js +324 -158
- package/dist/components/content/card.js.map +1 -1
- package/dist/components/content/daily-releases.js +14 -12
- package/dist/components/content/daily-releases.js.map +1 -1
- package/dist/components/content/editor-save.js +27 -25
- package/dist/components/content/editor-save.js.map +1 -1
- package/dist/components/content/editors.js +274 -253
- package/dist/components/content/editors.js.map +1 -1
- package/dist/components/content/favorites.d.ts +1 -1
- package/dist/components/content/favorites.js +36 -22
- package/dist/components/content/favorites.js.map +1 -1
- package/dist/components/content/grid.d.ts +11 -4
- package/dist/components/content/grid.js +52 -43
- package/dist/components/content/grid.js.map +1 -1
- package/dist/components/content/history.js +83 -63
- package/dist/components/content/history.js.map +1 -1
- package/dist/components/content/index.d.ts +5 -3
- package/dist/components/content/listing.d.ts +14 -3
- package/dist/components/content/listing.js +65 -56
- package/dist/components/content/listing.js.map +1 -1
- package/dist/components/content/offer-fields.js +6 -6
- package/dist/components/content/paged-grid.d.ts +10 -0
- package/dist/components/content/paged-grid.js +116 -0
- package/dist/components/content/paged-grid.js.map +1 -0
- package/dist/components/content/pagination.d.ts +19 -0
- package/dist/components/content/pagination.js +97 -0
- package/dist/components/content/pagination.js.map +1 -0
- package/dist/components/content/paywall.d.ts +9 -0
- package/dist/components/content/paywall.js +27 -3
- package/dist/components/content/paywall.js.map +1 -1
- package/dist/components/content/post-list.d.ts +37 -0
- package/dist/components/content/post-list.js +203 -0
- package/dist/components/content/post-list.js.map +1 -0
- package/dist/components/content/reader-settings.d.ts +2 -0
- package/dist/components/content/reader-settings.js +1 -1
- package/dist/components/content/reader-settings.js.map +1 -1
- package/dist/components/groups/banner.d.ts +6 -2
- package/dist/components/groups/banner.js +79 -61
- package/dist/components/groups/banner.js.map +1 -1
- package/dist/components/groups/directory.d.ts +12 -2
- package/dist/components/groups/directory.js +168 -105
- package/dist/components/groups/directory.js.map +1 -1
- package/dist/components/groups/editor.js +10 -10
- package/dist/components/groups/editor.js.map +1 -1
- package/dist/components/groups/entity-chips.d.ts +61 -0
- package/dist/components/groups/entity-chips.js +382 -0
- package/dist/components/groups/entity-chips.js.map +1 -0
- package/dist/components/groups/group-members.d.ts +29 -0
- package/dist/components/groups/group-members.js +474 -0
- package/dist/components/groups/group-members.js.map +1 -0
- package/dist/components/groups/header.js +53 -45
- package/dist/components/groups/header.js.map +1 -1
- package/dist/components/groups/index.d.ts +3 -1
- package/dist/components/groups/memberships.d.ts +3 -36
- package/dist/components/groups/memberships.js +105 -480
- package/dist/components/groups/memberships.js.map +1 -1
- package/dist/components/groups/scoped.d.ts +23 -0
- package/dist/components/groups/scoped.js +92 -0
- package/dist/components/groups/scoped.js.map +1 -0
- package/dist/components/media-folder-editor.d.ts +5 -0
- package/dist/components/media-folder-editor.js +418 -230
- package/dist/components/media-folder-editor.js.map +1 -1
- package/dist/components/social/poll.js +57 -48
- package/dist/components/social/poll.js.map +1 -1
- package/dist/components/sortable-list.d.ts +5 -1
- package/dist/components/sortable-list.js +97 -81
- package/dist/components/sortable-list.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +41 -37
- package/dist/locales/admin/de.js +78 -45
- package/dist/locales/admin/de.js.map +1 -1
- package/dist/locales/admin/en.d.ts +74 -41
- package/dist/locales/admin/en.js +78 -45
- package/dist/locales/admin/en.js.map +1 -1
- package/dist/locales/admin/es.js +78 -45
- package/dist/locales/admin/es.js.map +1 -1
- package/dist/locales/admin/ja.js +78 -45
- package/dist/locales/admin/ja.js.map +1 -1
- package/dist/locales/admin/ko.js +78 -45
- package/dist/locales/admin/ko.js.map +1 -1
- package/dist/locales/admin/zh.js +78 -45
- package/dist/locales/admin/zh.js.map +1 -1
- package/dist/locales/de.js +2 -0
- package/dist/locales/de.js.map +1 -1
- package/dist/locales/discovery/de.js +25 -1
- package/dist/locales/discovery/de.js.map +1 -1
- package/dist/locales/discovery/en.d.ts +24 -0
- package/dist/locales/discovery/en.js +25 -1
- package/dist/locales/discovery/en.js.map +1 -1
- package/dist/locales/discovery/es.js +25 -1
- package/dist/locales/discovery/es.js.map +1 -1
- package/dist/locales/discovery/ja.js +25 -1
- package/dist/locales/discovery/ja.js.map +1 -1
- package/dist/locales/discovery/ko.js +25 -1
- package/dist/locales/discovery/ko.js.map +1 -1
- package/dist/locales/discovery/zh.js +25 -1
- package/dist/locales/discovery/zh.js.map +1 -1
- package/dist/locales/en.d.ts +120 -43
- package/dist/locales/en.js +2 -0
- package/dist/locales/en.js.map +1 -1
- package/dist/locales/es.js +2 -0
- package/dist/locales/es.js.map +1 -1
- package/dist/locales/groups/de.js +22 -4
- package/dist/locales/groups/de.js.map +1 -1
- package/dist/locales/groups/en.d.ts +20 -2
- package/dist/locales/groups/en.js +22 -4
- package/dist/locales/groups/en.js.map +1 -1
- package/dist/locales/groups/es.js +22 -4
- package/dist/locales/groups/es.js.map +1 -1
- package/dist/locales/groups/ja.js +22 -4
- package/dist/locales/groups/ja.js.map +1 -1
- package/dist/locales/groups/ko.js +22 -4
- package/dist/locales/groups/ko.js.map +1 -1
- package/dist/locales/groups/zh.js +22 -4
- package/dist/locales/groups/zh.js.map +1 -1
- package/dist/locales/ja.js +2 -0
- package/dist/locales/ja.js.map +1 -1
- package/dist/locales/ko.js +2 -0
- package/dist/locales/ko.js.map +1 -1
- package/dist/locales/zh.js +2 -0
- package/dist/locales/zh.js.map +1 -1
- package/dist/react/contents.js +1 -1
- package/dist/react/contents.js.map +1 -1
- package/dist/react/discovery.d.ts +16 -0
- package/dist/react/discovery.js +69 -37
- package/dist/react/discovery.js.map +1 -1
- package/dist/react/groups.d.ts +19 -3
- package/dist/react/groups.js +49 -22
- package/dist/react/groups.js.map +1 -1
- package/dist/react/index.d.ts +6 -4
- package/dist/react/page-notices.d.ts +13 -0
- package/dist/react/page-notices.js +38 -0
- package/dist/react/page-notices.js.map +1 -0
- package/dist/react/post-reads.d.ts +23 -0
- package/dist/react/post-reads.js +90 -0
- package/dist/react/post-reads.js.map +1 -0
- package/dist/react/remembered-sort.d.ts +5 -0
- package/dist/react/remembered-sort.js +29 -0
- package/dist/react/remembered-sort.js.map +1 -0
- package/dist/react/resources.js +2 -2
- package/dist/react/resources.js.map +1 -1
- package/dist/react/stats.d.ts +3 -7
- package/dist/react/stats.js +2 -6
- package/dist/react/stats.js.map +1 -1
- package/dist/react/use-engagement.d.ts +2 -0
- package/dist/react/use-engagement.js +40 -34
- package/dist/react/use-engagement.js.map +1 -1
- package/dist/react.js +29 -27
- package/dist/styles.css +1 -1
- package/dist/urls/index.d.ts +1 -1
- package/dist/urls.js +2 -2
- package/dist/urls.js.map +1 -1
- package/package.json +1 -1
- package/dist/components/admin/page-review.d.ts +0 -13
- package/dist/components/admin/page-review.js +0 -225
- package/dist/components/admin/page-review.js.map +0 -1
- package/dist/react/page-review.d.ts +0 -14
- package/dist/react/page-review.js +0 -37
- package/dist/react/page-review.js.map +0 -1
|
@@ -0,0 +1,474 @@
|
|
|
1
|
+
import { useMessages as e } from "../../i18n/context.js";
|
|
2
|
+
import { ContentKitUiRoot as t } from "../../scope.js";
|
|
3
|
+
import { useContentKitClient as n } from "../../react/context.js";
|
|
4
|
+
import { useGroupMembers as r, useKinds as i } from "../../react/groups.js";
|
|
5
|
+
import { Button as a, buttonVariants as o } from "../../ui/button.js";
|
|
6
|
+
import { SortableList as s } from "../sortable-list.js";
|
|
7
|
+
import { Badge as c } from "../../ui/badge.js";
|
|
8
|
+
import { Select as l, SelectContent as u, SelectItem as d, SelectTrigger as f, SelectValue as p } from "../../ui/select.js";
|
|
9
|
+
import { Skeleton as m } from "../../ui/skeleton.js";
|
|
10
|
+
import { ErrorLine as h, contentError as g, formatDate as _, useAction as v } from "../social/parts.js";
|
|
11
|
+
import { useTypeahead as y } from "../../react/discovery.js";
|
|
12
|
+
import { labelOf as b } from "./parts.js";
|
|
13
|
+
import { WindowFields as x } from "./entity-chips.js";
|
|
14
|
+
import { accessLabel as S, contentStatus as C } from "../admin/content-manager.js";
|
|
15
|
+
import { useCallback as w, useEffect as T, useId as E, useMemo as D, useState as O } from "react";
|
|
16
|
+
import { Fragment as k, jsx as A, jsxs as j } from "react/jsx-runtime";
|
|
17
|
+
import { cn as M } from "cn";
|
|
18
|
+
import { Cancel01Icon as N, Image01Icon as P, Tick02Icon as F } from "@hugeicons/core-free-icons";
|
|
19
|
+
import { HugeiconsIcon as I } from "@hugeicons/react";
|
|
20
|
+
//#region src/components/groups/group-members.tsx
|
|
21
|
+
var L = "__none__", R = 100, z = (e) => `${e.content_id}|${e.version_id ?? ""}`;
|
|
22
|
+
function B(e, t) {
|
|
23
|
+
let [n, r] = O(/* @__PURE__ */ new Map()), i = D(() => [...new Set(e)].sort(), [e]);
|
|
24
|
+
return T(() => {
|
|
25
|
+
let e = i.filter((e) => !n.has(e));
|
|
26
|
+
if (!e.length) return;
|
|
27
|
+
let a = new AbortController(), o = [];
|
|
28
|
+
for (let t = 0; t < e.length; t += R) o.push(e.slice(t, t + R));
|
|
29
|
+
return Promise.all(o.map((e) => t.contents.manage({
|
|
30
|
+
ids: e,
|
|
31
|
+
limit: e.length
|
|
32
|
+
}, a.signal).catch(() => []))).then((e) => {
|
|
33
|
+
a.signal.aborted || r((t) => {
|
|
34
|
+
let n = new Map(t);
|
|
35
|
+
for (let t of e.flat()) n.set(t.id, t);
|
|
36
|
+
return n;
|
|
37
|
+
});
|
|
38
|
+
}), () => a.abort();
|
|
39
|
+
}, [i, t]), n;
|
|
40
|
+
}
|
|
41
|
+
var V = (e) => e?.cover?.url ?? e?.versions.find((e) => e.cover?.url)?.cover?.url;
|
|
42
|
+
function H(l) {
|
|
43
|
+
let u = e(), { t: d } = u, f = n(l.client), { kinds: p } = i({ client: l.client }), y = p?.entity_kinds?.[l.group.kind] ?? {}, w = r(l.group.id, {
|
|
44
|
+
pageSize: l.pageSize,
|
|
45
|
+
client: l.client
|
|
46
|
+
}), T = B(D(() => w.items.map((e) => e.content_id).filter(Boolean), [w.items]), f), E = v("membership.save", l.onError), [L, R] = O(null), [H, W] = O({}), G = (e) => T.get(e.content_id ?? "")?.title || e.content_id || "", K = (e) => `${G(e)}${e.version_id ? ` (${d("memberships.version")})` : ""}`, ee = (e) => [...new Map(e.map((e) => [z(e), {
|
|
47
|
+
content_id: e.content_id,
|
|
48
|
+
version_id: e.version_id
|
|
49
|
+
}])).values()], q = ({ id: e, ...t }) => t, J = (e, t) => /* @__PURE__ */ j(k, { children: [
|
|
50
|
+
t && t.access.level !== "public" && /* @__PURE__ */ A(c, {
|
|
51
|
+
variant: "secondary",
|
|
52
|
+
children: S(d, t.access, l.labels)
|
|
53
|
+
}),
|
|
54
|
+
t && (t.state === "deleted" || C(t) !== "published") && /* @__PURE__ */ A(c, {
|
|
55
|
+
variant: t.state === "deleted" ? "destructive" : "outline",
|
|
56
|
+
children: d(t.state === "deleted" ? "contentManager.deleted" : `contentManager.${C(t)}`)
|
|
57
|
+
}),
|
|
58
|
+
e.version_id && /* @__PURE__ */ A(c, {
|
|
59
|
+
variant: "outline",
|
|
60
|
+
children: d("memberships.version")
|
|
61
|
+
}),
|
|
62
|
+
e.role && /* @__PURE__ */ A(c, {
|
|
63
|
+
variant: "secondary",
|
|
64
|
+
children: b(l.labels, e.role)
|
|
65
|
+
}),
|
|
66
|
+
e.state === "proposed" && /* @__PURE__ */ A(c, {
|
|
67
|
+
variant: "secondary",
|
|
68
|
+
children: d("memberships.proposed")
|
|
69
|
+
})
|
|
70
|
+
] }), Y = (e) => /* @__PURE__ */ j(k, { children: [
|
|
71
|
+
e.state === "proposed" && /* @__PURE__ */ A(a, {
|
|
72
|
+
size: "icon-xs",
|
|
73
|
+
variant: "secondary",
|
|
74
|
+
disabled: E.pending,
|
|
75
|
+
"aria-label": `${d("memberships.accept")}: ${K(e)}`,
|
|
76
|
+
title: d("memberships.accept"),
|
|
77
|
+
onClick: () => void E.run(() => w.add([{
|
|
78
|
+
...q(e),
|
|
79
|
+
state: "active"
|
|
80
|
+
}])),
|
|
81
|
+
children: /* @__PURE__ */ A(I, {
|
|
82
|
+
icon: F,
|
|
83
|
+
strokeWidth: 2.5
|
|
84
|
+
})
|
|
85
|
+
}),
|
|
86
|
+
l.onUseCover && !e.version_id && /* @__PURE__ */ A(a, {
|
|
87
|
+
size: "icon-xs",
|
|
88
|
+
variant: "secondary",
|
|
89
|
+
"aria-label": `${d("memberships.useCover")}: ${K(e)}`,
|
|
90
|
+
title: d("memberships.useCover"),
|
|
91
|
+
disabled: E.pending || l.group.cover?.content_id === e.content_id && !l.group.cover?.auto,
|
|
92
|
+
onClick: () => void E.run(() => l.onUseCover(e.content_id)),
|
|
93
|
+
children: /* @__PURE__ */ A(I, {
|
|
94
|
+
icon: P,
|
|
95
|
+
strokeWidth: 2
|
|
96
|
+
})
|
|
97
|
+
}),
|
|
98
|
+
/* @__PURE__ */ A(a, {
|
|
99
|
+
size: "icon-xs",
|
|
100
|
+
variant: "secondary",
|
|
101
|
+
disabled: E.pending,
|
|
102
|
+
"aria-label": d("memberships.remove", { name: K(e) }),
|
|
103
|
+
title: d("common.remove"),
|
|
104
|
+
onClick: () => void E.run(() => w.remove([q(e)])),
|
|
105
|
+
children: /* @__PURE__ */ A(I, {
|
|
106
|
+
icon: N,
|
|
107
|
+
strokeWidth: 2.5
|
|
108
|
+
})
|
|
109
|
+
})
|
|
110
|
+
] }), X = (e) => y.windows && (L === e.id ? /* @__PURE__ */ j("span", {
|
|
111
|
+
className: "flex flex-wrap items-center gap-1",
|
|
112
|
+
children: [
|
|
113
|
+
/* @__PURE__ */ A(x, {
|
|
114
|
+
from: H.from,
|
|
115
|
+
until: H.until,
|
|
116
|
+
name: K(e),
|
|
117
|
+
onChange: (e) => W((t) => ({
|
|
118
|
+
from: "active_from" in e ? e.active_from : t.from,
|
|
119
|
+
until: "active_until" in e ? e.active_until : t.until
|
|
120
|
+
}))
|
|
121
|
+
}),
|
|
122
|
+
/* @__PURE__ */ A(a, {
|
|
123
|
+
size: "xs",
|
|
124
|
+
disabled: E.pending,
|
|
125
|
+
onClick: () => void E.run(() => w.add([{
|
|
126
|
+
...q(e),
|
|
127
|
+
active_from: H.from,
|
|
128
|
+
active_until: H.until
|
|
129
|
+
}])).then((e) => e !== void 0 && R(null)),
|
|
130
|
+
children: d("common.save")
|
|
131
|
+
}),
|
|
132
|
+
/* @__PURE__ */ A(a, {
|
|
133
|
+
size: "xs",
|
|
134
|
+
variant: "ghost",
|
|
135
|
+
onClick: () => R(null),
|
|
136
|
+
children: d("common.cancel")
|
|
137
|
+
})
|
|
138
|
+
]
|
|
139
|
+
}) : /* @__PURE__ */ A("button", {
|
|
140
|
+
type: "button",
|
|
141
|
+
className: "text-start text-xs text-muted-foreground hover:underline",
|
|
142
|
+
"data-ckui": "member-window",
|
|
143
|
+
onClick: () => {
|
|
144
|
+
W({
|
|
145
|
+
from: e.active_from,
|
|
146
|
+
until: e.active_until
|
|
147
|
+
}), R(e.id);
|
|
148
|
+
},
|
|
149
|
+
children: e.active_from || e.active_until ? d("memberships.window", {
|
|
150
|
+
from: e.active_from ? _(u, e.active_from) : "…",
|
|
151
|
+
until: e.active_until ? _(u, e.active_until) : "…"
|
|
152
|
+
}) : d("memberships.always")
|
|
153
|
+
})), Z = (e, t) => {
|
|
154
|
+
let n = V(e);
|
|
155
|
+
return n ? /* @__PURE__ */ A("img", {
|
|
156
|
+
src: n,
|
|
157
|
+
alt: "",
|
|
158
|
+
loading: "lazy",
|
|
159
|
+
className: M("object-cover", t)
|
|
160
|
+
}) : /* @__PURE__ */ A("span", {
|
|
161
|
+
"aria-hidden": !0,
|
|
162
|
+
className: M("bg-muted", t)
|
|
163
|
+
});
|
|
164
|
+
}, Q = (e, t, n) => {
|
|
165
|
+
let r = T.get(e.content_id ?? ""), i = r && l.contentHref?.(r);
|
|
166
|
+
return i ? /* @__PURE__ */ A("a", {
|
|
167
|
+
href: i,
|
|
168
|
+
className: M("hover:underline", n),
|
|
169
|
+
children: t
|
|
170
|
+
}) : /* @__PURE__ */ A("span", {
|
|
171
|
+
className: n,
|
|
172
|
+
children: t
|
|
173
|
+
});
|
|
174
|
+
}, te = (e) => {
|
|
175
|
+
let t = T.get(e.content_id ?? "");
|
|
176
|
+
return /* @__PURE__ */ j("li", {
|
|
177
|
+
className: "group/member relative grid content-start gap-1.5",
|
|
178
|
+
"data-ckui": "group-member",
|
|
179
|
+
"data-content": e.content_id,
|
|
180
|
+
"data-state": e.state ?? "active",
|
|
181
|
+
children: [
|
|
182
|
+
l.renderContent ? l.renderContent(e, t) : /* @__PURE__ */ j(k, { children: [Q(e, Z(t, "aspect-[7/10] w-full rounded-md"), "block"), Q(e, G(e), M("line-clamp-2 text-sm font-medium break-words", !t && "font-mono text-xs"))] }),
|
|
183
|
+
/* @__PURE__ */ A("span", {
|
|
184
|
+
className: "flex flex-wrap gap-1",
|
|
185
|
+
children: J(e, t)
|
|
186
|
+
}),
|
|
187
|
+
X(e),
|
|
188
|
+
/* @__PURE__ */ A("span", {
|
|
189
|
+
className: "absolute end-1 top-1 flex gap-1 opacity-0 transition-opacity group-hover/member:opacity-100 focus-within:opacity-100",
|
|
190
|
+
children: Y(e)
|
|
191
|
+
})
|
|
192
|
+
]
|
|
193
|
+
}, e.id);
|
|
194
|
+
}, ne = (e, t) => {
|
|
195
|
+
let n = T.get(e.content_id ?? "");
|
|
196
|
+
return /* @__PURE__ */ j("div", {
|
|
197
|
+
className: "group/member flex flex-wrap items-center gap-2",
|
|
198
|
+
"data-ckui": "group-member",
|
|
199
|
+
"data-content": e.content_id,
|
|
200
|
+
"data-state": e.state ?? "active",
|
|
201
|
+
children: [
|
|
202
|
+
t,
|
|
203
|
+
e.position !== void 0 && /* @__PURE__ */ A("span", {
|
|
204
|
+
className: "w-8 text-xs text-muted-foreground tabular-nums",
|
|
205
|
+
children: e.position
|
|
206
|
+
}),
|
|
207
|
+
l.renderContent ? /* @__PURE__ */ A("span", {
|
|
208
|
+
className: "min-w-0 flex-1",
|
|
209
|
+
children: l.renderContent(e, n)
|
|
210
|
+
}) : /* @__PURE__ */ j(k, { children: [Q(e, Z(n, "h-12 w-9 rounded-sm"), "shrink-0"), Q(e, G(e), M("min-w-0 flex-1 break-words", !n && "font-mono text-xs"))] }),
|
|
211
|
+
J(e, n),
|
|
212
|
+
X(e),
|
|
213
|
+
/* @__PURE__ */ A("span", {
|
|
214
|
+
className: "flex gap-1 opacity-60 transition-opacity group-hover/member:opacity-100 focus-within:opacity-100",
|
|
215
|
+
children: Y(e)
|
|
216
|
+
})
|
|
217
|
+
]
|
|
218
|
+
});
|
|
219
|
+
}, $ = D(() => {
|
|
220
|
+
let e = /* @__PURE__ */ new Map();
|
|
221
|
+
for (let t of w.items) {
|
|
222
|
+
let n = T.get(t.content_id ?? "")?.kind ?? "";
|
|
223
|
+
e.set(n, [...e.get(n) ?? [], t]);
|
|
224
|
+
}
|
|
225
|
+
return [...e].sort(([e], [t]) => e === "" ? 1 : t === "" ? -1 : e.localeCompare(t));
|
|
226
|
+
}, [w.items, T]), re = y.version_level ? [] : Object.entries(p?.kinds ?? {}).flatMap(([e, t]) => {
|
|
227
|
+
let n = t.entities?.includes(l.group.kind) ? l.newContentHref?.(e, l.group) : void 0;
|
|
228
|
+
return n ? [{
|
|
229
|
+
kind: e,
|
|
230
|
+
href: n
|
|
231
|
+
}] : [];
|
|
232
|
+
});
|
|
233
|
+
return /* @__PURE__ */ j(t, {
|
|
234
|
+
appearance: l.appearance,
|
|
235
|
+
className: M("grid gap-3 text-sm", l.className),
|
|
236
|
+
"data-ckui": "group-members",
|
|
237
|
+
children: [
|
|
238
|
+
/* @__PURE__ */ A("h3", {
|
|
239
|
+
className: "font-medium",
|
|
240
|
+
children: d("memberships.members")
|
|
241
|
+
}),
|
|
242
|
+
re.length > 0 && /* @__PURE__ */ A("div", {
|
|
243
|
+
className: "flex flex-wrap gap-2",
|
|
244
|
+
children: re.map((e) => /* @__PURE__ */ A("a", {
|
|
245
|
+
href: e.href,
|
|
246
|
+
className: o({
|
|
247
|
+
variant: "outline",
|
|
248
|
+
size: "sm"
|
|
249
|
+
}),
|
|
250
|
+
"data-ckui": "group-member-new",
|
|
251
|
+
children: d("memberships.newContent", {
|
|
252
|
+
kind: b(l.labels, e.kind),
|
|
253
|
+
name: l.group.name
|
|
254
|
+
})
|
|
255
|
+
}, e.kind))
|
|
256
|
+
}),
|
|
257
|
+
/* @__PURE__ */ A(U, {
|
|
258
|
+
spec: y,
|
|
259
|
+
labels: l.labels,
|
|
260
|
+
client: f,
|
|
261
|
+
onAdd: (e) => E.run(() => w.add([e]))
|
|
262
|
+
}),
|
|
263
|
+
w.loading && !w.items.length ? /* @__PURE__ */ A(m, { className: "h-40 w-full" }) : w.error && !w.items.length ? /* @__PURE__ */ j("div", {
|
|
264
|
+
role: "alert",
|
|
265
|
+
className: "grid justify-items-start gap-2",
|
|
266
|
+
children: [/* @__PURE__ */ A("p", {
|
|
267
|
+
className: "text-destructive",
|
|
268
|
+
children: g(u, w.error)
|
|
269
|
+
}), /* @__PURE__ */ A(a, {
|
|
270
|
+
size: "sm",
|
|
271
|
+
variant: "outline",
|
|
272
|
+
onClick: w.reload,
|
|
273
|
+
children: d("common.retry")
|
|
274
|
+
})]
|
|
275
|
+
}) : w.items.length ? y.ordered ? /* @__PURE__ */ A(s, {
|
|
276
|
+
items: w.items,
|
|
277
|
+
id: (e) => e.id,
|
|
278
|
+
name: K,
|
|
279
|
+
label: d("memberships.members"),
|
|
280
|
+
disabled: E.pending,
|
|
281
|
+
onMove: (e, t) => {
|
|
282
|
+
let n = [...w.items], [r] = n.splice(e, 1);
|
|
283
|
+
n.splice(t, 0, r), E.run(() => w.reorder(ee(n)));
|
|
284
|
+
},
|
|
285
|
+
children: (e, t) => ne(e, t)
|
|
286
|
+
}) : $.map(([e, t]) => /* @__PURE__ */ j("section", {
|
|
287
|
+
className: "grid gap-2",
|
|
288
|
+
"data-ckui": "group-members-kind",
|
|
289
|
+
"data-kind": e,
|
|
290
|
+
children: [$.length > 1 && e && /* @__PURE__ */ A("h4", {
|
|
291
|
+
className: "text-xs font-medium text-muted-foreground uppercase",
|
|
292
|
+
children: b(l.labels, e)
|
|
293
|
+
}), /* @__PURE__ */ A("ul", {
|
|
294
|
+
className: "grid grid-cols-[repeat(auto-fill,minmax(7.5rem,1fr))] gap-3",
|
|
295
|
+
children: t.map(te)
|
|
296
|
+
})]
|
|
297
|
+
}, e || "other")) : /* @__PURE__ */ A("p", {
|
|
298
|
+
className: "text-muted-foreground",
|
|
299
|
+
children: d("memberships.noMembers")
|
|
300
|
+
}),
|
|
301
|
+
w.hasMore && /* @__PURE__ */ j("div", {
|
|
302
|
+
className: "grid justify-items-center gap-2",
|
|
303
|
+
children: [w.error && /* @__PURE__ */ A("p", {
|
|
304
|
+
role: "alert",
|
|
305
|
+
className: "text-destructive",
|
|
306
|
+
children: g(u, w.error)
|
|
307
|
+
}), /* @__PURE__ */ A(a, {
|
|
308
|
+
variant: "outline",
|
|
309
|
+
size: "sm",
|
|
310
|
+
disabled: w.loadingMore,
|
|
311
|
+
onClick: () => void w.loadMore(),
|
|
312
|
+
children: w.loadingMore ? d("groups.loading") : w.error ? d("common.retry") : d("groups.loadMore")
|
|
313
|
+
})]
|
|
314
|
+
}),
|
|
315
|
+
/* @__PURE__ */ A(h, { error: E.error })
|
|
316
|
+
]
|
|
317
|
+
});
|
|
318
|
+
}
|
|
319
|
+
function U({ spec: t, labels: n, client: r, onAdd: i }) {
|
|
320
|
+
let { t: o } = e(), s = E(), [c, m] = O(""), [h, g] = O(0), [_, v] = O(null), [S, C] = O(""), [D, k] = O(""), [N, P] = O(), [F, I] = O(), R = w((e, t) => r.discovery.adminSuggestions({
|
|
321
|
+
q: e.q,
|
|
322
|
+
display_language: e.display_language,
|
|
323
|
+
include_contents: !0,
|
|
324
|
+
include_entities: !1,
|
|
325
|
+
limit: 8
|
|
326
|
+
}, t), [r]), z = y(c, {
|
|
327
|
+
request: R,
|
|
328
|
+
client: r,
|
|
329
|
+
limit: 8
|
|
330
|
+
}), B = z.contents, V = c.trim() !== "" && !_ && B.length > 0;
|
|
331
|
+
T(() => g(0), [c]);
|
|
332
|
+
let H = !!t.version_level || !!t.roles?.length || !!t.windows, U = () => {
|
|
333
|
+
m(""), v(null), C("");
|
|
334
|
+
}, W = (e, t) => void i({
|
|
335
|
+
content_id: e.id,
|
|
336
|
+
version_id: t || void 0,
|
|
337
|
+
role: D || void 0,
|
|
338
|
+
active_from: N,
|
|
339
|
+
active_until: F
|
|
340
|
+
}).then((e) => e !== void 0 && U()), G = (e) => {
|
|
341
|
+
if (!H) return W(e);
|
|
342
|
+
v({ card: e }), m(e.title), t.version_level && r.contents.manage({
|
|
343
|
+
ids: [e.id],
|
|
344
|
+
limit: 1
|
|
345
|
+
}).then((t) => v((n) => n?.card.id === e.id ? {
|
|
346
|
+
card: e,
|
|
347
|
+
versions: t[0]?.versions
|
|
348
|
+
} : n), () => void 0);
|
|
349
|
+
};
|
|
350
|
+
return /* @__PURE__ */ j("div", {
|
|
351
|
+
className: "grid gap-2",
|
|
352
|
+
"data-ckui": "add-member",
|
|
353
|
+
children: [/* @__PURE__ */ j("div", {
|
|
354
|
+
className: "relative",
|
|
355
|
+
children: [
|
|
356
|
+
/* @__PURE__ */ A("input", {
|
|
357
|
+
id: `${s}-q`,
|
|
358
|
+
role: "combobox",
|
|
359
|
+
"aria-label": o("memberships.searchContent"),
|
|
360
|
+
"aria-expanded": V,
|
|
361
|
+
"aria-controls": `${s}-list`,
|
|
362
|
+
"aria-activedescendant": V ? `${s}-${h}` : void 0,
|
|
363
|
+
"aria-autocomplete": "list",
|
|
364
|
+
autoComplete: "off",
|
|
365
|
+
className: "h-8 w-full rounded-md border border-input bg-transparent px-2.5 text-sm outline-none placeholder:text-muted-foreground focus-visible:border-ring focus-visible:ring-2 focus-visible:ring-ring/40",
|
|
366
|
+
placeholder: o("memberships.searchContent"),
|
|
367
|
+
value: c,
|
|
368
|
+
onChange: (e) => {
|
|
369
|
+
m(e.target.value), v(null);
|
|
370
|
+
},
|
|
371
|
+
onKeyDown: (e) => {
|
|
372
|
+
e.key === "ArrowDown" && V ? (e.preventDefault(), g((e) => Math.min(B.length - 1, e + 1))) : e.key === "ArrowUp" && V ? (e.preventDefault(), g((e) => Math.max(0, e - 1))) : e.key === "Enter" && V ? (e.preventDefault(), G(B[h])) : e.key === "Escape" && U();
|
|
373
|
+
}
|
|
374
|
+
}),
|
|
375
|
+
V && /* @__PURE__ */ A("ul", {
|
|
376
|
+
id: `${s}-list`,
|
|
377
|
+
role: "listbox",
|
|
378
|
+
"aria-label": o("memberships.searchContent"),
|
|
379
|
+
className: "absolute start-0 top-full z-10 mt-1 grid w-full overflow-hidden rounded-md border border-border bg-popover text-popover-foreground shadow-md",
|
|
380
|
+
children: B.map((e, t) => /* @__PURE__ */ j("li", {
|
|
381
|
+
id: `${s}-${t}`,
|
|
382
|
+
role: "option",
|
|
383
|
+
"aria-selected": t === h,
|
|
384
|
+
className: M("flex cursor-pointer items-center gap-2 px-2 py-1.5 text-sm", t === h && "bg-accent text-accent-foreground"),
|
|
385
|
+
onMouseEnter: () => g(t),
|
|
386
|
+
onMouseDown: (t) => {
|
|
387
|
+
t.preventDefault(), G(e);
|
|
388
|
+
},
|
|
389
|
+
children: [
|
|
390
|
+
e.cover[0]?.url ? /* @__PURE__ */ A("img", {
|
|
391
|
+
src: e.cover[0].url,
|
|
392
|
+
alt: "",
|
|
393
|
+
className: "h-9 w-6 shrink-0 rounded-sm object-cover"
|
|
394
|
+
}) : /* @__PURE__ */ A("span", {
|
|
395
|
+
"aria-hidden": !0,
|
|
396
|
+
className: "h-9 w-6 shrink-0 rounded-sm bg-muted"
|
|
397
|
+
}),
|
|
398
|
+
/* @__PURE__ */ A("span", {
|
|
399
|
+
className: "min-w-0 flex-1 truncate",
|
|
400
|
+
children: e.title
|
|
401
|
+
}),
|
|
402
|
+
/* @__PURE__ */ A("span", {
|
|
403
|
+
className: "text-xs text-muted-foreground",
|
|
404
|
+
children: b(n, e.kind)
|
|
405
|
+
})
|
|
406
|
+
]
|
|
407
|
+
}, e.id))
|
|
408
|
+
}),
|
|
409
|
+
c.trim() !== "" && !_ && !z.loading && z.query === c.trim() && !B.length && /* @__PURE__ */ A("p", {
|
|
410
|
+
className: "mt-1 text-xs text-muted-foreground",
|
|
411
|
+
children: o("memberships.noMatches")
|
|
412
|
+
})
|
|
413
|
+
]
|
|
414
|
+
}), _ && /* @__PURE__ */ j("div", {
|
|
415
|
+
className: "flex flex-wrap items-end gap-2",
|
|
416
|
+
"data-ckui": "add-member-details",
|
|
417
|
+
children: [
|
|
418
|
+
t.version_level && /* @__PURE__ */ j(l, {
|
|
419
|
+
value: S || L,
|
|
420
|
+
onValueChange: (e) => C(e === L ? "" : String(e)),
|
|
421
|
+
children: [/* @__PURE__ */ A(f, {
|
|
422
|
+
size: "sm",
|
|
423
|
+
"aria-label": o("memberships.version"),
|
|
424
|
+
children: /* @__PURE__ */ A(p, { children: (e) => e === L ? o("memberships.wholeContent") : _.versions?.find((t) => t.id === e)?.title ?? e })
|
|
425
|
+
}), /* @__PURE__ */ j(u, { children: [/* @__PURE__ */ A(d, {
|
|
426
|
+
value: L,
|
|
427
|
+
children: o("memberships.wholeContent")
|
|
428
|
+
}), (_.versions ?? []).map((e, t) => /* @__PURE__ */ A(d, {
|
|
429
|
+
value: e.id,
|
|
430
|
+
children: e.title || `#${t + 1}`
|
|
431
|
+
}, e.id))] })]
|
|
432
|
+
}),
|
|
433
|
+
!!t.roles?.length && /* @__PURE__ */ j(l, {
|
|
434
|
+
value: D || L,
|
|
435
|
+
onValueChange: (e) => k(e === L ? "" : String(e)),
|
|
436
|
+
children: [/* @__PURE__ */ A(f, {
|
|
437
|
+
size: "sm",
|
|
438
|
+
"aria-label": o("memberships.role"),
|
|
439
|
+
children: /* @__PURE__ */ A(p, { children: (e) => e === L ? o("memberships.noRole") : b(n, e) })
|
|
440
|
+
}), /* @__PURE__ */ j(u, { children: [/* @__PURE__ */ A(d, {
|
|
441
|
+
value: L,
|
|
442
|
+
children: o("memberships.noRole")
|
|
443
|
+
}), t.roles.map((e) => /* @__PURE__ */ A(d, {
|
|
444
|
+
value: e,
|
|
445
|
+
children: b(n, e)
|
|
446
|
+
}, e))] })]
|
|
447
|
+
}),
|
|
448
|
+
t.windows && /* @__PURE__ */ A(x, {
|
|
449
|
+
from: N,
|
|
450
|
+
until: F,
|
|
451
|
+
name: o("memberships.newMember"),
|
|
452
|
+
onChange: (e) => {
|
|
453
|
+
"active_from" in e && P(e.active_from), "active_until" in e && I(e.active_until);
|
|
454
|
+
}
|
|
455
|
+
}),
|
|
456
|
+
/* @__PURE__ */ A(a, {
|
|
457
|
+
size: "sm",
|
|
458
|
+
onClick: () => W(_.card, S),
|
|
459
|
+
children: o("memberships.addMember")
|
|
460
|
+
}),
|
|
461
|
+
/* @__PURE__ */ A(a, {
|
|
462
|
+
size: "sm",
|
|
463
|
+
variant: "ghost",
|
|
464
|
+
onClick: U,
|
|
465
|
+
children: o("common.cancel")
|
|
466
|
+
})
|
|
467
|
+
]
|
|
468
|
+
})]
|
|
469
|
+
});
|
|
470
|
+
}
|
|
471
|
+
//#endregion
|
|
472
|
+
export { H as GroupMembers };
|
|
473
|
+
|
|
474
|
+
//# sourceMappingURL=group-members.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"group-members.js","names":[],"sources":["../../../src/components/groups/group-members.tsx"],"sourcesContent":["import { Cancel01Icon, Image01Icon, Tick02Icon } from \"@hugeicons/core-free-icons\";\nimport { HugeiconsIcon } from \"@hugeicons/react\";\nimport { cn } from \"cn\";\nimport { useCallback, useEffect, useId, useMemo, useState, type ReactNode } from \"react\";\nimport type { ContentKitUiAppearance } from \"../../appearance.js\";\nimport type { ContentKitClient } from \"../../client/client.js\";\nimport type { TypeaheadQuery } from \"../../client/discovery.js\";\nimport type { Card, Content, GroupDetail, GroupKind, Membership } from \"../../client/generated/wire.js\";\nimport { useMessages } from \"../../i18n/context.js\";\nimport { useContentKitClient, type ContentKitErrorHandler } from \"../../react/context.js\";\nimport { useTypeahead } from \"../../react/discovery.js\";\nimport { useGroupMembers, useKinds, type Member } from \"../../react/groups.js\";\nimport { ContentKitUiRoot } from \"../../scope.js\";\nimport { Badge } from \"#ckui/ui/badge\";\nimport { Button, buttonVariants } from \"#ckui/ui/button\";\nimport { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from \"#ckui/ui/select\";\nimport { Skeleton } from \"#ckui/ui/skeleton\";\nimport { accessLabel, contentStatus } from \"../admin/content-manager.js\";\nimport { SortableList } from \"../sortable-list.js\";\nimport { contentError, ErrorLine, formatDate, useAction } from \"../social/parts.js\";\nimport { WindowFields } from \"./entity-chips.js\";\nimport { labelOf, type Labels } from \"./parts.js\";\n\nconst NONE = \"__none__\";\n// The managed listing hydrates at most this many ids per request.\nconst BATCH = 100;\n\nexport interface GroupMembersProps {\n group: Pick<GroupDetail, \"id\" | \"kind\" | \"name\" | \"slug\" | \"cover\" | \"code\">;\n labels?: Labels;\n /** Where a member's card links, e.g. its admin editor; none: not a link. */\n contentHref?: (content: Content) => string | undefined;\n /** Where a new item of a content kind starts already in this group, e.g. the host's editor with `?with=<code>`; none: no action. */\n newContentHref?: (contentKind: string, group: GroupMembersProps[\"group\"]) => string | undefined;\n /** Replaces a member's card body; default its cover and title. */\n renderContent?: (member: Membership, content?: Content) => ReactNode;\n /** Select a member's cover as the group's. */\n onUseCover?: (contentId: string) => Promise<unknown>;\n pageSize?: number;\n client?: ContentKitClient;\n onError?: ContentKitErrorHandler;\n className?: string;\n appearance?: ContentKitUiAppearance;\n}\n\nconst refKey = (x: Membership) => `${x.content_id}|${x.version_id ?? \"\"}`;\n\n/** Members' contents by id through the managed listing: drafts and deleted ones too. */\nfunction useMemberContents(ids: readonly string[], client: ContentKitClient) {\n const [byId, setById] = useState<ReadonlyMap<string, Content>>(new Map());\n const wanted = useMemo(() => [...new Set(ids)].sort(), [ids]);\n useEffect(() => {\n const missing = wanted.filter((id) => !byId.has(id));\n if (!missing.length) return;\n const ctl = new AbortController();\n const batches: string[][] = [];\n for (let i = 0; i < missing.length; i += BATCH) batches.push(missing.slice(i, i + BATCH));\n // A failed lookup leaves the member's id as its label; the list stays usable.\n void Promise.all(batches.map((b) => client.contents.manage({ ids: b, limit: b.length }, ctl.signal).catch(() => [] as Content[]))).then((pages) => {\n if (ctl.signal.aborted) return;\n setById((cur) => {\n const next = new Map(cur);\n for (const c of pages.flat()) next.set(c.id, c);\n return next;\n });\n });\n return () => ctl.abort();\n // byId is read, not a trigger: only new ids fetch.\n }, [wanted, client]); // eslint-disable-line react-hooks/exhaustive-deps\n return byId;\n}\n\nconst coverOf = (c?: Content) => c?.cover?.url ?? c?.versions.find((v) => v.cover?.url)?.cover?.url;\n\n/**\n * Staff: an entity's contents as cover cards grouped by content kind (an\n * ordered kind as a reorderable list), each with its access, state, role and\n * version; add one by searching titles, remove or use its cover on hover.\n */\nexport function GroupMembers(p: GroupMembersProps) {\n const m = useMessages();\n const { t } = m;\n const client = useContentKitClient(p.client);\n const { kinds } = useKinds({ client: p.client });\n const spec: GroupKind = kinds?.entity_kinds?.[p.group.kind] ?? {};\n const members = useGroupMembers(p.group.id, { pageSize: p.pageSize, client: p.client });\n const contents = useMemberContents(\n useMemo(() => members.items.map((x) => x.content_id!).filter(Boolean), [members.items]),\n client,\n );\n const save = useAction(\"membership.save\", p.onError);\n const [editing, setEditing] = useState<string | null>(null);\n const [win, setWin] = useState<{ from?: string; until?: string }>({});\n const title = (x: Membership) => contents.get(x.content_id ?? \"\")?.title || x.content_id || \"\";\n const spoken = (x: Member) => `${title(x)}${x.version_id ? ` (${t(\"memberships.version\")})` : \"\"}`;\n // Every role of one member shares its place: order unique content and version pairs.\n const order = (items: Member[]) => [...new Map(items.map((x) => [refKey(x), { content_id: x.content_id!, version_id: x.version_id }])).values()];\n const strip = ({ id: _id, ...x }: Member): Membership => x;\n const badges = (x: Member, c?: Content) => (\n <>\n {c && c.access.level !== \"public\" && <Badge variant=\"secondary\">{accessLabel(t, c.access, p.labels)}</Badge>}\n {c && (c.state === \"deleted\" || contentStatus(c) !== \"published\") && (\n <Badge variant={c.state === \"deleted\" ? \"destructive\" : \"outline\"}>{t(c.state === \"deleted\" ? \"contentManager.deleted\" : `contentManager.${contentStatus(c)}`)}</Badge>\n )}\n {x.version_id && <Badge variant=\"outline\">{t(\"memberships.version\")}</Badge>}\n {x.role && <Badge variant=\"secondary\">{labelOf(p.labels, x.role)}</Badge>}\n {x.state === \"proposed\" && <Badge variant=\"secondary\">{t(\"memberships.proposed\")}</Badge>}\n </>\n );\n const actions = (x: Member) => (\n <>\n {x.state === \"proposed\" && (\n <Button size=\"icon-xs\" variant=\"secondary\" disabled={save.pending} aria-label={`${t(\"memberships.accept\")}: ${spoken(x)}`} title={t(\"memberships.accept\")}\n onClick={() => void save.run(() => members.add([{ ...strip(x), state: \"active\" }]))}>\n <HugeiconsIcon icon={Tick02Icon} strokeWidth={2.5} />\n </Button>\n )}\n {p.onUseCover && !x.version_id && (\n <Button size=\"icon-xs\" variant=\"secondary\" aria-label={`${t(\"memberships.useCover\")}: ${spoken(x)}`} title={t(\"memberships.useCover\")}\n disabled={save.pending || (p.group.cover?.content_id === x.content_id && !p.group.cover?.auto)}\n onClick={() => void save.run(() => p.onUseCover!(x.content_id!))}>\n <HugeiconsIcon icon={Image01Icon} strokeWidth={2} />\n </Button>\n )}\n <Button size=\"icon-xs\" variant=\"secondary\" disabled={save.pending} aria-label={t(\"memberships.remove\", { name: spoken(x) })} title={t(\"common.remove\")}\n onClick={() => void save.run(() => members.remove([strip(x)]))}>\n <HugeiconsIcon icon={Cancel01Icon} strokeWidth={2.5} />\n </Button>\n </>\n );\n const dates = (x: Member) =>\n spec.windows &&\n (editing === x.id ? (\n <span className=\"flex flex-wrap items-center gap-1\">\n <WindowFields from={win.from} until={win.until} name={spoken(x)} onChange={(w) => setWin((cur) => ({ from: \"active_from\" in w ? w.active_from : cur.from, until: \"active_until\" in w ? w.active_until : cur.until }))} />\n <Button size=\"xs\" disabled={save.pending} onClick={() => void save.run(() => members.add([{ ...strip(x), active_from: win.from, active_until: win.until }])).then((d) => d !== undefined && setEditing(null))}>\n {t(\"common.save\")}\n </Button>\n <Button size=\"xs\" variant=\"ghost\" onClick={() => setEditing(null)}>\n {t(\"common.cancel\")}\n </Button>\n </span>\n ) : (\n <button type=\"button\" className=\"text-start text-xs text-muted-foreground hover:underline\" data-ckui=\"member-window\"\n onClick={() => {\n setWin({ from: x.active_from, until: x.active_until });\n setEditing(x.id);\n }}>\n {x.active_from || x.active_until\n ? t(\"memberships.window\", { from: x.active_from ? formatDate(m, x.active_from) : \"…\", until: x.active_until ? formatDate(m, x.active_until) : \"…\" })\n : t(\"memberships.always\")}\n </button>\n ));\n const thumb = (c: Content | undefined, className: string) => {\n const url = coverOf(c);\n return url ? <img src={url} alt=\"\" loading=\"lazy\" className={cn(\"object-cover\", className)} /> : <span aria-hidden className={cn(\"bg-muted\", className)} />;\n };\n const linked = (x: Member, body: ReactNode, className?: string) => {\n const c = contents.get(x.content_id ?? \"\");\n const href = c && p.contentHref?.(c);\n return href ? <a href={href} className={cn(\"hover:underline\", className)}>{body}</a> : <span className={className}>{body}</span>;\n };\n const card = (x: Member) => {\n const c = contents.get(x.content_id ?? \"\");\n return (\n <li key={x.id} className=\"group/member relative grid content-start gap-1.5\" data-ckui=\"group-member\" data-content={x.content_id} data-state={x.state ?? \"active\"}>\n {p.renderContent ? (\n p.renderContent(x, c)\n ) : (\n <>\n {linked(x, thumb(c, \"aspect-[7/10] w-full rounded-md\"), \"block\")}\n {linked(x, title(x), cn(\"line-clamp-2 text-sm font-medium break-words\", !c && \"font-mono text-xs\"))}\n </>\n )}\n <span className=\"flex flex-wrap gap-1\">{badges(x, c)}</span>\n {dates(x)}\n <span className=\"absolute end-1 top-1 flex gap-1 opacity-0 transition-opacity group-hover/member:opacity-100 focus-within:opacity-100\">{actions(x)}</span>\n </li>\n );\n };\n const row = (x: Member, handle?: ReactNode) => {\n const c = contents.get(x.content_id ?? \"\");\n return (\n <div className=\"group/member flex flex-wrap items-center gap-2\" data-ckui=\"group-member\" data-content={x.content_id} data-state={x.state ?? \"active\"}>\n {handle}\n {x.position !== undefined && <span className=\"w-8 text-xs text-muted-foreground tabular-nums\">{x.position}</span>}\n {p.renderContent ? (\n <span className=\"min-w-0 flex-1\">{p.renderContent(x, c)}</span>\n ) : (\n <>\n {linked(x, thumb(c, \"h-12 w-9 rounded-sm\"), \"shrink-0\")}\n {linked(x, title(x), cn(\"min-w-0 flex-1 break-words\", !c && \"font-mono text-xs\"))}\n </>\n )}\n {badges(x, c)}\n {dates(x)}\n <span className=\"flex gap-1 opacity-60 transition-opacity group-hover/member:opacity-100 focus-within:opacity-100\">{actions(x)}</span>\n </div>\n );\n };\n // Unordered kinds read best as covers per content kind; unknown kinds last.\n const byKind = useMemo(() => {\n const out = new Map<string, Member[]>();\n for (const x of members.items) {\n const kind = contents.get(x.content_id ?? \"\")?.kind ?? \"\";\n out.set(kind, [...(out.get(kind) ?? []), x]);\n }\n return [...out].sort(([a], [b]) => (a === \"\" ? 1 : b === \"\" ? -1 : a.localeCompare(b)));\n }, [members.items, contents]);\n // Version-level kinds link a version, which a new item does not have yet.\n const starts = spec.version_level\n ? []\n : Object.entries(kinds?.kinds ?? {}).flatMap(([kind, k]) => {\n const href = k.entities?.includes(p.group.kind) ? p.newContentHref?.(kind, p.group) : undefined;\n return href ? [{ kind, href }] : [];\n });\n return (\n <ContentKitUiRoot appearance={p.appearance} className={cn(\"grid gap-3 text-sm\", p.className)} data-ckui=\"group-members\">\n <h3 className=\"font-medium\">{t(\"memberships.members\")}</h3>\n {starts.length > 0 && (\n <div className=\"flex flex-wrap gap-2\">\n {starts.map((x) => (\n <a key={x.kind} href={x.href} className={buttonVariants({ variant: \"outline\", size: \"sm\" })} data-ckui=\"group-member-new\">\n {t(\"memberships.newContent\", { kind: labelOf(p.labels, x.kind), name: p.group.name })}\n </a>\n ))}\n </div>\n )}\n <AddContent spec={spec} labels={p.labels} client={client} onAdd={(x) => save.run(() => members.add([x]))} />\n {members.loading && !members.items.length ? (\n <Skeleton className=\"h-40 w-full\" />\n ) : members.error && !members.items.length ? (\n <div role=\"alert\" className=\"grid justify-items-start gap-2\">\n <p className=\"text-destructive\">{contentError(m, members.error)}</p>\n <Button size=\"sm\" variant=\"outline\" onClick={members.reload}>\n {t(\"common.retry\")}\n </Button>\n </div>\n ) : !members.items.length ? (\n <p className=\"text-muted-foreground\">{t(\"memberships.noMembers\")}</p>\n ) : spec.ordered ? (\n <SortableList\n items={members.items}\n id={(x) => x.id}\n name={spoken}\n label={t(\"memberships.members\")}\n disabled={save.pending}\n onMove={(from, to) => {\n const items = [...members.items];\n const [moved] = items.splice(from, 1);\n items.splice(to, 0, moved!);\n void save.run(() => members.reorder(order(items)));\n }}\n >\n {(x, handle) => row(x, handle)}\n </SortableList>\n ) : (\n byKind.map(([kind, items]) => (\n <section key={kind || \"other\"} className=\"grid gap-2\" data-ckui=\"group-members-kind\" data-kind={kind}>\n {byKind.length > 1 && kind && <h4 className=\"text-xs font-medium text-muted-foreground uppercase\">{labelOf(p.labels, kind)}</h4>}\n <ul className=\"grid grid-cols-[repeat(auto-fill,minmax(7.5rem,1fr))] gap-3\">{items.map(card)}</ul>\n </section>\n ))\n )}\n {members.hasMore && (\n <div className=\"grid justify-items-center gap-2\">\n {members.error && <p role=\"alert\" className=\"text-destructive\">{contentError(m, members.error)}</p>}\n <Button variant=\"outline\" size=\"sm\" disabled={members.loadingMore} onClick={() => void members.loadMore()}>\n {members.loadingMore ? t(\"groups.loading\") : members.error ? t(\"common.retry\") : t(\"groups.loadMore\")}\n </Button>\n </div>\n )}\n <ErrorLine error={save.error} />\n </ContentKitUiRoot>\n );\n}\n\n/** A title search over contents the caller manages; picking one adds it, after its role, version or dates when the kind has them. */\nfunction AddContent({ spec, labels, client, onAdd }: { spec: GroupKind; labels?: Labels; client: ContentKitClient; onAdd: (m: Membership) => Promise<unknown> }) {\n const { t } = useMessages();\n const id = useId();\n const [text, setText] = useState(\"\");\n const [active, setActive] = useState(0);\n const [picked, setPicked] = useState<{ card: Card; versions?: Content[\"versions\"] } | null>(null);\n const [version, setVersion] = useState(\"\");\n const [role, setRole] = useState(\"\");\n const [from, setFrom] = useState<string>();\n const [until, setUntil] = useState<string>();\n const request = useCallback(\n (q: TypeaheadQuery, signal: AbortSignal) =>\n client.discovery.adminSuggestions({ q: q.q, display_language: q.display_language, include_contents: true, include_entities: false, limit: 8 }, signal),\n [client],\n );\n const found = useTypeahead(text, { request, client, limit: 8 });\n const results = found.contents;\n const listOpen = text.trim() !== \"\" && !picked && results.length > 0;\n useEffect(() => setActive(0), [text]);\n const detailed = !!spec.version_level || !!spec.roles?.length || !!spec.windows;\n const reset = () => {\n setText(\"\");\n setPicked(null);\n setVersion(\"\");\n };\n const add = (card: Card, v?: string) =>\n void onAdd({ content_id: card.id, version_id: v || undefined, role: role || undefined, active_from: from, active_until: until }).then((d) => d !== undefined && reset());\n const pick = (card: Card) => {\n if (!detailed) return add(card);\n setPicked({ card });\n setText(card.title);\n // A version-level kind links one version: list the picked content's.\n if (spec.version_level)\n void client.contents.manage({ ids: [card.id], limit: 1 }).then(\n (r) => setPicked((cur) => (cur?.card.id === card.id ? { card, versions: r[0]?.versions } : cur)),\n () => undefined,\n );\n };\n return (\n <div className=\"grid gap-2\" data-ckui=\"add-member\">\n <div className=\"relative\">\n <input\n id={`${id}-q`}\n role=\"combobox\"\n aria-label={t(\"memberships.searchContent\")}\n aria-expanded={listOpen}\n aria-controls={`${id}-list`}\n aria-activedescendant={listOpen ? `${id}-${active}` : undefined}\n aria-autocomplete=\"list\"\n autoComplete=\"off\"\n className=\"h-8 w-full rounded-md border border-input bg-transparent px-2.5 text-sm outline-none placeholder:text-muted-foreground focus-visible:border-ring focus-visible:ring-2 focus-visible:ring-ring/40\"\n placeholder={t(\"memberships.searchContent\")}\n value={text}\n onChange={(e) => {\n setText(e.target.value);\n setPicked(null);\n }}\n onKeyDown={(e) => {\n if (e.key === \"ArrowDown\" && listOpen) {\n e.preventDefault();\n setActive((a) => Math.min(results.length - 1, a + 1));\n } else if (e.key === \"ArrowUp\" && listOpen) {\n e.preventDefault();\n setActive((a) => Math.max(0, a - 1));\n } else if (e.key === \"Enter\" && listOpen) {\n e.preventDefault();\n pick(results[active]!);\n } else if (e.key === \"Escape\") reset();\n }}\n />\n {listOpen && (\n <ul id={`${id}-list`} role=\"listbox\" aria-label={t(\"memberships.searchContent\")} className=\"absolute start-0 top-full z-10 mt-1 grid w-full overflow-hidden rounded-md border border-border bg-popover text-popover-foreground shadow-md\">\n {results.map((c, i) => (\n <li\n key={c.id}\n id={`${id}-${i}`}\n role=\"option\"\n aria-selected={i === active}\n className={cn(\"flex cursor-pointer items-center gap-2 px-2 py-1.5 text-sm\", i === active && \"bg-accent text-accent-foreground\")}\n onMouseEnter={() => setActive(i)}\n onMouseDown={(e) => {\n e.preventDefault();\n pick(c);\n }}\n >\n {c.cover[0]?.url ? <img src={c.cover[0].url} alt=\"\" className=\"h-9 w-6 shrink-0 rounded-sm object-cover\" /> : <span aria-hidden className=\"h-9 w-6 shrink-0 rounded-sm bg-muted\" />}\n <span className=\"min-w-0 flex-1 truncate\">{c.title}</span>\n <span className=\"text-xs text-muted-foreground\">{labelOf(labels, c.kind)}</span>\n </li>\n ))}\n </ul>\n )}\n {text.trim() !== \"\" && !picked && !found.loading && found.query === text.trim() && !results.length && (\n <p className=\"mt-1 text-xs text-muted-foreground\">{t(\"memberships.noMatches\")}</p>\n )}\n </div>\n {picked && (\n <div className=\"flex flex-wrap items-end gap-2\" data-ckui=\"add-member-details\">\n {spec.version_level && (\n <Select value={version || NONE} onValueChange={(v) => setVersion(v === NONE ? \"\" : String(v))}>\n <SelectTrigger size=\"sm\" aria-label={t(\"memberships.version\")}>\n <SelectValue>{(v: string) => (v === NONE ? t(\"memberships.wholeContent\") : (picked.versions?.find((x) => x.id === v)?.title ?? v))}</SelectValue>\n </SelectTrigger>\n <SelectContent>\n <SelectItem value={NONE}>{t(\"memberships.wholeContent\")}</SelectItem>\n {(picked.versions ?? []).map((v, i) => (\n <SelectItem key={v.id} value={v.id}>\n {v.title || `#${i + 1}`}\n </SelectItem>\n ))}\n </SelectContent>\n </Select>\n )}\n {!!spec.roles?.length && (\n <Select value={role || NONE} onValueChange={(v) => setRole(v === NONE ? \"\" : String(v))}>\n <SelectTrigger size=\"sm\" aria-label={t(\"memberships.role\")}>\n <SelectValue>{(v: string) => (v === NONE ? t(\"memberships.noRole\") : labelOf(labels, v))}</SelectValue>\n </SelectTrigger>\n <SelectContent>\n <SelectItem value={NONE}>{t(\"memberships.noRole\")}</SelectItem>\n {spec.roles.map((r) => (\n <SelectItem key={r} value={r}>\n {labelOf(labels, r)}\n </SelectItem>\n ))}\n </SelectContent>\n </Select>\n )}\n {spec.windows && (\n <WindowFields\n from={from}\n until={until}\n name={t(\"memberships.newMember\")}\n onChange={(w) => {\n if (\"active_from\" in w) setFrom(w.active_from);\n if (\"active_until\" in w) setUntil(w.active_until);\n }}\n />\n )}\n <Button size=\"sm\" onClick={() => add(picked.card, version)}>\n {t(\"memberships.addMember\")}\n </Button>\n <Button size=\"sm\" variant=\"ghost\" onClick={reset}>\n {t(\"common.cancel\")}\n </Button>\n </div>\n )}\n </div>\n );\n}\n"],"mappings":"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"}
|