@kyro-cms/admin 0.1.6 → 0.1.8
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 +149 -51
- package/package.json +54 -5
- package/src/collections/auth/index.ts +2 -2
- package/src/collections/portfolio/index.ts +343 -0
- package/src/components/ActionBar.tsx +153 -16
- package/src/components/Admin.tsx +137 -28
- package/src/components/ApiExplorer.tsx +325 -0
- package/src/components/ApiKeysManager.tsx +563 -0
- package/src/components/AuditLogsPage.tsx +664 -0
- package/src/components/AutoForm.tsx +2155 -770
- package/src/components/BrandingHub.tsx +267 -0
- package/src/components/BulkActionsBar.tsx +3 -3
- package/src/components/CreateView.tsx +4 -4
- package/src/components/Dashboard.tsx +393 -0
- package/src/components/DetailView.tsx +200 -58
- package/src/components/DeveloperCenter.tsx +403 -0
- package/src/components/EnhancedListView.tsx +890 -0
- package/src/components/GraphQLExplorer.tsx +675 -0
- package/src/components/GraphQLPlayground.tsx +627 -0
- package/src/components/ListView.tsx +192 -54
- package/src/components/MediaGallery.tsx +1569 -0
- package/src/components/Modal.tsx +206 -0
- package/src/components/RestPlayground.tsx +951 -0
- package/src/components/Sidebar.astro +237 -0
- package/src/components/ThemeProvider.tsx +8 -2
- package/src/components/UserManagement.tsx +204 -0
- package/src/components/VersionHistoryPanel.tsx +3 -3
- package/src/components/WebhookManager.tsx +608 -0
- package/src/components/blocks/AccordionBlock.tsx +65 -0
- package/src/components/blocks/ArrayBlock.tsx +84 -0
- package/src/components/blocks/BlockEditModal.tsx +363 -0
- package/src/components/blocks/ButtonBlock.tsx +64 -0
- package/src/components/blocks/ChildBlocksTree.tsx +551 -0
- package/src/components/blocks/CodeBlock.tsx +114 -0
- package/src/components/blocks/ColumnsBlock.tsx +93 -0
- package/src/components/blocks/DividerBlock.tsx +43 -0
- package/src/components/blocks/FileBlock.tsx +63 -0
- package/src/components/blocks/HeadingBlock.tsx +59 -0
- package/src/components/blocks/HeroBlock.tsx +99 -0
- package/src/components/blocks/ImageBlock.tsx +82 -0
- package/src/components/blocks/LinkBlock.tsx +65 -0
- package/src/components/blocks/ListBlock.tsx +60 -0
- package/src/components/blocks/ParagraphBlock.tsx +61 -0
- package/src/components/blocks/RelationshipBlock.tsx +72 -0
- package/src/components/blocks/RichTextBlock.tsx +66 -0
- package/src/components/blocks/VStackBlock.tsx +61 -0
- package/src/components/blocks/VideoBlock.tsx +65 -0
- package/src/components/blocks/index.ts +10 -0
- package/src/components/fields/AccordionField.tsx +213 -0
- package/src/components/fields/ArrayField.tsx +241 -0
- package/src/components/fields/BlocksField.tsx +323 -0
- package/src/components/fields/ButtonField.tsx +53 -0
- package/src/components/fields/CheckboxField.tsx +18 -8
- package/src/components/fields/ChildrenField.tsx +48 -0
- package/src/components/fields/CodeField.tsx +294 -0
- package/src/components/fields/ColumnsField.tsx +137 -0
- package/src/components/fields/DateField.tsx +24 -12
- package/src/components/fields/EditorClient.tsx +537 -0
- package/src/components/fields/HeadingField.tsx +31 -0
- package/src/components/fields/HeroField.tsx +101 -0
- package/src/components/fields/JSONField.tsx +341 -0
- package/src/components/fields/LinkField.tsx +81 -0
- package/src/components/fields/ListField.tsx +74 -0
- package/src/components/fields/MarkdownField.tsx +260 -0
- package/src/components/fields/NumberField.tsx +25 -13
- package/src/components/fields/PortableTextField.tsx +155 -0
- package/src/components/fields/PortableTextRenderer.tsx +68 -0
- package/src/components/fields/RelationshipBlockField.tsx +233 -0
- package/src/components/fields/RelationshipField.tsx +278 -60
- package/src/components/fields/SelectField.tsx +28 -16
- package/src/components/fields/TextField.tsx +31 -15
- package/src/components/fields/UploadField.tsx +613 -0
- package/src/components/fields/VideoField.tsx +73 -0
- package/src/components/fields/extensions/blockComponents.tsx +247 -0
- package/src/components/fields/extensions/blocksStore.ts +273 -0
- package/src/components/fields/index.ts +24 -0
- package/src/components/index.ts +1 -2
- package/src/components/layout/Header.tsx +2 -2
- package/src/components/layout/Layout.tsx +3 -3
- package/src/components/ui/Badge.tsx +9 -4
- package/src/components/ui/BlockDrawer.tsx +79 -0
- package/src/components/ui/Button.tsx +1 -1
- package/src/components/ui/CommandPalette.tsx +362 -0
- package/src/components/ui/CommandPaletteWrapper.tsx +97 -0
- package/src/components/ui/Dropdown.tsx +1 -1
- package/src/components/ui/Modal.tsx +37 -12
- package/src/components/ui/PromptModal.tsx +94 -0
- package/src/components/ui/SlidePanel.tsx +43 -16
- package/src/components/ui/Toast.tsx +80 -14
- package/src/env.d.ts +16 -0
- package/src/env.ts +20 -0
- package/src/index.ts +0 -1
- package/src/layouts/AdminLayout.astro +164 -170
- package/src/layouts/AuthLayout.astro +23 -6
- package/src/lib/MediaService.ts +541 -0
- package/src/lib/api.ts +163 -0
- package/src/lib/auth/sqlite-adapter.ts +319 -0
- package/src/lib/config.ts +23 -7
- package/src/lib/dataStore.ts +188 -73
- package/src/lib/date-utils.ts +69 -0
- package/src/lib/db/adapter.ts +54 -0
- package/src/lib/db/drizzle-mysql-adapter.ts +194 -0
- package/src/lib/db/drizzle-mysql-auth-adapter.ts +327 -0
- package/src/lib/db/drizzle-postgres-adapter.ts +202 -0
- package/src/lib/db/drizzle-postgres-auth-adapter.ts +304 -0
- package/src/lib/db/drizzle-sqlite-adapter.ts +227 -0
- package/src/lib/db/drizzle-sqlite-auth-adapter.ts +548 -0
- package/src/lib/db/index.ts +449 -0
- package/src/lib/db/mongodb-adapter.ts +207 -0
- package/src/lib/db/mongodb-auth-adapter.ts +305 -0
- package/src/lib/db/schema/mysql-auth.ts +113 -0
- package/src/lib/db/schema/mysql-content.ts +20 -0
- package/src/lib/db/schema/postgres-auth.ts +116 -0
- package/src/lib/db/schema/postgres-content.ts +35 -0
- package/src/lib/db/schema/postgres-media.ts +52 -0
- package/src/lib/db/schema/postgres-settings.ts +11 -0
- package/src/lib/db/schema/sqlite-auth.ts +112 -0
- package/src/lib/db/schema/sqlite-content.ts +20 -0
- package/src/lib/db/version-adapter.ts +248 -0
- package/src/lib/graphql/index.ts +1 -0
- package/src/lib/graphql/schema.ts +443 -0
- package/src/lib/i18n.tsx +353 -0
- package/src/lib/rate-limit.ts +267 -0
- package/src/lib/slugify.ts +15 -0
- package/src/lib/storage.ts +374 -0
- package/src/lib/store.ts +85 -0
- package/src/lib/validation.ts +250 -0
- package/src/middleware.ts +70 -11
- package/src/pages/[collection]/[id].astro +178 -122
- package/src/pages/[collection]/index.astro +24 -156
- package/src/pages/admin/api-explorer.astro +98 -0
- package/src/pages/admin/graphql-explorer.astro +40 -0
- package/src/pages/admin/graphql.astro +97 -0
- package/src/pages/admin/index.astro +200 -139
- package/src/pages/admin/keys.astro +8 -0
- package/src/pages/admin/rest-playground.astro +44 -0
- package/src/pages/admin/webhooks.astro +8 -0
- package/src/pages/api/[collection]/[id]/publish.ts +52 -0
- package/src/pages/api/[collection]/[id]/unpublish.ts +42 -0
- package/src/pages/api/[collection]/[id]/versions.ts +66 -0
- package/src/pages/api/[collection]/[id].ts +114 -159
- package/src/pages/api/[collection]/index.ts +150 -230
- package/src/pages/api/auth/[id].ts +48 -69
- package/src/pages/api/auth/audit-logs.ts +20 -43
- package/src/pages/api/auth/login.ts +159 -45
- package/src/pages/api/auth/logout.ts +42 -24
- package/src/pages/api/auth/refresh.ts +119 -0
- package/src/pages/api/auth/register.ts +110 -40
- package/src/pages/api/auth/users.ts +22 -97
- package/src/pages/api/collections.ts +59 -0
- package/src/pages/api/globals/[slug]/test.ts +172 -0
- package/src/pages/api/globals/[slug].ts +42 -0
- package/src/pages/api/graphql.ts +90 -0
- package/src/pages/api/health.ts +417 -40
- package/src/pages/api/keys/[id].ts +26 -0
- package/src/pages/api/keys/index.ts +75 -0
- package/src/pages/api/media/[id].ts +309 -0
- package/src/pages/api/media/folders.ts +609 -0
- package/src/pages/api/media/index.ts +146 -0
- package/src/pages/api/media/resize.ts +267 -0
- package/src/pages/api/search.ts +82 -0
- package/src/pages/api/slug-availability.ts +70 -0
- package/src/pages/api/storage-config.ts +20 -0
- package/src/pages/api/storage-status.ts +206 -0
- package/src/pages/api/upload.ts +334 -0
- package/src/pages/api/webhooks/index.ts +71 -0
- package/src/pages/audit/index.astro +2 -104
- package/src/pages/login.astro +11 -11
- package/src/pages/media.astro +10 -0
- package/src/pages/preview/[collection]/[id].astro +178 -0
- package/src/pages/register.astro +13 -13
- package/src/pages/roles/index.astro +21 -21
- package/src/pages/settings/[slug].astro +162 -0
- package/src/pages/settings/index.astro +9 -0
- package/src/pages/users/[id].astro +29 -21
- package/src/pages/users/index.astro +22 -17
- package/src/pages/users/new.astro +18 -17
- package/src/styles/main.css +563 -128
- package/src/components/layout/Sidebar.tsx +0 -497
|
@@ -0,0 +1,267 @@
|
|
|
1
|
+
import React, { useState, useEffect } from "react";
|
|
2
|
+
import {
|
|
3
|
+
Palette,
|
|
4
|
+
Tag,
|
|
5
|
+
Layout,
|
|
6
|
+
Type,
|
|
7
|
+
Image as ImageIcon,
|
|
8
|
+
Save,
|
|
9
|
+
Check,
|
|
10
|
+
RefreshCcw,
|
|
11
|
+
Sparkles,
|
|
12
|
+
} from "lucide-react";
|
|
13
|
+
|
|
14
|
+
export function BrandingHub() {
|
|
15
|
+
const [siteName, setSiteName] = useState("Kyro CMS");
|
|
16
|
+
const [adminTitle, setAdminTitle] = useState("Command Center");
|
|
17
|
+
const [primaryColor, setPrimaryColor] = useState("#6366f1");
|
|
18
|
+
const [dashboardGreeting, setDashboardGreeting] = useState(
|
|
19
|
+
"Welcome back to your Command Center.",
|
|
20
|
+
);
|
|
21
|
+
const [saving, setSaving] = useState(false);
|
|
22
|
+
const [saved, setSaved] = useState(false);
|
|
23
|
+
|
|
24
|
+
useEffect(() => {
|
|
25
|
+
const fetchBranding = async () => {
|
|
26
|
+
try {
|
|
27
|
+
const res = await fetch("/api/globals/site");
|
|
28
|
+
if (res.ok) {
|
|
29
|
+
const result = await res.json();
|
|
30
|
+
const data = result.data || result;
|
|
31
|
+
if (data && Object.keys(data).length > 0) {
|
|
32
|
+
if (data.siteName) setSiteName(data.siteName);
|
|
33
|
+
if (data.adminTitle) setAdminTitle(data.adminTitle);
|
|
34
|
+
if (data.primaryColor) setPrimaryColor(data.primaryColor);
|
|
35
|
+
if (data.dashboardGreeting)
|
|
36
|
+
setDashboardGreeting(data.dashboardGreeting);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
} catch (err) {
|
|
40
|
+
console.error("Failed to load branding:", err);
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
fetchBranding();
|
|
44
|
+
}, []);
|
|
45
|
+
|
|
46
|
+
const handleSave = async () => {
|
|
47
|
+
setSaving(true);
|
|
48
|
+
try {
|
|
49
|
+
const res = await fetch("/api/globals/site", {
|
|
50
|
+
method: "PATCH",
|
|
51
|
+
headers: { "Content-Type": "application/json" },
|
|
52
|
+
body: JSON.stringify({
|
|
53
|
+
siteName,
|
|
54
|
+
adminTitle,
|
|
55
|
+
primaryColor,
|
|
56
|
+
dashboardGreeting,
|
|
57
|
+
}),
|
|
58
|
+
});
|
|
59
|
+
if (res.ok) {
|
|
60
|
+
setSaved(true);
|
|
61
|
+
setTimeout(() => setSaved(false), 3000);
|
|
62
|
+
document.documentElement.style.setProperty(
|
|
63
|
+
"--kyro-primary",
|
|
64
|
+
primaryColor,
|
|
65
|
+
);
|
|
66
|
+
} else {
|
|
67
|
+
throw new Error("Failed to save");
|
|
68
|
+
}
|
|
69
|
+
} catch (e) {
|
|
70
|
+
console.error(e);
|
|
71
|
+
} finally {
|
|
72
|
+
setSaving(false);
|
|
73
|
+
}
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
const colors = [
|
|
77
|
+
{ name: "Indigo", hex: "#6366f1" },
|
|
78
|
+
{ name: "Emerald", hex: "#10b981" },
|
|
79
|
+
{ name: "Rose", hex: "#f43f5e" },
|
|
80
|
+
{ name: "Amber", hex: "#f59e0b" },
|
|
81
|
+
{ name: "Sky", hex: "#0ea5e9" },
|
|
82
|
+
{ name: "Violet", hex: "#8b5cf6" },
|
|
83
|
+
];
|
|
84
|
+
|
|
85
|
+
return (
|
|
86
|
+
<div className="w-full space-y-8 animate-in fade-in slide-in-from-bottom-4 duration-700 px-8 pb-32">
|
|
87
|
+
{/* Header */}
|
|
88
|
+
<div className="flex flex-col lg:flex-row lg:items-center justify-between gap-6 pt-4">
|
|
89
|
+
<div>
|
|
90
|
+
<h1 className="text-4xl font-black tracking-tighter text-[var(--kyro-text-primary)]">
|
|
91
|
+
Branding <span className="text-[var(--kyro-primary)]">Hub</span>
|
|
92
|
+
</h1>
|
|
93
|
+
<p className="text-[var(--kyro-text-secondary)] mt-1 font-medium opacity-60">
|
|
94
|
+
Customize the identity and aesthetic of your administrative
|
|
95
|
+
ecosystem.
|
|
96
|
+
</p>
|
|
97
|
+
</div>
|
|
98
|
+
<div className="flex items-center gap-3">
|
|
99
|
+
<button type="button"
|
|
100
|
+
onClick={handleSave}
|
|
101
|
+
disabled={saving}
|
|
102
|
+
className={`flex items-center gap-2 px-8 py-3 rounded-2xl font-black text-sm shadow-xl transition-all active:scale-95 ${
|
|
103
|
+
saved
|
|
104
|
+
? "bg-green-500 text-white"
|
|
105
|
+
: "bg-[var(--kyro-primary)] text-white hover:shadow-[var(--kyro-primary)]"
|
|
106
|
+
}`}
|
|
107
|
+
>
|
|
108
|
+
{saving ? (
|
|
109
|
+
<RefreshCcw className="w-4 h-4 animate-spin" />
|
|
110
|
+
) : saved ? (
|
|
111
|
+
<Check className="w-4 h-4" />
|
|
112
|
+
) : (
|
|
113
|
+
<Save className="w-4 h-4" />
|
|
114
|
+
)}
|
|
115
|
+
{saving
|
|
116
|
+
? "Saving..."
|
|
117
|
+
: saved
|
|
118
|
+
? "Identity Updated"
|
|
119
|
+
: "Publish Branding"}
|
|
120
|
+
</button>
|
|
121
|
+
</div>
|
|
122
|
+
</div>
|
|
123
|
+
|
|
124
|
+
<div className="grid grid-cols-1 lg:grid-cols-2 gap-8">
|
|
125
|
+
{/* Identity Settings */}
|
|
126
|
+
<section className="surface-tile p-8 space-y-8">
|
|
127
|
+
<div className="flex items-center gap-3 mb-2">
|
|
128
|
+
<Tag className="w-5 h-5 text-[var(--kyro-primary)]" />
|
|
129
|
+
<h2 className="text-xl font-black tracking-tight">Core Identity</h2>
|
|
130
|
+
</div>
|
|
131
|
+
|
|
132
|
+
<div className="space-y-6">
|
|
133
|
+
<div className="space-y-2">
|
|
134
|
+
<label className="text-[10px] font-black uppercase tracking-[0.2em] opacity-40">
|
|
135
|
+
Site Public Name
|
|
136
|
+
</label>
|
|
137
|
+
<input
|
|
138
|
+
type="text"
|
|
139
|
+
value={siteName}
|
|
140
|
+
onChange={(e) => setSiteName(e.target.value)}
|
|
141
|
+
className="w-full bg-[var(--kyro-bg-secondary)] border border-[var(--kyro-border)] rounded-xl py-3 px-4 text-sm font-bold focus:outline-none focus:ring-2 focus:ring-[var(--kyro-primary)] transition-all"
|
|
142
|
+
placeholder="e.g. Acme Corp CMS"
|
|
143
|
+
/>
|
|
144
|
+
</div>
|
|
145
|
+
|
|
146
|
+
<div className="space-y-2">
|
|
147
|
+
<label className="text-[10px] font-black uppercase tracking-[0.2em] opacity-40">
|
|
148
|
+
Admin Dashboard Title
|
|
149
|
+
</label>
|
|
150
|
+
<input
|
|
151
|
+
type="text"
|
|
152
|
+
value={adminTitle}
|
|
153
|
+
onChange={(e) => setAdminTitle(e.target.value)}
|
|
154
|
+
className="w-full bg-[var(--kyro-bg-secondary)] border border-[var(--kyro-border)] rounded-xl py-3 px-4 text-sm font-bold focus:outline-none focus:ring-2 focus:ring-[var(--kyro-primary)] transition-all"
|
|
155
|
+
placeholder="e.g. Command Center"
|
|
156
|
+
/>
|
|
157
|
+
</div>
|
|
158
|
+
|
|
159
|
+
<div className="space-y-2">
|
|
160
|
+
<label className="text-[10px] font-black uppercase tracking-[0.2em] opacity-40">
|
|
161
|
+
System Greeting
|
|
162
|
+
</label>
|
|
163
|
+
<textarea
|
|
164
|
+
value={dashboardGreeting}
|
|
165
|
+
onChange={(e) => setDashboardGreeting(e.target.value)}
|
|
166
|
+
rows={3}
|
|
167
|
+
className="w-full bg-[var(--kyro-bg-secondary)] border border-[var(--kyro-border)] rounded-xl py-3 px-4 text-sm font-bold focus:outline-none focus:ring-2 focus:ring-[var(--kyro-primary)] transition-all resize-none"
|
|
168
|
+
placeholder="Greeting text for the dashboard..."
|
|
169
|
+
/>
|
|
170
|
+
</div>
|
|
171
|
+
</div>
|
|
172
|
+
</section>
|
|
173
|
+
|
|
174
|
+
{/* Visual Aesthetic */}
|
|
175
|
+
<section className="surface-tile p-8 space-y-8">
|
|
176
|
+
<div className="flex items-center gap-3 mb-2">
|
|
177
|
+
<Palette className="w-5 h-5 text-[var(--kyro-primary)]" />
|
|
178
|
+
<h2 className="text-xl font-black tracking-tight">
|
|
179
|
+
Visual Aesthetic
|
|
180
|
+
</h2>
|
|
181
|
+
</div>
|
|
182
|
+
|
|
183
|
+
<div className="space-y-8">
|
|
184
|
+
<div className="space-y-4">
|
|
185
|
+
<label className="text-[10px] font-black uppercase tracking-[0.2em] opacity-40">
|
|
186
|
+
Primary Brand Color
|
|
187
|
+
</label>
|
|
188
|
+
<div className="grid grid-cols-6 gap-3">
|
|
189
|
+
{colors.map((c) => (
|
|
190
|
+
<button type="button"
|
|
191
|
+
key={c.name}
|
|
192
|
+
onClick={() => setPrimaryColor(c.hex)}
|
|
193
|
+
className={`aspect-square rounded-xl transition-all border-4 ${primaryColor === c.hex ? "border-white ring-2 ring-[var(--kyro-primary)]" : "border-transparent opacity-60 hover:opacity-100"}`}
|
|
194
|
+
style={{ backgroundColor: c.hex }}
|
|
195
|
+
title={c.name}
|
|
196
|
+
/>
|
|
197
|
+
))}
|
|
198
|
+
</div>
|
|
199
|
+
</div>
|
|
200
|
+
|
|
201
|
+
<div className="space-y-4 pt-4 border-t border-[var(--kyro-border)]">
|
|
202
|
+
<label className="text-[10px] font-black uppercase tracking-[0.2em] opacity-40">
|
|
203
|
+
Project Logo (SVG/PNG)
|
|
204
|
+
</label>
|
|
205
|
+
<div className="flex items-center gap-6">
|
|
206
|
+
<div className="w-20 h-20 rounded-2xl bg-[var(--kyro-bg-secondary)] border-2 border-dashed border-[var(--kyro-border)] flex flex-col items-center justify-center text-[var(--kyro-text-secondary)] hover:border-[var(--kyro-primary)] hover:text-[var(--kyro-primary)] cursor-pointer transition-all">
|
|
207
|
+
<ImageIcon className="w-6 h-6 mb-1 opacity-40" />
|
|
208
|
+
<span className="text-[8px] font-black uppercase">
|
|
209
|
+
Upload
|
|
210
|
+
</span>
|
|
211
|
+
</div>
|
|
212
|
+
<div className="flex-1">
|
|
213
|
+
<p className="text-xs font-bold mb-1">
|
|
214
|
+
Upload global CMS logo
|
|
215
|
+
</p>
|
|
216
|
+
<p className="text-[10px] opacity-40 leading-relaxed">
|
|
217
|
+
This will replace the Kyro brand in the sidebar and login
|
|
218
|
+
screens.
|
|
219
|
+
</p>
|
|
220
|
+
</div>
|
|
221
|
+
</div>
|
|
222
|
+
</div>
|
|
223
|
+
</div>
|
|
224
|
+
</section>
|
|
225
|
+
|
|
226
|
+
{/* Live Preview of Dashboard Card */}
|
|
227
|
+
<section className="lg:col-span-2 surface-tile p-8 overflow-hidden relative group">
|
|
228
|
+
<div className="absolute top-0 right-0 p-8 flex items-center gap-2 text-[var(--kyro-primary)]">
|
|
229
|
+
<Sparkles className="w-4 h-4" />
|
|
230
|
+
<span className="text-[10px] font-black uppercase tracking-widest">
|
|
231
|
+
Live Preview
|
|
232
|
+
</span>
|
|
233
|
+
</div>
|
|
234
|
+
|
|
235
|
+
<div className="max-w-2xl mx-auto py-12 text-center space-y-6">
|
|
236
|
+
<div className="inline-flex items-center gap-3 px-4 py-2 bg-[var(--kyro-bg-secondary)] rounded-full border border-[var(--kyro-border)]">
|
|
237
|
+
<span className="w-2 h-2 rounded-full bg-green-500 animate-pulse" />
|
|
238
|
+
<span className="text-[10px] font-black uppercase tracking-widest opacity-60">
|
|
239
|
+
{adminTitle} Online
|
|
240
|
+
</span>
|
|
241
|
+
</div>
|
|
242
|
+
<h2 className="text-5xl font-black tracking-tighter leading-none italic">
|
|
243
|
+
Welcome to {siteName}.
|
|
244
|
+
</h2>
|
|
245
|
+
<p className="text-xl font-medium text-[var(--kyro-text-secondary)] opacity-60">
|
|
246
|
+
{dashboardGreeting}
|
|
247
|
+
</p>
|
|
248
|
+
</div>
|
|
249
|
+
|
|
250
|
+
{/* Simulated Palette Update */}
|
|
251
|
+
<style
|
|
252
|
+
dangerouslySetInnerHTML={{
|
|
253
|
+
__html: `
|
|
254
|
+
:root {
|
|
255
|
+
--kyro-primary-temp: ${primaryColor};
|
|
256
|
+
}
|
|
257
|
+
.preview-btn {
|
|
258
|
+
background-color: var(--kyro-primary-temp);
|
|
259
|
+
}
|
|
260
|
+
`,
|
|
261
|
+
}}
|
|
262
|
+
/>
|
|
263
|
+
</section>
|
|
264
|
+
</div>
|
|
265
|
+
</div>
|
|
266
|
+
);
|
|
267
|
+
}
|
|
@@ -31,14 +31,14 @@ export function BulkActionsBar({
|
|
|
31
31
|
<CountBadge count={selectedCount} />
|
|
32
32
|
<span className="text-sm text-gray-600">selected</span>
|
|
33
33
|
</div>
|
|
34
|
-
<button
|
|
34
|
+
<button type="button"
|
|
35
35
|
onClick={onClearSelection}
|
|
36
36
|
className="text-sm text-gray-500 hover:text-gray-700"
|
|
37
37
|
>
|
|
38
38
|
Clear selection
|
|
39
39
|
</button>
|
|
40
40
|
{onSelectAll && (
|
|
41
|
-
<button
|
|
41
|
+
<button type="button"
|
|
42
42
|
onClick={onSelectAll}
|
|
43
43
|
className="text-sm text-gray-500 hover:text-gray-700"
|
|
44
44
|
>
|
|
@@ -49,7 +49,7 @@ export function BulkActionsBar({
|
|
|
49
49
|
|
|
50
50
|
<Dropdown
|
|
51
51
|
trigger={
|
|
52
|
-
<button className="kyro-btn kyro-btn-secondary kyro-btn-sm">
|
|
52
|
+
<button type="button" className="kyro-btn kyro-btn-secondary kyro-btn-sm">
|
|
53
53
|
Actions
|
|
54
54
|
<svg
|
|
55
55
|
width="12"
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { useState } from "react";
|
|
2
|
-
import type { KyroConfig, CollectionConfig } from "@kyro-cms/core";
|
|
2
|
+
import type { KyroConfig, CollectionConfig } from "@kyro-cms/core/client";
|
|
3
3
|
import { AutoForm } from "./AutoForm";
|
|
4
4
|
import { Spinner } from "./ui/Spinner";
|
|
5
5
|
|
|
@@ -50,7 +50,7 @@ export function CreateView({
|
|
|
50
50
|
return (
|
|
51
51
|
<div className="kyro-detail">
|
|
52
52
|
<div className="kyro-detail-header">
|
|
53
|
-
<button className="kyro-detail-back" onClick={onCancel}>
|
|
53
|
+
<button type="button" className="kyro-detail-back" onClick={onCancel}>
|
|
54
54
|
<svg
|
|
55
55
|
width="18"
|
|
56
56
|
height="18"
|
|
@@ -64,14 +64,14 @@ export function CreateView({
|
|
|
64
64
|
</button>
|
|
65
65
|
<h2 className="kyro-detail-title">Create {label}</h2>
|
|
66
66
|
<div className="kyro-detail-actions">
|
|
67
|
-
<button
|
|
67
|
+
<button type="button"
|
|
68
68
|
className="kyro-btn kyro-btn-secondary kyro-btn-md"
|
|
69
69
|
onClick={onCancel}
|
|
70
70
|
disabled={saving}
|
|
71
71
|
>
|
|
72
72
|
Cancel
|
|
73
73
|
</button>
|
|
74
|
-
<button
|
|
74
|
+
<button type="button"
|
|
75
75
|
className="kyro-btn kyro-btn-primary kyro-btn-md"
|
|
76
76
|
onClick={handleSubmit}
|
|
77
77
|
disabled={saving}
|