betterstart-cli 0.0.94 → 0.0.96

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.
Files changed (33) hide show
  1. package/dist/assets/adapters/next/integrations/_shared/actions/object-key.ts +16 -0
  2. package/dist/assets/adapters/next/integrations/r2/actions/r2.ts +2 -10
  3. package/dist/assets/adapters/next/integrations/r2/integration.ts +4 -0
  4. package/dist/assets/adapters/next/integrations/railway-bucket/actions/railway-bucket.ts +2 -10
  5. package/dist/assets/adapters/next/integrations/railway-bucket/integration.ts +4 -0
  6. package/dist/assets/adapters/next/integrations/vercel-blob/actions/vercel-blob.ts +2 -10
  7. package/dist/assets/adapters/next/integrations/vercel-blob/integration.ts +4 -0
  8. package/dist/assets/adapters/next/templates/init/api/upload-route.ts +37 -13
  9. package/dist/assets/adapters/next/templates/init/components/layouts/admin-settings-sidebar.tsx +3 -13
  10. package/dist/assets/adapters/next/templates/init/hooks/content-editor/use-color-highlight.ts +10 -64
  11. package/dist/assets/adapters/next/templates/init/hooks/content-editor/use-content-editor-source-mode.tsx +11 -4
  12. package/dist/assets/adapters/next/templates/init/lib/actions/audit/get-audit-logs.ts +1 -9
  13. package/dist/assets/adapters/next/templates/init/lib/actions/media/create-media.ts +6 -6
  14. package/dist/assets/adapters/next/templates/init/lib/actions/media/update-media.ts +5 -5
  15. package/dist/assets/adapters/next/templates/init/lib/actions/webhooks/get-webhook-deliveries.ts +1 -10
  16. package/dist/assets/adapters/next/templates/init/lib/actions/webhooks/get-webhooks.ts +1 -10
  17. package/dist/assets/adapters/next/templates/init/pages/settings/forms/forms-settings-page-content.tsx +1 -1
  18. package/dist/assets/adapters/next/templates/init/utils/date/date.ts +15 -0
  19. package/dist/assets/adapters/next/templates/init/utils/editor/content-editor.ts +98 -25
  20. package/dist/assets/adapters/next/templates/init/utils/editor/markdown.ts +5 -2
  21. package/dist/assets/shared-assets/react-admin/custom/content-editor/selection-bubble-menu.tsx +2 -2
  22. package/dist/assets/shared-assets/react-admin/custom/content-editor/source-mode.tsx +4 -2
  23. package/dist/assets/shared-assets/react-admin/custom/media-field.tsx +2 -2
  24. package/dist/assets/shared-assets/react-admin/schema.json +1143 -876
  25. package/dist/assets/shared-assets/react-admin/ui/sidebar.tsx +1 -1
  26. package/dist/{chunk-3CLINNJL.js → chunk-LGZBMR7E.js} +33 -9
  27. package/dist/chunk-LGZBMR7E.js.map +1 -0
  28. package/dist/cli.js +2338 -2872
  29. package/dist/cli.js.map +1 -1
  30. package/dist/{template-reader-PVN53GS7.js → template-reader-WRTNGRZV.js} +2 -2
  31. package/package.json +1 -1
  32. package/dist/chunk-3CLINNJL.js.map +0 -1
  33. /package/dist/{template-reader-PVN53GS7.js.map → template-reader-WRTNGRZV.js.map} +0 -0
@@ -9,6 +9,7 @@ export interface ContentEditorSelectionRequest {
9
9
  }
10
10
 
11
11
  export const CONTENT_EDITOR_HIGHLIGHT_COLORS = [
12
+ 'default',
12
13
  'gray',
13
14
  'brown',
14
15
  'orange',
@@ -22,20 +23,92 @@ export const CONTENT_EDITOR_HIGHLIGHT_COLORS = [
22
23
 
23
24
  export type ContentEditorHighlightColor = (typeof CONTENT_EDITOR_HIGHLIGHT_COLORS)[number]
24
25
 
25
- export const CONTENT_EDITOR_HIGHLIGHT_COLOR_VALUES: Record<ContentEditorHighlightColor, string> = {
26
- gray: 'var(--tt-color-highlight-gray)',
27
- brown: 'var(--tt-color-highlight-brown)',
28
- orange: 'var(--tt-color-highlight-orange)',
29
- yellow: 'var(--tt-color-highlight-yellow)',
30
- green: 'var(--tt-color-highlight-green)',
31
- blue: 'var(--tt-color-highlight-blue)',
32
- purple: 'var(--tt-color-highlight-purple)',
33
- pink: 'var(--tt-color-highlight-pink)',
34
- red: 'var(--tt-color-highlight-red)'
26
+ export interface ContentEditorHighlightColorOption {
27
+ label: string
28
+ value: string
29
+ colorValue: string
30
+ border: string
35
31
  }
36
32
 
37
- const HIGHLIGHT_VALUE_NAMES = new Map(
38
- Object.entries(CONTENT_EDITOR_HIGHLIGHT_COLOR_VALUES).map(([name, value]) => [value, name])
33
+ export const CONTENT_EDITOR_HIGHLIGHT_COLOR_OPTIONS: Record<
34
+ ContentEditorHighlightColor,
35
+ ContentEditorHighlightColorOption
36
+ > = {
37
+ default: {
38
+ label: 'Default background',
39
+ value: 'var(--tt-bg-color)',
40
+ colorValue: '#ffffff',
41
+ border: 'var(--tt-bg-color-contrast)'
42
+ },
43
+ gray: {
44
+ label: 'Gray background',
45
+ value: 'var(--tt-color-highlight-gray)',
46
+ colorValue: '#f8f8f7',
47
+ border: 'var(--tt-color-highlight-gray-contrast)'
48
+ },
49
+ brown: {
50
+ label: 'Brown background',
51
+ value: 'var(--tt-color-highlight-brown)',
52
+ colorValue: '#f4eeee',
53
+ border: 'var(--tt-color-highlight-brown-contrast)'
54
+ },
55
+ orange: {
56
+ label: 'Orange background',
57
+ value: 'var(--tt-color-highlight-orange)',
58
+ colorValue: '#fbecdd',
59
+ border: 'var(--tt-color-highlight-orange-contrast)'
60
+ },
61
+ yellow: {
62
+ label: 'Yellow background',
63
+ value: 'var(--tt-color-highlight-yellow)',
64
+ colorValue: '#fef9c3',
65
+ border: 'var(--tt-color-highlight-yellow-contrast)'
66
+ },
67
+ green: {
68
+ label: 'Green background',
69
+ value: 'var(--tt-color-highlight-green)',
70
+ colorValue: '#dcfce7',
71
+ border: 'var(--tt-color-highlight-green-contrast)'
72
+ },
73
+ blue: {
74
+ label: 'Blue background',
75
+ value: 'var(--tt-color-highlight-blue)',
76
+ colorValue: '#e0f2fe',
77
+ border: 'var(--tt-color-highlight-blue-contrast)'
78
+ },
79
+ purple: {
80
+ label: 'Purple background',
81
+ value: 'var(--tt-color-highlight-purple)',
82
+ colorValue: '#f3e8ff',
83
+ border: 'var(--tt-color-highlight-purple-contrast)'
84
+ },
85
+ pink: {
86
+ label: 'Pink background',
87
+ value: 'var(--tt-color-highlight-pink)',
88
+ colorValue: '#fcf1f6',
89
+ border: 'var(--tt-color-highlight-pink-contrast)'
90
+ },
91
+ red: {
92
+ label: 'Red background',
93
+ value: 'var(--tt-color-highlight-red)',
94
+ colorValue: '#ffe4e6',
95
+ border: 'var(--tt-color-highlight-red-contrast)'
96
+ }
97
+ }
98
+
99
+ export const CONTENT_EDITOR_HIGHLIGHT_COLOR_NAME_PATTERN = CONTENT_EDITOR_HIGHLIGHT_COLORS.join('|')
100
+
101
+ const HIGHLIGHT_NAMES_BY_VALUE = new Map(
102
+ CONTENT_EDITOR_HIGHLIGHT_COLORS.map(
103
+ (name) => [CONTENT_EDITOR_HIGHLIGHT_COLOR_OPTIONS[name].value, name] as const
104
+ )
105
+ )
106
+
107
+ const HIGHLIGHT_NAMES_BY_CSS_VARIABLE = new Map(
108
+ CONTENT_EDITOR_HIGHLIGHT_COLORS.map(
109
+ (name) =>
110
+ [CONTENT_EDITOR_HIGHLIGHT_COLOR_OPTIONS[name].value.slice('var('.length, -1), name] as const
111
+ )
39
112
  )
40
113
 
41
114
  export function getContentEditorHighlightColorName(
@@ -44,19 +117,16 @@ export function getContentEditorHighlightColorName(
44
117
  if (!value) return 'yellow'
45
118
 
46
119
  const normalized = value.trim()
47
- const variableMatch = normalized.match(/var\((--tt-color-highlight-[^)]+)\)/)
48
- const variableName = variableMatch ? `var(${variableMatch[1]})` : normalized
49
- const mapped = HIGHLIGHT_VALUE_NAMES.get(variableName)
120
+ const mapped = HIGHLIGHT_NAMES_BY_VALUE.get(normalized)
50
121
 
51
- if (mapped && isContentEditorHighlightColor(mapped)) {
122
+ if (mapped) {
52
123
  return mapped
53
124
  }
54
125
 
55
- const cssVariableMatch = normalized.match(
56
- /--tt-color-highlight-(gray|brown|orange|yellow|green|blue|purple|pink|red)/
57
- )
58
- if (cssVariableMatch && isContentEditorHighlightColor(cssVariableMatch[1])) {
59
- return cssVariableMatch[1]
126
+ for (const [cssVariable, name] of HIGHLIGHT_NAMES_BY_CSS_VARIABLE) {
127
+ if (normalized.includes(cssVariable)) {
128
+ return name
129
+ }
60
130
  }
61
131
 
62
132
  if (isContentEditorHighlightColor(normalized)) {
@@ -67,7 +137,7 @@ export function getContentEditorHighlightColorName(
67
137
  }
68
138
 
69
139
  export function getContentEditorHighlightColorValue(color: ContentEditorHighlightColor): string {
70
- return CONTENT_EDITOR_HIGHLIGHT_COLOR_VALUES[color]
140
+ return CONTENT_EDITOR_HIGHLIGHT_COLOR_OPTIONS[color].value
71
141
  }
72
142
 
73
143
  export function isContentEditorHighlightColor(value: string): value is ContentEditorHighlightColor {
@@ -295,13 +365,16 @@ function matchMarkdownMarkSyntax(markdown: string, index: number): number | null
295
365
  return null
296
366
  }
297
367
 
368
+ const HIGHLIGHT_SPAN_OPEN_PATTERN = new RegExp(
369
+ `^<span\\s+data-highlight-color="(?:${CONTENT_EDITOR_HIGHLIGHT_COLOR_NAME_PATTERN})">`,
370
+ 'i'
371
+ )
372
+
298
373
  function matchHtmlMarkSyntax(markdown: string, index: number): number | null {
299
374
  const remaining = markdown.slice(index)
300
375
  const match =
301
376
  /^<\/?(?:u|sub|sup|kbd)>/i.exec(remaining) ??
302
- /^<span\s+data-highlight-color="(?:gray|brown|orange|yellow|green|blue|purple|pink|red)">/i.exec(
303
- remaining
304
- ) ??
377
+ HIGHLIGHT_SPAN_OPEN_PATTERN.exec(remaining) ??
305
378
  /^<\/span>/i.exec(remaining)
306
379
 
307
380
  return match ? index + match[0].length : null
@@ -1,3 +1,4 @@
1
+ import { CONTENT_EDITOR_HIGHLIGHT_COLOR_NAME_PATTERN } from '@admin/utils/editor/content-editor'
1
2
  import type { EditorView } from '@codemirror/view'
2
3
 
3
4
  interface InsertResult {
@@ -22,8 +23,10 @@ export interface ContentEditorMathValue {
22
23
  raw: string
23
24
  }
24
25
 
25
- const HIGHLIGHT_SPAN_PATTERN =
26
- /<span\s+data-highlight-color="(?:gray|brown|orange|yellow|green|blue|purple|pink|red)">([\s\S]*?)<\/span>/g
26
+ const HIGHLIGHT_SPAN_PATTERN = new RegExp(
27
+ `<span\\s+data-highlight-color="(?:${CONTENT_EDITOR_HIGHLIGHT_COLOR_NAME_PATTERN})">([\\s\\S]*?)<\\/span>`,
28
+ 'g'
29
+ )
27
30
  const MARKDOWN_LINK_PATTERN = /\[([^\]\n]*)\]\(([^)\n]*)\)/g
28
31
  const BLOCK_MATH_ENVIRONMENT_NAMES = new Set([
29
32
  'align',
@@ -73,7 +73,7 @@ export function SelectionBubbleMenu({ editor }: { editor: Editor }) {
73
73
  aria-label="Link formatting toolbar"
74
74
  className={cn(
75
75
  'flex items-center gap-1 overflow-x-auto border-border border bg-popover p-4 text-foreground shadow-2xl [scrollbar-width:none] [&::-webkit-scrollbar]:hidden rounded-sm',
76
- 'relative z-10'
76
+ 'relative z-50'
77
77
  )}
78
78
  >
79
79
  <LinkContent editor={editor} />
@@ -102,7 +102,7 @@ export function SelectionBubbleMenu({ editor }: { editor: Editor }) {
102
102
  onPointerDownCapture={handleSelectionMenuPointerDown}
103
103
  className={cn(
104
104
  'flex items-center gap-1 overflow-x-auto border-border rounded-sm border bg-popover p-1 text-popover-foreground shadow-menu [scrollbar-width:none] [&::-webkit-scrollbar]:hidden',
105
- 'relative z-10'
105
+ 'relative z-50'
106
106
  )}
107
107
  >
108
108
  <div className="flex items-center gap-0.5">
@@ -92,6 +92,8 @@ export function SourceMode({
92
92
  applyList,
93
93
  applyStrike,
94
94
  applyUnderline,
95
+ canRedoMarkdownChange,
96
+ canUndoMarkdownChange,
95
97
  codeMirrorExtensions,
96
98
  editorRef,
97
99
  editorTheme,
@@ -135,7 +137,7 @@ export function SourceMode({
135
137
  variant="ghost"
136
138
  size="icon-sm"
137
139
  onClick={undoMarkdownChange}
138
- disabled={disabled}
140
+ disabled={disabled || !canUndoMarkdownChange}
139
141
  aria-label="Undo"
140
142
  title="Undo"
141
143
  >
@@ -146,7 +148,7 @@ export function SourceMode({
146
148
  variant="ghost"
147
149
  size="icon-sm"
148
150
  onClick={redoMarkdownChange}
149
- disabled={disabled}
151
+ disabled={disabled || !canRedoMarkdownChange}
150
152
  aria-label="Redo"
151
153
  title="Redo"
152
154
  >
@@ -94,9 +94,9 @@ export function MediaField({
94
94
  <>
95
95
  <div
96
96
  aria-hidden="true"
97
- className="pointer-events-none absolute inset-0 bg-black/10 opacity-0 backdrop-blur-xs transition-opacity duration-300 ease-out group-hover:opacity-100 rounded-sm"
97
+ className="pointer-events-none absolute inset-0 bg-black/10 opacity-0 backdrop-blur-xs transition-opacity duration-300 ease-out group-hover:opacity-100 group-focus-within:opacity-100 rounded-sm"
98
98
  />
99
- <div className="absolute inset-0 flex flex-col items-center justify-center gap-1 opacity-0 transition-opacity duration-200 ease-out group-hover:opacity-100">
99
+ <div className="absolute inset-0 flex flex-col items-center justify-center gap-1 opacity-0 transition-opacity duration-200 ease-out group-hover:opacity-100 group-focus-within:opacity-100">
100
100
  <Button
101
101
  type="button"
102
102
  data-media-field-action="true"