@vibecms/core 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/engine/index.d.mts +4 -0
- package/dist/engine/index.d.ts +4 -0
- package/dist/engine/index.js +1226 -0
- package/dist/engine/index.js.map +1 -0
- package/dist/engine/index.mjs +1184 -0
- package/dist/engine/index.mjs.map +1 -0
- package/dist/hooks/index.d.mts +27 -0
- package/dist/hooks/index.d.ts +27 -0
- package/dist/hooks/index.js +75 -0
- package/dist/hooks/index.js.map +1 -0
- package/dist/hooks/index.mjs +47 -0
- package/dist/hooks/index.mjs.map +1 -0
- package/dist/index-C3P1J_of.d.ts +339 -0
- package/dist/index-CO4uwTdH.d.mts +339 -0
- package/dist/index.css +2326 -0
- package/dist/index.css.map +1 -0
- package/dist/index.d.mts +412 -0
- package/dist/index.d.ts +412 -0
- package/dist/index.js +3715 -0
- package/dist/index.js.map +1 -0
- package/dist/index.mjs +3587 -0
- package/dist/index.mjs.map +1 -0
- package/dist/storage/index.d.mts +32 -0
- package/dist/storage/index.d.ts +32 -0
- package/dist/storage/index.js +103 -0
- package/dist/storage/index.js.map +1 -0
- package/dist/storage/index.mjs +75 -0
- package/dist/storage/index.mjs.map +1 -0
- package/dist/types-BkDsDmQJ.d.mts +83 -0
- package/dist/types-BkDsDmQJ.d.ts +83 -0
- package/dist/ui/index.d.mts +127 -0
- package/dist/ui/index.d.ts +127 -0
- package/dist/ui/index.js +1119 -0
- package/dist/ui/index.js.map +1 -0
- package/dist/ui/index.mjs +1030 -0
- package/dist/ui/index.mjs.map +1 -0
- package/dist/vite-plugin.d.mts +8 -0
- package/dist/vite-plugin.d.ts +8 -0
- package/dist/vite-plugin.js +193 -0
- package/dist/vite-plugin.js.map +1 -0
- package/dist/vite-plugin.mjs +165 -0
- package/dist/vite-plugin.mjs.map +1 -0
- package/package.json +89 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/engine/index.ts","../../src/config.ts","../../src/engine/validation.ts","../../src/engine/engine-node.ts","../../src/engine/engine-browser.ts","../../src/engine/engine-dev.ts","../../src/license.ts"],"sourcesContent":["import { SyncEngine, VibeEngineConfig } from './types';\nimport { NodeEngine } from './engine-node';\nimport { BrowserEngine } from './engine-browser';\nimport { DevEngine } from './engine-dev';\nimport { registerCollectionSchemas, VibeCollection } from '../config';\nimport { resolveLicenseKey, validateLicenseLocal, validateLicenseRemote } from '../license';\n\nexport * from './types';\nexport * from './validation';\nexport * from './engine-node';\nexport * from './engine-browser';\nexport * from './engine-dev';\n\nlet _licensed = false;\n\nconst getEngine = (): SyncEngine => {\n if (typeof window === 'undefined') return new NodeEngine();\n\n // In the browser, check if we should use DevEngine for local FS operations\n const isLocal = window.location.hostname === 'localhost' || window.location.hostname === '127.0.0.1';\n // We can also check for a specific flag or let init negotiate it\n return isLocal ? new DevEngine() : new BrowserEngine();\n};\n\nconst _raw = getEngine();\n\n/**\n * Proxy guard: prevents using VibeEngine methods without a valid license.\n * All function calls (except init) require `_licensed === true`, which is\n * only set by `initVibeEngine()` after successful license validation.\n */\nexport const VibeEngine: SyncEngine = new Proxy(_raw, {\n get(target: any, prop: string | symbol, receiver: any) {\n const value = Reflect.get(target, prop, receiver);\n if (!_licensed && typeof value === 'function' && prop !== 'init') {\n return (...args: any[]) => {\n throw new Error(\n '[VibeCMS] License key required. Call initVibeEngine() with a valid key.\\n' +\n 'Get your key at https://vibecms.com/pricing'\n );\n };\n }\n return value;\n },\n});\n\n/**\n * Initialize the engine with license validation, then register collection schemas.\n * Call this once at app startup (e.g. in EditProvider or AdminShell).\n *\n * @throws {Error} if the license key is missing, invalid, or expired\n */\nexport function initVibeEngine(\n config: VibeEngineConfig & { licenseKey?: string },\n collections?: Record<string, VibeCollection>,\n singletons?: Record<string, VibeCollection>\n) {\n // 1. License validation (local fast-path — throws on invalid)\n const key = resolveLicenseKey(config.licenseKey);\n validateLicenseLocal(key);\n _licensed = true;\n\n // 2. Async remote check (non-blocking — revocation + usage logging)\n validateLicenseRemote(key, '0.1.0').catch(() => {});\n\n // 3. Register schemas and init engine\n if (collections || singletons) {\n registerCollectionSchemas(collections, singletons);\n }\n return VibeEngine.init(config);\n}\n\nexport async function populate(document: any, refs: { field: string, collection: string }[]) {\n if (!document) return document;\n const doc = { ...document };\n for (const ref of refs) {\n if (typeof doc[ref.field] === 'string') {\n const data = await VibeEngine.read(ref.collection, doc[ref.field]);\n if (data) doc[ref.field] = data;\n } else if (Array.isArray(doc[ref.field])) {\n doc[ref.field] = await Promise.all(doc[ref.field].map(async (item: any) => {\n if (typeof item === 'string') {\n const data = await VibeEngine.read(ref.collection, item);\n return data || item;\n }\n return item;\n }));\n }\n }\n return doc;\n}\n","import { z } from 'zod';\nimport type { ComponentType } from 'react';\nimport { AuthProvider, VibeAccessRule, VibeRole } from './types/auth';\nimport { WebhookConfig } from './events';\nimport { StorageDriver } from './storage/types';\n\nexport interface VibeCollection {\n name: string;\n schema: z.ZodTypeAny;\n /** Restrict which roles can edit this collection. Default: ['owner', 'editor'] */\n editRoles?: VibeRole[];\n}\n\n/**\n * Registration entry for a custom block renderer.\n */\nexport interface VibeBlockRegistration {\n /** The `_type` value in your block schema */\n type: string;\n /** React component to render this block. Receives `{ data, index }` props. */\n component: ComponentType<{ data: any; index: string | number }>;\n}\n\nexport interface VibeConfig {\n /**\n * VibeCMS license key. Set via `VIBE_LICENSE_KEY` env var (preferred) or here.\n * Get your key at https://vibecms.com/pricing\n */\n licenseKey?: string;\n contentDir?: string;\n publicDir?: string;\n auth?: AuthProvider;\n media?: {\n driver: StorageDriver;\n };\n collections?: Record<string, VibeCollection>;\n /**\n * Single global documents that do not have a list view (e.g., globals, navigation, footer).\n * They behave like collections but are enforced to have a single slug 'index'.\n */\n singletons?: Record<string, VibeCollection>;\n /**\n * Register custom block renderers. These are merged with built-in blocks.\n * Custom registrations take precedence over built-in blocks with the same `_type`.\n *\n * Example:\n * blocks: [\n * { type: 'comparison-table', component: ComparisonTable },\n * { type: 'hero', component: CustomHero }, // overrides built-in hero\n * ]\n */\n blocks?: VibeBlockRegistration[];\n /**\n * Access control list. The first entry should be the owner.\n * Users not in this list are denied access to the CMS editor.\n *\n * Example:\n * access: [\n * { email: 'owner@example.com', role: 'owner' },\n * { email: 'editor@company.de', role: 'editor' },\n * { email: 'viewer@company.de', role: 'viewer' },\n * ]\n */\n access?: VibeAccessRule[];\n /**\n * Webhooks to notify on content lifecycle events.\n *\n * Example:\n * webhooks: [\n * { url: 'https://hooks.example.com/deploy', events: ['content:publish'], secret: 'whsec_...' },\n * ]\n */\n webhooks?: WebhookConfig[];\n /**\n * Localization support. Specify all locales you want the CMS to generate files for.\n * If enabled, documents are saved as `[slug].[locale].json`.\n */\n locales?: string[];\n defaultLocale?: string;\n}\n\nexport function defineConfig(config: VibeConfig): VibeConfig {\n return config;\n}\n\n/**\n * Global schema registry. Populated from `VibeConfig.collections` during engine init.\n * Used by engines to validate content before writing to disk.\n */\nconst schemaRegistry = new Map<string, z.ZodTypeAny>();\n\nexport function registerCollectionSchemas(collections?: Record<string, VibeCollection>, singletons?: Record<string, VibeCollection>) {\n schemaRegistry.clear();\n if (collections) {\n for (const [key, col] of Object.entries(collections)) {\n schemaRegistry.set(key, col.schema);\n }\n }\n if (singletons) {\n for (const [key, col] of Object.entries(singletons)) {\n schemaRegistry.set(key, col.schema);\n }\n }\n}\n\nexport function getCollectionSchema(collection: string): z.ZodTypeAny | undefined {\n return schemaRegistry.get(collection);\n}\n\n/**\n * Validate data against a collection's schema.\n * Returns { success: true, data } or { success: false, errors }.\n */\nexport function validateCollectionData(\n collection: string,\n data: unknown\n): { success: true; data: any } | { success: false; errors: string[] } {\n const schema = schemaRegistry.get(collection);\n if (!schema) {\n // No schema registered — allow write (backwards-compatible)\n return { success: true, data };\n }\n const result = schema.safeParse(data);\n if (result.success) {\n return { success: true, data: result.data };\n }\n const errors = result.error.issues.map(\n (issue) => `${issue.path.join('.')}: ${issue.message}`\n );\n return { success: false, errors };\n}\n\n/**\n * Resolve the role for a given email from the access list.\n * Returns null if the user is not whitelisted.\n */\nexport function resolveUserRole(config: VibeConfig, email: string | null | undefined): VibeRole | null {\n if (!email) return null;\n if (!config.access || config.access.length === 0) {\n // No access list configured — all authenticated users are treated as editors (backwards-compatible)\n return 'editor';\n }\n const entry = config.access.find(a => a.email.toLowerCase() === email.toLowerCase());\n return entry?.role ?? null;\n}\n\n/**\n * Check whether a role is allowed to edit a specific collection.\n */\nexport function canEditCollection(config: VibeConfig, role: VibeRole | null, collectionKey: string): boolean {\n if (!role) return false;\n if (role === 'owner') return true;\n if (role === 'viewer') return false;\n\n const collection = config.collections?.[collectionKey] || config.singletons?.[collectionKey];\n if (!collection) return false;\n\n const allowed = collection.editRoles ?? ['owner', 'editor'];\n return allowed.includes(role);\n}\n\n/**\n * Block registry for custom block renderers.\n * Custom blocks registered here take precedence over built-in blocks.\n */\nconst blockRegistry = new Map<string, ComponentType<{ data: any; index: string | number }>>();\n\nexport function registerCustomBlocks(blocks: VibeBlockRegistration[]) {\n for (const block of blocks) {\n blockRegistry.set(block.type, block.component);\n }\n}\n\nexport function getCustomBlockComponent(type: string): ComponentType<{ data: any; index: string | number }> | undefined {\n return blockRegistry.get(type);\n}\n","// packages/core/src/engine/validation.ts\n\nconst SLUG_REGEX = /^[a-z0-9][a-z0-9_/-]{0,100}$/i;\nconst COMMIT_OID_REGEX = /^[0-9a-f]{5,40}$/;\nconst COLLECTION_REGEX = /^[a-z0-9][a-z0-9_-]{0,50}$/i;\n\n/**\n * Validate a content slug. Slugs are used as filenames and must be safe\n * for filesystem paths and shell arguments.\n */\nexport function validateSlug(slug: string): boolean {\n return typeof slug === 'string' && SLUG_REGEX.test(slug);\n}\n\n/**\n * Validate a git commit OID (SHA-1 hex hash).\n */\nexport function validateCommitOid(oid: string): boolean {\n return typeof oid === 'string' && COMMIT_OID_REGEX.test(oid);\n}\n\n/**\n * Validate a collection name.\n */\nexport function validateCollection(collection: string): boolean {\n return typeof collection === 'string' && COLLECTION_REGEX.test(collection);\n}\n\n/**\n * Assert slug is valid, throw if not.\n */\nexport function assertValidSlug(slug: string): void {\n if (!validateSlug(slug)) {\n throw new Error(`Invalid slug: \"${slug}\". Slugs must match ${SLUG_REGEX}`);\n }\n}\n\n/**\n * Assert commit OID is valid, throw if not.\n */\nexport function assertValidCommitOid(oid: string): void {\n if (!validateCommitOid(oid)) {\n throw new Error(`Invalid commit OID: \"${oid}\". Must be a hex SHA hash.`);\n }\n}\n\n/**\n * Assert collection name is valid, throw if not.\n */\nexport function assertValidCollection(collection: string): void {\n if (!validateCollection(collection)) {\n throw new Error(`Invalid collection name: \"${collection}\"`);\n }\n}\n\n/**\n * Sanitize a redirect path to prevent open redirects.\n * Returns '/' if the path is invalid.\n */\nexport function sanitizeRedirectPath(path: string | null | undefined): string {\n if (!path) return '/';\n // Must start with single slash, must not contain protocol or double-slash\n if (!path.startsWith('/')) return '/';\n if (path.startsWith('//')) return '/';\n if (path.includes('://')) return '/';\n if (path.includes('\\\\')) return '/';\n return path;\n}\n","// packages/core/src/engine/engine.node.ts\nimport { SyncEngine, VibeEngineConfig, CommitAuthor, HistoryEntry } from './types';\nimport { validateCollectionData } from '../config';\nimport { assertValidSlug, assertValidCollection, assertValidCommitOid } from './validation';\n\n/**\n * Check if a parsed JSON document contains a reference to the given slug.\n * Only checks string values in fields typically used for references\n * (keys containing 'ref', 'author', 'category', or values that are exact slug matches).\n * Recurses through arrays and nested objects.\n */\nfunction hasReferenceToSlug(data: unknown, slug: string): boolean {\n if (data === slug) return true;\n if (Array.isArray(data)) {\n return data.some(item => hasReferenceToSlug(item, slug));\n }\n if (data && typeof data === 'object') {\n for (const [key, value] of Object.entries(data as Record<string, unknown>)) {\n // Skip internal fields and content-like fields (titles, descriptions, rich text)\n if (key.startsWith('_')) continue;\n if (['title', 'subtitle', 'description', 'content', 'body', 'text', 'html',\n 'seoTitle', 'seoDescription', 'label', 'name', 'placeholder',\n 'helpText', 'successMessage', 'quote', 'answer', 'question',\n 'caption', 'alt', 'icon', 'url', 'image', 'ogImage',\n 'backgroundColor', 'textColor', 'keywords'].includes(key)) {\n continue;\n }\n if (hasReferenceToSlug(value, slug)) return true;\n }\n }\n return false;\n}\n\n/** Simple in-memory LRU cache with TTL for content reads. */\nclass ContentCache {\n private cache = new Map<string, { data: any; expiresAt: number }>();\n private maxEntries: number;\n private ttlMs: number;\n\n constructor(maxEntries = 200, ttlMs = 30_000) {\n this.maxEntries = maxEntries;\n this.ttlMs = ttlMs;\n }\n\n get(key: string): any | undefined {\n const entry = this.cache.get(key);\n if (!entry) return undefined;\n if (Date.now() > entry.expiresAt) {\n this.cache.delete(key);\n return undefined;\n }\n // Move to end (most recently used)\n this.cache.delete(key);\n this.cache.set(key, entry);\n return entry.data;\n }\n\n set(key: string, data: any) {\n if (this.cache.size >= this.maxEntries) {\n // Evict oldest entry\n const firstKey = this.cache.keys().next().value;\n if (firstKey !== undefined) this.cache.delete(firstKey);\n }\n this.cache.set(key, { data, expiresAt: Date.now() + this.ttlMs });\n }\n\n invalidate(key: string) {\n this.cache.delete(key);\n }\n\n invalidateCollection(collection: string) {\n for (const key of this.cache.keys()) {\n if (key.startsWith(`${collection}/`)) {\n this.cache.delete(key);\n }\n }\n }\n}\n\nexport class NodeEngine implements SyncEngine {\n private contentDir = 'src/content';\n private publicDir = 'public';\n private config?: VibeEngineConfig;\n private contentCache = new ContentCache();\n\n async init(config?: VibeEngineConfig) {\n this.config = config;\n if (config?.contentDir) this.contentDir = config.contentDir;\n if (config?.publicDir) this.publicDir = config.publicDir;\n }\n\n private resolveFilename(slug: string, locale?: string): string {\n const base = slug.endsWith('.json') ? slug.replace(/\\.json$/, '') : slug;\n return locale ? `${base}.${locale}.json` : `${base}.json`;\n }\n\n async read(collection: string, slug: string, options?: { locale?: string }) {\n if (typeof window !== 'undefined') return null;\n assertValidCollection(collection);\n assertValidSlug(slug);\n\n const filename = this.resolveFilename(slug, options?.locale);\n const cacheKey = `${collection}/${filename}`;\n const cached = this.contentCache.get(cacheKey);\n if (cached !== undefined) return cached;\n\n const fs = await import('fs/promises');\n const path = await import('path');\n const filePath = path.join(process.cwd(), this.contentDir, collection, filename);\n try {\n const [content, stat] = await Promise.all([\n fs.readFile(filePath, 'utf-8'),\n fs.stat(filePath),\n ]);\n const data = JSON.parse(content);\n // Stamp version for optimistic locking (mtime in ms)\n data._vibeVersion = stat.mtimeMs;\n this.contentCache.set(cacheKey, data);\n return data;\n } catch (e) {\n return null;\n }\n }\n\n async write(collection: string, slug: string, data: any, options?: { locale?: string }) {\n if (typeof window !== 'undefined') return;\n assertValidCollection(collection);\n assertValidSlug(slug);\n\n // Validate against collection schema before writing\n const validation = validateCollectionData(collection, data);\n if (!validation.success) {\n throw new Error(\n `Schema validation failed for ${collection}/${slug}: ${validation.errors.join('; ')}`\n );\n }\n\n const fs = await import('fs/promises');\n const path = await import('path');\n const filename = this.resolveFilename(slug, options?.locale);\n const dir = path.join(process.cwd(), this.contentDir, collection);\n await fs.mkdir(dir, { recursive: true });\n const filePath = path.join(dir, filename);\n\n // Optimistic locking: if _vibeVersion is present, check file hasn't changed\n const dataToWrite = { ...validation.data };\n const clientVersion = data._vibeVersion;\n delete dataToWrite._vibeVersion; // Don't persist the version field\n\n if (clientVersion) {\n try {\n const stat = await fs.stat(filePath);\n if (Math.abs(stat.mtimeMs - clientVersion) > 100) {\n throw new Error(\n `Conflict: \"${collection}/${slug}\" was modified by another editor. Reload to see the latest version.`\n );\n }\n } catch (e: any) {\n if (e.message.startsWith('Conflict:')) throw e;\n // File doesn't exist yet — OK, new document\n }\n }\n\n await fs.writeFile(filePath, JSON.stringify(dataToWrite, null, 2), 'utf-8');\n\n // Invalidate cache for this document\n this.contentCache.invalidate(`${collection}/${filename}`);\n }\n\n async delete(collection: string, slug: string, options?: { locale?: string }) {\n if (typeof window !== 'undefined') return;\n assertValidCollection(collection);\n assertValidSlug(slug);\n\n const fs = await import('fs/promises');\n const path = await import('path');\n const filename = this.resolveFilename(slug, options?.locale);\n const baseDir = path.join(process.cwd(), this.contentDir);\n\n // Referential integrity: check parsed JSON reference fields, not raw string matching\n const cols = await fs.readdir(baseDir);\n for (const col of cols) {\n if (col === collection) continue;\n const colDir = path.join(baseDir, col);\n const stat = await fs.stat(colDir);\n if (!stat.isDirectory()) continue;\n\n const files = await fs.readdir(colDir);\n for (const file of files) {\n if (!file.endsWith('.json')) continue;\n const raw = await fs.readFile(path.join(colDir, file), 'utf8');\n try {\n const data = JSON.parse(raw);\n if (hasReferenceToSlug(data, slug)) {\n throw new Error(\n `Referential Integrity Error: Cannot delete \"${slug}\" because it is referenced by ${col}/${file}`\n );\n }\n } catch (e: any) {\n if (e.message.startsWith('Referential Integrity')) throw e;\n // Skip unparseable JSON\n }\n }\n }\n\n const filePath = path.join(baseDir, collection, filename);\n await fs.unlink(filePath);\n this.contentCache.invalidate(`${collection}/${filename}`);\n }\n\n async isDirty() {\n return false; // Dev mode relies on native cli git\n }\n\n async revert() {}\n\n async commit(_message: string, _author?: CommitAuthor) {}\n\n async push() {\n // In Node (dev mode) we don't automatically push from the engine,\n // the developer uses their normal git cli.\n }\n\n async pull() {\n // No-op for Node, handled by developer cli\n }\n\n async writeMedia(file: File, author?: CommitAuthor) {\n if (this.config?.media?.driver) {\n return this.config.media.driver.upload(file, { engine: this, author });\n }\n \n if (typeof window !== 'undefined') return '';\n const fs = await import('fs/promises');\n const path = await import('path');\n const buffer = Buffer.from(await file.arrayBuffer());\n const dir = path.join(process.cwd(), this.publicDir, 'assets', 'uploads');\n await fs.mkdir(dir, { recursive: true });\n \n // Normalize filename\n const safeName = file.name.replace(/[^a-z0-9.-]/gi, '_').toLowerCase();\n const filePath = path.join(dir, safeName);\n \n await fs.writeFile(filePath, buffer);\n const url = `/assets/uploads/${safeName}`;\n\n try {\n // Intelligent Media Schema: Parse intrinsic dimensions\n const sizeOf = (await import('image-size')).default;\n const dimensions = sizeOf(buffer);\n if (dimensions && dimensions.width && dimensions.height) {\n return {\n url,\n width: dimensions.width,\n height: dimensions.height,\n alt: file.name\n };\n }\n } catch (e) {\n // Fallback for non-images\n }\n \n return `/assets/uploads/${safeName}`;\n }\n\n async listMedia(): Promise<string[]> {\n if (this.config?.media?.driver?.list) {\n return this.config.media.driver.list({ engine: this });\n }\n if (typeof window !== 'undefined') return [];\n try {\n const fs = await import('fs/promises');\n const path = await import('path');\n const uploadsDir = path.join(process.cwd(), this.publicDir, 'assets', 'uploads');\n const files = await fs.readdir(uploadsDir);\n return files.filter(f => !f.startsWith('.')).map(f => `/assets/uploads/${f}`);\n } catch {\n return [];\n }\n }\n\n async deleteMedia(filename: string): Promise<void> {\n if (this.config?.media?.driver?.delete) {\n return this.config.media.driver.delete(filename, { engine: this });\n }\n if (typeof window !== 'undefined') return;\n const fs = await import('fs/promises');\n const path = await import('path');\n const safeName = filename.split('/').pop() || filename;\n const filePath = path.join(process.cwd(), this.publicDir, 'assets', 'uploads', safeName);\n try {\n await fs.unlink(filePath);\n } catch (e) {\n // ignore if missing\n }\n }\n\n async renameMedia(oldFilename: string, newFilename: string): Promise<void> {\n if (this.config?.media?.driver?.rename) {\n return this.config.media.driver.rename(oldFilename, newFilename, { engine: this });\n }\n if (typeof window !== 'undefined') return;\n const fs = await import('fs/promises');\n const path = await import('path');\n const safeOldName = oldFilename.split('/').pop() || oldFilename;\n const safeNewName = newFilename.split('/').pop() || newFilename;\n const oldPath = path.join(process.cwd(), this.publicDir, 'assets', 'uploads', safeOldName);\n const newPath = path.join(process.cwd(), this.publicDir, 'assets', 'uploads', safeNewName);\n try {\n await fs.rename(oldPath, newPath);\n } catch (e) {\n throw new Error(`Failed to rename local media: ${e}`);\n }\n }\n\n async pruneMedia(): Promise<{ deletedCount: number, bytesFreed: number }> {\n if (typeof window !== 'undefined') return { deletedCount: 0, bytesFreed: 0 };\n const fs = await import('fs/promises');\n const path = await import('path');\n let usedMedia = new Set<string>();\n const contentDir = path.join(process.cwd(), 'src', 'content');\n const uploadsDir = path.join(process.cwd(), this.publicDir, 'assets', 'uploads');\n \n async function scanDir(dir: string) {\n if (!require('fs').existsSync(dir)) return;\n const entries = await fs.readdir(dir, { withFileTypes: true });\n for (const entry of entries) {\n const fullPath = path.join(dir, entry.name);\n if (entry.isDirectory()) await scanDir(fullPath);\n else if (entry.name.endsWith('.json')) {\n const content = await fs.readFile(fullPath, 'utf-8');\n const regex = /\\/assets\\/uploads\\/([^\"'\\s\\\\]+)/g;\n let match;\n while ((match = regex.exec(content)) !== null) {\n usedMedia.add(match[1]);\n }\n }\n }\n }\n \n await scanDir(contentDir);\n \n let deletedCount = 0;\n let bytesFreed = 0;\n if (require('fs').existsSync(uploadsDir)) {\n const uFiles = await fs.readdir(uploadsDir);\n for (const f of uFiles) {\n if (!usedMedia.has(f) && !f.startsWith('.')) {\n const stat = await fs.stat(path.join(uploadsDir, f));\n bytesFreed += stat.size;\n await fs.unlink(path.join(uploadsDir, f));\n deletedCount++;\n }\n }\n }\n return { deletedCount, bytesFreed };\n }\n\n async getMediaUrl(relativePath: string) {\n // In node/dev environment, Next.js serves the public folder directly\n return relativePath;\n }\n\n async list(collection: string, options?: import('./types').ListOptions) {\n if (typeof window !== 'undefined') return [];\n try {\n const fs = await import('fs/promises');\n const path = await import('path');\n const dir = path.join(process.cwd(), this.contentDir, collection);\n const files = await fs.readdir(dir);\n const slugs = files.filter((f: string) => f.endsWith('.json')).map((f: string) => f.replace('.json', ''));\n \n if (options?.withMeta) {\n const metaList = await Promise.all(slugs.map(async (slug: string) => {\n try {\n const content = await fs.readFile(path.join(dir, `${slug}.json`), 'utf-8');\n const data = JSON.parse(content);\n return { slug, title: data.title || data.name || slug, ...data };\n } catch(e) {\n return { slug, title: slug };\n }\n }));\n return metaList;\n }\n return slugs;\n } catch { return []; }\n }\n\n async getHistory(collection: string, slug: string): Promise<HistoryEntry[]> {\n if (typeof window !== 'undefined') return [];\n assertValidCollection(collection);\n assertValidSlug(slug);\n try {\n const { execFileSync } = require('child_process');\n const filePath = `${this.contentDir}/${collection}/${slug}.json`;\n // execFileSync does NOT invoke a shell — prevents command injection\n const raw = (execFileSync(\n 'git',\n ['log', '--follow', '--format=%H%x00%s%x00%an%x00%ae%x00%at', '--', filePath],\n { cwd: process.cwd(), encoding: 'utf-8', timeout: 5000 }\n ) as string).trim();\n if (!raw) return [];\n return raw.split('\\n').map((line: string) => {\n const [oid, message, author, email, ts] = line.split('\\0');\n return { oid, message, author, email, timestamp: parseInt(ts, 10) * 1000 };\n });\n } catch {\n return [];\n }\n }\n\n async getVersionContent(commitOid: string, collection: string, slug: string) {\n if (typeof window !== 'undefined') return null;\n assertValidCollection(collection);\n assertValidSlug(slug);\n assertValidCommitOid(commitOid);\n try {\n const { execFileSync } = require('child_process');\n const filePath = `${this.contentDir}/${collection}/${slug}.json`;\n // execFileSync does NOT invoke a shell — prevents command injection\n const content = execFileSync(\n 'git',\n ['show', `${commitOid}:${filePath}`],\n { cwd: process.cwd(), encoding: 'utf-8', timeout: 5000 }\n ) as string;\n return JSON.parse(content);\n } catch {\n return null;\n }\n }\n}\n","// packages/core/src/engine/engine.browser.ts\nimport { SyncEngine, VibeEngineConfig, CommitAuthor, HistoryEntry } from './types';\nimport { validateCollectionData } from '../config';\n\nconst DEFAULT_AUTHOR: CommitAuthor = { name: 'VibeCMS Editor', email: 'editor@vibecms.local' };\n\n/** Check if parsed JSON contains a reference to a slug (skips content fields). */\nfunction hasReferenceToSlug(data: unknown, slug: string): boolean {\n if (data === slug) return true;\n if (Array.isArray(data)) {\n return data.some(item => hasReferenceToSlug(item, slug));\n }\n if (data && typeof data === 'object') {\n for (const [key, value] of Object.entries(data as Record<string, unknown>)) {\n if (key.startsWith('_')) continue;\n if (['title', 'subtitle', 'description', 'content', 'body', 'text', 'html',\n 'seoTitle', 'seoDescription', 'label', 'name', 'placeholder',\n 'helpText', 'successMessage', 'quote', 'answer', 'question',\n 'caption', 'alt', 'icon', 'url', 'image', 'ogImage',\n 'backgroundColor', 'textColor', 'keywords'].includes(key)) {\n continue;\n }\n if (hasReferenceToSlug(value, slug)) return true;\n }\n }\n return false;\n}\n\nexport class BrowserEngine implements SyncEngine {\n private fs: any;\n private pfs: any;\n private dir = '/vibecms';\n private contentDir = 'src/content';\n private publicDir = 'public';\n private gitProxyUrl = '/api/git-proxy/';\n private isInitializing = false;\n private initialized = false;\n private config?: VibeEngineConfig;\n\n constructor() {\n if (typeof window !== 'undefined') {\n try {\n // We still use require here for lightning-fs because it can be tricky with ESM in some setups,\n // but we wrap it to be safer in non-browser envs.\n const LightningFS = require('@isomorphic-git/lightning-fs');\n const FS = LightningFS.default || LightningFS;\n this.fs = new FS('vibecms-fs');\n this.pfs = this.fs.promises;\n } catch (e) {\n console.error('Failed to init lightning-fs', e);\n }\n }\n }\n\n async init(config?: VibeEngineConfig) {\n if (typeof window === 'undefined') return;\n this.config = config;\n if (config?.contentDir) this.contentDir = config.contentDir;\n if (config?.publicDir) this.publicDir = config.publicDir;\n if (this.initialized || this.isInitializing) return;\n this.isInitializing = true;\n \n const git = await import('isomorphic-git');\n const http = (await import('isomorphic-git/http/web')).default;\n \n try {\n await this.pfs.readdir(this.dir);\n this.initialized = true;\n this.isInitializing = false;\n } catch (e) {\n try {\n await git.clone({\n fs: this.fs,\n http,\n dir: this.dir,\n corsProxy: config?.corsProxy || this.gitProxyUrl,\n url: config?.repoUrl || '',\n singleBranch: true,\n depth: 1\n });\n this.initialized = true;\n } catch (cloneErr) {\n console.error('Failed to clone repository:', cloneErr);\n } finally {\n this.isInitializing = false;\n }\n }\n }\n\n private resolveFilename(slug: string, locale?: string): string {\n const base = slug.endsWith('.json') ? slug.replace(/\\.json$/, '') : slug;\n return locale ? `${base}.${locale}.json` : `${base}.json`;\n }\n\n async read(collection: string, slug: string, options?: { locale?: string }) {\n if (typeof window === 'undefined' || !this.pfs) return null;\n try {\n const filename = this.resolveFilename(slug, options?.locale);\n const filePath = `${this.dir}/${this.contentDir}/${collection}/${filename}`;\n const content = await this.pfs.readFile(filePath, { encoding: 'utf8' });\n return JSON.parse(content as string);\n } catch (e) {\n return null;\n }\n }\n\n async write(collection: string, slug: string, data: any, options?: { locale?: string }) {\n if (typeof window === 'undefined' || !this.pfs) return;\n\n // Validate against collection schema before writing\n const validation = validateCollectionData(collection, data);\n if (!validation.success) {\n throw new Error(\n `Schema validation failed for ${collection}/${slug}: ${validation.errors.join('; ')}`\n );\n }\n\n const filename = this.resolveFilename(slug, options?.locale);\n const dirPath = `${this.dir}/${this.contentDir}/${collection}`;\n const filePath = `${dirPath}/${filename}`;\n\n const parts = dirPath.split('/').filter(Boolean);\n let currentPath = '';\n for (const part of parts) {\n currentPath += `/${part}`;\n try {\n await this.pfs.mkdir(currentPath);\n } catch (e: any) {\n // Ignore \"already exists\" errors\n }\n }\n\n await this.pfs.writeFile(filePath, JSON.stringify(validation.data, null, 2), 'utf8');\n }\n\n async delete(collection: string, slug: string, options?: { locale?: string }) {\n if (typeof window === 'undefined' || !this.pfs) return;\n const baseDir = `${this.dir}/${this.contentDir}`;\n\n // Referential integrity: parse JSON and check reference-like fields\n const cols = await this.pfs.readdir(baseDir);\n for (const col of cols) {\n if (col === collection) continue;\n const colDir = `${baseDir}/${col}`;\n try {\n const files = await this.pfs.readdir(colDir);\n for (const file of files) {\n if (!file.endsWith('.json')) continue;\n const raw = await this.pfs.readFile(`${colDir}/${file}`, { encoding: 'utf8' });\n try {\n const data = JSON.parse(raw as string);\n if (hasReferenceToSlug(data, slug)) {\n throw new Error(\n `Referential Integrity Error: Cannot delete \"${slug}\" because it is referenced by ${col}/${file}`\n );\n }\n } catch (e: any) {\n if (e.message.startsWith('Referential Integrity')) throw e;\n }\n }\n } catch (e: any) {\n if (e.message?.startsWith('Referential Integrity')) throw e;\n // Not a dir or read error\n }\n }\n\n const filename = this.resolveFilename(slug, options?.locale);\n await this.pfs.unlink(`${baseDir}/${collection}/${filename}`);\n }\n\n async isDirty(collection: string, slug: string) {\n if (typeof window === 'undefined' || !this.pfs) return false;\n try {\n const git = await import('isomorphic-git');\n const relativeFilePath = `${this.contentDir}/${collection}/${slug}.json`;\n const status = await git.status({ fs: this.fs, dir: this.dir, filepath: relativeFilePath });\n return status !== 'unmodified' && status !== 'ignored';\n } catch (e) {\n return false;\n }\n }\n\n async revert(collection: string, slug: string) {\n if (typeof window === 'undefined' || !this.pfs) return;\n try {\n const git = await import('isomorphic-git');\n const relativeFilePath = `${this.contentDir}/${collection}/${slug}.json`;\n await git.checkout({\n fs: this.fs,\n dir: this.dir,\n filepaths: [relativeFilePath],\n force: true\n });\n } catch (e) {\n console.error('Failed to revert', e);\n }\n }\n\n async commit(message: string, author?: CommitAuthor) {\n if (typeof window === 'undefined' || !this.pfs) return;\n const git = await import('isomorphic-git');\n const commitAuthor = author || DEFAULT_AUTHOR;\n\n const listFiles = async (dirPath: string): Promise<string[]> => {\n const entries = await this.pfs.readdir(dirPath);\n let files: string[] = [];\n for (const entry of entries) {\n if (entry === '.git') continue;\n const internalPath = `${dirPath}/${entry}`;\n const stat = await this.pfs.stat(internalPath);\n if (stat.isDirectory()) {\n files = files.concat(await listFiles(internalPath));\n } else if (entry.endsWith('.json')) {\n files.push(internalPath.replace(`${this.dir}/`, ''));\n }\n }\n return files;\n };\n\n try {\n const formFiles = await listFiles(`${this.dir}/${this.contentDir}`);\n for (const filepath of formFiles) {\n await git.add({ fs: this.fs, dir: this.dir, filepath });\n }\n\n await git.commit({\n fs: this.fs,\n dir: this.dir,\n author: { name: commitAuthor.name, email: commitAuthor.email },\n message: message || 'CMS Content Update',\n });\n } catch(e) {\n console.error('Commit failed', e);\n }\n }\n\n async push(oauthToken: string) {\n if (typeof window === 'undefined' || !this.pfs) return;\n const git = await import('isomorphic-git');\n const http = (await import('isomorphic-git/http/web')).default;\n \n await git.push({\n fs: this.fs,\n http,\n dir: this.dir,\n remote: 'origin',\n ref: 'main',\n onAuth: () => ({ oauth2format: 'github', password: oauthToken }),\n });\n }\n\n async pull() {\n if (typeof window === 'undefined' || !this.pfs) return;\n const git = await import('isomorphic-git');\n const http = (await import('isomorphic-git/http/web')).default;\n\n await git.pull({\n fs: this.fs,\n http,\n dir: this.dir,\n ref: 'main',\n singleBranch: true,\n corsProxy: this.gitProxyUrl,\n author: { name: DEFAULT_AUTHOR.name, email: DEFAULT_AUTHOR.email }\n });\n }\n\n async writeMedia(file: File, author?: CommitAuthor) {\n if (this.config?.media?.driver) {\n return this.config.media.driver.upload(file, { engine: this, author });\n }\n \n if (typeof window === 'undefined' || !this.pfs) return '';\n const git = await import('isomorphic-git');\n const dirPath = `${this.dir}/${this.publicDir}/assets/uploads`;\n \n try {\n const parts = `${this.publicDir}/assets/uploads`.split('/').filter(Boolean);\n let currentPath = this.dir;\n for (const part of parts) {\n currentPath += `/${part}`;\n try { await this.pfs.mkdir(currentPath); } catch (e) {}\n }\n } catch (e) {}\n\n const safeName = file.name.replace(/[^a-z0-9.-]/gi, '_').toLowerCase();\n const filePath = `${dirPath}/${safeName}`;\n \n const arrayBuffer = await file.arrayBuffer();\n const buffer = new Uint8Array(arrayBuffer);\n \n await this.pfs.writeFile(filePath, buffer);\n\n await git.add({ fs: this.fs, dir: this.dir, filepath: `${this.publicDir}/assets/uploads/${safeName}` });\n const commitAuthor = author || DEFAULT_AUTHOR;\n await git.commit({\n fs: this.fs,\n dir: this.dir,\n author: { name: commitAuthor.name, email: commitAuthor.email },\n message: `Upload media ${safeName}`,\n });\n\n try {\n const blob = new Blob([buffer], { type: file.type });\n const src = URL.createObjectURL(blob);\n const img = new Image();\n img.src = src;\n await new Promise(resolve => { img.onload = resolve; img.onerror = resolve; });\n return {\n url: `/assets/uploads/${safeName}`,\n width: img.naturalWidth,\n height: img.naturalHeight,\n alt: file.name\n };\n } catch {\n return `/assets/uploads/${safeName}`;\n }\n }\n\n async pruneMedia(): Promise<{ deletedCount: number, bytesFreed: number }> {\n return { deletedCount: 0, bytesFreed: 0 };\n }\n\n async listMedia(): Promise<string[]> {\n if (this.config?.media?.driver?.list) {\n return this.config.media.driver.list({ engine: this });\n }\n if (typeof window === 'undefined' || !this.pfs) return [];\n try {\n const dirPath = `${this.dir}/${this.publicDir}/assets/uploads`;\n const files = await this.pfs.readdir(dirPath);\n return files.filter((f: string) => !f.startsWith('.')).map((f: string) => `/assets/uploads/${f}`);\n } catch {\n return [];\n }\n }\n\n async deleteMedia(filename: string): Promise<void> {\n if (this.config?.media?.driver?.delete) {\n return this.config.media.driver.delete(filename, { engine: this });\n }\n if (typeof window === 'undefined' || !this.pfs) return;\n const safeName = filename.split('/').pop() || filename;\n const filePath = `${this.dir}/${this.publicDir}/assets/uploads/${safeName}`;\n try {\n await this.pfs.unlink(filePath);\n const git = await import('isomorphic-git');\n await git.remove({ fs: this.fs, dir: this.dir, filepath: `${this.publicDir}/assets/uploads/${safeName}` });\n } catch {}\n }\n\n async renameMedia(oldFilename: string, newFilename: string): Promise<void> {\n if (this.config?.media?.driver?.rename) {\n return this.config.media.driver.rename(oldFilename, newFilename, { engine: this });\n }\n if (typeof window === 'undefined' || !this.pfs) return;\n const safeOldName = oldFilename.split('/').pop() || oldFilename;\n const safeNewName = newFilename.split('/').pop() || newFilename;\n const oldPath = `${this.dir}/${this.publicDir}/assets/uploads/${safeOldName}`;\n const newPath = `${this.dir}/${this.publicDir}/assets/uploads/${safeNewName}`;\n try {\n const buffer = await this.pfs.readFile(oldPath);\n await this.pfs.writeFile(newPath, buffer);\n await this.pfs.unlink(oldPath);\n\n const git = await import('isomorphic-git');\n await git.remove({ fs: this.fs, dir: this.dir, filepath: `${this.publicDir}/assets/uploads/${safeOldName}` });\n await git.add({ fs: this.fs, dir: this.dir, filepath: `${this.publicDir}/assets/uploads/${safeNewName}` });\n } catch {}\n }\n\n async getMediaUrl(relativePath: string) {\n if (typeof window === 'undefined' || !this.pfs) return relativePath;\n try {\n const filePath = `${this.dir}/${this.publicDir}${relativePath}`;\n const uint8Array = await this.pfs.readFile(filePath);\n const ext = relativePath.split('.').pop()?.toLowerCase();\n let mime = 'image/png';\n if (ext === 'jpg' || ext === 'jpeg') mime = 'image/jpeg';\n else if (ext === 'svg') mime = 'image/svg+xml';\n else if (ext === 'gif') mime = 'image/gif';\n else if (ext === 'webp') mime = 'image/webp';\n \n const blob = new Blob([uint8Array], { type: mime });\n return URL.createObjectURL(blob);\n } catch (e) {\n return relativePath;\n }\n }\n\n async list(collection: string, options?: import('./types').ListOptions) {\n if (typeof window === 'undefined' || !this.pfs) return [];\n try {\n const files = await this.pfs.readdir(`${this.dir}/${this.contentDir}/${collection}`);\n const slugs = files.filter((f: string) => f.endsWith('.json')).map((f: string) => f.replace('.json', ''));\n \n if (options?.withMeta) {\n const metaList = await Promise.all(slugs.map(async (slug: string) => {\n try {\n const content = await this.pfs.readFile(`${this.dir}/${this.contentDir}/${collection}/${slug}.json`, { encoding: 'utf8' });\n const data = JSON.parse(content as string);\n return { slug, title: data.title || data.name || slug, ...data };\n } catch(e) {\n return { slug, title: slug };\n }\n }));\n return metaList;\n }\n return slugs;\n } catch { return []; }\n }\n\n async getHistory(collection: string, slug: string): Promise<HistoryEntry[]> {\n if (typeof window === 'undefined' || !this.pfs) return [];\n try {\n const git = await import('isomorphic-git');\n const relativeFilePath = `${this.contentDir}/${collection}/${slug}.json`;\n const commits = await git.log({\n fs: this.fs,\n dir: this.dir,\n filepath: relativeFilePath\n });\n return commits.map(c => ({\n oid: c.oid,\n message: c.commit.message,\n author: c.commit.author.name,\n email: c.commit.author.email,\n timestamp: c.commit.author.timestamp * 1000\n }));\n } catch (e: any) {\n return [];\n }\n }\n\n async getVersionContent(commitOid: string, collection: string, slug: string) {\n if (typeof window === 'undefined' || !this.pfs) return null;\n try {\n const git = await import('isomorphic-git');\n const relativeFilePath = `${this.contentDir}/${collection}/${slug}.json`;\n const { blob } = await git.readBlob({\n fs: this.fs,\n dir: this.dir,\n oid: commitOid,\n filepath: relativeFilePath\n });\n const content = new TextDecoder('utf-8').decode(blob);\n return JSON.parse(content);\n } catch (e) {\n return null;\n }\n }\n}\n","// packages/core/src/engine/engine.dev.ts\nimport { SyncEngine, VibeEngineConfig, CommitAuthor, HistoryEntry } from './types';\n\nexport class DevEngine implements SyncEngine {\n private apiBase = '/__vibecms/api';\n private config?: VibeEngineConfig;\n\n async init(config?: VibeEngineConfig) {\n this.config = config;\n if (config?.devMode === false) {\n console.warn('DevEngine initialized but devMode is false');\n }\n }\n\n private async fetchApi(method: string, body?: any) {\n const res = await fetch(this.apiBase, {\n method: 'POST',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ method, ...body })\n });\n if (!res.ok) {\n const err = await res.json();\n throw new Error(err.message || 'API Error');\n }\n return res.json();\n }\n\n async read<T = any>(collection: string, slug: string, options?: { locale?: string }): Promise<T | null> {\n return this.fetchApi('read', { collection, slug, options })\n .catch(() => null);\n }\n\n async write<T = any>(collection: string, slug: string, data: T, options?: { locale?: string }): Promise<void> {\n await this.fetchApi('write', { collection, slug, data, options });\n }\n\n async delete(collection: string, slug: string, options?: { locale?: string }): Promise<void> {\n await this.fetchApi('delete', { collection, slug, options });\n }\n\n async isDirty() {\n return false; // DevEngine writes directly to disk\n }\n\n async revert() {}\n\n async commit(_message: string, _author?: CommitAuthor) {}\n\n async push() {}\n\n async pull() {}\n\n async writeMedia(file: File, author?: CommitAuthor) {\n if (this.config?.media?.driver) {\n return this.config.media.driver.upload(file, { engine: this, author });\n }\n\n // Media uploads in DevEngine involve sending the file to the dev server.\n // We'll use FormData for this specific call.\n const formData = new FormData();\n formData.append('file', file);\n formData.append('method', 'writeMedia');\n \n const res = await fetch(this.apiBase, {\n method: 'POST',\n body: formData\n });\n \n if (!res.ok) throw new Error('Failed to upload media');\n const data = await res.json();\n return data.url && data.width ? data : data.url;\n }\n\n async listMedia(): Promise<string[]> {\n if (this.config?.media?.driver?.list) {\n return this.config.media.driver.list({ engine: this });\n }\n const res = await this.fetchApi('listMedia');\n return res.files || [];\n }\n\n async deleteMedia(filename: string): Promise<void> {\n if (this.config?.media?.driver?.delete) {\n return this.config.media.driver.delete(filename, { engine: this });\n }\n await this.fetchApi('deleteMedia', { file: filename });\n }\n\n async renameMedia(oldFilename: string, newFilename: string): Promise<void> {\n if (this.config?.media?.driver?.rename) {\n return this.config.media.driver.rename(oldFilename, newFilename, { engine: this });\n }\n await this.fetchApi('renameMedia', { oldFile: oldFilename, newFile: newFilename });\n }\n\n async pruneMedia(): Promise<{ deletedCount: number, bytesFreed: number }> {\n return this.fetchApi('pruneMedia');\n }\n\n async getMediaUrl(relativePath: string) {\n return relativePath; // Served by Vite/Next.js from public\n }\n\n async list(collection: string, options?: import('./types').ListOptions) {\n return this.fetchApi('list', { collection, options });\n }\n\n async getHistory(_collection: string, _slug: string): Promise<HistoryEntry[]> {\n return this.fetchApi('getHistory', { collection: _collection, slug: _slug }).catch(() => []);\n }\n async getVersionContent(commitOid: string, collection: string, slug: string) {\n return this.fetchApi('getVersionContent', { commitOid, collection, slug }).catch(() => null);\n }\n}\n","/**\n * VibeCMS License Key Validation\n *\n * Key format: vibe_<base64url-payload>.<base64url-ed25519-signature>\n *\n * Payload: { sub, plan, iat, exp, kid }\n * Signature: Ed25519 over raw payload bytes\n *\n * Validation is two-tier:\n * 1. Local fast-path: Ed25519 signature + expiry check (synchronous)\n * 2. Remote async check: revocation + usage logging (non-blocking)\n */\n\n// Ed25519 public key (SPKI DER, base64-encoded) — used for local signature verification.\n// The corresponding private key is NEVER included in the published package.\nconst VIBE_PUBLIC_KEY_B64 = 'MCowBQYDK2VwAyEAhoV+ydoo3GG0wM0tjBmtBWKMaHo7gVg25J5lsSfoBI0=';\n\nconst VALIDATION_API = 'https://api.vibecms.com/v1/license/validate';\n\nexport type VibePlan = 'starter' | 'pro' | 'team' | 'enterprise';\n\nexport interface LicensePayload {\n /** Customer identifier (email or ID) */\n sub: string;\n /** License plan tier */\n plan: VibePlan;\n /** Issued-at timestamp (seconds since epoch) */\n iat: number;\n /** Expiration timestamp (seconds since epoch) */\n exp: number;\n /** Key ID for individual revocation */\n kid: string;\n}\n\n// ── In-memory cache for remote validation ──────────────────────────\n\ninterface RemoteResult {\n valid: boolean;\n reason?: string;\n checkedAt: number;\n}\n\nlet _remoteCache: RemoteResult | null = null;\nconst REMOTE_CACHE_TTL_MS = 24 * 60 * 60 * 1000; // 24 hours\n\n// Grace period tracking for revoked keys\nlet _revokedAt: number | null = null;\nconst GRACE_PERIOD_MS = 72 * 60 * 60 * 1000; // 72 hours\n\n// ── Base64url helpers ──────────────────────────────────────────────\n\nfunction base64urlDecode(str: string): Uint8Array {\n // Convert base64url to standard base64\n let b64 = str.replace(/-/g, '+').replace(/_/g, '/');\n while (b64.length % 4 !== 0) b64 += '=';\n\n if (typeof Buffer !== 'undefined') {\n return new Uint8Array(Buffer.from(b64, 'base64'));\n }\n // Browser fallback\n const binary = atob(b64);\n const bytes = new Uint8Array(binary.length);\n for (let i = 0; i < binary.length; i++) bytes[i] = binary.charCodeAt(i);\n return bytes;\n}\n\n// ── Local validation ───────────────────────────────────────────────\n\n/**\n * Validate a license key locally using Ed25519 signature verification.\n * This is the fast-path check that runs synchronously at engine init.\n *\n * @throws {Error} if the key is missing, malformed, has an invalid signature, or is expired\n */\nexport function validateLicenseLocal(key: string): LicensePayload {\n if (!key || !key.startsWith('vibe_')) {\n throw new Error(\n '[VibeCMS] Invalid license key format. Keys start with \"vibe_\".\\n' +\n 'Get your key at https://vibecms.com/pricing'\n );\n }\n\n const body = key.slice(5); // strip \"vibe_\" prefix\n const dotIndex = body.lastIndexOf('.');\n if (dotIndex === -1) {\n throw new Error(\n '[VibeCMS] Malformed license key. Expected format: vibe_<payload>.<signature>\\n' +\n 'Get a new key at https://vibecms.com/pricing'\n );\n }\n\n const payloadB64 = body.slice(0, dotIndex);\n const signatureB64 = body.slice(dotIndex + 1);\n\n // Decode payload\n let payload: LicensePayload;\n try {\n const payloadBytes = base64urlDecode(payloadB64);\n const payloadJson = new TextDecoder().decode(payloadBytes);\n payload = JSON.parse(payloadJson);\n } catch {\n throw new Error(\n '[VibeCMS] Invalid license key. Could not decode payload.\\n' +\n 'Check your key or get a new one at https://vibecms.com/pricing'\n );\n }\n\n // Verify required fields\n if (!payload.sub || !payload.plan || !payload.iat || !payload.exp || !payload.kid) {\n throw new Error(\n '[VibeCMS] Invalid license key. Missing required fields.\\n' +\n 'Get a new key at https://vibecms.com/pricing'\n );\n }\n\n // Verify Ed25519 signature (Node.js crypto)\n try {\n const crypto = require('crypto');\n const pubKeyDer = Buffer.from(VIBE_PUBLIC_KEY_B64, 'base64');\n const publicKey = crypto.createPublicKey({\n key: pubKeyDer,\n format: 'der',\n type: 'spki',\n });\n\n const payloadBytes = base64urlDecode(payloadB64);\n const signatureBytes = base64urlDecode(signatureB64);\n\n const isValid = crypto.verify(null, payloadBytes, publicKey, signatureBytes);\n if (!isValid) {\n throw new Error('signature mismatch');\n }\n } catch (e: any) {\n if (e.message?.includes('[VibeCMS]')) throw e;\n throw new Error(\n '[VibeCMS] Invalid license key. Signature verification failed.\\n' +\n 'Check your key or get a new one at https://vibecms.com/pricing'\n );\n }\n\n // Check expiration\n const nowSec = Math.floor(Date.now() / 1000);\n if (payload.exp < nowSec) {\n const expDate = new Date(payload.exp * 1000).toLocaleDateString('en-US', {\n year: 'numeric',\n month: 'long',\n day: 'numeric',\n });\n throw new Error(\n `[VibeCMS] License expired on ${expDate}.\\n` +\n 'Renew at https://vibecms.com/account'\n );\n }\n\n return payload;\n}\n\n// ── Remote validation ──────────────────────────────────────────────\n\n/**\n * Async remote validation against the VibeCMS license API.\n * Non-blocking: fire-and-forget from engine init.\n *\n * - Checks revocation status\n * - Logs usage for analytics\n * - Caches result for 24 hours\n * - On revocation: sets 72h grace period, then hard-fail\n * - On network error: silent pass (local sig is sufficient)\n */\nexport async function validateLicenseRemote(key: string, version: string): Promise<void> {\n // Check cache\n if (_remoteCache && Date.now() - _remoteCache.checkedAt < REMOTE_CACHE_TTL_MS) {\n if (!_remoteCache.valid) {\n handleRevocation();\n }\n return;\n }\n\n try {\n const res = await fetch(VALIDATION_API, {\n method: 'POST',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ key, version }),\n signal: AbortSignal.timeout(5000), // 5s timeout\n });\n\n if (res.ok) {\n const data = await res.json();\n _remoteCache = {\n valid: data.valid !== false,\n reason: data.reason,\n checkedAt: Date.now(),\n };\n\n if (!_remoteCache.valid) {\n handleRevocation();\n } else {\n // Key is confirmed valid — clear any revocation state\n _revokedAt = null;\n }\n }\n // Non-200 responses: silent pass (API might be down)\n } catch {\n // Network error: silent pass — local signature is sufficient\n }\n}\n\nfunction handleRevocation(): void {\n if (!_revokedAt) {\n _revokedAt = Date.now();\n console.warn(\n '[VibeCMS] ⚠ Warning: Your license key has been revoked.\\n' +\n 'VibeCMS will stop working in 72 hours.\\n' +\n 'Contact support@vibecms.com or visit https://vibecms.com/account'\n );\n }\n\n const elapsed = Date.now() - _revokedAt;\n if (elapsed > GRACE_PERIOD_MS) {\n throw new Error(\n '[VibeCMS] License has been revoked and the grace period has expired.\\n' +\n 'Contact support@vibecms.com or get a new key at https://vibecms.com/pricing'\n );\n }\n}\n\n// ── Key resolution ─────────────────────────────────────────────────\n\n/**\n * Resolve the license key from environment variable or config.\n * Env var `VIBE_LICENSE_KEY` takes precedence.\n */\nexport function resolveLicenseKey(configKey?: string): string {\n const key = (typeof process !== 'undefined' ? process.env?.VIBE_LICENSE_KEY : undefined) ?? configKey;\n\n if (!key) {\n throw new Error(\n '[VibeCMS] License key required.\\n' +\n 'Set the VIBE_LICENSE_KEY environment variable or pass licenseKey in defineConfig().\\n' +\n 'Get your free key at https://vibecms.com/pricing'\n );\n }\n\n return key;\n}\n\n/**\n * Check if the revocation grace period is active (for use by engine proxy guard).\n */\nexport function isInGracePeriod(): boolean {\n if (!_revokedAt) return false;\n return Date.now() - _revokedAt <= GRACE_PERIOD_MS;\n}\n"],"mappings":"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","names":["hasReferenceToSlug"]}
|