@aphexcms/cms-core 2.0.6 → 2.0.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.
@@ -1038,43 +1038,39 @@
1038
1038
  <p class="text-muted-foreground text-sm">
1039
1039
  Revision from {new Date(activePreview.createdAt || Date.now()).toLocaleString(undefined, { month: 'short', day: 'numeric', hour: 'numeric', minute: '2-digit', hour12: true })}
1040
1040
  </p>
1041
- {#if fullDocument?._meta?.publishedHash && fullDocument?._meta?.status !== 'unpublished'}
1042
- <p class="text-muted-foreground text-xs">Unpublish first to restore</p>
1043
- {:else}
1044
- <Button
1045
- size="sm"
1046
- onclick={async () => {
1047
- if (!documentId || !activePreview) return;
1048
- try {
1049
- await documents.restoreVersion(documentId, activePreview.versionNumber);
1050
- const docRes = await documents.getById(documentId);
1051
- if (docRes.success && docRes.data) {
1052
- const doc = docRes.data as Record<string, any>;
1053
- fullDocument = doc;
1054
- const newData: Record<string, any> = {};
1055
- if (schema) {
1056
- for (const field of schema.fields) {
1057
- if (doc[field.name] !== undefined) {
1058
- newData[field.name] = doc[field.name];
1059
- }
1041
+ <Button
1042
+ size="sm"
1043
+ onclick={async () => {
1044
+ if (!documentId || !activePreview) return;
1045
+ try {
1046
+ await documents.restoreVersion(documentId, activePreview.versionNumber);
1047
+ const docRes = await documents.getById(documentId);
1048
+ if (docRes.success && docRes.data) {
1049
+ const doc = docRes.data as Record<string, any>;
1050
+ fullDocument = doc;
1051
+ const newData: Record<string, any> = {};
1052
+ if (schema) {
1053
+ for (const field of schema.fields) {
1054
+ if (doc[field.name] !== undefined) {
1055
+ newData[field.name] = doc[field.name];
1060
1056
  }
1061
1057
  }
1062
- documentData = newData;
1063
- hasUnsavedChanges = false;
1064
- lastSaved = new Date();
1065
1058
  }
1066
- previewingVersion = null;
1067
- perspective = 'draft';
1068
- publishedData = null;
1069
- toast.success('Revision restored');
1070
- } catch {
1071
- toast.error('Failed to restore revision');
1059
+ documentData = newData;
1060
+ hasUnsavedChanges = false;
1061
+ lastSaved = new Date();
1072
1062
  }
1073
- }}
1074
- >
1075
- Restore
1076
- </Button>
1077
- {/if}
1063
+ previewingVersion = null;
1064
+ perspective = 'draft';
1065
+ publishedData = null;
1066
+ toast.success('Revision restored');
1067
+ } catch {
1068
+ toast.error('Failed to restore revision');
1069
+ }
1070
+ }}
1071
+ >
1072
+ Restore
1073
+ </Button>
1078
1074
  </div>
1079
1075
  {:else if isViewingPublished}
1080
1076
  <!-- Published view footer -->
@@ -1 +1 @@
1
- {"version":3,"file":"DocumentEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/lib/components/admin/DocumentEditor.svelte.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAWxD,UAAU,KAAK;IACd,OAAO,EAAE,UAAU,EAAE,CAAC;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,UAAU,EAAE,OAAO,CAAC;IACpB,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,OAAO,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IACvC,WAAW,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1D,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;IACvB,WAAW,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C,eAAe,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,KAAK,IAAI,CAAC;IACrE,oBAAoB,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IACpD,sBAAsB,CAAC,EAAE;QAAE,aAAa,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5H,UAAU,CAAC,EAAE,OAAO,CAAC;CACrB;AAsrCF,QAAA,MAAM,cAAc,2CAAwC,CAAC;AAC7D,KAAK,cAAc,GAAG,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC;AACxD,eAAe,cAAc,CAAC"}
1
+ {"version":3,"file":"DocumentEditor.svelte.d.ts","sourceRoot":"","sources":["../../../src/lib/components/admin/DocumentEditor.svelte.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAWxD,UAAU,KAAK;IACd,OAAO,EAAE,UAAU,EAAE,CAAC;IACtB,YAAY,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,UAAU,EAAE,OAAO,CAAC;IACpB,MAAM,EAAE,MAAM,IAAI,CAAC;IACnB,OAAO,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IACvC,WAAW,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1D,SAAS,CAAC,EAAE,MAAM,IAAI,CAAC;IACvB,WAAW,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IAC3C,eAAe,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,KAAK,IAAI,CAAC;IACrE,oBAAoB,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,IAAI,CAAC;IACpD,sBAAsB,CAAC,EAAE;QAAE,aAAa,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,CAAC;IAC5H,UAAU,CAAC,EAAE,OAAO,CAAC;CACrB;AAkrCF,QAAA,MAAM,cAAc,2CAAwC,CAAC;AAC7D,KAAK,cAAc,GAAG,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC;AACxD,eAAe,cAAc,CAAC"}
@@ -0,0 +1,138 @@
1
+ <script lang="ts">
2
+ import { Badge } from '@aphexcms/ui/shadcn/badge';
3
+ import { Button } from '@aphexcms/ui/shadcn/button';
4
+ import { documents } from '../../api/documents';
5
+ import { toast } from 'svelte-sonner';
6
+
7
+ interface Props {
8
+ documentId: string;
9
+ onClose: () => void;
10
+ onRestored?: () => void;
11
+ onPreviewVersion?: (version: { versionNumber: number; data: Record<string, any>; eventType: string; createdAt?: string } | null) => void;
12
+ }
13
+
14
+ let { documentId, onClose, onRestored, onPreviewVersion }: Props = $props();
15
+
16
+ let versions = $state<any[]>([]);
17
+ let loading = $state(true);
18
+ let previewVersion = $state<any>(null);
19
+ let filter = $state<'all' | 'publish' | 'draft'>('all');
20
+
21
+ const filteredVersions = $derived(
22
+ filter === 'all' ? versions : versions.filter((v) => v.eventType === filter)
23
+ );
24
+
25
+ $effect(() => {
26
+ loadVersions();
27
+ });
28
+
29
+ async function loadVersions() {
30
+ loading = true;
31
+ try {
32
+ const res = await documents.listVersions(documentId, { limit: 100 });
33
+ if (res.success && res.data) {
34
+ versions = res.data;
35
+ }
36
+ } catch {
37
+ toast.error('Failed to load versions');
38
+ } finally {
39
+ loading = false;
40
+ }
41
+ }
42
+
43
+ async function previewVersionData(version: any) {
44
+ try {
45
+ const res = await documents.getVersion(documentId, version.versionNumber);
46
+ if (res.success && res.data) {
47
+ previewVersion = { ...version, data: res.data.data };
48
+ onPreviewVersion?.({
49
+ versionNumber: version.versionNumber,
50
+ data: res.data.data,
51
+ eventType: version.eventType,
52
+ createdAt: version.createdAt
53
+ });
54
+ }
55
+ } catch {
56
+ toast.error('Failed to load version');
57
+ }
58
+ }
59
+
60
+ function clearPreview() {
61
+ previewVersion = null;
62
+ onPreviewVersion?.(null);
63
+ }
64
+
65
+ async function restoreVersion() {
66
+ if (!previewVersion) return;
67
+ try {
68
+ await documents.restoreVersion(documentId, previewVersion.versionNumber);
69
+ toast.success(`Restored to v${previewVersion.versionNumber}`);
70
+ clearPreview();
71
+ onRestored?.();
72
+ await loadVersions();
73
+ } catch {
74
+ toast.error('Failed to restore');
75
+ }
76
+ }
77
+ </script>
78
+
79
+ <div class="flex h-full flex-col">
80
+ <!-- Header -->
81
+ <div class="border-border bg-background flex h-14 items-center justify-between border-b px-3">
82
+ <h3 class="text-sm font-medium">History</h3>
83
+ <button
84
+ class="hover:bg-muted rounded p-1 transition-colors"
85
+ onclick={onClose}
86
+ >
87
+ <svg class="h-4 w-4" fill="none" viewBox="0 0 24 24" stroke="currentColor">
88
+ <path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M6 18L18 6M6 6l12 12" />
89
+ </svg>
90
+ </button>
91
+ </div>
92
+
93
+ <!-- Filter tabs -->
94
+ <div class="border-border flex border-b">
95
+ {#each [{ value: 'all', label: 'All' }, { value: 'publish', label: 'Published' }, { value: 'draft', label: 'Drafts' }] as tab}
96
+ <button
97
+ class="flex-1 px-2 py-2 text-xs font-medium transition-colors {filter === tab.value ? 'border-b-2 border-primary text-foreground' : 'text-muted-foreground hover:text-foreground'}"
98
+ onclick={() => { filter = tab.value as any; }}
99
+ >
100
+ {tab.label}
101
+ </button>
102
+ {/each}
103
+ </div>
104
+
105
+ <!-- Version List -->
106
+ <div class="flex-1 overflow-auto">
107
+ {#if loading}
108
+ <div class="p-4 text-center">
109
+ <span class="text-muted-foreground text-xs">Loading...</span>
110
+ </div>
111
+ {:else if filteredVersions.length === 0}
112
+ <div class="p-4 text-center">
113
+ <span class="text-muted-foreground text-xs">No {filter === 'all' ? '' : filter} versions</span>
114
+ </div>
115
+ {:else}
116
+ {#each filteredVersions as version}
117
+ <button
118
+ class="w-full border-b px-3 py-2.5 text-left transition-colors hover:bg-muted {previewVersion?.versionNumber === version.versionNumber ? 'bg-muted border-l-2 border-l-primary' : ''}"
119
+ onclick={() => previewVersionData(version)}
120
+ >
121
+ <div class="flex items-center justify-between">
122
+ <span class="text-muted-foreground text-[11px]">
123
+ {new Date(version.createdAt).toLocaleString(undefined, { month: 'short', day: 'numeric', hour: 'numeric', minute: '2-digit', hour12: true })}
124
+ </span>
125
+ <Badge variant={version.eventType === 'publish' ? 'default' : 'secondary'} class="text-[9px] px-1.5 py-0">
126
+ {version.eventType}
127
+ </Badge>
128
+ </div>
129
+ {#if version.createdByName || version.createdBy}
130
+ <p class="text-muted-foreground mt-0.5 truncate text-[10px]">
131
+ {version.createdByName || version.createdBy}
132
+ </p>
133
+ {/if}
134
+ </button>
135
+ {/each}
136
+ {/if}
137
+ </div>
138
+ </div>
@@ -0,0 +1,15 @@
1
+ interface Props {
2
+ documentId: string;
3
+ onClose: () => void;
4
+ onRestored?: () => void;
5
+ onPreviewVersion?: (version: {
6
+ versionNumber: number;
7
+ data: Record<string, any>;
8
+ eventType: string;
9
+ createdAt?: string;
10
+ } | null) => void;
11
+ }
12
+ declare const DocumentVersionPanel: import("svelte").Component<Props, {}, "">;
13
+ type DocumentVersionPanel = ReturnType<typeof DocumentVersionPanel>;
14
+ export default DocumentVersionPanel;
15
+ //# sourceMappingURL=DocumentVersionPanel.svelte.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DocumentVersionPanel.svelte.d.ts","sourceRoot":"","sources":["../../../src/lib/components/admin/DocumentVersionPanel.svelte.ts"],"names":[],"mappings":"AASC,UAAU,KAAK;IACd,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,UAAU,CAAC,EAAE,MAAM,IAAI,CAAC;IACxB,gBAAgB,CAAC,EAAE,CAAC,OAAO,EAAE;QAAE,aAAa,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,IAAI,KAAK,IAAI,CAAC;CACzI;AA+HF,QAAA,MAAM,oBAAoB,2CAAwC,CAAC;AACnE,KAAK,oBAAoB,GAAG,UAAU,CAAC,OAAO,oBAAoB,CAAC,CAAC;AACpE,eAAe,oBAAoB,CAAC"}
@@ -4,5 +4,6 @@ export { default as DocumentEditor } from './admin/DocumentEditor.svelte';
4
4
  export { default as SchemaField } from './admin/SchemaField.svelte';
5
5
  export { default as MediaBrowser } from './admin/MediaBrowser.svelte';
6
6
  export { default as AssetBrowserModal } from './admin/AssetBrowserModal.svelte';
7
+ export { default as DocumentVersionPanel } from './admin/DocumentVersionPanel.svelte';
7
8
  export * from './fields/index.js';
8
9
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/lib/components/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGxD,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAG7D,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAGhF,cAAc,gBAAgB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/lib/components/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGxD,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAG7D,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAChF,OAAO,EAAE,OAAO,IAAI,oBAAoB,EAAE,MAAM,qCAAqC,CAAC;AAGtF,cAAc,gBAAgB,CAAC"}
@@ -9,5 +9,6 @@ export { default as DocumentEditor } from './admin/DocumentEditor.svelte';
9
9
  export { default as SchemaField } from './admin/SchemaField.svelte';
10
10
  export { default as MediaBrowser } from './admin/MediaBrowser.svelte';
11
11
  export { default as AssetBrowserModal } from './admin/AssetBrowserModal.svelte';
12
+ export { default as DocumentVersionPanel } from './admin/DocumentVersionPanel.svelte';
12
13
  // Field components
13
14
  export * from './fields/index.js';
@@ -4,5 +4,6 @@ export { default as DocumentEditor } from './admin/DocumentEditor.svelte';
4
4
  export { default as SchemaField } from './admin/SchemaField.svelte';
5
5
  export { default as MediaBrowser } from './admin/MediaBrowser.svelte';
6
6
  export { default as AssetBrowserModal } from './admin/AssetBrowserModal.svelte';
7
+ export { default as DocumentVersionPanel } from './admin/DocumentVersionPanel.svelte';
7
8
  export * from './fields/index.js';
8
9
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGxD,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAG7D,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAGhF,cAAc,gBAAgB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAGxD,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAG7D,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAChF,OAAO,EAAE,OAAO,IAAI,oBAAoB,EAAE,MAAM,qCAAqC,CAAC;AAGtF,cAAc,gBAAgB,CAAC"}
@@ -9,6 +9,7 @@ export { default as DocumentEditor } from './admin/DocumentEditor.svelte';
9
9
  export { default as SchemaField } from './admin/SchemaField.svelte';
10
10
  export { default as MediaBrowser } from './admin/MediaBrowser.svelte';
11
11
  export { default as AssetBrowserModal } from './admin/AssetBrowserModal.svelte';
12
+ export { default as DocumentVersionPanel } from './admin/DocumentVersionPanel.svelte';
12
13
  // Field components
13
14
  export * from './fields/index.js';
14
15
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAAA,uBAAuB;AACvB,wDAAwD;AAExD,iBAAiB;AACjB,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAExD,UAAU;AACV,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAE7D,kEAAkE;AAClE,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAEhF,mBAAmB;AACnB,cAAc,gBAAgB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/components/index.ts"],"names":[],"mappings":"AAAA,uBAAuB;AACvB,wDAAwD;AAExD,iBAAiB;AACjB,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAExD,UAAU;AACV,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAAyB,CAAC;AAE7D,kEAAkE;AAClE,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC1E,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACpE,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,EAAE,OAAO,IAAI,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AAChF,OAAO,EAAE,OAAO,IAAI,oBAAoB,EAAE,MAAM,qCAAqC,CAAC;AAEtF,mBAAmB;AACnB,cAAc,gBAAgB,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aphexcms/cms-core",
3
- "version": "2.0.6",
3
+ "version": "2.0.8",
4
4
  "description": "Aphex CMS Core - A Sanity-style CMS with ports and adapters architecture",
5
5
  "publishConfig": {
6
6
  "access": "public",