appflare 0.2.13 → 0.2.14
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/cli/index.js +23 -23
- package/dist/cli/index.mjs +23 -23
- package/dist/index.d.mts +31 -0
- package/dist/index.d.ts +31 -0
- package/dist/index.js +1 -1
- package/dist/index.mjs +1 -1
- package/package.json +1 -1
- package/schema.ts +119 -39
package/dist/cli/index.js
CHANGED
|
@@ -3319,10 +3319,10 @@ import * as authSchema from "./auth.schema";
|
|
|
3319
3319
|
import * as schema from "${t}";
|
|
3320
3320
|
|
|
3321
3321
|
${qt()}
|
|
3322
|
-
`}function En(t){let e=t.replace(/[^A-Za-z0-9_]/g,"_");return /^[0-9]/.test(e)?`_${e}`:e}function
|
|
3322
|
+
`}function En(t){let e=t.replace(/[^A-Za-z0-9_]/g,"_");return /^[0-9]/.test(e)?`_${e}`:e}function Dn(t,e){let n=t.routePath.replace(/^\//,"").replace(/\//g,"_");return En(`op_${e}_${n}`)}function On(t){return t.map((e,n)=>({operation:e,index:n,alias:Dn(e,n)}))}function In(t){return t.map(({operation:e,alias:n})=>`import { ${e.exportName} as ${n} } from "${e.importPath}";`).join(`
|
|
3323
3323
|
`)}function Mn(t){return t.filter(({operation:e})=>e.kind==="query"||e.kind==="mutation").map(({alias:e})=>`const ${`${e}Schema`} = z.object(${e}.definition.args);`).join(`
|
|
3324
|
-
`)}function
|
|
3325
|
-
`)}function
|
|
3324
|
+
`)}function Fn(t){return t.filter(({operation:e})=>e.kind==="scheduler").map(({alias:e})=>`const ${`${e}SchedulerSchema`} = ${e}.definition.args ? z.object(${e}.definition.args) : z.undefined();`).join(`
|
|
3325
|
+
`)}function jn(t){return t.filter(({operation:e})=>e.kind==="query").map(({operation:e,alias:n})=>{let r=`${n}Schema`;return `
|
|
3326
3326
|
app.get(
|
|
3327
3327
|
"${e.routePath}",
|
|
3328
3328
|
sValidator("query", ${r}),
|
|
@@ -3369,7 +3369,7 @@ ${qt()}
|
|
|
3369
3369
|
},`}).join(`
|
|
3370
3370
|
`)}function Ln(t){return t.filter(({operation:e})=>e.kind==="storage").map(({alias:e})=>`
|
|
3371
3371
|
${e}.definition.handler,`).join(`
|
|
3372
|
-
`)}function Pt(t){let e=
|
|
3372
|
+
`)}function Pt(t){let e=On(t);return {imports:In(e),operationSchemas:Mn(e),schedulerSchemas:Fn(e),queryRoutes:jn(e),mutationRoutes:Bn(e),queryRegistryEntries:Hn(e),schedulerEntries:Vn(e),schedulerPayloadMapEntries:zn(e),cronEntries:Wn(e),storageHandlersEntries:Ln(e)}}var Et=`
|
|
3373
3373
|
function getRealtimeStub(
|
|
3374
3374
|
env: Record<string, unknown>,
|
|
3375
3375
|
options: RegisterHandlersOptions,
|
|
@@ -3443,7 +3443,7 @@ function buildRealtimeWsUrl(requestUrl: string, websocketPath: string): string {
|
|
|
3443
3443
|
url.protocol = url.protocol === "https:" ? "wss:" : "ws:";
|
|
3444
3444
|
return url.toString();
|
|
3445
3445
|
}
|
|
3446
|
-
`;var
|
|
3446
|
+
`;var Dt=`
|
|
3447
3447
|
export class AppflareRealtimeDurableObject {
|
|
3448
3448
|
private readonly subscriptions = new Map<string, RealtimeSubscription>();
|
|
3449
3449
|
private readonly sockets = new Map<string, WebSocket>();
|
|
@@ -3586,7 +3586,7 @@ export class AppflareRealtimeDurableObject {
|
|
|
3586
3586
|
return new Response("Not found", { status: 404 });
|
|
3587
3587
|
}
|
|
3588
3588
|
}
|
|
3589
|
-
`;var
|
|
3589
|
+
`;var Ot=`
|
|
3590
3590
|
async function publishMutationEvents(
|
|
3591
3591
|
c: { req: { raw: Request }; env: Record<string, unknown> },
|
|
3592
3592
|
options: RegisterHandlersOptions,
|
|
@@ -3879,7 +3879,7 @@ type RealtimeDurableObjectNamespace = {
|
|
|
3879
3879
|
type RealtimeQueryName = keyof typeof realtimeQueryHandlers extends never
|
|
3880
3880
|
? string
|
|
3881
3881
|
: Extract<keyof typeof realtimeQueryHandlers, string>;
|
|
3882
|
-
`;var
|
|
3882
|
+
`;var Ft=`
|
|
3883
3883
|
function isRecord(value: unknown): value is Record<string, unknown> {
|
|
3884
3884
|
return typeof value === "object" && value !== null;
|
|
3885
3885
|
}
|
|
@@ -4394,7 +4394,7 @@ function doesSubscriptionMatchMutation(
|
|
|
4394
4394
|
|
|
4395
4395
|
return false;
|
|
4396
4396
|
}
|
|
4397
|
-
`;var
|
|
4397
|
+
`;var jt=[Mt,Ft,Et,Ot,It,Dt].join(`
|
|
4398
4398
|
|
|
4399
4399
|
`);var Bt=`
|
|
4400
4400
|
function parseExpiresIn(value: string | undefined): number | undefined {
|
|
@@ -4724,7 +4724,7 @@ setStorageHandlers([...storageHandlers]);
|
|
|
4724
4724
|
|
|
4725
4725
|
${Ht}
|
|
4726
4726
|
|
|
4727
|
-
${
|
|
4727
|
+
${jt}
|
|
4728
4728
|
|
|
4729
4729
|
export function registerGeneratedHandlers(
|
|
4730
4730
|
app: Hono<WorkerEnv>,
|
|
@@ -4740,7 +4740,7 @@ export function registerGeneratedHandlers(
|
|
|
4740
4740
|
${Bt}
|
|
4741
4741
|
|
|
4742
4742
|
${Vt}
|
|
4743
|
-
`}function
|
|
4743
|
+
`}function F(t,e,n){let r=Ct(t),a=pt(n),o=gt(),i=zt(e);return [{relativePath:"handlers.ts",source:r},{relativePath:"handlers.context.ts",source:a},{relativePath:"handlers.execution.ts",source:o},{relativePath:"handlers.routes.ts",source:i}]}function Un(t){return t?`,
|
|
4744
4744
|
KV: c.env["${t}"] as KVNamespace`:""}function Wt(t,e){return `{
|
|
4745
4745
|
DATABASE: c.env["${t}"] as D1Database${Un(e)}
|
|
4746
4746
|
}`}function Lt(t,e,n){return `app.on(["GET", "POST"], "${t}/*", async (c) => {
|
|
@@ -4804,7 +4804,7 @@ app.use('*', cors({
|
|
|
4804
4804
|
},
|
|
4805
4805
|
credentials: true
|
|
4806
4806
|
}));
|
|
4807
|
-
`}function
|
|
4807
|
+
`}function Kt(){return `export { AppflareRealtimeDurableObject };
|
|
4808
4808
|
|
|
4809
4809
|
export default {
|
|
4810
4810
|
fetch: app.fetch,
|
|
@@ -4815,7 +4815,7 @@ export default {
|
|
|
4815
4815
|
await executeCronTriggers(controller, env, generatedHandlerOptions);
|
|
4816
4816
|
},
|
|
4817
4817
|
};
|
|
4818
|
-
`}function
|
|
4818
|
+
`}function Gt(t,e,n="APPFLARE_SCHEDULER_QUEUE",r,a="APPFLARE_REALTIME",o="global",i="/realtime/subscribe",s="/realtime/ws",l="appflare.realtime.v1"){let c=e?`
|
|
4819
4819
|
kvBinding: "${e}",`:"",d=r?`
|
|
4820
4820
|
r2Binding: "${r}",`:"",g=`
|
|
4821
4821
|
realtimeBinding: "${a}",
|
|
@@ -4838,7 +4838,7 @@ import type { D1Database, IncomingRequestCfProperties, KVNamespace } from "@clou
|
|
|
4838
4838
|
`}function Zt(){return `type WorkerEnv = {
|
|
4839
4839
|
Bindings: Record<string, unknown>;
|
|
4840
4840
|
};
|
|
4841
|
-
`}function Yt(t,e,n,r,a,o,i,s,l,c){return Jt()+Zt()+_t()+
|
|
4841
|
+
`}function Yt(t,e,n,r,a,o,i,s,l,c){return Jt()+Zt()+_t()+Gt(e,n,r,a,o,i,s,l,c)+Qt(t,e,n)+Kt()}function Xt(t){return !!t&&typeof t=="object"&&!Array.isArray(t)}function j(t,e){let n={...t};for(let[r,a]of Object.entries(e)){let o=n[r];if(Xt(o)&&Xt(a)){n[r]=j(o,a);continue}n[r]=a;}return n}function Kn(t){return Array.from(new Set(t.filter(e=>e.length>0)))}function te(t,e){let n=e.filter(u=>u.kind==="scheduler"||u.kind==="cron"),r=Kn(e.filter(u=>u.kind==="cron").flatMap(u=>u.cronTriggers??[])),a=t.config.scheduler.enabled&&n.length>0,o=t.config.realtime.enabled,s=(typeof t.config.wranglerOverrides?.name=="string"?t.config.wranglerOverrides.name:void 0)??"appflare-worker",l=t.config.scheduler.queue??`${s}-scheduler`,c={name:s,main:"./src/index.ts",d1_databases:t.config.database.map(u=>({binding:u.binding,database_name:u.databaseName,database_id:u.databaseId,preview_database_id:u.previewDatabaseId??u.databaseId,...u.migrationsDir?{migrations_dir:u.migrationsDir}:{}})),kv_namespaces:t.config.kv.map(u=>({binding:u.binding,id:u.id,...u.previewId?{preview_id:u.previewId}:{}})),r2_buckets:t.config.r2.map(u=>({binding:u.binding,bucket_name:u.bucketName,...u.previewBucketName?{preview_bucket_name:u.previewBucketName}:{},...u.jurisdiction?{jurisdiction:u.jurisdiction}:{}})),...a?{queues:{producers:[{binding:t.config.scheduler.binding,queue:l}],consumers:[{queue:l}]}}:{},...r.length>0?{triggers:{crons:r}}:{},...o?{durable_objects:{bindings:[{name:t.config.realtime.binding,class_name:t.config.realtime.className}]},migrations:[{tag:"appflare-realtime-v1",new_sqlite_classes:[t.config.realtime.className]}]}:{}};if(!t.config.wranglerOverrides)return c;let{scheduler:d,...g}=t.config.wranglerOverrides;return j(c,g)}function ee(t){return t.tables.map(e=>({exportName:e.exportName,tableName:e.tableName,columns:e.columns.map(n=>n.name)}))}function ne(t){return `<li data-name="users">
|
|
4842
4842
|
<a href="/admin/users" hx-get="/admin/users" hx-target="#main-content" hx-push-url="true" hx-swap="outerHTML" class="sidebar-link flex items-center gap-2 px-3 py-2 text-sm rounded-lg w-full">
|
|
4843
4843
|
<iconify-icon icon="mdi:account-group" width="16" height="16" class="opacity-50 shrink-0"></iconify-icon>
|
|
4844
4844
|
<span class="truncate">users</span>
|
|
@@ -4903,7 +4903,7 @@ import type { D1Database, IncomingRequestCfProperties, KVNamespace } from "@clou
|
|
|
4903
4903
|
</a>
|
|
4904
4904
|
`.replace(/\n/g,"\\n")).join("")}function oe(t){return t.columns.filter(e=>e.type==="string").map(e=>`
|
|
4905
4905
|
try { searchConditions.push(like(tableSchema.${e.name}, \`%\${search}%\`)); } catch (e) {}
|
|
4906
|
-
`).join("")}function
|
|
4906
|
+
`).join("")}function Gn(t){switch(t){case "number":return "mdi:pound";case "boolean":return "mdi:toggle-switch-outline";case "date":return "mdi:calendar";default:return "mdi:format-text"}}function ie(t,e){return e.map(n=>{let r=t.columns.find(o=>o.name===n),a=r?Gn(r.type):"mdi:format-text";return `
|
|
4907
4907
|
<th>
|
|
4908
4908
|
<a href="#"
|
|
4909
4909
|
hx-get="/admin/table/${t.exportName}?page=\${page}&search=\${search}&sort=${n}&order=\${sort === '${n}' && order === 'asc' ? 'desc' : 'asc'}"
|
|
@@ -6878,7 +6878,7 @@ ${z()}`}function ke(t){return `
|
|
|
6878
6878
|
c.header('HX-Redirect', prefixToStoragePath(prefix));
|
|
6879
6879
|
return c.html('');
|
|
6880
6880
|
});
|
|
6881
|
-
`}function
|
|
6881
|
+
`}function De(){return `
|
|
6882
6882
|
adminApp.post('/storage/directory', async (c) => {
|
|
6883
6883
|
const bucket = getStorageBucket(c);
|
|
6884
6884
|
if (!bucket) return c.text("Storage not configured", 400);
|
|
@@ -6904,7 +6904,7 @@ ${z()}`}function ke(t){return `
|
|
|
6904
6904
|
|
|
6905
6905
|
return c.redirect(prefixToStoragePath(prefix));
|
|
6906
6906
|
});
|
|
6907
|
-
`}function
|
|
6907
|
+
`}function Oe(){return `
|
|
6908
6908
|
adminApp.get('/storage/download', async (c) => {
|
|
6909
6909
|
const bucket = getStorageBucket(c);
|
|
6910
6910
|
if (!bucket) return c.text("Storage not configured", 400);
|
|
@@ -6943,7 +6943,7 @@ ${z()}`}function ke(t){return `
|
|
|
6943
6943
|
return new Response(object.body, { headers });
|
|
6944
6944
|
});
|
|
6945
6945
|
`}function Me(){return `
|
|
6946
|
-
${
|
|
6946
|
+
${Oe()}
|
|
6947
6947
|
|
|
6948
6948
|
${Ie()}
|
|
6949
6949
|
|
|
@@ -6951,16 +6951,16 @@ ${z()}`}function ke(t){return `
|
|
|
6951
6951
|
|
|
6952
6952
|
${Ee()}
|
|
6953
6953
|
|
|
6954
|
-
${
|
|
6954
|
+
${De()}
|
|
6955
6955
|
|
|
6956
6956
|
${Ce()}
|
|
6957
|
-
`}function
|
|
6957
|
+
`}function Fe(){return `
|
|
6958
6958
|
${Ne()}
|
|
6959
6959
|
|
|
6960
6960
|
${qe()}
|
|
6961
6961
|
|
|
6962
6962
|
${Me()}
|
|
6963
|
-
`}function
|
|
6963
|
+
`}function je(t,e){let n=re(e);return `
|
|
6964
6964
|
function Layout(props: { children: any; title: string; hideSidebar?: boolean }) {
|
|
6965
6965
|
return html\`<!DOCTYPE html>
|
|
6966
6966
|
<html lang="en" data-theme="light">
|
|
@@ -7411,7 +7411,7 @@ function Layout(props: { children: any; title: string; hideSidebar?: boolean })
|
|
|
7411
7411
|
\`
|
|
7412
7412
|
}));
|
|
7413
7413
|
});
|
|
7414
|
-
`}function Ve(t,e,n){let r=ee(e),a=ne(r),o=ae(r),i=ve(e),s=$e(n),l=
|
|
7414
|
+
`}function Ve(t,e,n){let r=ee(e),a=ne(r),o=ae(r),i=ve(e),s=$e(n),l=Fe(),c=je(a,n),d=Be(),g=He(o);return `import { Hono } from "hono";
|
|
7415
7415
|
import { html, raw } from "hono/html";
|
|
7416
7416
|
import { drizzle } from "drizzle-orm/d1";
|
|
7417
7417
|
import { eq, desc, asc, sql, like, or, inArray } from "drizzle-orm";
|
|
@@ -7496,9 +7496,9 @@ ${i.join(`
|
|
|
7496
7496
|
};`);}return `${e.join(`
|
|
7497
7497
|
|
|
7498
7498
|
`)}
|
|
7499
|
-
`}function xr(t,e){if(e){let n=t[e];if(!W(n))throw new Error(`schemaDsl.exportName '${e}' does not point to a schema() export.`);return n}for(let n of Object.values(t))if(W(n))return n;throw new Error("No schema() export found in schemaDsl entry module. Set schemaDsl.exportName to the correct export.")}async function Ge(t){let e=t.config.schemaDsl;if(!e)return;let n=e.namingStrategy??"camelToSnake",r=path.resolve(t.configDir,e.entry),a=path.resolve(t.configDir,e.outFile??path.resolve(t.outDirAbs,"schema.compiled.ts")),o=path.resolve(t.configDir,e.typesOutFile??path.resolve(t.outDirAbs,"schema.types.ts")),i=path.resolve(t.configDir,e.zodOutFile??path.resolve(t.outDirAbs,"schema.zod.ts")),l=await import(`${url.pathToFileURL(r).href}?t=${Date.now()}`),c=xr(l,e.exportName),d=cr(c);await Promise.all([promises.mkdir(path.dirname(a),{recursive:true}),promises.mkdir(path.dirname(o),{recursive:true}),promises.mkdir(path.dirname(i),{recursive:true})]);let g=fr(d,n),u=yr(d),y=hr(d);return await Promise.all([Bun.write(a,g),Bun.write(o,u),Bun.write(i,y)]),{schemaPath:a,typesPath:o,zodPath:i,tableNames:Object.keys(d.tables)}}function vr(t){return t.replaceAll("\\","/")}function S(t,e){let n=vr(path.relative(t,e)).replace(/\.tsx?$/,"");return n.startsWith(".")?n:`./${n}`}var Rr=new Set([".ts",".tsx",".mts",".cts"]);async function Ye(t){let e=await promises.readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=path.resolve(t,r.name);if(r.isDirectory()){n.push(...await Ye(a));continue}r.isFile()&&Rr.has(path.extname(r.name))&&n.push(a);}return n}function Q(t){return t.replace(/\.[cm]?tsx?$/,"")}function Ar(t,e){let n=t,r=false,a,o="unknown";for(;m__namespace.isCallExpression(n);){let i=n.expression;if(!m__namespace.isPropertyAccessExpression(i))break;let s=i.name.text;if(s==="optional"||s==="nullable")r=true,n=i.expression;else if(s==="default"){r=true;let l=n.arguments[0];l&&(m__namespace.isStringLiteral(l)||m__namespace.isNumericLiteral(l)?a=l.text:l.kind===m__namespace.SyntaxKind.TrueKeyword?a="true":l.kind===m__namespace.SyntaxKind.FalseKeyword&&(a="false")),n=i.expression;}else if(s==="string"||s==="uuid"||s==="email"||s==="url"){o="string";break}else if(s==="number"||s==="int"||s==="float"){o="number";break}else if(s==="boolean"){o="boolean";break}else n=i.expression;}return {name:e,type:o,optional:r,defaultValue:a}}function $r(t){if(!t||!m__namespace.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>m__namespace.isPropertyAssignment(r)&&m__namespace.isIdentifier(r.name)&&r.name.text==="args");if(!e||!m__namespace.isObjectLiteralExpression(e.initializer))return [];let n=[];for(let r of e.initializer.properties)!m__namespace.isPropertyAssignment(r)||!m__namespace.isIdentifier(r.name)||n.push(Ar(r.initializer,r.name.text));return n}function Nr(t){return m__namespace.isVariableStatement(t)?t.modifiers?.some(e=>e.kind===m__namespace.SyntaxKind.ExportKeyword)??false:false}function Xe(t){return m__namespace.isIdentifier(t)?t.text:m__namespace.isParenthesizedExpression(t)?Xe(t.expression):null}function qr(t){if(!t||!m__namespace.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>!m__namespace.isPropertyAssignment(r)||!m__namespace.isIdentifier(r.name)?false:r.name.text==="cronTrigger");if(!e||!m__namespace.isPropertyAssignment(e))return [];let n=e.initializer;return m__namespace.isStringLiteral(n)||m__namespace.isNoSubstitutionTemplateLiteral(n)?[n.text.trim()].filter(r=>r.length>0):m__namespace.isArrayLiteralExpression(n)?n.elements.map(r=>m__namespace.isStringLiteral(r)||m__namespace.isNoSubstitutionTemplateLiteral(r)?r.text.trim():"").filter(r=>r.length>0):[]}function Cr(t,e){let n=m__namespace.createSourceFile(e,t,m__namespace.ScriptTarget.Latest,true,m__namespace.ScriptKind.TS),r=[];for(let a of n.statements)if(Nr(a))for(let o of a.declarationList.declarations){if(!m__namespace.isIdentifier(o.name)||!o.initializer||!m__namespace.isCallExpression(o.initializer))continue;let i=Xe(o.initializer.expression);i!=="query"&&i!=="mutation"&&i!=="scheduler"&&i!=="cron"&&i!=="storageManager"||r.push({exportName:o.name.text,kind:i==="storageManager"?"storage":i,cronTriggers:i==="cron"?qr(o.initializer.arguments[0]):[],args:i==="query"||i==="mutation"?$r(o.initializer.arguments[0]):[]});}return r}function Ke(t,e,n){let r=e.replace(/\\/g,"/"),o=Q(r).split("/").filter(Boolean);return `/${[t,...o,n].filter(Boolean).map(s=>s.trim()).filter(s=>s.length>0).join("/")}`}function Pr(t,e){let n=t.replace(/\\/g,"/"),r=`${e}/`,a=n.indexOf(r);return a>=0?n.slice(a+r.length):n===e?"index.ts":n}function Je(t,e){let n=t.replace(/\\/g,"/"),a=Q(n).split("/").filter(Boolean),o=a[a.length-1]??"index";return [a.length>1?a[a.length-2]:"root",o,e].map(s=>s.trim()).filter(s=>s.length>0).join("/")}async function tn(t){let e=[],n=await Ye(t.scanDirAbs).catch(()=>[]);for(let a of n){let o=Bun.file(a);if(!await o.exists())continue;let i=await o.text(),s=path.relative(t.scanDirAbs,a),l=Cr(i,a),c=[{kind:"query",kindDirectory:"queries",exports:l.filter(d=>d.kind==="query")},{kind:"mutation",kindDirectory:"mutations",exports:l.filter(d=>d.kind==="mutation")},{kind:"scheduler",kindDirectory:"schedulers",exports:l.filter(d=>d.kind==="scheduler")},{kind:"cron",kindDirectory:"crons",exports:l.filter(d=>d.kind==="cron")},{kind:"storage",kindDirectory:"queries",exports:l.filter(d=>d.kind==="storage")}];for(let d of c){if(d.exports.length===0)continue;let g=Pr(s,d.kindDirectory);for(let u of d.exports){let y=d.kind==="query"||d.kind==="mutation"?Je(g,u.exportName):void 0,h=d.kind==="scheduler"||d.kind==="cron"?Je(g,u.exportName):void 0,f=d.kind==="query"||d.kind==="mutation"?[...Q(g).split("/").filter(Boolean),u.exportName]:void 0,b=d.kind==="query"?Ke("queries",g,u.exportName):d.kind==="mutation"?Ke("mutations",g,u.exportName):d.kind==="storage"?`/storage/managers/${u.exportName}`:`/${d.kindDirectory}/${h}`;e.push({kind:d.kind,exportName:u.exportName,filePath:a,importPath:S(t.outDirAbs,a),clientImportPath:S(path.resolve(t.outDirAbs,"client"),a),routePath:b,handlerName:y,clientSegments:f,taskName:h,cronTriggers:u.cronTriggers,args:u.args});}}}e.sort((a,o)=>a.routePath.localeCompare(o.routePath));let r=new Map;for(let a of e){let o=a.taskName?`task:${a.taskName}`:`route:${a.routePath}`,i=r.get(o);if(i)throw new Error(`Duplicate handler operation discovered: ${a.taskName??a.routePath} (${i} and ${a.filePath}#${a.exportName}).`);r.set(o,`${a.filePath}#${a.exportName}`);}return e}function Or(t){let e=[],n="",r=0,a=0,o=0,i=false,s=false,l=false,c=false;for(let g=0;g<t.length;g+=1){let u=t[g];if(c){n+=u,c=false;continue}if(u==="\\"){n+=u,c=true;continue}if(!s&&!l&&u==="'"){i=!i,n+=u;continue}if(!i&&!l&&u==='"'){s=!s,n+=u;continue}if(!i&&!s&&u==="`"){l=!l,n+=u;continue}if(i||s||l){n+=u;continue}if(u==="("?r+=1:u===")"?r-=1:u==="{"?a+=1:u==="}"?a-=1:u==="["?o+=1:u==="]"&&(o-=1),u===","&&r===0&&a===0&&o===0){let y=n.trim();y.length>0&&e.push(y),n="";continue}n+=u;}let d=n.trim();return d.length>0&&e.push(d),e}function Dr(t){let e=0,n=0,r=0,a=false,o=false,i=false,s=false;for(let l=0;l<t.length;l+=1){let c=t[l];if(s){s=false;continue}if(c==="\\"){s=true;continue}if(!o&&!i&&c==="'"){a=!a;continue}if(!a&&!i&&c==='"'){o=!o;continue}if(!a&&!o&&c==="`"){i=!i;continue}if(!(a||o||i)){if(c==="("){e+=1;continue}if(c===")"){e-=1;continue}if(c==="{"){n+=1;continue}if(c==="}"){n-=1;continue}if(c==="["){r+=1;continue}if(c==="]"){r-=1;continue}if(c===":"&&e===0&&n===0&&r===0)return l}}return -1}function Ir(t){let e=t.toLowerCase();return /mode\s*:\s*["'`](timestamp|timestamp_ms)["'`]/.test(e)?"date":/mode\s*:\s*["'`]boolean["'`]/.test(e)?"boolean":/\.(date|datetime|timestamp)\s*\(/.test(e)?"date":/\.(int|integer|real|numeric|decimal|float|double)\s*\(/.test(e)?"number":/\.(text|varchar|char)\s*\(/.test(e)?"string":/\.(boolean|bool)\s*\(/.test(e)?"boolean":"unknown"}function Mr(t){let e=Or(t),n=[];for(let r of e){let a=Dr(r);if(a===-1)continue;let o=r.slice(0,a).trim().replace(/^['"]|['"]$/g,"");if(!o)continue;let i=r.slice(a+1).trim(),s=/\.primarykey\s*\(/i.test(i),l=/autoincrement\s*:\s*true/i.test(i),c=/\.default\s*\(/i.test(i),g=!/\.notnull\s*\(/i.test(i)||c||l;n.push({name:o,expression:i,type:Ir(i),optional:g,primaryKey:s,autoIncrement:l});}return n}function jr(t){let e=/export\s+const\s+(\w+)\s*=\s*table\s*\(\s*["'`]([^"'`]+)["'`]/g,n=[],r=(o,i)=>{let s=0,l=false,c=false,d=false,g=false;for(let u=i;u<o.length;u+=1){let y=o[u];if(g){g=false;continue}if(y==="\\"){g=true;continue}if(!c&&!d&&y==="'"){l=!l;continue}if(!l&&!d&&y==='"'){c=!c;continue}if(!l&&!c&&y==="`"){d=!d;continue}if(!(l||c||d)){if(y==="{"){s+=1;continue}if(y==="}"&&(s-=1,s===0))return u}}return -1},a=e.exec(t);for(;a;){let o=a[1],i=a[2],s=t.indexOf("{",e.lastIndex);if(s===-1){a=e.exec(t);continue}let l=r(t,s);if(l===-1){a=e.exec(t);continue}let c=t.slice(s+1,l);n.push({exportName:o,tableName:i,columns:Mr(c)}),a=e.exec(t);}return n}async function nn(t){let e=await promises.readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=path.resolve(t,r.name);if(r.isDirectory()){n.push(...await nn(a));continue}r.isFile()&&r.name==="schema.ts"&&n.push(a);}return n}async function rn(t,e=[]){let n=await nn(t.scanDirAbs).catch(()=>[]),r=path.resolve(t.configDir,"schema.ts"),a=[...e,...n.length?n:[r]];for(let o of a){let i=Bun.file(o);if(!await i.exists())continue;let s=await i.text(),l=jr(s);if(l.length>0)return {schemaPath:o,tables:l}}throw new Error(`Unable to discover schema.ts under scanDir (${t.scanDirAbs}) or fallback (${r}).`)}function Fr(t,e){let n=path.relative(t,e).replace(/\\/g,"/");return n.startsWith(".")?n:`./${n}`}async function an(t){let{outDirAbs:e,wranglerOutDirAbs:n,config:r,configPath:a,configDir:o}=t,i=S(e,a),s=path.resolve(e,"client"),l=S(s,a);await Promise.all([promises.mkdir(e,{recursive:true}),promises.mkdir(s,{recursive:true}),promises.mkdir(n,{recursive:true})]);let c=path.resolve(e,"server.ts"),d=path.resolve(e,"client.ts"),g=path.resolve(e,"auth.config.ts"),u=path.resolve(e,"auth.schema.ts"),y=path.resolve(e,"drizzle.config.ts"),h=path.resolve(n,"wrangler.json"),f=await Ge(t),b=await rn(t,f?[f.schemaPath]:[]),R=S(e,b.schemaPath),v=await tn(t),fn=Yt(r.auth.basePath,r.database[0].binding,r.kv[0]?.binding,r.scheduler.binding,r.r2[0]?.binding,r.realtime.binding,r.realtime.objectName,r.realtime.subscribePath,r.realtime.websocketPath,r.realtime.protocol),hn=rt(l,v),bn=j(R,v,r.r2[0]?.binding),yn=J(i),xn=f?[Fr(o,f.schemaPath),...r.schema.filter(k=>!/(^|\/)schema\.ts$/.test(k))]:r.schema,wn=at(xn),vn=te(t,v),kn=Ve(R,b,v),Tn=path.resolve(e,"admin.routes.ts"),Sn=bn.map(k=>Bun.write(path.resolve(e,k.relativePath),k.source)),Rn=hn.map(k=>Bun.write(path.resolve(e,k.relativePath),k.source));await Promise.all([Bun.write(c,fn),Bun.write(d,`export * from "./client/index";
|
|
7499
|
+
`}function xr(t,e){if(e){let n=t[e];if(!W(n))throw new Error(`schemaDsl.exportName '${e}' does not point to a schema() export.`);return n}for(let n of Object.values(t))if(W(n))return n;throw new Error("No schema() export found in schemaDsl entry module. Set schemaDsl.exportName to the correct export.")}async function Ke(t){let e=t.config.schemaDsl;if(!e)return;let n=e.namingStrategy??"camelToSnake",r=path.resolve(t.configDir,e.entry),a=path.resolve(t.configDir,e.outFile??path.resolve(t.outDirAbs,"schema.compiled.ts")),o=path.resolve(t.configDir,e.typesOutFile??path.resolve(t.outDirAbs,"schema.types.ts")),i=path.resolve(t.configDir,e.zodOutFile??path.resolve(t.outDirAbs,"schema.zod.ts")),l=await import(`${url.pathToFileURL(r).href}?t=${Date.now()}`),c=xr(l,e.exportName),d=cr(c);await Promise.all([promises.mkdir(path.dirname(a),{recursive:true}),promises.mkdir(path.dirname(o),{recursive:true}),promises.mkdir(path.dirname(i),{recursive:true})]);let g=fr(d,n),u=yr(d),y=hr(d);return await Promise.all([Bun.write(a,g),Bun.write(o,u),Bun.write(i,y)]),{schemaPath:a,typesPath:o,zodPath:i,tableNames:Object.keys(d.tables)}}function vr(t){return t.replaceAll("\\","/")}function S(t,e){let n=vr(path.relative(t,e)).replace(/\.tsx?$/,"");return n.startsWith(".")?n:`./${n}`}var Rr=new Set([".ts",".tsx",".mts",".cts"]);async function Ye(t){let e=await promises.readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=path.resolve(t,r.name);if(r.isDirectory()){n.push(...await Ye(a));continue}r.isFile()&&Rr.has(path.extname(r.name))&&n.push(a);}return n}function Q(t){return t.replace(/\.[cm]?tsx?$/,"")}function Ar(t,e){let n=t,r=false,a,o="unknown";for(;m__namespace.isCallExpression(n);){let i=n.expression;if(!m__namespace.isPropertyAccessExpression(i))break;let s=i.name.text;if(s==="optional"||s==="nullable")r=true,n=i.expression;else if(s==="default"){r=true;let l=n.arguments[0];l&&(m__namespace.isStringLiteral(l)||m__namespace.isNumericLiteral(l)?a=l.text:l.kind===m__namespace.SyntaxKind.TrueKeyword?a="true":l.kind===m__namespace.SyntaxKind.FalseKeyword&&(a="false")),n=i.expression;}else if(s==="string"||s==="uuid"||s==="email"||s==="url"){o="string";break}else if(s==="number"||s==="int"||s==="float"){o="number";break}else if(s==="boolean"){o="boolean";break}else n=i.expression;}return {name:e,type:o,optional:r,defaultValue:a}}function $r(t){if(!t||!m__namespace.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>m__namespace.isPropertyAssignment(r)&&m__namespace.isIdentifier(r.name)&&r.name.text==="args");if(!e||!m__namespace.isObjectLiteralExpression(e.initializer))return [];let n=[];for(let r of e.initializer.properties)!m__namespace.isPropertyAssignment(r)||!m__namespace.isIdentifier(r.name)||n.push(Ar(r.initializer,r.name.text));return n}function Nr(t){return m__namespace.isVariableStatement(t)?t.modifiers?.some(e=>e.kind===m__namespace.SyntaxKind.ExportKeyword)??false:false}function Xe(t){return m__namespace.isIdentifier(t)?t.text:m__namespace.isParenthesizedExpression(t)?Xe(t.expression):null}function qr(t){if(!t||!m__namespace.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>!m__namespace.isPropertyAssignment(r)||!m__namespace.isIdentifier(r.name)?false:r.name.text==="cronTrigger");if(!e||!m__namespace.isPropertyAssignment(e))return [];let n=e.initializer;return m__namespace.isStringLiteral(n)||m__namespace.isNoSubstitutionTemplateLiteral(n)?[n.text.trim()].filter(r=>r.length>0):m__namespace.isArrayLiteralExpression(n)?n.elements.map(r=>m__namespace.isStringLiteral(r)||m__namespace.isNoSubstitutionTemplateLiteral(r)?r.text.trim():"").filter(r=>r.length>0):[]}function Cr(t,e){let n=m__namespace.createSourceFile(e,t,m__namespace.ScriptTarget.Latest,true,m__namespace.ScriptKind.TS),r=[];for(let a of n.statements)if(Nr(a))for(let o of a.declarationList.declarations){if(!m__namespace.isIdentifier(o.name)||!o.initializer||!m__namespace.isCallExpression(o.initializer))continue;let i=Xe(o.initializer.expression);i!=="query"&&i!=="mutation"&&i!=="scheduler"&&i!=="cron"&&i!=="storageManager"||r.push({exportName:o.name.text,kind:i==="storageManager"?"storage":i,cronTriggers:i==="cron"?qr(o.initializer.arguments[0]):[],args:i==="query"||i==="mutation"?$r(o.initializer.arguments[0]):[]});}return r}function Ge(t,e,n){let r=e.replace(/\\/g,"/"),o=Q(r).split("/").filter(Boolean);return `/${[t,...o,n].filter(Boolean).map(s=>s.trim()).filter(s=>s.length>0).join("/")}`}function Pr(t,e){let n=t.replace(/\\/g,"/"),r=`${e}/`,a=n.indexOf(r);return a>=0?n.slice(a+r.length):n===e?"index.ts":n}function Je(t,e){let n=t.replace(/\\/g,"/"),a=Q(n).split("/").filter(Boolean),o=a[a.length-1]??"index";return [a.length>1?a[a.length-2]:"root",o,e].map(s=>s.trim()).filter(s=>s.length>0).join("/")}async function tn(t){let e=[],n=await Ye(t.scanDirAbs).catch(()=>[]);for(let a of n){let o=Bun.file(a);if(!await o.exists())continue;let i=await o.text(),s=path.relative(t.scanDirAbs,a),l=Cr(i,a),c=[{kind:"query",kindDirectory:"queries",exports:l.filter(d=>d.kind==="query")},{kind:"mutation",kindDirectory:"mutations",exports:l.filter(d=>d.kind==="mutation")},{kind:"scheduler",kindDirectory:"schedulers",exports:l.filter(d=>d.kind==="scheduler")},{kind:"cron",kindDirectory:"crons",exports:l.filter(d=>d.kind==="cron")},{kind:"storage",kindDirectory:"queries",exports:l.filter(d=>d.kind==="storage")}];for(let d of c){if(d.exports.length===0)continue;let g=Pr(s,d.kindDirectory);for(let u of d.exports){let y=d.kind==="query"||d.kind==="mutation"?Je(g,u.exportName):void 0,h=d.kind==="scheduler"||d.kind==="cron"?Je(g,u.exportName):void 0,f=d.kind==="query"||d.kind==="mutation"?[...Q(g).split("/").filter(Boolean),u.exportName]:void 0,b=d.kind==="query"?Ge("queries",g,u.exportName):d.kind==="mutation"?Ge("mutations",g,u.exportName):d.kind==="storage"?`/storage/managers/${u.exportName}`:`/${d.kindDirectory}/${h}`;e.push({kind:d.kind,exportName:u.exportName,filePath:a,importPath:S(t.outDirAbs,a),clientImportPath:S(path.resolve(t.outDirAbs,"client"),a),routePath:b,handlerName:y,clientSegments:f,taskName:h,cronTriggers:u.cronTriggers,args:u.args});}}}e.sort((a,o)=>a.routePath.localeCompare(o.routePath));let r=new Map;for(let a of e){let o=a.taskName?`task:${a.taskName}`:`route:${a.routePath}`,i=r.get(o);if(i)throw new Error(`Duplicate handler operation discovered: ${a.taskName??a.routePath} (${i} and ${a.filePath}#${a.exportName}).`);r.set(o,`${a.filePath}#${a.exportName}`);}return e}function Dr(t){let e=[],n="",r=0,a=0,o=0,i=false,s=false,l=false,c=false;for(let g=0;g<t.length;g+=1){let u=t[g];if(c){n+=u,c=false;continue}if(u==="\\"){n+=u,c=true;continue}if(!s&&!l&&u==="'"){i=!i,n+=u;continue}if(!i&&!l&&u==='"'){s=!s,n+=u;continue}if(!i&&!s&&u==="`"){l=!l,n+=u;continue}if(i||s||l){n+=u;continue}if(u==="("?r+=1:u===")"?r-=1:u==="{"?a+=1:u==="}"?a-=1:u==="["?o+=1:u==="]"&&(o-=1),u===","&&r===0&&a===0&&o===0){let y=n.trim();y.length>0&&e.push(y),n="";continue}n+=u;}let d=n.trim();return d.length>0&&e.push(d),e}function Or(t){let e=0,n=0,r=0,a=false,o=false,i=false,s=false;for(let l=0;l<t.length;l+=1){let c=t[l];if(s){s=false;continue}if(c==="\\"){s=true;continue}if(!o&&!i&&c==="'"){a=!a;continue}if(!a&&!i&&c==='"'){o=!o;continue}if(!a&&!o&&c==="`"){i=!i;continue}if(!(a||o||i)){if(c==="("){e+=1;continue}if(c===")"){e-=1;continue}if(c==="{"){n+=1;continue}if(c==="}"){n-=1;continue}if(c==="["){r+=1;continue}if(c==="]"){r-=1;continue}if(c===":"&&e===0&&n===0&&r===0)return l}}return -1}function Ir(t){let e=t.toLowerCase();return /mode\s*:\s*["'`](timestamp|timestamp_ms)["'`]/.test(e)?"date":/mode\s*:\s*["'`]boolean["'`]/.test(e)?"boolean":/\.(date|datetime|timestamp)\s*\(/.test(e)?"date":/\.(int|integer|real|numeric|decimal|float|double)\s*\(/.test(e)?"number":/\.(text|varchar|char)\s*\(/.test(e)?"string":/\.(boolean|bool)\s*\(/.test(e)?"boolean":"unknown"}function Mr(t){let e=Dr(t),n=[];for(let r of e){let a=Or(r);if(a===-1)continue;let o=r.slice(0,a).trim().replace(/^['"]|['"]$/g,"");if(!o)continue;let i=r.slice(a+1).trim(),s=/\.primarykey\s*\(/i.test(i),l=/autoincrement\s*:\s*true/i.test(i),c=/\.default\s*\(/i.test(i),g=!/\.notnull\s*\(/i.test(i)||c||l;n.push({name:o,expression:i,type:Ir(i),optional:g,primaryKey:s,autoIncrement:l});}return n}function Fr(t){let e=/export\s+const\s+(\w+)\s*=\s*table\s*\(\s*["'`]([^"'`]+)["'`]/g,n=[],r=(o,i)=>{let s=0,l=false,c=false,d=false,g=false;for(let u=i;u<o.length;u+=1){let y=o[u];if(g){g=false;continue}if(y==="\\"){g=true;continue}if(!c&&!d&&y==="'"){l=!l;continue}if(!l&&!d&&y==='"'){c=!c;continue}if(!l&&!c&&y==="`"){d=!d;continue}if(!(l||c||d)){if(y==="{"){s+=1;continue}if(y==="}"&&(s-=1,s===0))return u}}return -1},a=e.exec(t);for(;a;){let o=a[1],i=a[2],s=t.indexOf("{",e.lastIndex);if(s===-1){a=e.exec(t);continue}let l=r(t,s);if(l===-1){a=e.exec(t);continue}let c=t.slice(s+1,l);n.push({exportName:o,tableName:i,columns:Mr(c)}),a=e.exec(t);}return n}async function nn(t){let e=await promises.readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=path.resolve(t,r.name);if(r.isDirectory()){n.push(...await nn(a));continue}r.isFile()&&r.name==="schema.ts"&&n.push(a);}return n}async function rn(t,e=[]){let n=await nn(t.scanDirAbs).catch(()=>[]),r=path.resolve(t.configDir,"schema.ts"),a=[...e,...n.length?n:[r]];for(let o of a){let i=Bun.file(o);if(!await i.exists())continue;let s=await i.text(),l=Fr(s);if(l.length>0)return {schemaPath:o,tables:l}}throw new Error(`Unable to discover schema.ts under scanDir (${t.scanDirAbs}) or fallback (${r}).`)}function jr(t,e){let n=path.relative(t,e).replace(/\\/g,"/");return n.startsWith(".")?n:`./${n}`}async function an(t){let{outDirAbs:e,wranglerOutDirAbs:n,config:r,configPath:a,configDir:o}=t,i=S(e,a),s=path.resolve(e,"client"),l=S(s,a);await Promise.all([promises.mkdir(e,{recursive:true}),promises.mkdir(s,{recursive:true}),promises.mkdir(n,{recursive:true})]);let c=path.resolve(e,"server.ts"),d=path.resolve(e,"client.ts"),g=path.resolve(e,"auth.config.ts"),u=path.resolve(e,"auth.schema.ts"),y=path.resolve(e,"drizzle.config.ts"),h=path.resolve(n,"wrangler.json"),f=await Ke(t),b=await rn(t,f?[f.schemaPath]:[]),R=S(e,b.schemaPath),v=await tn(t),fn=Yt(r.auth.basePath,r.database[0].binding,r.kv[0]?.binding,r.scheduler.binding,r.r2[0]?.binding,r.realtime.binding,r.realtime.objectName,r.realtime.subscribePath,r.realtime.websocketPath,r.realtime.protocol),hn=rt(l,v),bn=F(R,v,r.r2[0]?.binding),yn=J(i),xn=f?[jr(o,f.schemaPath),...r.schema.filter(k=>!/(^|\/)schema\.ts$/.test(k))]:r.schema,wn=at(xn),vn=te(t,v),kn=Ve(R,b,v),Tn=path.resolve(e,"admin.routes.ts"),Sn=bn.map(k=>Bun.write(path.resolve(e,k.relativePath),k.source)),Rn=hn.map(k=>Bun.write(path.resolve(e,k.relativePath),k.source));await Promise.all([Bun.write(c,fn),Bun.write(d,`export * from "./client/index";
|
|
7500
7500
|
`),...Rn,...Sn,Bun.write(g,yn),Bun.write(u,""),Bun.write(y,wn),Bun.write(h,`${JSON.stringify(vn,null,2)}
|
|
7501
|
-
`),Bun.write(Tn,kn)]);let
|
|
7501
|
+
`),Bun.write(Tn,kn)]);let D=path.relative(o,g).replace(/\\/g,"/"),An=D.startsWith(".")?D:`./${D}`,O=path.relative(o,u).replace(/\\/g,"/"),$n=O.startsWith(".")?O:`./${O}`,G=await Bun.spawn(["npx","@better-auth/cli","generate","--config",An,"--output",$n,"--yes"],{cwd:o,stdout:"inherit",stderr:"inherit"}).exited;if(G!==0)throw new Error(`better-auth generation failed with exit code ${G}`)}var on=zod.z.object({binding:zod.z.string().min(1),databaseName:zod.z.string().min(1),databaseId:zod.z.string().min(1),previewDatabaseId:zod.z.string().min(1).optional(),migrationsDir:zod.z.string().min(1).optional()}).strict(),sn=zod.z.object({binding:zod.z.string().min(1),id:zod.z.string().min(1),previewId:zod.z.string().min(1).optional()}).strict(),ln=zod.z.object({binding:zod.z.string().min(1),bucketName:zod.z.string().min(1),previewBucketName:zod.z.string().min(1).optional(),jurisdiction:zod.z.string().min(1).optional()}).strict(),cn=zod.z.object({enabled:zod.z.boolean().optional(),binding:zod.z.string().min(1).optional(),queue:zod.z.string().min(1).optional()}).strict(),zr=zod.z.object({enabled:zod.z.boolean().optional(),binding:zod.z.string().min(1).optional(),className:zod.z.string().min(1).optional(),objectName:zod.z.string().min(1).optional(),subscribePath:zod.z.string().min(1).optional(),websocketPath:zod.z.string().min(1).optional(),protocol:zod.z.string().min(1).optional()}).strict(),Wr=zod.z.object({scanDir:zod.z.string().min(1),outDir:zod.z.string().min(1),wranglerOutDir:zod.z.string().min(1).optional(),wranglerOutPath:zod.z.string().min(1).optional(),schema:zod.z.array(zod.z.string()).min(1),schemaDsl:zod.z.object({entry:zod.z.string().min(1),exportName:zod.z.string().min(1).optional(),outFile:zod.z.string().min(1).optional(),typesOutFile:zod.z.string().min(1).optional(),zodOutFile:zod.z.string().min(1).optional(),namingStrategy:zod.z.literal("camelToSnake").optional()}).strict().optional(),database:zod.z.union([on,zod.z.array(on).min(1)]),kv:zod.z.union([sn,zod.z.array(sn)]).optional(),r2:zod.z.union([ln,zod.z.array(ln)]).optional(),auth:zod.z.object({enabled:zod.z.boolean(),basePath:zod.z.string().min(1),options:zod.z.custom(t=>typeof t=="object"&&t!==null),clientOptions:zod.z.custom(t=>typeof t=="object"&&t!==null)}).strict(),scheduler:cn.optional(),realtime:zr.optional(),wranglerOverrides:zod.z.record(zod.z.string(),zod.z.unknown()).optional()}).strict();function un(t){return typeof t=="object"&&t!==null}function Lr(t){let e=un(t.wranglerOverrides)?t.wranglerOverrides.scheduler:void 0,n=cn.safeParse(e);return n.success?n.data:{}}function Ur(t){if(!un(t)||!("scheduler"in t))return t;let{scheduler:e,...n}=t;return n}function Qr(t){let n={...Lr(t)??{},...t.scheduler??{}},r=t.realtime??{};return {...t,database:Array.isArray(t.database)?t.database:[t.database],kv:t.kv?Array.isArray(t.kv)?t.kv:[t.kv]:[],r2:t.r2?Array.isArray(t.r2)?t.r2:[t.r2]:[],scheduler:{enabled:n.enabled??true,binding:n.binding??"APPFLARE_SCHEDULER_QUEUE",queue:n.queue},realtime:{enabled:r.enabled??true,binding:r.binding??"APPFLARE_REALTIME",className:r.className??"AppflareRealtimeDurableObject",objectName:r.objectName??"global",subscribePath:r.subscribePath??"/realtime/subscribe",websocketPath:r.websocketPath??"/realtime/ws",protocol:r.protocol??"appflare.realtime.v1"},wranglerOverrides:Ur(t.wranglerOverrides),wranglerOutDir:t.wranglerOutDir??t.wranglerOutPath??t.outDir}}async function $(t){let e=path.isAbsolute(t??"")?t:path.resolve(process.cwd(),t??"appflare.config.ts"),n=path.dirname(e),o=(await import(url.pathToFileURL(e).href)).default,i=Wr.parse(o),s=Qr(i);return {configPath:e,configDir:n,scanDirAbs:path.resolve(n,s.scanDir),outDirAbs:path.resolve(n,s.outDir),wranglerOutDirAbs:path.resolve(n,s.wranglerOutDir),config:s}}function Jr(t){let e=t;for(;;){if(fs.existsSync(path.resolve(e,"package.json")))return e;let n=path.dirname(e);if(n===e)return t;e=n;}}async function E(t){let e=await $(t);if(await an(e),e.wranglerOutDirAbs===e.outDirAbs){process.stdout.write(`\u2705 Generated artifacts in ${e.outDirAbs}
|
|
7502
7502
|
`);return}process.stdout.write(`\u2705 Generated server/client in ${e.outDirAbs} and wrangler.json in ${e.wranglerOutDirAbs}
|
|
7503
7503
|
`);}async function pn(t,e=false){if(await E(t),!e)return;let n=await $(t),r=false,a=false,o=async()=>{if(r){a=true;return}r=true;try{await E(t);}catch(s){process.stderr.write(`\u274C Build failed: ${s.message}
|
|
7504
7504
|
`);}finally{r=false,a&&(a=false,await o());}};_r__default.default.watch(n.scanDirAbs,{ignoreInitial:true}).on("all",async(s,l)=>{process.stdout.write(`\u{1F504} Change detected: ${l}
|
package/dist/cli/index.mjs
CHANGED
|
@@ -3319,10 +3319,10 @@ import * as authSchema from "./auth.schema";
|
|
|
3319
3319
|
import * as schema from "${t}";
|
|
3320
3320
|
|
|
3321
3321
|
${qt()}
|
|
3322
|
-
`}function En(t){let e=t.replace(/[^A-Za-z0-9_]/g,"_");return /^[0-9]/.test(e)?`_${e}`:e}function
|
|
3322
|
+
`}function En(t){let e=t.replace(/[^A-Za-z0-9_]/g,"_");return /^[0-9]/.test(e)?`_${e}`:e}function Dn(t,e){let n=t.routePath.replace(/^\//,"").replace(/\//g,"_");return En(`op_${e}_${n}`)}function On(t){return t.map((e,n)=>({operation:e,index:n,alias:Dn(e,n)}))}function In(t){return t.map(({operation:e,alias:n})=>`import { ${e.exportName} as ${n} } from "${e.importPath}";`).join(`
|
|
3323
3323
|
`)}function Mn(t){return t.filter(({operation:e})=>e.kind==="query"||e.kind==="mutation").map(({alias:e})=>`const ${`${e}Schema`} = z.object(${e}.definition.args);`).join(`
|
|
3324
|
-
`)}function
|
|
3325
|
-
`)}function
|
|
3324
|
+
`)}function Fn(t){return t.filter(({operation:e})=>e.kind==="scheduler").map(({alias:e})=>`const ${`${e}SchedulerSchema`} = ${e}.definition.args ? z.object(${e}.definition.args) : z.undefined();`).join(`
|
|
3325
|
+
`)}function jn(t){return t.filter(({operation:e})=>e.kind==="query").map(({operation:e,alias:n})=>{let r=`${n}Schema`;return `
|
|
3326
3326
|
app.get(
|
|
3327
3327
|
"${e.routePath}",
|
|
3328
3328
|
sValidator("query", ${r}),
|
|
@@ -3369,7 +3369,7 @@ ${qt()}
|
|
|
3369
3369
|
},`}).join(`
|
|
3370
3370
|
`)}function Ln(t){return t.filter(({operation:e})=>e.kind==="storage").map(({alias:e})=>`
|
|
3371
3371
|
${e}.definition.handler,`).join(`
|
|
3372
|
-
`)}function Pt(t){let e=
|
|
3372
|
+
`)}function Pt(t){let e=On(t);return {imports:In(e),operationSchemas:Mn(e),schedulerSchemas:Fn(e),queryRoutes:jn(e),mutationRoutes:Bn(e),queryRegistryEntries:Hn(e),schedulerEntries:Vn(e),schedulerPayloadMapEntries:zn(e),cronEntries:Wn(e),storageHandlersEntries:Ln(e)}}var Et=`
|
|
3373
3373
|
function getRealtimeStub(
|
|
3374
3374
|
env: Record<string, unknown>,
|
|
3375
3375
|
options: RegisterHandlersOptions,
|
|
@@ -3443,7 +3443,7 @@ function buildRealtimeWsUrl(requestUrl: string, websocketPath: string): string {
|
|
|
3443
3443
|
url.protocol = url.protocol === "https:" ? "wss:" : "ws:";
|
|
3444
3444
|
return url.toString();
|
|
3445
3445
|
}
|
|
3446
|
-
`;var
|
|
3446
|
+
`;var Dt=`
|
|
3447
3447
|
export class AppflareRealtimeDurableObject {
|
|
3448
3448
|
private readonly subscriptions = new Map<string, RealtimeSubscription>();
|
|
3449
3449
|
private readonly sockets = new Map<string, WebSocket>();
|
|
@@ -3586,7 +3586,7 @@ export class AppflareRealtimeDurableObject {
|
|
|
3586
3586
|
return new Response("Not found", { status: 404 });
|
|
3587
3587
|
}
|
|
3588
3588
|
}
|
|
3589
|
-
`;var
|
|
3589
|
+
`;var Ot=`
|
|
3590
3590
|
async function publishMutationEvents(
|
|
3591
3591
|
c: { req: { raw: Request }; env: Record<string, unknown> },
|
|
3592
3592
|
options: RegisterHandlersOptions,
|
|
@@ -3879,7 +3879,7 @@ type RealtimeDurableObjectNamespace = {
|
|
|
3879
3879
|
type RealtimeQueryName = keyof typeof realtimeQueryHandlers extends never
|
|
3880
3880
|
? string
|
|
3881
3881
|
: Extract<keyof typeof realtimeQueryHandlers, string>;
|
|
3882
|
-
`;var
|
|
3882
|
+
`;var Ft=`
|
|
3883
3883
|
function isRecord(value: unknown): value is Record<string, unknown> {
|
|
3884
3884
|
return typeof value === "object" && value !== null;
|
|
3885
3885
|
}
|
|
@@ -4394,7 +4394,7 @@ function doesSubscriptionMatchMutation(
|
|
|
4394
4394
|
|
|
4395
4395
|
return false;
|
|
4396
4396
|
}
|
|
4397
|
-
`;var
|
|
4397
|
+
`;var jt=[Mt,Ft,Et,Ot,It,Dt].join(`
|
|
4398
4398
|
|
|
4399
4399
|
`);var Bt=`
|
|
4400
4400
|
function parseExpiresIn(value: string | undefined): number | undefined {
|
|
@@ -4724,7 +4724,7 @@ setStorageHandlers([...storageHandlers]);
|
|
|
4724
4724
|
|
|
4725
4725
|
${Ht}
|
|
4726
4726
|
|
|
4727
|
-
${
|
|
4727
|
+
${jt}
|
|
4728
4728
|
|
|
4729
4729
|
export function registerGeneratedHandlers(
|
|
4730
4730
|
app: Hono<WorkerEnv>,
|
|
@@ -4740,7 +4740,7 @@ export function registerGeneratedHandlers(
|
|
|
4740
4740
|
${Bt}
|
|
4741
4741
|
|
|
4742
4742
|
${Vt}
|
|
4743
|
-
`}function
|
|
4743
|
+
`}function F(t,e,n){let r=Ct(t),a=pt(n),o=gt(),i=zt(e);return [{relativePath:"handlers.ts",source:r},{relativePath:"handlers.context.ts",source:a},{relativePath:"handlers.execution.ts",source:o},{relativePath:"handlers.routes.ts",source:i}]}function Un(t){return t?`,
|
|
4744
4744
|
KV: c.env["${t}"] as KVNamespace`:""}function Wt(t,e){return `{
|
|
4745
4745
|
DATABASE: c.env["${t}"] as D1Database${Un(e)}
|
|
4746
4746
|
}`}function Lt(t,e,n){return `app.on(["GET", "POST"], "${t}/*", async (c) => {
|
|
@@ -4804,7 +4804,7 @@ app.use('*', cors({
|
|
|
4804
4804
|
},
|
|
4805
4805
|
credentials: true
|
|
4806
4806
|
}));
|
|
4807
|
-
`}function
|
|
4807
|
+
`}function Kt(){return `export { AppflareRealtimeDurableObject };
|
|
4808
4808
|
|
|
4809
4809
|
export default {
|
|
4810
4810
|
fetch: app.fetch,
|
|
@@ -4815,7 +4815,7 @@ export default {
|
|
|
4815
4815
|
await executeCronTriggers(controller, env, generatedHandlerOptions);
|
|
4816
4816
|
},
|
|
4817
4817
|
};
|
|
4818
|
-
`}function
|
|
4818
|
+
`}function Gt(t,e,n="APPFLARE_SCHEDULER_QUEUE",r,a="APPFLARE_REALTIME",o="global",i="/realtime/subscribe",s="/realtime/ws",l="appflare.realtime.v1"){let c=e?`
|
|
4819
4819
|
kvBinding: "${e}",`:"",d=r?`
|
|
4820
4820
|
r2Binding: "${r}",`:"",g=`
|
|
4821
4821
|
realtimeBinding: "${a}",
|
|
@@ -4838,7 +4838,7 @@ import type { D1Database, IncomingRequestCfProperties, KVNamespace } from "@clou
|
|
|
4838
4838
|
`}function Zt(){return `type WorkerEnv = {
|
|
4839
4839
|
Bindings: Record<string, unknown>;
|
|
4840
4840
|
};
|
|
4841
|
-
`}function Yt(t,e,n,r,a,o,i,s,l,c){return Jt()+Zt()+_t()+
|
|
4841
|
+
`}function Yt(t,e,n,r,a,o,i,s,l,c){return Jt()+Zt()+_t()+Gt(e,n,r,a,o,i,s,l,c)+Qt(t,e,n)+Kt()}function Xt(t){return !!t&&typeof t=="object"&&!Array.isArray(t)}function j(t,e){let n={...t};for(let[r,a]of Object.entries(e)){let o=n[r];if(Xt(o)&&Xt(a)){n[r]=j(o,a);continue}n[r]=a;}return n}function Kn(t){return Array.from(new Set(t.filter(e=>e.length>0)))}function te(t,e){let n=e.filter(u=>u.kind==="scheduler"||u.kind==="cron"),r=Kn(e.filter(u=>u.kind==="cron").flatMap(u=>u.cronTriggers??[])),a=t.config.scheduler.enabled&&n.length>0,o=t.config.realtime.enabled,s=(typeof t.config.wranglerOverrides?.name=="string"?t.config.wranglerOverrides.name:void 0)??"appflare-worker",l=t.config.scheduler.queue??`${s}-scheduler`,c={name:s,main:"./src/index.ts",d1_databases:t.config.database.map(u=>({binding:u.binding,database_name:u.databaseName,database_id:u.databaseId,preview_database_id:u.previewDatabaseId??u.databaseId,...u.migrationsDir?{migrations_dir:u.migrationsDir}:{}})),kv_namespaces:t.config.kv.map(u=>({binding:u.binding,id:u.id,...u.previewId?{preview_id:u.previewId}:{}})),r2_buckets:t.config.r2.map(u=>({binding:u.binding,bucket_name:u.bucketName,...u.previewBucketName?{preview_bucket_name:u.previewBucketName}:{},...u.jurisdiction?{jurisdiction:u.jurisdiction}:{}})),...a?{queues:{producers:[{binding:t.config.scheduler.binding,queue:l}],consumers:[{queue:l}]}}:{},...r.length>0?{triggers:{crons:r}}:{},...o?{durable_objects:{bindings:[{name:t.config.realtime.binding,class_name:t.config.realtime.className}]},migrations:[{tag:"appflare-realtime-v1",new_sqlite_classes:[t.config.realtime.className]}]}:{}};if(!t.config.wranglerOverrides)return c;let{scheduler:d,...g}=t.config.wranglerOverrides;return j(c,g)}function ee(t){return t.tables.map(e=>({exportName:e.exportName,tableName:e.tableName,columns:e.columns.map(n=>n.name)}))}function ne(t){return `<li data-name="users">
|
|
4842
4842
|
<a href="/admin/users" hx-get="/admin/users" hx-target="#main-content" hx-push-url="true" hx-swap="outerHTML" class="sidebar-link flex items-center gap-2 px-3 py-2 text-sm rounded-lg w-full">
|
|
4843
4843
|
<iconify-icon icon="mdi:account-group" width="16" height="16" class="opacity-50 shrink-0"></iconify-icon>
|
|
4844
4844
|
<span class="truncate">users</span>
|
|
@@ -4903,7 +4903,7 @@ import type { D1Database, IncomingRequestCfProperties, KVNamespace } from "@clou
|
|
|
4903
4903
|
</a>
|
|
4904
4904
|
`.replace(/\n/g,"\\n")).join("")}function oe(t){return t.columns.filter(e=>e.type==="string").map(e=>`
|
|
4905
4905
|
try { searchConditions.push(like(tableSchema.${e.name}, \`%\${search}%\`)); } catch (e) {}
|
|
4906
|
-
`).join("")}function
|
|
4906
|
+
`).join("")}function Gn(t){switch(t){case "number":return "mdi:pound";case "boolean":return "mdi:toggle-switch-outline";case "date":return "mdi:calendar";default:return "mdi:format-text"}}function ie(t,e){return e.map(n=>{let r=t.columns.find(o=>o.name===n),a=r?Gn(r.type):"mdi:format-text";return `
|
|
4907
4907
|
<th>
|
|
4908
4908
|
<a href="#"
|
|
4909
4909
|
hx-get="/admin/table/${t.exportName}?page=\${page}&search=\${search}&sort=${n}&order=\${sort === '${n}' && order === 'asc' ? 'desc' : 'asc'}"
|
|
@@ -6878,7 +6878,7 @@ ${z()}`}function ke(t){return `
|
|
|
6878
6878
|
c.header('HX-Redirect', prefixToStoragePath(prefix));
|
|
6879
6879
|
return c.html('');
|
|
6880
6880
|
});
|
|
6881
|
-
`}function
|
|
6881
|
+
`}function De(){return `
|
|
6882
6882
|
adminApp.post('/storage/directory', async (c) => {
|
|
6883
6883
|
const bucket = getStorageBucket(c);
|
|
6884
6884
|
if (!bucket) return c.text("Storage not configured", 400);
|
|
@@ -6904,7 +6904,7 @@ ${z()}`}function ke(t){return `
|
|
|
6904
6904
|
|
|
6905
6905
|
return c.redirect(prefixToStoragePath(prefix));
|
|
6906
6906
|
});
|
|
6907
|
-
`}function
|
|
6907
|
+
`}function Oe(){return `
|
|
6908
6908
|
adminApp.get('/storage/download', async (c) => {
|
|
6909
6909
|
const bucket = getStorageBucket(c);
|
|
6910
6910
|
if (!bucket) return c.text("Storage not configured", 400);
|
|
@@ -6943,7 +6943,7 @@ ${z()}`}function ke(t){return `
|
|
|
6943
6943
|
return new Response(object.body, { headers });
|
|
6944
6944
|
});
|
|
6945
6945
|
`}function Me(){return `
|
|
6946
|
-
${
|
|
6946
|
+
${Oe()}
|
|
6947
6947
|
|
|
6948
6948
|
${Ie()}
|
|
6949
6949
|
|
|
@@ -6951,16 +6951,16 @@ ${z()}`}function ke(t){return `
|
|
|
6951
6951
|
|
|
6952
6952
|
${Ee()}
|
|
6953
6953
|
|
|
6954
|
-
${
|
|
6954
|
+
${De()}
|
|
6955
6955
|
|
|
6956
6956
|
${Ce()}
|
|
6957
|
-
`}function
|
|
6957
|
+
`}function Fe(){return `
|
|
6958
6958
|
${Ne()}
|
|
6959
6959
|
|
|
6960
6960
|
${qe()}
|
|
6961
6961
|
|
|
6962
6962
|
${Me()}
|
|
6963
|
-
`}function
|
|
6963
|
+
`}function je(t,e){let n=re(e);return `
|
|
6964
6964
|
function Layout(props: { children: any; title: string; hideSidebar?: boolean }) {
|
|
6965
6965
|
return html\`<!DOCTYPE html>
|
|
6966
6966
|
<html lang="en" data-theme="light">
|
|
@@ -7411,7 +7411,7 @@ function Layout(props: { children: any; title: string; hideSidebar?: boolean })
|
|
|
7411
7411
|
\`
|
|
7412
7412
|
}));
|
|
7413
7413
|
});
|
|
7414
|
-
`}function Ve(t,e,n){let r=ee(e),a=ne(r),o=ae(r),i=ve(e),s=$e(n),l=
|
|
7414
|
+
`}function Ve(t,e,n){let r=ee(e),a=ne(r),o=ae(r),i=ve(e),s=$e(n),l=Fe(),c=je(a,n),d=Be(),g=He(o);return `import { Hono } from "hono";
|
|
7415
7415
|
import { html, raw } from "hono/html";
|
|
7416
7416
|
import { drizzle } from "drizzle-orm/d1";
|
|
7417
7417
|
import { eq, desc, asc, sql, like, or, inArray } from "drizzle-orm";
|
|
@@ -7496,9 +7496,9 @@ ${i.join(`
|
|
|
7496
7496
|
};`);}return `${e.join(`
|
|
7497
7497
|
|
|
7498
7498
|
`)}
|
|
7499
|
-
`}function xr(t,e){if(e){let n=t[e];if(!W(n))throw new Error(`schemaDsl.exportName '${e}' does not point to a schema() export.`);return n}for(let n of Object.values(t))if(W(n))return n;throw new Error("No schema() export found in schemaDsl entry module. Set schemaDsl.exportName to the correct export.")}async function Ge(t){let e=t.config.schemaDsl;if(!e)return;let n=e.namingStrategy??"camelToSnake",r=resolve(t.configDir,e.entry),a=resolve(t.configDir,e.outFile??resolve(t.outDirAbs,"schema.compiled.ts")),o=resolve(t.configDir,e.typesOutFile??resolve(t.outDirAbs,"schema.types.ts")),i=resolve(t.configDir,e.zodOutFile??resolve(t.outDirAbs,"schema.zod.ts")),l=await import(`${pathToFileURL(r).href}?t=${Date.now()}`),c=xr(l,e.exportName),d=cr(c);await Promise.all([mkdir(dirname(a),{recursive:true}),mkdir(dirname(o),{recursive:true}),mkdir(dirname(i),{recursive:true})]);let g=fr(d,n),u=yr(d),y=hr(d);return await Promise.all([Bun.write(a,g),Bun.write(o,u),Bun.write(i,y)]),{schemaPath:a,typesPath:o,zodPath:i,tableNames:Object.keys(d.tables)}}function vr(t){return t.replaceAll("\\","/")}function S(t,e){let n=vr(relative(t,e)).replace(/\.tsx?$/,"");return n.startsWith(".")?n:`./${n}`}var Rr=new Set([".ts",".tsx",".mts",".cts"]);async function Ye(t){let e=await readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=resolve(t,r.name);if(r.isDirectory()){n.push(...await Ye(a));continue}r.isFile()&&Rr.has(extname(r.name))&&n.push(a);}return n}function Q(t){return t.replace(/\.[cm]?tsx?$/,"")}function Ar(t,e){let n=t,r=false,a,o="unknown";for(;m.isCallExpression(n);){let i=n.expression;if(!m.isPropertyAccessExpression(i))break;let s=i.name.text;if(s==="optional"||s==="nullable")r=true,n=i.expression;else if(s==="default"){r=true;let l=n.arguments[0];l&&(m.isStringLiteral(l)||m.isNumericLiteral(l)?a=l.text:l.kind===m.SyntaxKind.TrueKeyword?a="true":l.kind===m.SyntaxKind.FalseKeyword&&(a="false")),n=i.expression;}else if(s==="string"||s==="uuid"||s==="email"||s==="url"){o="string";break}else if(s==="number"||s==="int"||s==="float"){o="number";break}else if(s==="boolean"){o="boolean";break}else n=i.expression;}return {name:e,type:o,optional:r,defaultValue:a}}function $r(t){if(!t||!m.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>m.isPropertyAssignment(r)&&m.isIdentifier(r.name)&&r.name.text==="args");if(!e||!m.isObjectLiteralExpression(e.initializer))return [];let n=[];for(let r of e.initializer.properties)!m.isPropertyAssignment(r)||!m.isIdentifier(r.name)||n.push(Ar(r.initializer,r.name.text));return n}function Nr(t){return m.isVariableStatement(t)?t.modifiers?.some(e=>e.kind===m.SyntaxKind.ExportKeyword)??false:false}function Xe(t){return m.isIdentifier(t)?t.text:m.isParenthesizedExpression(t)?Xe(t.expression):null}function qr(t){if(!t||!m.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>!m.isPropertyAssignment(r)||!m.isIdentifier(r.name)?false:r.name.text==="cronTrigger");if(!e||!m.isPropertyAssignment(e))return [];let n=e.initializer;return m.isStringLiteral(n)||m.isNoSubstitutionTemplateLiteral(n)?[n.text.trim()].filter(r=>r.length>0):m.isArrayLiteralExpression(n)?n.elements.map(r=>m.isStringLiteral(r)||m.isNoSubstitutionTemplateLiteral(r)?r.text.trim():"").filter(r=>r.length>0):[]}function Cr(t,e){let n=m.createSourceFile(e,t,m.ScriptTarget.Latest,true,m.ScriptKind.TS),r=[];for(let a of n.statements)if(Nr(a))for(let o of a.declarationList.declarations){if(!m.isIdentifier(o.name)||!o.initializer||!m.isCallExpression(o.initializer))continue;let i=Xe(o.initializer.expression);i!=="query"&&i!=="mutation"&&i!=="scheduler"&&i!=="cron"&&i!=="storageManager"||r.push({exportName:o.name.text,kind:i==="storageManager"?"storage":i,cronTriggers:i==="cron"?qr(o.initializer.arguments[0]):[],args:i==="query"||i==="mutation"?$r(o.initializer.arguments[0]):[]});}return r}function Ke(t,e,n){let r=e.replace(/\\/g,"/"),o=Q(r).split("/").filter(Boolean);return `/${[t,...o,n].filter(Boolean).map(s=>s.trim()).filter(s=>s.length>0).join("/")}`}function Pr(t,e){let n=t.replace(/\\/g,"/"),r=`${e}/`,a=n.indexOf(r);return a>=0?n.slice(a+r.length):n===e?"index.ts":n}function Je(t,e){let n=t.replace(/\\/g,"/"),a=Q(n).split("/").filter(Boolean),o=a[a.length-1]??"index";return [a.length>1?a[a.length-2]:"root",o,e].map(s=>s.trim()).filter(s=>s.length>0).join("/")}async function tn(t){let e=[],n=await Ye(t.scanDirAbs).catch(()=>[]);for(let a of n){let o=Bun.file(a);if(!await o.exists())continue;let i=await o.text(),s=relative(t.scanDirAbs,a),l=Cr(i,a),c=[{kind:"query",kindDirectory:"queries",exports:l.filter(d=>d.kind==="query")},{kind:"mutation",kindDirectory:"mutations",exports:l.filter(d=>d.kind==="mutation")},{kind:"scheduler",kindDirectory:"schedulers",exports:l.filter(d=>d.kind==="scheduler")},{kind:"cron",kindDirectory:"crons",exports:l.filter(d=>d.kind==="cron")},{kind:"storage",kindDirectory:"queries",exports:l.filter(d=>d.kind==="storage")}];for(let d of c){if(d.exports.length===0)continue;let g=Pr(s,d.kindDirectory);for(let u of d.exports){let y=d.kind==="query"||d.kind==="mutation"?Je(g,u.exportName):void 0,h=d.kind==="scheduler"||d.kind==="cron"?Je(g,u.exportName):void 0,f=d.kind==="query"||d.kind==="mutation"?[...Q(g).split("/").filter(Boolean),u.exportName]:void 0,b=d.kind==="query"?Ke("queries",g,u.exportName):d.kind==="mutation"?Ke("mutations",g,u.exportName):d.kind==="storage"?`/storage/managers/${u.exportName}`:`/${d.kindDirectory}/${h}`;e.push({kind:d.kind,exportName:u.exportName,filePath:a,importPath:S(t.outDirAbs,a),clientImportPath:S(resolve(t.outDirAbs,"client"),a),routePath:b,handlerName:y,clientSegments:f,taskName:h,cronTriggers:u.cronTriggers,args:u.args});}}}e.sort((a,o)=>a.routePath.localeCompare(o.routePath));let r=new Map;for(let a of e){let o=a.taskName?`task:${a.taskName}`:`route:${a.routePath}`,i=r.get(o);if(i)throw new Error(`Duplicate handler operation discovered: ${a.taskName??a.routePath} (${i} and ${a.filePath}#${a.exportName}).`);r.set(o,`${a.filePath}#${a.exportName}`);}return e}function Or(t){let e=[],n="",r=0,a=0,o=0,i=false,s=false,l=false,c=false;for(let g=0;g<t.length;g+=1){let u=t[g];if(c){n+=u,c=false;continue}if(u==="\\"){n+=u,c=true;continue}if(!s&&!l&&u==="'"){i=!i,n+=u;continue}if(!i&&!l&&u==='"'){s=!s,n+=u;continue}if(!i&&!s&&u==="`"){l=!l,n+=u;continue}if(i||s||l){n+=u;continue}if(u==="("?r+=1:u===")"?r-=1:u==="{"?a+=1:u==="}"?a-=1:u==="["?o+=1:u==="]"&&(o-=1),u===","&&r===0&&a===0&&o===0){let y=n.trim();y.length>0&&e.push(y),n="";continue}n+=u;}let d=n.trim();return d.length>0&&e.push(d),e}function Dr(t){let e=0,n=0,r=0,a=false,o=false,i=false,s=false;for(let l=0;l<t.length;l+=1){let c=t[l];if(s){s=false;continue}if(c==="\\"){s=true;continue}if(!o&&!i&&c==="'"){a=!a;continue}if(!a&&!i&&c==='"'){o=!o;continue}if(!a&&!o&&c==="`"){i=!i;continue}if(!(a||o||i)){if(c==="("){e+=1;continue}if(c===")"){e-=1;continue}if(c==="{"){n+=1;continue}if(c==="}"){n-=1;continue}if(c==="["){r+=1;continue}if(c==="]"){r-=1;continue}if(c===":"&&e===0&&n===0&&r===0)return l}}return -1}function Ir(t){let e=t.toLowerCase();return /mode\s*:\s*["'`](timestamp|timestamp_ms)["'`]/.test(e)?"date":/mode\s*:\s*["'`]boolean["'`]/.test(e)?"boolean":/\.(date|datetime|timestamp)\s*\(/.test(e)?"date":/\.(int|integer|real|numeric|decimal|float|double)\s*\(/.test(e)?"number":/\.(text|varchar|char)\s*\(/.test(e)?"string":/\.(boolean|bool)\s*\(/.test(e)?"boolean":"unknown"}function Mr(t){let e=Or(t),n=[];for(let r of e){let a=Dr(r);if(a===-1)continue;let o=r.slice(0,a).trim().replace(/^['"]|['"]$/g,"");if(!o)continue;let i=r.slice(a+1).trim(),s=/\.primarykey\s*\(/i.test(i),l=/autoincrement\s*:\s*true/i.test(i),c=/\.default\s*\(/i.test(i),g=!/\.notnull\s*\(/i.test(i)||c||l;n.push({name:o,expression:i,type:Ir(i),optional:g,primaryKey:s,autoIncrement:l});}return n}function jr(t){let e=/export\s+const\s+(\w+)\s*=\s*table\s*\(\s*["'`]([^"'`]+)["'`]/g,n=[],r=(o,i)=>{let s=0,l=false,c=false,d=false,g=false;for(let u=i;u<o.length;u+=1){let y=o[u];if(g){g=false;continue}if(y==="\\"){g=true;continue}if(!c&&!d&&y==="'"){l=!l;continue}if(!l&&!d&&y==='"'){c=!c;continue}if(!l&&!c&&y==="`"){d=!d;continue}if(!(l||c||d)){if(y==="{"){s+=1;continue}if(y==="}"&&(s-=1,s===0))return u}}return -1},a=e.exec(t);for(;a;){let o=a[1],i=a[2],s=t.indexOf("{",e.lastIndex);if(s===-1){a=e.exec(t);continue}let l=r(t,s);if(l===-1){a=e.exec(t);continue}let c=t.slice(s+1,l);n.push({exportName:o,tableName:i,columns:Mr(c)}),a=e.exec(t);}return n}async function nn(t){let e=await readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=resolve(t,r.name);if(r.isDirectory()){n.push(...await nn(a));continue}r.isFile()&&r.name==="schema.ts"&&n.push(a);}return n}async function rn(t,e=[]){let n=await nn(t.scanDirAbs).catch(()=>[]),r=resolve(t.configDir,"schema.ts"),a=[...e,...n.length?n:[r]];for(let o of a){let i=Bun.file(o);if(!await i.exists())continue;let s=await i.text(),l=jr(s);if(l.length>0)return {schemaPath:o,tables:l}}throw new Error(`Unable to discover schema.ts under scanDir (${t.scanDirAbs}) or fallback (${r}).`)}function Fr(t,e){let n=relative(t,e).replace(/\\/g,"/");return n.startsWith(".")?n:`./${n}`}async function an(t){let{outDirAbs:e,wranglerOutDirAbs:n,config:r,configPath:a,configDir:o}=t,i=S(e,a),s=resolve(e,"client"),l=S(s,a);await Promise.all([mkdir(e,{recursive:true}),mkdir(s,{recursive:true}),mkdir(n,{recursive:true})]);let c=resolve(e,"server.ts"),d=resolve(e,"client.ts"),g=resolve(e,"auth.config.ts"),u=resolve(e,"auth.schema.ts"),y=resolve(e,"drizzle.config.ts"),h=resolve(n,"wrangler.json"),f=await Ge(t),b=await rn(t,f?[f.schemaPath]:[]),R=S(e,b.schemaPath),v=await tn(t),fn=Yt(r.auth.basePath,r.database[0].binding,r.kv[0]?.binding,r.scheduler.binding,r.r2[0]?.binding,r.realtime.binding,r.realtime.objectName,r.realtime.subscribePath,r.realtime.websocketPath,r.realtime.protocol),hn=rt(l,v),bn=j(R,v,r.r2[0]?.binding),yn=J(i),xn=f?[Fr(o,f.schemaPath),...r.schema.filter(k=>!/(^|\/)schema\.ts$/.test(k))]:r.schema,wn=at(xn),vn=te(t,v),kn=Ve(R,b,v),Tn=resolve(e,"admin.routes.ts"),Sn=bn.map(k=>Bun.write(resolve(e,k.relativePath),k.source)),Rn=hn.map(k=>Bun.write(resolve(e,k.relativePath),k.source));await Promise.all([Bun.write(c,fn),Bun.write(d,`export * from "./client/index";
|
|
7499
|
+
`}function xr(t,e){if(e){let n=t[e];if(!W(n))throw new Error(`schemaDsl.exportName '${e}' does not point to a schema() export.`);return n}for(let n of Object.values(t))if(W(n))return n;throw new Error("No schema() export found in schemaDsl entry module. Set schemaDsl.exportName to the correct export.")}async function Ke(t){let e=t.config.schemaDsl;if(!e)return;let n=e.namingStrategy??"camelToSnake",r=resolve(t.configDir,e.entry),a=resolve(t.configDir,e.outFile??resolve(t.outDirAbs,"schema.compiled.ts")),o=resolve(t.configDir,e.typesOutFile??resolve(t.outDirAbs,"schema.types.ts")),i=resolve(t.configDir,e.zodOutFile??resolve(t.outDirAbs,"schema.zod.ts")),l=await import(`${pathToFileURL(r).href}?t=${Date.now()}`),c=xr(l,e.exportName),d=cr(c);await Promise.all([mkdir(dirname(a),{recursive:true}),mkdir(dirname(o),{recursive:true}),mkdir(dirname(i),{recursive:true})]);let g=fr(d,n),u=yr(d),y=hr(d);return await Promise.all([Bun.write(a,g),Bun.write(o,u),Bun.write(i,y)]),{schemaPath:a,typesPath:o,zodPath:i,tableNames:Object.keys(d.tables)}}function vr(t){return t.replaceAll("\\","/")}function S(t,e){let n=vr(relative(t,e)).replace(/\.tsx?$/,"");return n.startsWith(".")?n:`./${n}`}var Rr=new Set([".ts",".tsx",".mts",".cts"]);async function Ye(t){let e=await readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=resolve(t,r.name);if(r.isDirectory()){n.push(...await Ye(a));continue}r.isFile()&&Rr.has(extname(r.name))&&n.push(a);}return n}function Q(t){return t.replace(/\.[cm]?tsx?$/,"")}function Ar(t,e){let n=t,r=false,a,o="unknown";for(;m.isCallExpression(n);){let i=n.expression;if(!m.isPropertyAccessExpression(i))break;let s=i.name.text;if(s==="optional"||s==="nullable")r=true,n=i.expression;else if(s==="default"){r=true;let l=n.arguments[0];l&&(m.isStringLiteral(l)||m.isNumericLiteral(l)?a=l.text:l.kind===m.SyntaxKind.TrueKeyword?a="true":l.kind===m.SyntaxKind.FalseKeyword&&(a="false")),n=i.expression;}else if(s==="string"||s==="uuid"||s==="email"||s==="url"){o="string";break}else if(s==="number"||s==="int"||s==="float"){o="number";break}else if(s==="boolean"){o="boolean";break}else n=i.expression;}return {name:e,type:o,optional:r,defaultValue:a}}function $r(t){if(!t||!m.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>m.isPropertyAssignment(r)&&m.isIdentifier(r.name)&&r.name.text==="args");if(!e||!m.isObjectLiteralExpression(e.initializer))return [];let n=[];for(let r of e.initializer.properties)!m.isPropertyAssignment(r)||!m.isIdentifier(r.name)||n.push(Ar(r.initializer,r.name.text));return n}function Nr(t){return m.isVariableStatement(t)?t.modifiers?.some(e=>e.kind===m.SyntaxKind.ExportKeyword)??false:false}function Xe(t){return m.isIdentifier(t)?t.text:m.isParenthesizedExpression(t)?Xe(t.expression):null}function qr(t){if(!t||!m.isObjectLiteralExpression(t))return [];let e=t.properties.find(r=>!m.isPropertyAssignment(r)||!m.isIdentifier(r.name)?false:r.name.text==="cronTrigger");if(!e||!m.isPropertyAssignment(e))return [];let n=e.initializer;return m.isStringLiteral(n)||m.isNoSubstitutionTemplateLiteral(n)?[n.text.trim()].filter(r=>r.length>0):m.isArrayLiteralExpression(n)?n.elements.map(r=>m.isStringLiteral(r)||m.isNoSubstitutionTemplateLiteral(r)?r.text.trim():"").filter(r=>r.length>0):[]}function Cr(t,e){let n=m.createSourceFile(e,t,m.ScriptTarget.Latest,true,m.ScriptKind.TS),r=[];for(let a of n.statements)if(Nr(a))for(let o of a.declarationList.declarations){if(!m.isIdentifier(o.name)||!o.initializer||!m.isCallExpression(o.initializer))continue;let i=Xe(o.initializer.expression);i!=="query"&&i!=="mutation"&&i!=="scheduler"&&i!=="cron"&&i!=="storageManager"||r.push({exportName:o.name.text,kind:i==="storageManager"?"storage":i,cronTriggers:i==="cron"?qr(o.initializer.arguments[0]):[],args:i==="query"||i==="mutation"?$r(o.initializer.arguments[0]):[]});}return r}function Ge(t,e,n){let r=e.replace(/\\/g,"/"),o=Q(r).split("/").filter(Boolean);return `/${[t,...o,n].filter(Boolean).map(s=>s.trim()).filter(s=>s.length>0).join("/")}`}function Pr(t,e){let n=t.replace(/\\/g,"/"),r=`${e}/`,a=n.indexOf(r);return a>=0?n.slice(a+r.length):n===e?"index.ts":n}function Je(t,e){let n=t.replace(/\\/g,"/"),a=Q(n).split("/").filter(Boolean),o=a[a.length-1]??"index";return [a.length>1?a[a.length-2]:"root",o,e].map(s=>s.trim()).filter(s=>s.length>0).join("/")}async function tn(t){let e=[],n=await Ye(t.scanDirAbs).catch(()=>[]);for(let a of n){let o=Bun.file(a);if(!await o.exists())continue;let i=await o.text(),s=relative(t.scanDirAbs,a),l=Cr(i,a),c=[{kind:"query",kindDirectory:"queries",exports:l.filter(d=>d.kind==="query")},{kind:"mutation",kindDirectory:"mutations",exports:l.filter(d=>d.kind==="mutation")},{kind:"scheduler",kindDirectory:"schedulers",exports:l.filter(d=>d.kind==="scheduler")},{kind:"cron",kindDirectory:"crons",exports:l.filter(d=>d.kind==="cron")},{kind:"storage",kindDirectory:"queries",exports:l.filter(d=>d.kind==="storage")}];for(let d of c){if(d.exports.length===0)continue;let g=Pr(s,d.kindDirectory);for(let u of d.exports){let y=d.kind==="query"||d.kind==="mutation"?Je(g,u.exportName):void 0,h=d.kind==="scheduler"||d.kind==="cron"?Je(g,u.exportName):void 0,f=d.kind==="query"||d.kind==="mutation"?[...Q(g).split("/").filter(Boolean),u.exportName]:void 0,b=d.kind==="query"?Ge("queries",g,u.exportName):d.kind==="mutation"?Ge("mutations",g,u.exportName):d.kind==="storage"?`/storage/managers/${u.exportName}`:`/${d.kindDirectory}/${h}`;e.push({kind:d.kind,exportName:u.exportName,filePath:a,importPath:S(t.outDirAbs,a),clientImportPath:S(resolve(t.outDirAbs,"client"),a),routePath:b,handlerName:y,clientSegments:f,taskName:h,cronTriggers:u.cronTriggers,args:u.args});}}}e.sort((a,o)=>a.routePath.localeCompare(o.routePath));let r=new Map;for(let a of e){let o=a.taskName?`task:${a.taskName}`:`route:${a.routePath}`,i=r.get(o);if(i)throw new Error(`Duplicate handler operation discovered: ${a.taskName??a.routePath} (${i} and ${a.filePath}#${a.exportName}).`);r.set(o,`${a.filePath}#${a.exportName}`);}return e}function Dr(t){let e=[],n="",r=0,a=0,o=0,i=false,s=false,l=false,c=false;for(let g=0;g<t.length;g+=1){let u=t[g];if(c){n+=u,c=false;continue}if(u==="\\"){n+=u,c=true;continue}if(!s&&!l&&u==="'"){i=!i,n+=u;continue}if(!i&&!l&&u==='"'){s=!s,n+=u;continue}if(!i&&!s&&u==="`"){l=!l,n+=u;continue}if(i||s||l){n+=u;continue}if(u==="("?r+=1:u===")"?r-=1:u==="{"?a+=1:u==="}"?a-=1:u==="["?o+=1:u==="]"&&(o-=1),u===","&&r===0&&a===0&&o===0){let y=n.trim();y.length>0&&e.push(y),n="";continue}n+=u;}let d=n.trim();return d.length>0&&e.push(d),e}function Or(t){let e=0,n=0,r=0,a=false,o=false,i=false,s=false;for(let l=0;l<t.length;l+=1){let c=t[l];if(s){s=false;continue}if(c==="\\"){s=true;continue}if(!o&&!i&&c==="'"){a=!a;continue}if(!a&&!i&&c==='"'){o=!o;continue}if(!a&&!o&&c==="`"){i=!i;continue}if(!(a||o||i)){if(c==="("){e+=1;continue}if(c===")"){e-=1;continue}if(c==="{"){n+=1;continue}if(c==="}"){n-=1;continue}if(c==="["){r+=1;continue}if(c==="]"){r-=1;continue}if(c===":"&&e===0&&n===0&&r===0)return l}}return -1}function Ir(t){let e=t.toLowerCase();return /mode\s*:\s*["'`](timestamp|timestamp_ms)["'`]/.test(e)?"date":/mode\s*:\s*["'`]boolean["'`]/.test(e)?"boolean":/\.(date|datetime|timestamp)\s*\(/.test(e)?"date":/\.(int|integer|real|numeric|decimal|float|double)\s*\(/.test(e)?"number":/\.(text|varchar|char)\s*\(/.test(e)?"string":/\.(boolean|bool)\s*\(/.test(e)?"boolean":"unknown"}function Mr(t){let e=Dr(t),n=[];for(let r of e){let a=Or(r);if(a===-1)continue;let o=r.slice(0,a).trim().replace(/^['"]|['"]$/g,"");if(!o)continue;let i=r.slice(a+1).trim(),s=/\.primarykey\s*\(/i.test(i),l=/autoincrement\s*:\s*true/i.test(i),c=/\.default\s*\(/i.test(i),g=!/\.notnull\s*\(/i.test(i)||c||l;n.push({name:o,expression:i,type:Ir(i),optional:g,primaryKey:s,autoIncrement:l});}return n}function Fr(t){let e=/export\s+const\s+(\w+)\s*=\s*table\s*\(\s*["'`]([^"'`]+)["'`]/g,n=[],r=(o,i)=>{let s=0,l=false,c=false,d=false,g=false;for(let u=i;u<o.length;u+=1){let y=o[u];if(g){g=false;continue}if(y==="\\"){g=true;continue}if(!c&&!d&&y==="'"){l=!l;continue}if(!l&&!d&&y==='"'){c=!c;continue}if(!l&&!c&&y==="`"){d=!d;continue}if(!(l||c||d)){if(y==="{"){s+=1;continue}if(y==="}"&&(s-=1,s===0))return u}}return -1},a=e.exec(t);for(;a;){let o=a[1],i=a[2],s=t.indexOf("{",e.lastIndex);if(s===-1){a=e.exec(t);continue}let l=r(t,s);if(l===-1){a=e.exec(t);continue}let c=t.slice(s+1,l);n.push({exportName:o,tableName:i,columns:Mr(c)}),a=e.exec(t);}return n}async function nn(t){let e=await readdir(t,{withFileTypes:true}),n=[];for(let r of e){if(r.name.startsWith(".")||r.name==="node_modules"||r.name==="_generated")continue;let a=resolve(t,r.name);if(r.isDirectory()){n.push(...await nn(a));continue}r.isFile()&&r.name==="schema.ts"&&n.push(a);}return n}async function rn(t,e=[]){let n=await nn(t.scanDirAbs).catch(()=>[]),r=resolve(t.configDir,"schema.ts"),a=[...e,...n.length?n:[r]];for(let o of a){let i=Bun.file(o);if(!await i.exists())continue;let s=await i.text(),l=Fr(s);if(l.length>0)return {schemaPath:o,tables:l}}throw new Error(`Unable to discover schema.ts under scanDir (${t.scanDirAbs}) or fallback (${r}).`)}function jr(t,e){let n=relative(t,e).replace(/\\/g,"/");return n.startsWith(".")?n:`./${n}`}async function an(t){let{outDirAbs:e,wranglerOutDirAbs:n,config:r,configPath:a,configDir:o}=t,i=S(e,a),s=resolve(e,"client"),l=S(s,a);await Promise.all([mkdir(e,{recursive:true}),mkdir(s,{recursive:true}),mkdir(n,{recursive:true})]);let c=resolve(e,"server.ts"),d=resolve(e,"client.ts"),g=resolve(e,"auth.config.ts"),u=resolve(e,"auth.schema.ts"),y=resolve(e,"drizzle.config.ts"),h=resolve(n,"wrangler.json"),f=await Ke(t),b=await rn(t,f?[f.schemaPath]:[]),R=S(e,b.schemaPath),v=await tn(t),fn=Yt(r.auth.basePath,r.database[0].binding,r.kv[0]?.binding,r.scheduler.binding,r.r2[0]?.binding,r.realtime.binding,r.realtime.objectName,r.realtime.subscribePath,r.realtime.websocketPath,r.realtime.protocol),hn=rt(l,v),bn=F(R,v,r.r2[0]?.binding),yn=J(i),xn=f?[jr(o,f.schemaPath),...r.schema.filter(k=>!/(^|\/)schema\.ts$/.test(k))]:r.schema,wn=at(xn),vn=te(t,v),kn=Ve(R,b,v),Tn=resolve(e,"admin.routes.ts"),Sn=bn.map(k=>Bun.write(resolve(e,k.relativePath),k.source)),Rn=hn.map(k=>Bun.write(resolve(e,k.relativePath),k.source));await Promise.all([Bun.write(c,fn),Bun.write(d,`export * from "./client/index";
|
|
7500
7500
|
`),...Rn,...Sn,Bun.write(g,yn),Bun.write(u,""),Bun.write(y,wn),Bun.write(h,`${JSON.stringify(vn,null,2)}
|
|
7501
|
-
`),Bun.write(Tn,kn)]);let
|
|
7501
|
+
`),Bun.write(Tn,kn)]);let D=relative(o,g).replace(/\\/g,"/"),An=D.startsWith(".")?D:`./${D}`,O=relative(o,u).replace(/\\/g,"/"),$n=O.startsWith(".")?O:`./${O}`,G=await Bun.spawn(["npx","@better-auth/cli","generate","--config",An,"--output",$n,"--yes"],{cwd:o,stdout:"inherit",stderr:"inherit"}).exited;if(G!==0)throw new Error(`better-auth generation failed with exit code ${G}`)}var on=z$1.object({binding:z$1.string().min(1),databaseName:z$1.string().min(1),databaseId:z$1.string().min(1),previewDatabaseId:z$1.string().min(1).optional(),migrationsDir:z$1.string().min(1).optional()}).strict(),sn=z$1.object({binding:z$1.string().min(1),id:z$1.string().min(1),previewId:z$1.string().min(1).optional()}).strict(),ln=z$1.object({binding:z$1.string().min(1),bucketName:z$1.string().min(1),previewBucketName:z$1.string().min(1).optional(),jurisdiction:z$1.string().min(1).optional()}).strict(),cn=z$1.object({enabled:z$1.boolean().optional(),binding:z$1.string().min(1).optional(),queue:z$1.string().min(1).optional()}).strict(),zr=z$1.object({enabled:z$1.boolean().optional(),binding:z$1.string().min(1).optional(),className:z$1.string().min(1).optional(),objectName:z$1.string().min(1).optional(),subscribePath:z$1.string().min(1).optional(),websocketPath:z$1.string().min(1).optional(),protocol:z$1.string().min(1).optional()}).strict(),Wr=z$1.object({scanDir:z$1.string().min(1),outDir:z$1.string().min(1),wranglerOutDir:z$1.string().min(1).optional(),wranglerOutPath:z$1.string().min(1).optional(),schema:z$1.array(z$1.string()).min(1),schemaDsl:z$1.object({entry:z$1.string().min(1),exportName:z$1.string().min(1).optional(),outFile:z$1.string().min(1).optional(),typesOutFile:z$1.string().min(1).optional(),zodOutFile:z$1.string().min(1).optional(),namingStrategy:z$1.literal("camelToSnake").optional()}).strict().optional(),database:z$1.union([on,z$1.array(on).min(1)]),kv:z$1.union([sn,z$1.array(sn)]).optional(),r2:z$1.union([ln,z$1.array(ln)]).optional(),auth:z$1.object({enabled:z$1.boolean(),basePath:z$1.string().min(1),options:z$1.custom(t=>typeof t=="object"&&t!==null),clientOptions:z$1.custom(t=>typeof t=="object"&&t!==null)}).strict(),scheduler:cn.optional(),realtime:zr.optional(),wranglerOverrides:z$1.record(z$1.string(),z$1.unknown()).optional()}).strict();function un(t){return typeof t=="object"&&t!==null}function Lr(t){let e=un(t.wranglerOverrides)?t.wranglerOverrides.scheduler:void 0,n=cn.safeParse(e);return n.success?n.data:{}}function Ur(t){if(!un(t)||!("scheduler"in t))return t;let{scheduler:e,...n}=t;return n}function Qr(t){let n={...Lr(t)??{},...t.scheduler??{}},r=t.realtime??{};return {...t,database:Array.isArray(t.database)?t.database:[t.database],kv:t.kv?Array.isArray(t.kv)?t.kv:[t.kv]:[],r2:t.r2?Array.isArray(t.r2)?t.r2:[t.r2]:[],scheduler:{enabled:n.enabled??true,binding:n.binding??"APPFLARE_SCHEDULER_QUEUE",queue:n.queue},realtime:{enabled:r.enabled??true,binding:r.binding??"APPFLARE_REALTIME",className:r.className??"AppflareRealtimeDurableObject",objectName:r.objectName??"global",subscribePath:r.subscribePath??"/realtime/subscribe",websocketPath:r.websocketPath??"/realtime/ws",protocol:r.protocol??"appflare.realtime.v1"},wranglerOverrides:Ur(t.wranglerOverrides),wranglerOutDir:t.wranglerOutDir??t.wranglerOutPath??t.outDir}}async function $(t){let e=isAbsolute(t??"")?t:resolve(process.cwd(),t??"appflare.config.ts"),n=dirname(e),o=(await import(pathToFileURL(e).href)).default,i=Wr.parse(o),s=Qr(i);return {configPath:e,configDir:n,scanDirAbs:resolve(n,s.scanDir),outDirAbs:resolve(n,s.outDir),wranglerOutDirAbs:resolve(n,s.wranglerOutDir),config:s}}function Jr(t){let e=t;for(;;){if(existsSync(resolve(e,"package.json")))return e;let n=dirname(e);if(n===e)return t;e=n;}}async function E(t){let e=await $(t);if(await an(e),e.wranglerOutDirAbs===e.outDirAbs){process.stdout.write(`\u2705 Generated artifacts in ${e.outDirAbs}
|
|
7502
7502
|
`);return}process.stdout.write(`\u2705 Generated server/client in ${e.outDirAbs} and wrangler.json in ${e.wranglerOutDirAbs}
|
|
7503
7503
|
`);}async function pn(t,e=false){if(await E(t),!e)return;let n=await $(t),r=false,a=false,o=async()=>{if(r){a=true;return}r=true;try{await E(t);}catch(s){process.stderr.write(`\u274C Build failed: ${s.message}
|
|
7504
7504
|
`);}finally{r=false,a&&(a=false,await o());}};_r.watch(n.scanDirAbs,{ignoreInitial:true}).on("all",async(s,l)=>{process.stdout.write(`\u{1F504} Change detected: ${l}
|
package/dist/index.d.mts
CHANGED
|
@@ -91,12 +91,16 @@ type ColumnBuilderOptions = {
|
|
|
91
91
|
type PrimaryKeyOptions = {
|
|
92
92
|
autoIncrement?: boolean;
|
|
93
93
|
};
|
|
94
|
+
type ForeignKeyAction = "cascade" | "set null" | "set default" | "restrict" | "no action";
|
|
94
95
|
type RelationOneOptions = {
|
|
95
96
|
referenceField?: string;
|
|
96
97
|
field?: string;
|
|
97
98
|
fkType?: ColumnType;
|
|
98
99
|
sqlName?: string;
|
|
99
100
|
notNull?: boolean;
|
|
101
|
+
nullable?: boolean;
|
|
102
|
+
onDelete?: ForeignKeyAction;
|
|
103
|
+
onUpdate?: ForeignKeyAction;
|
|
100
104
|
};
|
|
101
105
|
type RelationManyOptions = {
|
|
102
106
|
referenceField?: string;
|
|
@@ -104,6 +108,9 @@ type RelationManyOptions = {
|
|
|
104
108
|
fkType?: ColumnType;
|
|
105
109
|
sqlName?: string;
|
|
106
110
|
notNull?: boolean;
|
|
111
|
+
nullable?: boolean;
|
|
112
|
+
onDelete?: ForeignKeyAction;
|
|
113
|
+
onUpdate?: ForeignKeyAction;
|
|
107
114
|
};
|
|
108
115
|
type ColumnReference = {
|
|
109
116
|
table: string;
|
|
@@ -115,8 +122,11 @@ type ColumnDefinition = {
|
|
|
115
122
|
sqlName?: string;
|
|
116
123
|
length?: number;
|
|
117
124
|
notNull?: boolean;
|
|
125
|
+
nullable?: boolean;
|
|
118
126
|
primaryKey?: boolean;
|
|
119
127
|
autoIncrement?: boolean;
|
|
128
|
+
/** When true the column stores a UUID generated at runtime (string type). */
|
|
129
|
+
uuidPrimaryKey?: boolean;
|
|
120
130
|
unique?: true | {
|
|
121
131
|
name?: string;
|
|
122
132
|
};
|
|
@@ -124,6 +134,8 @@ type ColumnDefinition = {
|
|
|
124
134
|
name?: string;
|
|
125
135
|
};
|
|
126
136
|
sqlDefault?: unknown;
|
|
137
|
+
/** When true, the SQL column gets DEFAULT CURRENT_TIMESTAMP and runtime inserts use `new Date()`. */
|
|
138
|
+
nowDefault?: boolean;
|
|
127
139
|
runtimeDefaultFn?: () => unknown;
|
|
128
140
|
references?: ColumnReference;
|
|
129
141
|
};
|
|
@@ -136,6 +148,9 @@ type OneRelationDefinition = {
|
|
|
136
148
|
fkType?: ColumnType;
|
|
137
149
|
sqlName?: string;
|
|
138
150
|
notNull?: boolean;
|
|
151
|
+
nullable?: boolean;
|
|
152
|
+
onDelete?: ForeignKeyAction;
|
|
153
|
+
onUpdate?: ForeignKeyAction;
|
|
139
154
|
};
|
|
140
155
|
type ManyRelationDefinition = {
|
|
141
156
|
kind: "relation";
|
|
@@ -146,6 +161,9 @@ type ManyRelationDefinition = {
|
|
|
146
161
|
fkType?: ColumnType;
|
|
147
162
|
sqlName?: string;
|
|
148
163
|
notNull?: boolean;
|
|
164
|
+
nullable?: boolean;
|
|
165
|
+
onDelete?: ForeignKeyAction;
|
|
166
|
+
onUpdate?: ForeignKeyAction;
|
|
149
167
|
};
|
|
150
168
|
type RelationDefinition = OneRelationDefinition | ManyRelationDefinition;
|
|
151
169
|
type TableOptions = {
|
|
@@ -168,11 +186,18 @@ declare class ColumnBuilder {
|
|
|
168
186
|
private with;
|
|
169
187
|
sql(name: string): ColumnBuilder;
|
|
170
188
|
notNull(): ColumnBuilder;
|
|
189
|
+
nullable(): ColumnBuilder;
|
|
171
190
|
primaryKey(options?: PrimaryKeyOptions): ColumnBuilder;
|
|
172
191
|
unique(name?: string): ColumnBuilder;
|
|
173
192
|
index(name?: string): ColumnBuilder;
|
|
174
193
|
default(value: unknown): ColumnBuilder;
|
|
175
194
|
defaultFn(fn: () => unknown): ColumnBuilder;
|
|
195
|
+
/**
|
|
196
|
+
* Shorthand for date columns that should default to the current timestamp.
|
|
197
|
+
* Sets SQL `DEFAULT CURRENT_TIMESTAMP` (via `nowDefault`) and
|
|
198
|
+
* a runtime default of `new Date()`.
|
|
199
|
+
*/
|
|
200
|
+
defaultNow(): ColumnBuilder;
|
|
176
201
|
references(table: string, column?: string): ColumnBuilder;
|
|
177
202
|
toDefinition(): ColumnDefinition;
|
|
178
203
|
}
|
|
@@ -184,6 +209,12 @@ declare const v: {
|
|
|
184
209
|
string: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
185
210
|
boolean: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
186
211
|
date: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
212
|
+
/**
|
|
213
|
+
* UUID primary key column.
|
|
214
|
+
* Stored as a string, marked as primary key and auto-populated with
|
|
215
|
+
* `crypto.randomUUID()` at runtime (no SQL sequence).
|
|
216
|
+
*/
|
|
217
|
+
uuid: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
187
218
|
one: (targetTable: string, fieldOrOptions?: string | RelationOneOptions, options?: RelationOneOptions) => OneRelationDefinition;
|
|
188
219
|
many: (targetTable: string, fieldOrOptions?: string | RelationManyOptions, options?: RelationManyOptions) => ManyRelationDefinition;
|
|
189
220
|
};
|
package/dist/index.d.ts
CHANGED
|
@@ -91,12 +91,16 @@ type ColumnBuilderOptions = {
|
|
|
91
91
|
type PrimaryKeyOptions = {
|
|
92
92
|
autoIncrement?: boolean;
|
|
93
93
|
};
|
|
94
|
+
type ForeignKeyAction = "cascade" | "set null" | "set default" | "restrict" | "no action";
|
|
94
95
|
type RelationOneOptions = {
|
|
95
96
|
referenceField?: string;
|
|
96
97
|
field?: string;
|
|
97
98
|
fkType?: ColumnType;
|
|
98
99
|
sqlName?: string;
|
|
99
100
|
notNull?: boolean;
|
|
101
|
+
nullable?: boolean;
|
|
102
|
+
onDelete?: ForeignKeyAction;
|
|
103
|
+
onUpdate?: ForeignKeyAction;
|
|
100
104
|
};
|
|
101
105
|
type RelationManyOptions = {
|
|
102
106
|
referenceField?: string;
|
|
@@ -104,6 +108,9 @@ type RelationManyOptions = {
|
|
|
104
108
|
fkType?: ColumnType;
|
|
105
109
|
sqlName?: string;
|
|
106
110
|
notNull?: boolean;
|
|
111
|
+
nullable?: boolean;
|
|
112
|
+
onDelete?: ForeignKeyAction;
|
|
113
|
+
onUpdate?: ForeignKeyAction;
|
|
107
114
|
};
|
|
108
115
|
type ColumnReference = {
|
|
109
116
|
table: string;
|
|
@@ -115,8 +122,11 @@ type ColumnDefinition = {
|
|
|
115
122
|
sqlName?: string;
|
|
116
123
|
length?: number;
|
|
117
124
|
notNull?: boolean;
|
|
125
|
+
nullable?: boolean;
|
|
118
126
|
primaryKey?: boolean;
|
|
119
127
|
autoIncrement?: boolean;
|
|
128
|
+
/** When true the column stores a UUID generated at runtime (string type). */
|
|
129
|
+
uuidPrimaryKey?: boolean;
|
|
120
130
|
unique?: true | {
|
|
121
131
|
name?: string;
|
|
122
132
|
};
|
|
@@ -124,6 +134,8 @@ type ColumnDefinition = {
|
|
|
124
134
|
name?: string;
|
|
125
135
|
};
|
|
126
136
|
sqlDefault?: unknown;
|
|
137
|
+
/** When true, the SQL column gets DEFAULT CURRENT_TIMESTAMP and runtime inserts use `new Date()`. */
|
|
138
|
+
nowDefault?: boolean;
|
|
127
139
|
runtimeDefaultFn?: () => unknown;
|
|
128
140
|
references?: ColumnReference;
|
|
129
141
|
};
|
|
@@ -136,6 +148,9 @@ type OneRelationDefinition = {
|
|
|
136
148
|
fkType?: ColumnType;
|
|
137
149
|
sqlName?: string;
|
|
138
150
|
notNull?: boolean;
|
|
151
|
+
nullable?: boolean;
|
|
152
|
+
onDelete?: ForeignKeyAction;
|
|
153
|
+
onUpdate?: ForeignKeyAction;
|
|
139
154
|
};
|
|
140
155
|
type ManyRelationDefinition = {
|
|
141
156
|
kind: "relation";
|
|
@@ -146,6 +161,9 @@ type ManyRelationDefinition = {
|
|
|
146
161
|
fkType?: ColumnType;
|
|
147
162
|
sqlName?: string;
|
|
148
163
|
notNull?: boolean;
|
|
164
|
+
nullable?: boolean;
|
|
165
|
+
onDelete?: ForeignKeyAction;
|
|
166
|
+
onUpdate?: ForeignKeyAction;
|
|
149
167
|
};
|
|
150
168
|
type RelationDefinition = OneRelationDefinition | ManyRelationDefinition;
|
|
151
169
|
type TableOptions = {
|
|
@@ -168,11 +186,18 @@ declare class ColumnBuilder {
|
|
|
168
186
|
private with;
|
|
169
187
|
sql(name: string): ColumnBuilder;
|
|
170
188
|
notNull(): ColumnBuilder;
|
|
189
|
+
nullable(): ColumnBuilder;
|
|
171
190
|
primaryKey(options?: PrimaryKeyOptions): ColumnBuilder;
|
|
172
191
|
unique(name?: string): ColumnBuilder;
|
|
173
192
|
index(name?: string): ColumnBuilder;
|
|
174
193
|
default(value: unknown): ColumnBuilder;
|
|
175
194
|
defaultFn(fn: () => unknown): ColumnBuilder;
|
|
195
|
+
/**
|
|
196
|
+
* Shorthand for date columns that should default to the current timestamp.
|
|
197
|
+
* Sets SQL `DEFAULT CURRENT_TIMESTAMP` (via `nowDefault`) and
|
|
198
|
+
* a runtime default of `new Date()`.
|
|
199
|
+
*/
|
|
200
|
+
defaultNow(): ColumnBuilder;
|
|
176
201
|
references(table: string, column?: string): ColumnBuilder;
|
|
177
202
|
toDefinition(): ColumnDefinition;
|
|
178
203
|
}
|
|
@@ -184,6 +209,12 @@ declare const v: {
|
|
|
184
209
|
string: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
185
210
|
boolean: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
186
211
|
date: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
212
|
+
/**
|
|
213
|
+
* UUID primary key column.
|
|
214
|
+
* Stored as a string, marked as primary key and auto-populated with
|
|
215
|
+
* `crypto.randomUUID()` at runtime (no SQL sequence).
|
|
216
|
+
*/
|
|
217
|
+
uuid: (options?: ColumnBuilderOptions) => ColumnBuilder;
|
|
187
218
|
one: (targetTable: string, fieldOrOptions?: string | RelationOneOptions, options?: RelationOneOptions) => OneRelationDefinition;
|
|
188
219
|
many: (targetTable: string, fieldOrOptions?: string | RelationManyOptions, options?: RelationManyOptions) => ManyRelationDefinition;
|
|
189
220
|
};
|
package/dist/index.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
'use strict';var o=class n{definition;constructor(e,t={}){if(typeof e=="string"){this.definition={kind:"column",type:e,sqlName:t.sqlName,length:t.length};return}this.definition={...e};}with(e){return new n({...this.definition,...e})}sql(e){return this.with({sqlName:e})}notNull(){return this.with({notNull:true})}primaryKey(e={}){return this.with({primaryKey:true,autoIncrement:e.autoIncrement??this.definition.autoIncrement})}unique(e){return this.with({unique:e?{name:e}:true})}index(e){return this.with({index:e?{name:e}:true})}default(e){return this.with({sqlDefault:e})}defaultFn(e){return this.with({runtimeDefaultFn:e})}references(e,t="id"){return this.with({references:{table:e,column:t}})}toDefinition(){return {...this.definition}}};function a(n,e={}){let t={},l={};for(let[i,r]of Object.entries(n)){if(r instanceof o){t[i]=r.toDefinition();continue}if(r.kind==="relation"){l[i]=r;continue}throw new Error(`Invalid table field '${i}'. Use column builders or relation helpers.`)}return {kind:"table",sqlName:e.sqlName,columns:t,relations:l}}function u(n){return {kind:"schema",tables:n}}function s(n){if(typeof n!="object"||n===null)return false;let e=n;return e.kind==="schema"&&typeof e.tables=="object"}
|
|
1
|
+
'use strict';var o=class n{definition;constructor(e,t={}){if(typeof e=="string"){this.definition={kind:"column",type:e,sqlName:t.sqlName,length:t.length};return}this.definition={...e};}with(e){return new n({...this.definition,...e})}sql(e){return this.with({sqlName:e})}notNull(){return this.with({notNull:true,nullable:false})}nullable(){return this.with({nullable:true,notNull:false})}primaryKey(e={}){return this.with({primaryKey:true,autoIncrement:e.autoIncrement??this.definition.autoIncrement})}unique(e){return this.with({unique:e?{name:e}:true})}index(e){return this.with({index:e?{name:e}:true})}default(e){return this.with({sqlDefault:e})}defaultFn(e){return this.with({runtimeDefaultFn:e})}defaultNow(){return this.with({nowDefault:true,runtimeDefaultFn:()=>new Date})}references(e,t="id"){return this.with({references:{table:e,column:t}})}toDefinition(){return {...this.definition}}};function a(n,e={}){let t={},l={};for(let[i,r]of Object.entries(n)){if(r instanceof o){t[i]=r.toDefinition();continue}if(r.kind==="relation"){l[i]=r;continue}throw new Error(`Invalid table field '${i}'. Use column builders or relation helpers.`)}return {kind:"table",sqlName:e.sqlName,columns:t,relations:l}}function u(n){return {kind:"schema",tables:n}}function s(n){if(typeof n!="object"||n===null)return false;let e=n;return e.kind==="schema"&&typeof e.tables=="object"}function p(n,e,t={}){let l=typeof e=="string"?e:void 0,i=typeof e=="string"?t:e??t;return {kind:"relation",relation:"one",targetTable:n,field:i.field??l,referenceField:i.referenceField,fkType:i.fkType,sqlName:i.sqlName,notNull:i.notNull,nullable:i.nullable,onDelete:i.onDelete,onUpdate:i.onUpdate}}function f(n,e,t={}){let l=typeof e=="string"?e:void 0,i=typeof e=="string"?t:e??t;return {kind:"relation",relation:"many",targetTable:n,field:i.field??l,referenceField:i.referenceField,fkType:i.fkType,sqlName:i.sqlName,notNull:i.notNull,nullable:i.nullable,onDelete:i.onDelete,onUpdate:i.onUpdate}}var m={int:(n={})=>new o("int",n),string:(n={})=>new o("string",n),boolean:(n={})=>new o("boolean",n),date:(n={})=>new o("date",n),uuid:(n={})=>new o({kind:"column",type:"string",sqlName:n.sqlName,length:n.length??36,primaryKey:true,uuidPrimaryKey:true,runtimeDefaultFn:()=>crypto.randomUUID()}),one:(n,e,t={})=>p(n,e,t),many:(n,e,t={})=>f(n,e,t)};exports.isSchemaDefinition=s;exports.schema=u;exports.table=a;exports.v=m;
|
package/dist/index.mjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var o=class n{definition;constructor(e,t={}){if(typeof e=="string"){this.definition={kind:"column",type:e,sqlName:t.sqlName,length:t.length};return}this.definition={...e};}with(e){return new n({...this.definition,...e})}sql(e){return this.with({sqlName:e})}notNull(){return this.with({notNull:true})}primaryKey(e={}){return this.with({primaryKey:true,autoIncrement:e.autoIncrement??this.definition.autoIncrement})}unique(e){return this.with({unique:e?{name:e}:true})}index(e){return this.with({index:e?{name:e}:true})}default(e){return this.with({sqlDefault:e})}defaultFn(e){return this.with({runtimeDefaultFn:e})}references(e,t="id"){return this.with({references:{table:e,column:t}})}toDefinition(){return {...this.definition}}};function a(n,e={}){let t={},l={};for(let[i,r]of Object.entries(n)){if(r instanceof o){t[i]=r.toDefinition();continue}if(r.kind==="relation"){l[i]=r;continue}throw new Error(`Invalid table field '${i}'. Use column builders or relation helpers.`)}return {kind:"table",sqlName:e.sqlName,columns:t,relations:l}}function u(n){return {kind:"schema",tables:n}}function s(n){if(typeof n!="object"||n===null)return false;let e=n;return e.kind==="schema"&&typeof e.tables=="object"}
|
|
1
|
+
var o=class n{definition;constructor(e,t={}){if(typeof e=="string"){this.definition={kind:"column",type:e,sqlName:t.sqlName,length:t.length};return}this.definition={...e};}with(e){return new n({...this.definition,...e})}sql(e){return this.with({sqlName:e})}notNull(){return this.with({notNull:true,nullable:false})}nullable(){return this.with({nullable:true,notNull:false})}primaryKey(e={}){return this.with({primaryKey:true,autoIncrement:e.autoIncrement??this.definition.autoIncrement})}unique(e){return this.with({unique:e?{name:e}:true})}index(e){return this.with({index:e?{name:e}:true})}default(e){return this.with({sqlDefault:e})}defaultFn(e){return this.with({runtimeDefaultFn:e})}defaultNow(){return this.with({nowDefault:true,runtimeDefaultFn:()=>new Date})}references(e,t="id"){return this.with({references:{table:e,column:t}})}toDefinition(){return {...this.definition}}};function a(n,e={}){let t={},l={};for(let[i,r]of Object.entries(n)){if(r instanceof o){t[i]=r.toDefinition();continue}if(r.kind==="relation"){l[i]=r;continue}throw new Error(`Invalid table field '${i}'. Use column builders or relation helpers.`)}return {kind:"table",sqlName:e.sqlName,columns:t,relations:l}}function u(n){return {kind:"schema",tables:n}}function s(n){if(typeof n!="object"||n===null)return false;let e=n;return e.kind==="schema"&&typeof e.tables=="object"}function p(n,e,t={}){let l=typeof e=="string"?e:void 0,i=typeof e=="string"?t:e??t;return {kind:"relation",relation:"one",targetTable:n,field:i.field??l,referenceField:i.referenceField,fkType:i.fkType,sqlName:i.sqlName,notNull:i.notNull,nullable:i.nullable,onDelete:i.onDelete,onUpdate:i.onUpdate}}function f(n,e,t={}){let l=typeof e=="string"?e:void 0,i=typeof e=="string"?t:e??t;return {kind:"relation",relation:"many",targetTable:n,field:i.field??l,referenceField:i.referenceField,fkType:i.fkType,sqlName:i.sqlName,notNull:i.notNull,nullable:i.nullable,onDelete:i.onDelete,onUpdate:i.onUpdate}}var m={int:(n={})=>new o("int",n),string:(n={})=>new o("string",n),boolean:(n={})=>new o("boolean",n),date:(n={})=>new o("date",n),uuid:(n={})=>new o({kind:"column",type:"string",sqlName:n.sqlName,length:n.length??36,primaryKey:true,uuidPrimaryKey:true,runtimeDefaultFn:()=>crypto.randomUUID()}),one:(n,e,t={})=>p(n,e,t),many:(n,e,t={})=>f(n,e,t)};export{s as isSchemaDefinition,u as schema,a as table,m as v};
|
package/package.json
CHANGED
package/schema.ts
CHANGED
|
@@ -9,12 +9,22 @@ export type PrimaryKeyOptions = {
|
|
|
9
9
|
autoIncrement?: boolean;
|
|
10
10
|
};
|
|
11
11
|
|
|
12
|
+
export type ForeignKeyAction =
|
|
13
|
+
| "cascade"
|
|
14
|
+
| "set null"
|
|
15
|
+
| "set default"
|
|
16
|
+
| "restrict"
|
|
17
|
+
| "no action";
|
|
18
|
+
|
|
12
19
|
export type RelationOneOptions = {
|
|
13
20
|
referenceField?: string;
|
|
14
21
|
field?: string;
|
|
15
22
|
fkType?: ColumnType;
|
|
16
23
|
sqlName?: string;
|
|
17
24
|
notNull?: boolean;
|
|
25
|
+
nullable?: boolean;
|
|
26
|
+
onDelete?: ForeignKeyAction;
|
|
27
|
+
onUpdate?: ForeignKeyAction;
|
|
18
28
|
};
|
|
19
29
|
|
|
20
30
|
export type RelationManyOptions = {
|
|
@@ -23,6 +33,9 @@ export type RelationManyOptions = {
|
|
|
23
33
|
fkType?: ColumnType;
|
|
24
34
|
sqlName?: string;
|
|
25
35
|
notNull?: boolean;
|
|
36
|
+
nullable?: boolean;
|
|
37
|
+
onDelete?: ForeignKeyAction;
|
|
38
|
+
onUpdate?: ForeignKeyAction;
|
|
26
39
|
};
|
|
27
40
|
|
|
28
41
|
export type ColumnReference = {
|
|
@@ -36,11 +49,16 @@ export type ColumnDefinition = {
|
|
|
36
49
|
sqlName?: string;
|
|
37
50
|
length?: number;
|
|
38
51
|
notNull?: boolean;
|
|
52
|
+
nullable?: boolean;
|
|
39
53
|
primaryKey?: boolean;
|
|
40
54
|
autoIncrement?: boolean;
|
|
55
|
+
/** When true the column stores a UUID generated at runtime (string type). */
|
|
56
|
+
uuidPrimaryKey?: boolean;
|
|
41
57
|
unique?: true | { name?: string };
|
|
42
58
|
index?: true | { name?: string };
|
|
43
59
|
sqlDefault?: unknown;
|
|
60
|
+
/** When true, the SQL column gets DEFAULT CURRENT_TIMESTAMP and runtime inserts use `new Date()`. */
|
|
61
|
+
nowDefault?: boolean;
|
|
44
62
|
runtimeDefaultFn?: () => unknown;
|
|
45
63
|
references?: ColumnReference;
|
|
46
64
|
};
|
|
@@ -54,6 +72,9 @@ export type OneRelationDefinition = {
|
|
|
54
72
|
fkType?: ColumnType;
|
|
55
73
|
sqlName?: string;
|
|
56
74
|
notNull?: boolean;
|
|
75
|
+
nullable?: boolean;
|
|
76
|
+
onDelete?: ForeignKeyAction;
|
|
77
|
+
onUpdate?: ForeignKeyAction;
|
|
57
78
|
};
|
|
58
79
|
|
|
59
80
|
export type ManyRelationDefinition = {
|
|
@@ -65,6 +86,9 @@ export type ManyRelationDefinition = {
|
|
|
65
86
|
fkType?: ColumnType;
|
|
66
87
|
sqlName?: string;
|
|
67
88
|
notNull?: boolean;
|
|
89
|
+
nullable?: boolean;
|
|
90
|
+
onDelete?: ForeignKeyAction;
|
|
91
|
+
onUpdate?: ForeignKeyAction;
|
|
68
92
|
};
|
|
69
93
|
|
|
70
94
|
export type RelationDefinition = OneRelationDefinition | ManyRelationDefinition;
|
|
@@ -121,7 +145,11 @@ export class ColumnBuilder {
|
|
|
121
145
|
}
|
|
122
146
|
|
|
123
147
|
public notNull(): ColumnBuilder {
|
|
124
|
-
return this.with({ notNull: true });
|
|
148
|
+
return this.with({ notNull: true, nullable: false });
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
public nullable(): ColumnBuilder {
|
|
152
|
+
return this.with({ nullable: true, notNull: false });
|
|
125
153
|
}
|
|
126
154
|
|
|
127
155
|
public primaryKey(options: PrimaryKeyOptions = {}): ColumnBuilder {
|
|
@@ -147,6 +175,18 @@ export class ColumnBuilder {
|
|
|
147
175
|
return this.with({ runtimeDefaultFn: fn });
|
|
148
176
|
}
|
|
149
177
|
|
|
178
|
+
/**
|
|
179
|
+
* Shorthand for date columns that should default to the current timestamp.
|
|
180
|
+
* Sets SQL `DEFAULT CURRENT_TIMESTAMP` (via `nowDefault`) and
|
|
181
|
+
* a runtime default of `new Date()`.
|
|
182
|
+
*/
|
|
183
|
+
public defaultNow(): ColumnBuilder {
|
|
184
|
+
return this.with({
|
|
185
|
+
nowDefault: true,
|
|
186
|
+
runtimeDefaultFn: () => new Date(),
|
|
187
|
+
});
|
|
188
|
+
}
|
|
189
|
+
|
|
150
190
|
public references(table: string, column = "id"): ColumnBuilder {
|
|
151
191
|
return this.with({ references: { table, column } });
|
|
152
192
|
}
|
|
@@ -204,6 +244,62 @@ export function isSchemaDefinition(value: unknown): value is SchemaDefinition {
|
|
|
204
244
|
return candidate.kind === "schema" && typeof candidate.tables === "object";
|
|
205
245
|
}
|
|
206
246
|
|
|
247
|
+
// ---------------------------------------------------------------------------
|
|
248
|
+
// Relation builder helpers
|
|
249
|
+
// ---------------------------------------------------------------------------
|
|
250
|
+
|
|
251
|
+
function buildOneRelation(
|
|
252
|
+
targetTable: string,
|
|
253
|
+
fieldOrOptions?: string | RelationOneOptions,
|
|
254
|
+
options: RelationOneOptions = {},
|
|
255
|
+
): OneRelationDefinition {
|
|
256
|
+
const field = typeof fieldOrOptions === "string" ? fieldOrOptions : undefined;
|
|
257
|
+
const mergedOptions =
|
|
258
|
+
typeof fieldOrOptions === "string" ? options : (fieldOrOptions ?? options);
|
|
259
|
+
|
|
260
|
+
return {
|
|
261
|
+
kind: "relation",
|
|
262
|
+
relation: "one",
|
|
263
|
+
targetTable,
|
|
264
|
+
field: mergedOptions.field ?? field,
|
|
265
|
+
referenceField: mergedOptions.referenceField,
|
|
266
|
+
fkType: mergedOptions.fkType,
|
|
267
|
+
sqlName: mergedOptions.sqlName,
|
|
268
|
+
notNull: mergedOptions.notNull,
|
|
269
|
+
nullable: mergedOptions.nullable,
|
|
270
|
+
onDelete: mergedOptions.onDelete,
|
|
271
|
+
onUpdate: mergedOptions.onUpdate,
|
|
272
|
+
};
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
function buildManyRelation(
|
|
276
|
+
targetTable: string,
|
|
277
|
+
fieldOrOptions?: string | RelationManyOptions,
|
|
278
|
+
options: RelationManyOptions = {},
|
|
279
|
+
): ManyRelationDefinition {
|
|
280
|
+
const field = typeof fieldOrOptions === "string" ? fieldOrOptions : undefined;
|
|
281
|
+
const mergedOptions =
|
|
282
|
+
typeof fieldOrOptions === "string" ? options : (fieldOrOptions ?? options);
|
|
283
|
+
|
|
284
|
+
return {
|
|
285
|
+
kind: "relation",
|
|
286
|
+
relation: "many",
|
|
287
|
+
targetTable,
|
|
288
|
+
field: mergedOptions.field ?? field,
|
|
289
|
+
referenceField: mergedOptions.referenceField,
|
|
290
|
+
fkType: mergedOptions.fkType,
|
|
291
|
+
sqlName: mergedOptions.sqlName,
|
|
292
|
+
notNull: mergedOptions.notNull,
|
|
293
|
+
nullable: mergedOptions.nullable,
|
|
294
|
+
onDelete: mergedOptions.onDelete,
|
|
295
|
+
onUpdate: mergedOptions.onUpdate,
|
|
296
|
+
};
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
// ---------------------------------------------------------------------------
|
|
300
|
+
// Public API
|
|
301
|
+
// ---------------------------------------------------------------------------
|
|
302
|
+
|
|
207
303
|
export const v = {
|
|
208
304
|
int: (options: ColumnBuilderOptions = {}) =>
|
|
209
305
|
new ColumnBuilder("int", options),
|
|
@@ -213,50 +309,34 @@ export const v = {
|
|
|
213
309
|
new ColumnBuilder("boolean", options),
|
|
214
310
|
date: (options: ColumnBuilderOptions = {}) =>
|
|
215
311
|
new ColumnBuilder("date", options),
|
|
312
|
+
|
|
313
|
+
/**
|
|
314
|
+
* UUID primary key column.
|
|
315
|
+
* Stored as a string, marked as primary key and auto-populated with
|
|
316
|
+
* `crypto.randomUUID()` at runtime (no SQL sequence).
|
|
317
|
+
*/
|
|
318
|
+
uuid: (options: ColumnBuilderOptions = {}) =>
|
|
319
|
+
new ColumnBuilder({
|
|
320
|
+
kind: "column",
|
|
321
|
+
type: "string",
|
|
322
|
+
sqlName: options.sqlName,
|
|
323
|
+
length: options.length ?? 36,
|
|
324
|
+
primaryKey: true,
|
|
325
|
+
uuidPrimaryKey: true,
|
|
326
|
+
runtimeDefaultFn: () => crypto.randomUUID(),
|
|
327
|
+
}),
|
|
328
|
+
|
|
216
329
|
one: (
|
|
217
330
|
targetTable: string,
|
|
218
331
|
fieldOrOptions?: string | RelationOneOptions,
|
|
219
332
|
options: RelationOneOptions = {},
|
|
220
|
-
): OneRelationDefinition =>
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
const mergedOptions =
|
|
224
|
-
typeof fieldOrOptions === "string"
|
|
225
|
-
? options
|
|
226
|
-
: (fieldOrOptions ?? options);
|
|
227
|
-
|
|
228
|
-
return {
|
|
229
|
-
kind: "relation",
|
|
230
|
-
relation: "one",
|
|
231
|
-
targetTable,
|
|
232
|
-
field: mergedOptions.field ?? field,
|
|
233
|
-
referenceField: mergedOptions.referenceField,
|
|
234
|
-
fkType: mergedOptions.fkType,
|
|
235
|
-
sqlName: mergedOptions.sqlName,
|
|
236
|
-
notNull: mergedOptions.notNull,
|
|
237
|
-
};
|
|
238
|
-
},
|
|
333
|
+
): OneRelationDefinition =>
|
|
334
|
+
buildOneRelation(targetTable, fieldOrOptions, options),
|
|
335
|
+
|
|
239
336
|
many: (
|
|
240
337
|
targetTable: string,
|
|
241
338
|
fieldOrOptions?: string | RelationManyOptions,
|
|
242
339
|
options: RelationManyOptions = {},
|
|
243
|
-
): ManyRelationDefinition =>
|
|
244
|
-
|
|
245
|
-
typeof fieldOrOptions === "string" ? fieldOrOptions : undefined;
|
|
246
|
-
const mergedOptions =
|
|
247
|
-
typeof fieldOrOptions === "string"
|
|
248
|
-
? options
|
|
249
|
-
: (fieldOrOptions ?? options);
|
|
250
|
-
|
|
251
|
-
return {
|
|
252
|
-
kind: "relation",
|
|
253
|
-
relation: "many",
|
|
254
|
-
targetTable,
|
|
255
|
-
field: mergedOptions.field ?? field,
|
|
256
|
-
referenceField: mergedOptions.referenceField,
|
|
257
|
-
fkType: mergedOptions.fkType,
|
|
258
|
-
sqlName: mergedOptions.sqlName,
|
|
259
|
-
notNull: mergedOptions.notNull,
|
|
260
|
-
};
|
|
261
|
-
},
|
|
340
|
+
): ManyRelationDefinition =>
|
|
341
|
+
buildManyRelation(targetTable, fieldOrOptions, options),
|
|
262
342
|
};
|