@lunora/values 1.0.0-alpha.29 → 1.0.0-alpha.30

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/index.d.mts CHANGED
@@ -350,6 +350,38 @@ declare const objectValidator: <S extends ObjectShape>(shape: S) => ColumnValida
350
350
  declare const record: <K extends Validator<string>, V extends Validator>(keyValidator: K, valueValidator: V) => ColumnValidator<Record<Infer<K>, Infer<V>>, Record<Infer<K>, Infer<V>>>;
351
351
  declare const union: <Vs extends ReadonlyArray<Validator>>(...members: Vs) => ColumnValidator<Infer<Vs[number]>, Infer<Vs[number]>>;
352
352
  declare const optional: <V extends Validator>(inner: V) => ColumnValidator<Infer<V> | undefined, Infer<V> | undefined>;
353
+ /** Every member of a shape made optional — the result of {@link partial}. */
354
+ type PartialShape<S extends ObjectShape> = { [K in keyof S]: ColumnValidator<Infer<S[K]> | undefined, Infer<S[K]> | undefined>; };
355
+ /**
356
+ * Wrap every member of a shape in {@link optional}.
357
+ *
358
+ * A patch-style procedure takes "any subset of these columns" — the same shape
359
+ * the table declares, with nothing required. Spelling that out by hand means a
360
+ * second copy of the shape that has to be kept in step with the first, and the
361
+ * failure when it drifts is quiet: a column added to the table is simply not
362
+ * accepted by the patch, and nothing typechecks it against the table.
363
+ *
364
+ * Takes and returns a *shape record* rather than a `v.object(...)`, so the one
365
+ * function serves both positions — a procedure's args map (`.input(...)`) and a
366
+ * nested object (`v.object(v.partial(shape))`).
367
+ *
368
+ * A member that is already `v.optional(...)` is passed through rather than
369
+ * double-wrapped, so this is idempotent.
370
+ *
371
+ * **Pass the fields a caller may patch, not a whole table's shape.** Handing this
372
+ * `schema.tables.x.shape` makes every present and *future* column client-writable:
373
+ * add `ownerId`, `role`, or `isVerified` to the table later and it silently joins
374
+ * the patch, with no diff on the procedure to review. Row-level policies do not
375
+ * close that — they decide which ROW you may write, not which fields — so the
376
+ * allow-list has to be here.
377
+ * @example
378
+ * ```ts
379
+ * const editable = { body: v.string(), title: v.string() };
380
+ *
381
+ * mutation.input({ id: v.id("threads"), ...v.partial(editable) }).mutation(…)
382
+ * ```
383
+ */
384
+ declare const partial: <S extends ObjectShape>(shape: S) => PartialShape<S>;
353
385
  declare const any: () => ColumnValidator<unknown, unknown>;
354
386
  /**
355
387
  * The type a Standard Schema v1 object validates TO — what a read gets back.
@@ -446,6 +478,7 @@ declare const v: {
446
478
  number: typeof number;
447
479
  object: typeof objectValidator;
448
480
  optional: typeof optional;
481
+ partial: typeof partial;
449
482
  record: typeof record;
450
483
  storage: typeof storage;
451
484
  string: typeof string;
package/dist/index.d.ts CHANGED
@@ -350,6 +350,38 @@ declare const objectValidator: <S extends ObjectShape>(shape: S) => ColumnValida
350
350
  declare const record: <K extends Validator<string>, V extends Validator>(keyValidator: K, valueValidator: V) => ColumnValidator<Record<Infer<K>, Infer<V>>, Record<Infer<K>, Infer<V>>>;
351
351
  declare const union: <Vs extends ReadonlyArray<Validator>>(...members: Vs) => ColumnValidator<Infer<Vs[number]>, Infer<Vs[number]>>;
352
352
  declare const optional: <V extends Validator>(inner: V) => ColumnValidator<Infer<V> | undefined, Infer<V> | undefined>;
353
+ /** Every member of a shape made optional — the result of {@link partial}. */
354
+ type PartialShape<S extends ObjectShape> = { [K in keyof S]: ColumnValidator<Infer<S[K]> | undefined, Infer<S[K]> | undefined>; };
355
+ /**
356
+ * Wrap every member of a shape in {@link optional}.
357
+ *
358
+ * A patch-style procedure takes "any subset of these columns" — the same shape
359
+ * the table declares, with nothing required. Spelling that out by hand means a
360
+ * second copy of the shape that has to be kept in step with the first, and the
361
+ * failure when it drifts is quiet: a column added to the table is simply not
362
+ * accepted by the patch, and nothing typechecks it against the table.
363
+ *
364
+ * Takes and returns a *shape record* rather than a `v.object(...)`, so the one
365
+ * function serves both positions — a procedure's args map (`.input(...)`) and a
366
+ * nested object (`v.object(v.partial(shape))`).
367
+ *
368
+ * A member that is already `v.optional(...)` is passed through rather than
369
+ * double-wrapped, so this is idempotent.
370
+ *
371
+ * **Pass the fields a caller may patch, not a whole table's shape.** Handing this
372
+ * `schema.tables.x.shape` makes every present and *future* column client-writable:
373
+ * add `ownerId`, `role`, or `isVerified` to the table later and it silently joins
374
+ * the patch, with no diff on the procedure to review. Row-level policies do not
375
+ * close that — they decide which ROW you may write, not which fields — so the
376
+ * allow-list has to be here.
377
+ * @example
378
+ * ```ts
379
+ * const editable = { body: v.string(), title: v.string() };
380
+ *
381
+ * mutation.input({ id: v.id("threads"), ...v.partial(editable) }).mutation(…)
382
+ * ```
383
+ */
384
+ declare const partial: <S extends ObjectShape>(shape: S) => PartialShape<S>;
353
385
  declare const any: () => ColumnValidator<unknown, unknown>;
354
386
  /**
355
387
  * The type a Standard Schema v1 object validates TO — what a read gets back.
@@ -446,6 +478,7 @@ declare const v: {
446
478
  number: typeof number;
447
479
  object: typeof objectValidator;
448
480
  optional: typeof optional;
481
+ partial: typeof partial;
449
482
  record: typeof record;
450
483
  storage: typeof storage;
451
484
  string: typeof string;
package/dist/index.mjs CHANGED
@@ -1 +1 @@
1
- import{ValidationError as a,describeValue as e,formatPath as t}from"./packem_shared/ValidationError-BLw-y3Pk.mjs";import{jsonSchemaFromNode as p,objectSchemaFromNodes as i}from"./packem_shared/jsonSchemaFromNode-DtU81nPr.mjs";import{argsToJsonSchema as l,toJsonSchema as d}from"./packem_shared/argsToJsonSchema-ujumcrdC.mjs";import{isOrWrapsFromValidator as c,optionalInner as f,v as V}from"./packem_shared/isOrWrapsFromValidator-CDPE1VQ2.mjs";import{DEFER_VALIDATION as x,installCompiledValidatorMap as F,parseValidatorMap as S}from"./packem_shared/DEFER_VALIDATION-9tLHpbIF.mjs";export{x as DEFER_VALIDATION,a as ValidationError,l as argsToJsonSchema,e as describeValue,t as formatPath,F as installCompiledValidatorMap,c as isOrWrapsFromValidator,p as jsonSchemaFromNode,i as objectSchemaFromNodes,f as optionalInner,S as parseValidatorMap,d as toJsonSchema,V as v};
1
+ import{ValidationError as a,describeValue as e,formatPath as t}from"./packem_shared/ValidationError-BLw-y3Pk.mjs";import{jsonSchemaFromNode as p,objectSchemaFromNodes as i}from"./packem_shared/jsonSchemaFromNode-DtU81nPr.mjs";import{argsToJsonSchema as l,toJsonSchema as d}from"./packem_shared/argsToJsonSchema-ujumcrdC.mjs";import{isOrWrapsFromValidator as c,optionalInner as f,v as V}from"./packem_shared/isOrWrapsFromValidator-CgCgLFc3.mjs";import{DEFER_VALIDATION as x,installCompiledValidatorMap as F,parseValidatorMap as S}from"./packem_shared/DEFER_VALIDATION-9tLHpbIF.mjs";export{x as DEFER_VALIDATION,a as ValidationError,l as argsToJsonSchema,e as describeValue,t as formatPath,F as installCompiledValidatorMap,c as isOrWrapsFromValidator,p as jsonSchemaFromNode,i as objectSchemaFromNodes,f as optionalInner,S as parseValidatorMap,d as toJsonSchema,V as v};
@@ -0,0 +1 @@
1
+ import{LunoraError as k}from"@lunora/errors";import{ValidationError as h,describeValue as b,formatPath as _}from"./ValidationError-BLw-y3Pk.mjs";const A=/^[^\s@]+@[^\s@.]+(?:\.[^\s@.]+)+$/u,v=e=>{if(!URL.canParse(e))return!1;const{protocol:n}=new URL(e);return n==="http:"||n==="https:"};function d(e,n,s,a){const o=[...e.path],i=b(s,{literal:!a?.redactValue});throw new h(`Expected ${n} at ${_(o)}, received ${i}`,{expected:n,path:o,received:i})}const S=(e,n)=>{if(n===void 0)return e;const s=e?.constraints;return{...e,constraints:{...s,...n}}},l=(e,n,s)=>{const a=s?.column??{notNull:!0},o={__type:void 0,"~standard":{validate(r){const t=o.safeParse(r);return t.ok?{value:t.value}:{issues:[{message:t.error.message,path:t.error.path}]}},vendor:"lunora",version:1},_meta:{...s,column:a},_parse(r,t){return n(r,t)},kind:e,parse(r){return n(r,{path:[]})},safeParse(r){try{return{ok:!0,value:n(r,{path:[]})}}catch(t){if(t instanceof h)return{error:t,ok:!1};throw t}}},i=r=>l(e,n,{...s,column:{...a,...r}});switch(o.default=r=>i({defaultValue:r}),o.defaultNow=()=>i({defaultFn:()=>Date.now()}),o.unique=()=>i({unique:!0}),o.$defaultFn=r=>i({defaultFn:r}),o.$onUpdateFn=r=>i({onUpdateFn:r}),o.serverDefault=r=>i({serverDefault:r}),o.$type=(()=>i({})),o.nullable=()=>l(e,(t,c)=>t===null?null:n(t,c),{...s,column:{...a,notNull:!1}}),o.check=(r,t)=>{const c=typeof t=="string"?t:t?.message,u=typeof t=="string"?void 0:t?.schema;return l(e,(g,w)=>{const y=n(g,w);return r(y)||d(w,c??"value matching refinement",y,{redactValue:!0}),y},S(s,u))},o.meta=r=>{const t=r.description===void 0?r.schema:{description:r.description,...r.schema};return l(e,n,S(s,t))},e){case"array":{const r=o;r.min=t=>r.check(c=>c.length>=t,{message:`expected array length >= ${String(t)}`,schema:{minItems:t}}),r.max=t=>r.check(c=>c.length<=t,{message:`expected array length <= ${String(t)}`,schema:{maxItems:t}});break}case"number":{const r=o;r.min=t=>r.check(c=>c>=t,{message:`expected number >= ${String(t)}`,schema:{minimum:t}}),r.max=t=>r.check(c=>c<=t,{message:`expected number <= ${String(t)}`,schema:{maximum:t}}),r.int=()=>r.check(t=>Number.isInteger(t),{message:"expected an integer",schema:{type:"integer"}}),r.positive=()=>r.check(t=>t>0,{message:"expected a positive number",schema:{exclusiveMinimum:0}});break}case"string":{const r=o;r.min=t=>r.check(c=>c.length>=t,{message:`expected string length >= ${String(t)}`,schema:{minLength:t}}),r.max=t=>r.check(c=>c.length<=t,{message:`expected string length <= ${String(t)}`,schema:{maxLength:t}}),r.length=t=>r.check(c=>c.length===t,{message:`expected string length === ${String(t)}`,schema:{maxLength:t,minLength:t}}),r.pattern=t=>{const c=t.global||t.sticky?new RegExp(t.source,t.flags.replaceAll(/[gy]/gu,"")):t;return r.check(u=>c.test(u),{message:`expected string matching ${t.toString()}`,schema:{pattern:t.source}})},r.email=()=>r.check(t=>A.test(t),{message:"expected a valid email address",schema:{format:"email"}}),r.url=()=>r.check(t=>v(t),{message:"expected a valid URL",schema:{format:"uri"}});break}}return o},p=e=>e,f=e=>e,I=e=>e,P=e=>e,N=e=>e,L=()=>I(l("string",(e,n)=>(typeof e!="string"&&d(n,"string",e),e))),j=(e,n)=>((typeof e!="number"||!Number.isFinite(e))&&d(n,"number",e),e),O=()=>P(l("number",j)),E=()=>l("timestamp",j),V=()=>l("date",j),F=()=>f(l("boolean",(e,n)=>(typeof e!="boolean"&&d(n,"boolean",e),e))),R=()=>f(l("bigint",(e,n)=>(typeof e!="bigint"&&d(n,"bigint",e),e))),x=()=>f(l("null",(e,n)=>(e!==null&&d(n,"null",e),e))),U=()=>f(l("bytes",(e,n)=>(e instanceof ArrayBuffer||d(n,"ArrayBuffer",e),e))),C=e=>f(l("id",(n,s)=>(typeof n!="string"&&d(s,`Id<"${e}">`,n),n),{tableName:e})),D=e=>f(l("storage",(n,s)=>(typeof n!="string"&&d(s,"storage object key (string)",n),n),e===void 0?void 0:{bucket:e})),T=()=>f(l("geoPoint",(e,n)=>{(typeof e!="object"||e===null||Array.isArray(e))&&d(n,"geoPoint { lat, lng }",e);const s=e,{lat:a,lng:o}=s;return(typeof a!="number"||!Number.isFinite(a)||a<-90||a>90)&&(n.path.push("lat"),d(n,"latitude in [-90, 90]",a)),(typeof o!="number"||!Number.isFinite(o)||o<-180||o>180)&&(n.path.push("lng"),d(n,"longitude in [-180, 180]",o)),{lat:a,lng:o}})),q=e=>f(l("literal",(n,s)=>(n!==e&&d(s,`literal(${String(e)})`,n),n),{value:e})),B=e=>{const n=p(e);return N(l("array",(s,a)=>{Array.isArray(s)||d(a,"array",s);const{length:o}=s,i=[],{path:r}=a;for(let t=0;t<o;t+=1)r.push(t),i.push(n._parse(s[t],a)),r.pop();return i},{inner:e}))},M=e=>{const n=Object.keys(e).map(s=>{const a=p(e[s]);return{child:a,isOptional:a.kind==="optional",key:s}});if(n.some(({key:s})=>s==="__proto__"))throw new k("INTERNAL",'v.object: "__proto__" cannot be a declared field name — it collides with the Object.prototype accessor');return f(l("object",(s,a)=>{(typeof s!="object"||s===null||Array.isArray(s))&&d(a,"object",s);const o=s,i={},{path:r}=a;for(const{child:t,isOptional:c,key:u}of n){const m=Object.hasOwn(o,u)?o[u]:void 0;m===void 0&&c||(r.push(u),i[u]=t._parse(m,a),r.pop())}return i},{shape:e}))},K=(e,n)=>{const s=p(e),a=p(n);return f(l("record",(o,i)=>{(typeof o!="object"||o===null||Array.isArray(o))&&d(i,"record",o);const r=o,t=Object.create(null),{path:c}=i;for(const u of Object.keys(r)){c.push(u);const m=s._parse(u,i),g=a._parse(r[u],i);c.pop(),t[m]=g}return t},{keyValidator:e,valueValidator:n}))},W=(...e)=>{if(e.length===0)throw new k("INTERNAL","v.union requires at least one member");const n=e.map(s=>p(s));return f(l("union",(s,a)=>{let o;const{path:i}=a,r=i.length;for(const c of n)try{return c._parse(s,a)}catch(u){if(!(u instanceof h))throw u;i.length=r,(o===void 0||u.path.length>o.path.length)&&(o=u)}if(n.length===1&&o!==void 0)throw o;const t=o===void 0?"":` (closest: expected ${o.expected} at ${_(o.path)})`;return d(a,`union of ${String(e.length)} member(s)${t}`,s)},{members:e}))},$=e=>{const n=p(e);return f(l("optional",(s,a)=>s===void 0?void 0:n._parse(s,a),{inner:e}))},z=e=>Object.fromEntries(Object.entries(e).map(([n,s])=>[n,p(s).kind==="optional"?s:$(s)])),G=()=>f(l("any",e=>e)),H=e=>{const n=[];if(!e)return n;for(const s of e){const a=typeof s=="object"&&s!==null&&"key"in s?s.key:s;(typeof a=="string"||typeof a=="number")&&n.push(a)}return n},J=e=>{const n=e["~standard"];if(n?.version!==1||typeof n.validate!="function")throw new k("INTERNAL",'@lunora/values: v.from() expects a Standard Schema v1 object (missing or invalid "~standard")');const s=n.validate;return f(l("from",(a,o)=>{const i=s(a);if(i instanceof Promise||typeof i?.then=="function")throw new h("v.from(): async Standard Schema validators are not supported in args",{expected:"sync Standard Schema result",path:[...o.path],received:"Promise"});const r=i;if(r===null||typeof r!="object")throw new h("v.from(): Standard Schema validator returned a non-object result",{expected:"Standard Schema result object",path:[...o.path],received:b(r)});const t=i;if(t.issues!==void 0){const c=t.issues[0],u=c?.message??"Standard Schema validation failed";throw new h(u,{expected:"valid value",path:[...o.path,...H(c?.path)],received:b(a)})}return t.value}))},Q=e=>{if(e.kind==="from")return!0;const n=e._meta;if(!n)return!1;const s=[n.inner,n.keyValidator,n.valueValidator];Array.isArray(n.members)&&s.push(...n.members),n.shape!==null&&typeof n.shape=="object"&&s.push(...Object.values(n.shape));for(const a of s)if(a!==null&&typeof a=="object"&&"kind"in a&&Q(a))return!0;return!1},Z=e=>{if(e.kind==="optional")return e._meta?.inner},ee={any:G,array:B,bigint:R,boolean:F,bytes:U,date:V,from:J,geoPoint:T,id:C,literal:q,null:x,number:O,object:M,optional:$,partial:z,record:K,storage:D,string:L,timestamp:E,union:W};export{Q as isOrWrapsFromValidator,Z as optionalInner,ee as v};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lunora/values",
3
- "version": "1.0.0-alpha.29",
3
+ "version": "1.0.0-alpha.30",
4
4
  "description": "Validators for Lunora: the v.* validator suite with end-to-end return-type inference",
5
5
  "keywords": [
6
6
  "cloudflare",
@@ -1 +0,0 @@
1
- import{LunoraError as k}from"@lunora/errors";import{ValidationError as p,describeValue as b,formatPath as _}from"./ValidationError-BLw-y3Pk.mjs";const $=/^[^\s@]+@[^\s@.]+(?:\.[^\s@.]+)+$/u,A=e=>{if(!URL.canParse(e))return!1;const{protocol:r}=new URL(e);return r==="http:"||r==="https:"};function d(e,r,s,a){const o=[...e.path],i=b(s,{literal:!a?.redactValue});throw new p(`Expected ${r} at ${_(o)}, received ${i}`,{expected:r,path:o,received:i})}const j=(e,r)=>{if(r===void 0)return e;const s=e?.constraints;return{...e,constraints:{...s,...r}}},l=(e,r,s)=>{const a=s?.column??{notNull:!0},o={__type:void 0,"~standard":{validate(n){const t=o.safeParse(n);return t.ok?{value:t.value}:{issues:[{message:t.error.message,path:t.error.path}]}},vendor:"lunora",version:1},_meta:{...s,column:a},_parse(n,t){return r(n,t)},kind:e,parse(n){return r(n,{path:[]})},safeParse(n){try{return{ok:!0,value:r(n,{path:[]})}}catch(t){if(t instanceof p)return{error:t,ok:!1};throw t}}},i=n=>l(e,r,{...s,column:{...a,...n}});switch(o.default=n=>i({defaultValue:n}),o.defaultNow=()=>i({defaultFn:()=>Date.now()}),o.unique=()=>i({unique:!0}),o.$defaultFn=n=>i({defaultFn:n}),o.$onUpdateFn=n=>i({onUpdateFn:n}),o.serverDefault=n=>i({serverDefault:n}),o.$type=(()=>i({})),o.nullable=()=>l(e,(t,c)=>t===null?null:r(t,c),{...s,column:{...a,notNull:!1}}),o.check=(n,t)=>{const c=typeof t=="string"?t:t?.message,u=typeof t=="string"?void 0:t?.schema;return l(e,(g,S)=>{const y=r(g,S);return n(y)||d(S,c??"value matching refinement",y,{redactValue:!0}),y},j(s,u))},o.meta=n=>{const t=n.description===void 0?n.schema:{description:n.description,...n.schema};return l(e,r,j(s,t))},e){case"array":{const n=o;n.min=t=>n.check(c=>c.length>=t,{message:`expected array length >= ${String(t)}`,schema:{minItems:t}}),n.max=t=>n.check(c=>c.length<=t,{message:`expected array length <= ${String(t)}`,schema:{maxItems:t}});break}case"number":{const n=o;n.min=t=>n.check(c=>c>=t,{message:`expected number >= ${String(t)}`,schema:{minimum:t}}),n.max=t=>n.check(c=>c<=t,{message:`expected number <= ${String(t)}`,schema:{maximum:t}}),n.int=()=>n.check(t=>Number.isInteger(t),{message:"expected an integer",schema:{type:"integer"}}),n.positive=()=>n.check(t=>t>0,{message:"expected a positive number",schema:{exclusiveMinimum:0}});break}case"string":{const n=o;n.min=t=>n.check(c=>c.length>=t,{message:`expected string length >= ${String(t)}`,schema:{minLength:t}}),n.max=t=>n.check(c=>c.length<=t,{message:`expected string length <= ${String(t)}`,schema:{maxLength:t}}),n.length=t=>n.check(c=>c.length===t,{message:`expected string length === ${String(t)}`,schema:{maxLength:t,minLength:t}}),n.pattern=t=>{const c=t.global||t.sticky?new RegExp(t.source,t.flags.replaceAll(/[gy]/gu,"")):t;return n.check(u=>c.test(u),{message:`expected string matching ${t.toString()}`,schema:{pattern:t.source}})},n.email=()=>n.check(t=>$.test(t),{message:"expected a valid email address",schema:{format:"email"}}),n.url=()=>n.check(t=>A(t),{message:"expected a valid URL",schema:{format:"uri"}});break}}return o},h=e=>e,f=e=>e,v=e=>e,I=e=>e,P=e=>e,N=()=>v(l("string",(e,r)=>(typeof e!="string"&&d(r,"string",e),e))),w=(e,r)=>((typeof e!="number"||!Number.isFinite(e))&&d(r,"number",e),e),L=()=>I(l("number",w)),V=()=>l("timestamp",w),E=()=>l("date",w),F=()=>f(l("boolean",(e,r)=>(typeof e!="boolean"&&d(r,"boolean",e),e))),O=()=>f(l("bigint",(e,r)=>(typeof e!="bigint"&&d(r,"bigint",e),e))),R=()=>f(l("null",(e,r)=>(e!==null&&d(r,"null",e),e))),x=()=>f(l("bytes",(e,r)=>(e instanceof ArrayBuffer||d(r,"ArrayBuffer",e),e))),U=e=>f(l("id",(r,s)=>(typeof r!="string"&&d(s,`Id<"${e}">`,r),r),{tableName:e})),C=e=>f(l("storage",(r,s)=>(typeof r!="string"&&d(s,"storage object key (string)",r),r),e===void 0?void 0:{bucket:e})),D=()=>f(l("geoPoint",(e,r)=>{(typeof e!="object"||e===null||Array.isArray(e))&&d(r,"geoPoint { lat, lng }",e);const s=e,{lat:a,lng:o}=s;return(typeof a!="number"||!Number.isFinite(a)||a<-90||a>90)&&(r.path.push("lat"),d(r,"latitude in [-90, 90]",a)),(typeof o!="number"||!Number.isFinite(o)||o<-180||o>180)&&(r.path.push("lng"),d(r,"longitude in [-180, 180]",o)),{lat:a,lng:o}})),T=e=>f(l("literal",(r,s)=>(r!==e&&d(s,`literal(${String(e)})`,r),r),{value:e})),q=e=>{const r=h(e);return P(l("array",(s,a)=>{Array.isArray(s)||d(a,"array",s);const{length:o}=s,i=[],{path:n}=a;for(let t=0;t<o;t+=1)n.push(t),i.push(r._parse(s[t],a)),n.pop();return i},{inner:e}))},B=e=>{const r=Object.keys(e).map(s=>{const a=h(e[s]);return{child:a,isOptional:a.kind==="optional",key:s}});if(r.some(({key:s})=>s==="__proto__"))throw new k("INTERNAL",'v.object: "__proto__" cannot be a declared field name — it collides with the Object.prototype accessor');return f(l("object",(s,a)=>{(typeof s!="object"||s===null||Array.isArray(s))&&d(a,"object",s);const o=s,i={},{path:n}=a;for(const{child:t,isOptional:c,key:u}of r){const m=Object.hasOwn(o,u)?o[u]:void 0;m===void 0&&c||(n.push(u),i[u]=t._parse(m,a),n.pop())}return i},{shape:e}))},M=(e,r)=>{const s=h(e),a=h(r);return f(l("record",(o,i)=>{(typeof o!="object"||o===null||Array.isArray(o))&&d(i,"record",o);const n=o,t=Object.create(null),{path:c}=i;for(const u of Object.keys(n)){c.push(u);const m=s._parse(u,i),g=a._parse(n[u],i);c.pop(),t[m]=g}return t},{keyValidator:e,valueValidator:r}))},K=(...e)=>{if(e.length===0)throw new k("INTERNAL","v.union requires at least one member");const r=e.map(s=>h(s));return f(l("union",(s,a)=>{let o;const{path:i}=a,n=i.length;for(const c of r)try{return c._parse(s,a)}catch(u){if(!(u instanceof p))throw u;i.length=n,(o===void 0||u.path.length>o.path.length)&&(o=u)}if(r.length===1&&o!==void 0)throw o;const t=o===void 0?"":` (closest: expected ${o.expected} at ${_(o.path)})`;return d(a,`union of ${String(e.length)} member(s)${t}`,s)},{members:e}))},W=e=>{const r=h(e);return f(l("optional",(s,a)=>s===void 0?void 0:r._parse(s,a),{inner:e}))},z=()=>f(l("any",e=>e)),G=e=>{const r=[];if(!e)return r;for(const s of e){const a=typeof s=="object"&&s!==null&&"key"in s?s.key:s;(typeof a=="string"||typeof a=="number")&&r.push(a)}return r},H=e=>{const r=e["~standard"];if(r?.version!==1||typeof r.validate!="function")throw new k("INTERNAL",'@lunora/values: v.from() expects a Standard Schema v1 object (missing or invalid "~standard")');const s=r.validate;return f(l("from",(a,o)=>{const i=s(a);if(i instanceof Promise||typeof i?.then=="function")throw new p("v.from(): async Standard Schema validators are not supported in args",{expected:"sync Standard Schema result",path:[...o.path],received:"Promise"});const n=i;if(n===null||typeof n!="object")throw new p("v.from(): Standard Schema validator returned a non-object result",{expected:"Standard Schema result object",path:[...o.path],received:b(n)});const t=i;if(t.issues!==void 0){const c=t.issues[0],u=c?.message??"Standard Schema validation failed";throw new p(u,{expected:"valid value",path:[...o.path,...G(c?.path)],received:b(a)})}return t.value}))},J=e=>{if(e.kind==="from")return!0;const r=e._meta;if(!r)return!1;const s=[r.inner,r.keyValidator,r.valueValidator];Array.isArray(r.members)&&s.push(...r.members),r.shape!==null&&typeof r.shape=="object"&&s.push(...Object.values(r.shape));for(const a of s)if(a!==null&&typeof a=="object"&&"kind"in a&&J(a))return!0;return!1},Y=e=>{if(e.kind==="optional")return e._meta?.inner},Z={any:z,array:q,bigint:O,boolean:F,bytes:x,date:E,from:H,geoPoint:D,id:U,literal:T,null:R,number:L,object:B,optional:W,record:M,storage:C,string:N,timestamp:V,union:K};export{J as isOrWrapsFromValidator,Y as optionalInner,Z as v};