@arkenv/cli 0.2.10 → 1.0.0-alpha.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/index.cjs +1 -1
  2. package/package.json +1 -1
package/dist/index.cjs CHANGED
@@ -110,7 +110,7 @@ ${t?(0,a.styleText)(`cyan`,U):``}
110
110
  outdir: "./dist",
111
111
  ${y.default.green(`plugins: [arkenv]`)}
112
112
  });
113
- `),{success:!0,instructions:a.trim()}}async function Mt(e,t){let n=t||await pt();if(!n)return{status:`not_found`};let i=r.default.basename(n);try{let t=await e.readFile(n);if((0,d.parse)(t)?.compilerOptions?.strict===!0)return{status:`already_strict`,file:i};let r=(0,d.applyEdits)(t,(0,d.modify)(t,[`compilerOptions`,`strict`],!0,{formattingOptions:{insertSpaces:!0,tabSize:2}}));return await e.writeFile(n,r),{status:`updated`,file:i}}catch{return{status:`error`,file:i}}}var Nt=class{constructor(e,t){this.isQuiet=e,this.stdio=t}async exists(e){try{return await n.default.access(e),!0}catch{return!1}}async readFile(e){return n.default.readFile(e,`utf-8`)}async writeFile(e,t){await n.default.writeFile(e,t,`utf-8`)}async mkdir(e,t){await n.default.mkdir(e,{recursive:t})}async execute(e,t=[],n){return new Promise((r,i)=>{let a=(0,l.spawn)(e,t,{cwd:n,stdio:this.isQuiet?`pipe`:this.stdio,shell:!1}),o=``,s=``,c=1e4;this.isQuiet&&(a.stdout?.on(`data`,e=>{o=(o+e.toString()).slice(-c)}),a.stderr?.on(`data`,e=>{s=(s+e.toString()).slice(-c)})),a.on(`close`,(e,t)=>{if(e===0)r();else{let n=e===null?`Command terminated by signal ${t}`:`Command failed with code ${e}`;this.isQuiet&&(o&&(n+=`\n${y.default.dim(`STDOUT:`)}\n${o}`),s&&(n+=`\n${y.default.red(`STDERR:`)}\n${s}`)),i(Error(n))}}),a.on(`error`,i)})}async updateTsConfigToStrict(e){return Mt(this,e)}async findViteConfig(e){return Et(e)}async findBunConfig(e){return Dt(e)}async findNextjsConfig(e){return Ot(e)}async bootstrapViteConfig(e,t){return At(this,e,t)}async bootstrapBunConfig(e,t){return jt(e,t)}async bootstrapNextjsConfig(e){return kt(this,e)}async safeAppend(e,t,n){let{safeAppend:r}=await Promise.resolve().then(()=>p);return r(e,t,n)}};async function Pt(e){let t=e.defaultPath||`./src/env.ts`;if(e.hasEnvSchemaFile){let e=await G({message:y.default.yellow(`An existing ArkEnv configuration was found at ${Y(t)}. Do you want to overwrite it?`),initialValue:!1,active:`Yes (override my configuration)`,inactive:`No (abort)`});return I(e)||!e?null:e}return!0}async function Ft(e){let t=e.detectedKeys,n=e.keysSource||`.env.example`;if(t&&t.length>0){let e=t.length,r=e===1,i=await G({message:n===`.env.example`?`Detected ${Y(`.env.example`)} with ${e} ${r?`key`:`keys`}. Use ${r?`it`:`them`} for your schema?`:`Detected ${e} environment variable${r?``:`s`} used in your project. Use ${r?`it`:`them`} for your schema?`,active:`Yes (Recommended)`,initialValue:!0});return I(i)?null:i}return!1}async function It(e){if(e.framework===`vite`||e.framework===`bun-fullstack`){let t=e.framework===`vite`?`vite-env.d.ts`:`bun-env.d.ts`;if(e.hasTypeFile)return!0;let n=await G({message:`Establish ${Y(t)} for typesafe environment variables?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No`});return I(n)?null:n}return!0}async function Lt(e){if(!e.installTypeDefinitions||e.framework!==`vite`&&e.framework!==`bun-fullstack`)return`skip`;let t=e.framework===`vite`?`vite-env.d.ts`:`bun-env.d.ts`;if(e.hasTypeFile){let e=await q({message:`Found existing ${Y(t)}. How should we handle ArkEnv types?`,options:[{value:`append`,label:`Append types safely (if needed)`,hint:`Recommended`},{value:`overwrite`,label:`Overwrite entirely`,hint:`Destructive`},{value:`skip`,label:`Skip`}]});return I(e)?null:e}return`overwrite`}async function Rt(e){let t=await q({message:`Select an example:`,options:e.examples.map(e=>({value:e.id,label:e.name,...e.description?{hint:e.description}:{}}))});return I(t)?null:t}async function zt(e){let t=await q({message:`Select your framework or build tool:`,initialValue:e.framework,options:[{value:`vanilla`,label:`Vanilla${e.framework===`vanilla`?` (Detected)`:``}`,hint:`Node.js, Bun, server-side or runtime-only validation`},{value:`vite`,label:`Vite${e.framework===`vite`?` (Detected)`:``}`,hint:`Client-side and static inlining validation`},{value:`bun-fullstack`,label:`Bun fullstack dev server${e.framework===`bun-fullstack`?` (Detected)`:``}`,hint:`Client-side bundling and Bun.serve integration`},{value:`nextjs`,label:`Next.js${e.framework===`nextjs`?` (Detected)`:``}`,hint:`Next.js App or Pages Router with build and runtime validation`}]});return I(t)?null:t}async function Bt(e){let t=await G({message:`Optional: Would you also like to bootstrap a custom Bun.build script for programmatic bundling?`,initialValue:e.initialValue??!1});return I(t)?null:t}async function Vt(){let e=await q({message:`Select your preferred validator library:`,options:[{value:`arktype`,label:`ArkType (Recommended)`,hint:`TypeScript's 1:1 validator, optimized from editor to runtime`},{value:`zod`,label:`Zod`,hint:`TypeScript-first schema validation with static type inference`},{value:`valibot`,label:`Valibot`,hint:`The modular and type safe schema library`}]});return I(e)?null:e}async function Ht(){let e=await q({message:`How would you like to structure your environment variables?`,options:[{value:`simple`,label:`Simple (Recommended)`,hint:`A single env.ts file for the best DX`},{value:`strict`,label:`Strict`,hint:`Separate shared, client, and server files for hard bundle boundaries.`}]});return I(e)?null:e}async function Ut(e){let t=await G({message:`Enable automated Next.js code generation for environment variables?`,initialValue:e.initialValue??!0,active:`Yes (Recommended)`,inactive:`No`});return I(t)?null:t}async function Wt(e){let t=await G({message:`Use default config path (${Y(e.defaultEnvPath||`./src/env.ts`)})?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No, let me customize it`});return I(t)?null:t}async function Gt(e){let t=e.defaultEnvPath||`./src/env.ts`;if(!e.useDefaultPath){let e=await Qe({message:`Where should we create the ArkEnv config?`,placeholder:t,initialValue:t,defaultValue:t});if(I(e))return null;let n=typeof e==`string`?e.trim():``;return n===``?t:n}return t}const X={example:Rt,overwriteEnvSchemaFile:Pt,framework:zt,bunBuild:Bt,layout:Ht,nextjsCodegen:Ut,useDefaultPath:Wt,path:Gt,installTypeDefinitions:It,envDtsHandling:Lt,validator:Vt,useEnvExample:Ft};async function Kt(e,t=!1){return(e?.mode||`existing`)===`new`?qt(e,t):Jt(e,t)}async function qt(e,t=!1){let n=e?.examples||[],i=`arkenv-project`;try{let a;if(e?.name){let t=e.name.trim();a=t===`.`||t===`./`||r.default.resolve(process.cwd(),t)===process.cwd()?`.`:t}else if(t)a=i;else{let e=(Z(await Qe({message:`Project name:`,placeholder:i,defaultValue:i}))||i).trim();a=e===`.`||e===`./`||r.default.resolve(process.cwd(),e)===process.cwd()?`.`:e}let o=e?.example;!o&&!t?o=Z(await X.example({examples:n})):!o&&t&&(o=`basic`);let s=n.find(e=>e.id===o);if(!s){let e=n.map(e=>e.id).join(`, `);throw Error(`Unknown example ${o}. Available examples: ${e}`)}return{mode:`new`,example:s.id,name:a,path:`./src/env.ts`,validator:`arktype`,framework:s.framework,language:`ts`,installSkill:!1}}catch(e){if(e instanceof Xt)return null;throw e}}async function Jt(e,n=!1){let r=e?.defaultEnvPath||`./src/env.ts`,i=e?.envKeys||null,a=e?.envKeysSource||`.env.example`;if(n){let n=e?.framework||`vanilla`,a;n===`nextjs`&&(a=e?.isStrict?`strict`:(e?.isSimple,`simple`));let o=await Yt(e,n,r),s;return(n===`vite`||n===`bun-fullstack`)&&(s=o?`append`:`overwrite`),(0,t.shake)({mode:`existing`,path:r,validator:`arktype`,framework:n,layout:a,bunFeatures:n===`bun-fullstack`?e?.bunFeatures??[`serve`]:void 0,language:`ts`,overwriteEnvSchemaFile:!0,installTypeDefinitions:n===`vite`||n===`bun-fullstack`,installSkill:!1,envDtsHandling:s,envKeys:i??void 0,disableCodegen:e?.disableCodegen??!1,wrapNextjsConfig:n===`nextjs`?!0:void 0})}try{let n=Z(await X.overwriteEnvSchemaFile({hasEnvSchemaFile:e?.hasEnvSchemaFile??!1,defaultPath:r})),o=Z(await X.framework({framework:e?.framework})),s;o===`nextjs`&&(s=e?.isStrict?`strict`:e?.isSimple?`simple`:Z(await X.layout()));let c;if(o===`bun-fullstack`){let t=!!e?.bunFeatures?.includes(`build`);c=Z(await X.bunBuild({initialValue:t}))}let l=e?.disableCodegen;o===`nextjs`&&l===void 0&&(l=!Z(await X.nextjsCodegen({initialValue:!0})));let u;if(o===`nextjs`&&!l){let e=await G({message:`Would you like to wrap your Next.js config with ${Y(`withArkEnv`)}?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No`});if(I(e))throw Ue(`Operation cancelled`),new Xt;u=e}let d=Z(await X.useDefaultPath({defaultEnvPath:r})),f=Z(await X.path({useDefaultPath:d,defaultEnvPath:r})),p=await Yt(e,o,f),m=Z(await X.installTypeDefinitions({framework:o,hasTypeFile:p})),h=Z(await X.envDtsHandling({framework:o,installTypeDefinitions:m,hasTypeFile:p})),g=Z(await X.validator()),_=Z(await X.useEnvExample({detectedKeys:i,keysSource:a}));return(0,t.shake)({mode:`existing`,overwriteEnvSchemaFile:n,framework:o,layout:s,path:f,installTypeDefinitions:m,envDtsHandling:h,validator:g,bunFeatures:o===`bun-fullstack`?c?[`serve`,`build`]:[`serve`]:void 0,language:`ts`,installSkill:!1,envKeys:_?i??void 0:void 0,disableCodegen:l,wrapNextjsConfig:u})}catch(e){if(e instanceof Xt)return null;throw e}}async function Yt(e,t,n){return await e?.hasTypeFileAtPath?.({framework:t,envPath:n})??e?.hasTypeFile??!1}var Xt=class extends Error{constructor(){super(`Operation cancelled`)}};function Z(e){if(e===null||I(e))throw Ue(`Operation cancelled`),new Xt;return e}var Zt=class{async confirm(e,n=!0,r,i){let a=await G((0,t.shake)({message:e,initialValue:n,active:r,inactive:i}));return I(a)?null:a}async runWizard(e,t=!1){return Kt(e,t)}};const Qt={isYes:{long:`--yes`,short:`-y`,kind:`boolean`},isForce:{long:`--force`,short:`-f`,kind:`boolean`},isQuiet:{long:`--quiet`,short:`-q`,kind:`boolean`},isJson:{long:`--json`,short:`-j`,kind:`boolean`},isAgent:{long:`--agent`,short:`-a`,kind:`boolean`},helpRequested:{long:`--help`,short:`-h`,kind:`boolean`},example:{long:`--example`,short:`-e`,kind:`value`},isStrict:{long:`--strict`,short:``,kind:`boolean`},isSimple:{long:`--simple`,short:``,kind:`boolean`},noCodegen:{long:`--no-codegen`,short:`-C`,kind:`boolean`}},$t=new Set(Object.values(Qt).flatMap(e=>[e.long,e.short].filter(Boolean))),en=new Set(Object.values(Qt).filter(e=>e.kind===`value`).flatMap(e=>[e.long,e.short].filter(Boolean)));var tn=class{constructor(e,t={}){let n=e.slice(2),r=[],i=!1;for(let e of n){if(i){r.push(e),i=!1;continue}if(en.has(e)){r.push(e),i=!0;continue}if(/^-[a-zA-Z]{2,}$/.test(e)){let t=e.slice(1).split(``);for(let e of t)r.push(`-${e}`);en.has(`-${t[t.length-1]}`)&&(i=!0)}else r.push(e)}this.args=r,this.command=this.args[0];let a=1,o=[];for(this.validationError=void 0;a<this.args.length;){let e=this.args[a];if(e.startsWith(`-`)){if(!$t.has(e)){this.validationError=`Unknown argument: ${e}`;break}if(en.has(e))if(a+1<this.args.length&&!this.args[a+1].startsWith(`-`))a+=2;else{this.validationError=`Missing value for option: ${e}`;break}else a+=1}else o.push(e),a+=1}this.validationError||(o.length>1?this.validationError=`Unknown argument: ${o[1]}`:this.name=o[0]),this.logger=t.logger||new et({isQuiet:this.isQuiet,isJson:this.isJson,isYes:this.isYes})}get isAgent(){return this.hasFlag(`isAgent`)}get isYes(){return this.isAgent||this.hasFlag(`isYes`)}get isQuiet(){return this.isAgent||this.hasFlag(`isQuiet`)}get isJson(){return this.isAgent||this.hasFlag(`isJson`)}get isForce(){return this.hasFlag(`isForce`)}get helpRequested(){return this.hasFlag(`helpRequested`)}get example(){let e=Qt.example;return this.getFlagValue(e.long,e.short)}get isStrict(){return this.hasFlag(`isStrict`)}get isSimple(){return this.hasFlag(`isSimple`)}get noCodegen(){return this.hasFlag(`noCodegen`)}hasFlag(e){let t=Qt[e];return this.args.includes(t.long)||!!t.short&&this.args.includes(t.short)}get initInput(){let e={isYes:this.isYes,isForce:this.isForce,isQuiet:this.isQuiet,isAgent:this.isAgent,isStrict:this.isStrict,isSimple:this.isSimple};return this.example!==void 0&&(e.example=this.example),this.name!==void 0&&(e.name=this.name),this.noCodegen&&(e.noCodegen=!0),e}getFlagValue(e,t){let n=this.args.findIndex(n=>n===e||n===t);if(n!==-1&&this.args[n+1]&&!this.args[n+1].startsWith(`-`))return this.args[n+1]}},nn=`0.2.10`;function rn(e,t=2,n=4){let r=Math.max(...e.map(e=>e.left.length),0),i=` `.repeat(t);return e.map(e=>{let t=` `.repeat(r-e.left.length+n);return`${i}${e.left}${t}${e.right}`})}var an=class{constructor(e){this.logger=e}async execute(){let e=[{left:`arkenv init [project-name]`,right:`Set up ArkEnv in your project`}],t=[{left:`--yes, -y`,right:`Skip prompts and use defaults (also passed to subprocesses)`},{left:`--force, -f`,right:`Bypass technical requirement checks and dirty git working tree check, then force scaffolding`},{left:`--agent, -a`,right:`Enable non-interactive, machine-readable mode for AI agents. Bypasses all prompts and outputs structured JSON. Macro for --yes --quiet --json`},{left:`--example, -e`,right:`Specify an example name when creating a new project`},{left:`--quiet, -q`,right:`Quiet mode: Suppress output, capture logs on failure`},{left:`--json, -j`,right:`Output structured JSON to stdout`},{left:`--no-codegen, -C`,right:`Disable automatic env.gen.ts code generation for Next.js`},{left:`--help, -h`,right:`Show this help message`}];this.logger.log(`ArkEnv CLI v${nn}`),this.logger.log(`\n${y.default.bold(`Usage:`)}`);for(let t of rn(e))this.logger.log(t);this.logger.log(`\n${y.default.bold(`Options:`)}`);for(let e of rn(t))this.logger.log(e)}};function on(e,t,n,r){let{extraImports:i,serverField:a,clientField:o,sharedField:s,defaultServerFields:c,defaultClientFields:l,defaultSharedFields:u}=t,d=[],f=[],p=[];if(e&&e.length>0)for(let t of e)t.startsWith(`NEXT_PUBLIC_`)?f.push(o(t)):t===`NODE_ENV`?p.push(s(t)):d.push(a(t));else d.push(...c),f.push(...l),p.push(...u);let m=[];if(d.length>0&&m.push(`\tserver: {\n${d.join(`
113
+ `),{success:!0,instructions:a.trim()}}async function Mt(e,t){let n=t||await pt();if(!n)return{status:`not_found`};let i=r.default.basename(n);try{let t=await e.readFile(n);if((0,d.parse)(t)?.compilerOptions?.strict===!0)return{status:`already_strict`,file:i};let r=(0,d.applyEdits)(t,(0,d.modify)(t,[`compilerOptions`,`strict`],!0,{formattingOptions:{insertSpaces:!0,tabSize:2}}));return await e.writeFile(n,r),{status:`updated`,file:i}}catch{return{status:`error`,file:i}}}var Nt=class{constructor(e,t){this.isQuiet=e,this.stdio=t}async exists(e){try{return await n.default.access(e),!0}catch{return!1}}async readFile(e){return n.default.readFile(e,`utf-8`)}async writeFile(e,t){await n.default.writeFile(e,t,`utf-8`)}async mkdir(e,t){await n.default.mkdir(e,{recursive:t})}async execute(e,t=[],n){return new Promise((r,i)=>{let a=(0,l.spawn)(e,t,{cwd:n,stdio:this.isQuiet?`pipe`:this.stdio,shell:!1}),o=``,s=``,c=1e4;this.isQuiet&&(a.stdout?.on(`data`,e=>{o=(o+e.toString()).slice(-c)}),a.stderr?.on(`data`,e=>{s=(s+e.toString()).slice(-c)})),a.on(`close`,(e,t)=>{if(e===0)r();else{let n=e===null?`Command terminated by signal ${t}`:`Command failed with code ${e}`;this.isQuiet&&(o&&(n+=`\n${y.default.dim(`STDOUT:`)}\n${o}`),s&&(n+=`\n${y.default.red(`STDERR:`)}\n${s}`)),i(Error(n))}}),a.on(`error`,i)})}async updateTsConfigToStrict(e){return Mt(this,e)}async findViteConfig(e){return Et(e)}async findBunConfig(e){return Dt(e)}async findNextjsConfig(e){return Ot(e)}async bootstrapViteConfig(e,t){return At(this,e,t)}async bootstrapBunConfig(e,t){return jt(e,t)}async bootstrapNextjsConfig(e){return kt(this,e)}async safeAppend(e,t,n){let{safeAppend:r}=await Promise.resolve().then(()=>p);return r(e,t,n)}};async function Pt(e){let t=e.defaultPath||`./src/env.ts`;if(e.hasEnvSchemaFile){let e=await G({message:y.default.yellow(`An existing ArkEnv configuration was found at ${Y(t)}. Do you want to overwrite it?`),initialValue:!1,active:`Yes (override my configuration)`,inactive:`No (abort)`});return I(e)||!e?null:e}return!0}async function Ft(e){let t=e.detectedKeys,n=e.keysSource||`.env.example`;if(t&&t.length>0){let e=t.length,r=e===1,i=await G({message:n===`.env.example`?`Detected ${Y(`.env.example`)} with ${e} ${r?`key`:`keys`}. Use ${r?`it`:`them`} for your schema?`:`Detected ${e} environment variable${r?``:`s`} used in your project. Use ${r?`it`:`them`} for your schema?`,active:`Yes (Recommended)`,initialValue:!0});return I(i)?null:i}return!1}async function It(e){if(e.framework===`vite`||e.framework===`bun-fullstack`){let t=e.framework===`vite`?`vite-env.d.ts`:`bun-env.d.ts`;if(e.hasTypeFile)return!0;let n=await G({message:`Establish ${Y(t)} for typesafe environment variables?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No`});return I(n)?null:n}return!0}async function Lt(e){if(!e.installTypeDefinitions||e.framework!==`vite`&&e.framework!==`bun-fullstack`)return`skip`;let t=e.framework===`vite`?`vite-env.d.ts`:`bun-env.d.ts`;if(e.hasTypeFile){let e=await q({message:`Found existing ${Y(t)}. How should we handle ArkEnv types?`,options:[{value:`append`,label:`Append types safely (if needed)`,hint:`Recommended`},{value:`overwrite`,label:`Overwrite entirely`,hint:`Destructive`},{value:`skip`,label:`Skip`}]});return I(e)?null:e}return`overwrite`}async function Rt(e){let t=await q({message:`Select an example:`,options:e.examples.map(e=>({value:e.id,label:e.name,...e.description?{hint:e.description}:{}}))});return I(t)?null:t}async function zt(e){let t=await q({message:`Select your framework or build tool:`,initialValue:e.framework,options:[{value:`vanilla`,label:`Vanilla${e.framework===`vanilla`?` (Detected)`:``}`,hint:`Node.js, Bun, server-side or runtime-only validation`},{value:`vite`,label:`Vite${e.framework===`vite`?` (Detected)`:``}`,hint:`Client-side and static inlining validation`},{value:`bun-fullstack`,label:`Bun fullstack dev server${e.framework===`bun-fullstack`?` (Detected)`:``}`,hint:`Client-side bundling and Bun.serve integration`},{value:`nextjs`,label:`Next.js${e.framework===`nextjs`?` (Detected)`:``}`,hint:`Next.js App or Pages Router with build and runtime validation`}]});return I(t)?null:t}async function Bt(e){let t=await G({message:`Optional: Would you also like to bootstrap a custom Bun.build script for programmatic bundling?`,initialValue:e.initialValue??!1});return I(t)?null:t}async function Vt(){let e=await q({message:`Select your preferred validator library:`,options:[{value:`arktype`,label:`ArkType (Recommended)`,hint:`TypeScript's 1:1 validator, optimized from editor to runtime`},{value:`zod`,label:`Zod`,hint:`TypeScript-first schema validation with static type inference`},{value:`valibot`,label:`Valibot`,hint:`The modular and type safe schema library`}]});return I(e)?null:e}async function Ht(){let e=await q({message:`How would you like to structure your environment variables?`,options:[{value:`simple`,label:`Simple (Recommended)`,hint:`A single env.ts file for the best DX`},{value:`strict`,label:`Strict`,hint:`Separate shared, client, and server files for hard bundle boundaries.`}]});return I(e)?null:e}async function Ut(e){let t=await G({message:`Enable automated Next.js code generation for environment variables?`,initialValue:e.initialValue??!0,active:`Yes (Recommended)`,inactive:`No`});return I(t)?null:t}async function Wt(e){let t=await G({message:`Use default config path (${Y(e.defaultEnvPath||`./src/env.ts`)})?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No, let me customize it`});return I(t)?null:t}async function Gt(e){let t=e.defaultEnvPath||`./src/env.ts`;if(!e.useDefaultPath){let e=await Qe({message:`Where should we create the ArkEnv config?`,placeholder:t,initialValue:t,defaultValue:t});if(I(e))return null;let n=typeof e==`string`?e.trim():``;return n===``?t:n}return t}const X={example:Rt,overwriteEnvSchemaFile:Pt,framework:zt,bunBuild:Bt,layout:Ht,nextjsCodegen:Ut,useDefaultPath:Wt,path:Gt,installTypeDefinitions:It,envDtsHandling:Lt,validator:Vt,useEnvExample:Ft};async function Kt(e,t=!1){return(e?.mode||`existing`)===`new`?qt(e,t):Jt(e,t)}async function qt(e,t=!1){let n=e?.examples||[],i=`arkenv-project`;try{let a;if(e?.name){let t=e.name.trim();a=t===`.`||t===`./`||r.default.resolve(process.cwd(),t)===process.cwd()?`.`:t}else if(t)a=i;else{let e=(Z(await Qe({message:`Project name:`,placeholder:i,defaultValue:i}))||i).trim();a=e===`.`||e===`./`||r.default.resolve(process.cwd(),e)===process.cwd()?`.`:e}let o=e?.example;!o&&!t?o=Z(await X.example({examples:n})):!o&&t&&(o=`basic`);let s=n.find(e=>e.id===o);if(!s){let e=n.map(e=>e.id).join(`, `);throw Error(`Unknown example ${o}. Available examples: ${e}`)}return{mode:`new`,example:s.id,name:a,path:`./src/env.ts`,validator:`arktype`,framework:s.framework,language:`ts`,installSkill:!1}}catch(e){if(e instanceof Xt)return null;throw e}}async function Jt(e,n=!1){let r=e?.defaultEnvPath||`./src/env.ts`,i=e?.envKeys||null,a=e?.envKeysSource||`.env.example`;if(n){let n=e?.framework||`vanilla`,a;n===`nextjs`&&(a=e?.isStrict?`strict`:(e?.isSimple,`simple`));let o=await Yt(e,n,r),s;return(n===`vite`||n===`bun-fullstack`)&&(s=o?`append`:`overwrite`),(0,t.shake)({mode:`existing`,path:r,validator:`arktype`,framework:n,layout:a,bunFeatures:n===`bun-fullstack`?e?.bunFeatures??[`serve`]:void 0,language:`ts`,overwriteEnvSchemaFile:!0,installTypeDefinitions:n===`vite`||n===`bun-fullstack`,installSkill:!1,envDtsHandling:s,envKeys:i??void 0,disableCodegen:e?.disableCodegen??!1,wrapNextjsConfig:n===`nextjs`?!0:void 0})}try{let n=Z(await X.overwriteEnvSchemaFile({hasEnvSchemaFile:e?.hasEnvSchemaFile??!1,defaultPath:r})),o=Z(await X.framework({framework:e?.framework})),s;o===`nextjs`&&(s=e?.isStrict?`strict`:e?.isSimple?`simple`:Z(await X.layout()));let c;if(o===`bun-fullstack`){let t=!!e?.bunFeatures?.includes(`build`);c=Z(await X.bunBuild({initialValue:t}))}let l=e?.disableCodegen;o===`nextjs`&&l===void 0&&(l=!Z(await X.nextjsCodegen({initialValue:!0})));let u;if(o===`nextjs`&&!l){let e=await G({message:`Would you like to wrap your Next.js config with ${Y(`withArkEnv`)}?`,initialValue:!0,active:`Yes (Recommended)`,inactive:`No`});if(I(e))throw Ue(`Operation cancelled`),new Xt;u=e}let d=Z(await X.useDefaultPath({defaultEnvPath:r})),f=Z(await X.path({useDefaultPath:d,defaultEnvPath:r})),p=await Yt(e,o,f),m=Z(await X.installTypeDefinitions({framework:o,hasTypeFile:p})),h=Z(await X.envDtsHandling({framework:o,installTypeDefinitions:m,hasTypeFile:p})),g=Z(await X.validator()),_=Z(await X.useEnvExample({detectedKeys:i,keysSource:a}));return(0,t.shake)({mode:`existing`,overwriteEnvSchemaFile:n,framework:o,layout:s,path:f,installTypeDefinitions:m,envDtsHandling:h,validator:g,bunFeatures:o===`bun-fullstack`?c?[`serve`,`build`]:[`serve`]:void 0,language:`ts`,installSkill:!1,envKeys:_?i??void 0:void 0,disableCodegen:l,wrapNextjsConfig:u})}catch(e){if(e instanceof Xt)return null;throw e}}async function Yt(e,t,n){return await e?.hasTypeFileAtPath?.({framework:t,envPath:n})??e?.hasTypeFile??!1}var Xt=class extends Error{constructor(){super(`Operation cancelled`)}};function Z(e){if(e===null||I(e))throw Ue(`Operation cancelled`),new Xt;return e}var Zt=class{async confirm(e,n=!0,r,i){let a=await G((0,t.shake)({message:e,initialValue:n,active:r,inactive:i}));return I(a)?null:a}async runWizard(e,t=!1){return Kt(e,t)}};const Qt={isYes:{long:`--yes`,short:`-y`,kind:`boolean`},isForce:{long:`--force`,short:`-f`,kind:`boolean`},isQuiet:{long:`--quiet`,short:`-q`,kind:`boolean`},isJson:{long:`--json`,short:`-j`,kind:`boolean`},isAgent:{long:`--agent`,short:`-a`,kind:`boolean`},helpRequested:{long:`--help`,short:`-h`,kind:`boolean`},example:{long:`--example`,short:`-e`,kind:`value`},isStrict:{long:`--strict`,short:``,kind:`boolean`},isSimple:{long:`--simple`,short:``,kind:`boolean`},noCodegen:{long:`--no-codegen`,short:`-C`,kind:`boolean`}},$t=new Set(Object.values(Qt).flatMap(e=>[e.long,e.short].filter(Boolean))),en=new Set(Object.values(Qt).filter(e=>e.kind===`value`).flatMap(e=>[e.long,e.short].filter(Boolean)));var tn=class{constructor(e,t={}){let n=e.slice(2),r=[],i=!1;for(let e of n){if(i){r.push(e),i=!1;continue}if(en.has(e)){r.push(e),i=!0;continue}if(/^-[a-zA-Z]{2,}$/.test(e)){let t=e.slice(1).split(``);for(let e of t)r.push(`-${e}`);en.has(`-${t[t.length-1]}`)&&(i=!0)}else r.push(e)}this.args=r,this.command=this.args[0];let a=1,o=[];for(this.validationError=void 0;a<this.args.length;){let e=this.args[a];if(e.startsWith(`-`)){if(!$t.has(e)){this.validationError=`Unknown argument: ${e}`;break}if(en.has(e))if(a+1<this.args.length&&!this.args[a+1].startsWith(`-`))a+=2;else{this.validationError=`Missing value for option: ${e}`;break}else a+=1}else o.push(e),a+=1}this.validationError||(o.length>1?this.validationError=`Unknown argument: ${o[1]}`:this.name=o[0]),this.logger=t.logger||new et({isQuiet:this.isQuiet,isJson:this.isJson,isYes:this.isYes})}get isAgent(){return this.hasFlag(`isAgent`)}get isYes(){return this.isAgent||this.hasFlag(`isYes`)}get isQuiet(){return this.isAgent||this.hasFlag(`isQuiet`)}get isJson(){return this.isAgent||this.hasFlag(`isJson`)}get isForce(){return this.hasFlag(`isForce`)}get helpRequested(){return this.hasFlag(`helpRequested`)}get example(){let e=Qt.example;return this.getFlagValue(e.long,e.short)}get isStrict(){return this.hasFlag(`isStrict`)}get isSimple(){return this.hasFlag(`isSimple`)}get noCodegen(){return this.hasFlag(`noCodegen`)}hasFlag(e){let t=Qt[e];return this.args.includes(t.long)||!!t.short&&this.args.includes(t.short)}get initInput(){let e={isYes:this.isYes,isForce:this.isForce,isQuiet:this.isQuiet,isAgent:this.isAgent,isStrict:this.isStrict,isSimple:this.isSimple};return this.example!==void 0&&(e.example=this.example),this.name!==void 0&&(e.name=this.name),this.noCodegen&&(e.noCodegen=!0),e}getFlagValue(e,t){let n=this.args.findIndex(n=>n===e||n===t);if(n!==-1&&this.args[n+1]&&!this.args[n+1].startsWith(`-`))return this.args[n+1]}},nn=`1.0.0-alpha.0`;function rn(e,t=2,n=4){let r=Math.max(...e.map(e=>e.left.length),0),i=` `.repeat(t);return e.map(e=>{let t=` `.repeat(r-e.left.length+n);return`${i}${e.left}${t}${e.right}`})}var an=class{constructor(e){this.logger=e}async execute(){let e=[{left:`arkenv init [project-name]`,right:`Set up ArkEnv in your project`}],t=[{left:`--yes, -y`,right:`Skip prompts and use defaults (also passed to subprocesses)`},{left:`--force, -f`,right:`Bypass technical requirement checks and dirty git working tree check, then force scaffolding`},{left:`--agent, -a`,right:`Enable non-interactive, machine-readable mode for AI agents. Bypasses all prompts and outputs structured JSON. Macro for --yes --quiet --json`},{left:`--example, -e`,right:`Specify an example name when creating a new project`},{left:`--quiet, -q`,right:`Quiet mode: Suppress output, capture logs on failure`},{left:`--json, -j`,right:`Output structured JSON to stdout`},{left:`--no-codegen, -C`,right:`Disable automatic env.gen.ts code generation for Next.js`},{left:`--help, -h`,right:`Show this help message`}];this.logger.log(`ArkEnv CLI v${nn}`),this.logger.log(`\n${y.default.bold(`Usage:`)}`);for(let t of rn(e))this.logger.log(t);this.logger.log(`\n${y.default.bold(`Options:`)}`);for(let e of rn(t))this.logger.log(e)}};function on(e,t,n,r){let{extraImports:i,serverField:a,clientField:o,sharedField:s,defaultServerFields:c,defaultClientFields:l,defaultSharedFields:u}=t,d=[],f=[],p=[];if(e&&e.length>0)for(let t of e)t.startsWith(`NEXT_PUBLIC_`)?f.push(o(t)):t===`NODE_ENV`?p.push(s(t)):d.push(a(t));else d.push(...c),f.push(...l),p.push(...u);let m=[];if(d.length>0&&m.push(`\tserver: {\n${d.join(`
114
114
  `)}\n\t}`),f.length>0&&m.push(`\tclient: {\n${f.join(`
115
115
  `)}\n\t}`),p.length>0&&m.push(`\tshared: {\n${p.join(`
116
116
  `)}\n\t}`),r){let t=[];if(e&&e.length>0)for(let n of e)(n.startsWith(`NEXT_PUBLIC_`)||n===`NODE_ENV`)&&t.push(`\t\t${n}: process.env.${n},`);else t.push(` NEXT_PUBLIC_API_URL: process.env.NEXT_PUBLIC_API_URL,`,` NODE_ENV: process.env.NODE_ENV,`);return m.push(`\truntimeEnv: {\n${t.join(`
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@arkenv/cli",
3
3
  "type": "module",
4
- "version": "0.2.10",
4
+ "version": "1.0.0-alpha.0",
5
5
  "description": "Interactive CLI for scaffolding ArkEnv projects",
6
6
  "bin": {
7
7
  "arkenv": "./dist/index.cjs"