untitledui 0.1.33 → 0.1.35

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.mjs +21 -21
  2. package/package.json +1 -1
package/dist/index.mjs CHANGED
@@ -1,10 +1,10 @@
1
1
  #!/usr/bin/env node
2
- import{Command as n0}from"commander";import r3 from"async-retry";import N from"chalk";import{Command as v0}from"commander";import{execa as J3}from"execa";import*as F from"fs";import Y3 from"ora";import R0 from"os";import*as D from"path";import Z3 from"prompts";import{Project as u0}from"ts-morph";import h3 from"node-fetch";import{Readable as q0,pipeline as X0}from"stream";import{x as B0}from"tar";import{promisify as K0}from"util";var U0=K0(X0);async function f3(Q,W){try{let z=await b0(W);await U0(z,B0({cwd:Q,strip:1}))}catch(z){throw new Error(`Failed to download or extract repository from API: ${z instanceof Error?z.message:z}`)}}async function b0(Q){let W=`https://www.untitledui.com/react/api/download-repo?template=${Q.template}`;try{let z=await h3(W,{method:"GET",headers:{"Content-Type":"application/json",Accept:"application/octet-stream"}});if(z.status===403||z.status===404)throw new Error("Repository not found");if(!z.ok)throw new Error(`Failed to download from API. Status: ${z.status} ${z.statusText}`);if(!z.body)throw new Error("Response body is empty");return q0.from(z.body)}catch(z){throw new Error(`Error downloading tarball: ${z instanceof Error?z.message:z}`)}}async function X3(Q){let W=`https://www.untitledui.com/react/api/validate-key?key=${Q}`;try{return(await h3(W)).status===200}catch{return!1}}import J0 from"node-fetch";var m3={invalid_key:"Invalid key provided",no_components_found:"No components found",no_components_provided:"No components provided"};async function I3(Q,W,z){try{let Z=await J0("https://www.untitledui.com/react/api/components",{method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json"},body:JSON.stringify({type:Q,components:W,key:z})});if(!Z.ok)console.log(m3?.[Z.statusText]||m3.no_components_found),process.exit(1);return await Z.json()}catch(Z){return null}}import N3 from"node-fetch";var i={invalid_key:"Invalid key provided",no_components_found:"No components found",no_components_provided:"No components provided"};async function c3(Q,W=""){let z=`https://www.untitledui.com/react/api/components/list?key=${W}&type=${Q}`;try{let q=await N3(z),Z=await q.json();if(!q.ok)console.log(i?.[q.statusText]||i.no_components_found),process.exit(1);if(!Z?.components?.length)return null;return Z}catch(q){return console.error(q),null}}async function l3(Q,W="",z){let q=`https://www.untitledui.com/react/api/components/list?key=${W}&type=${Q}&subfolders=${z.join(",")}`;try{let Z=await N3(q);if(!Z.ok)console.log(i?.[Z.statusText]||i.no_components_found),process.exit(1);let U=await Z.json();if(!U?.components?.length)return null;return U}catch(Z){return console.error(Z),null}}async function a3(Q=""){let W=`https://www.untitledui.com/react/api/components/list?key=${Q}`;try{let z=await N3(W);if(!z.ok)console.log(i?.[z.statusText]||i.no_components_found),process.exit(1);let q=await z.json();if(!q?.types?.length)return null;return q}catch(z){return console.error(z),null}}import j0 from"fast-glob";import*as E3 from"path";import{Project as V1}from"ts-morph";import{loadConfig as G0}from"tsconfig-paths";import $1 from"prettier";import U3 from"fast-glob";import*as B3 from"fs";import*as K3 from"path";import{loadConfig as V0}from"tsconfig-paths";var h=["**/node_modules/**",".next","public","dist","build"],s3={"next-app":"Next.js (App)","next-pages":"Next.js (Pages)",vite:"Vite",other:"Other"};async function p(Q){let W=B3.existsSync(K3.resolve(Q,"src")),z=B3.existsSync(K3.resolve(Q,`${W?"src/":""}app`)),[q,Z,U,L]=await Promise.all([U3.glob("**/{next,vite,astro}.config.*|gatsby-config.*",{cwd:Q,deep:2,ignore:h}),L0(Q),M0(Q),H0(Q)]),H={framework:"other",isTsx:Z,tailwindFile:U||null,aliasPrefix:L,isSrcDir:W,isUsingAppDir:z};if(q.find((V)=>V.startsWith("next.config."))?.length)return H.framework=z?"next-app":"next-pages",H;else if(q.find((V)=>V.startsWith("vite.config."))?.length)return H.framework="vite",H;else if(q?.length||B3.existsSync(K3.resolve(Q,"package.json")))return H.framework="other",H;return null}async function L0(Q){return(await U3.glob("tsconfig.*",{cwd:Q,deep:2,ignore:h})).length>0}async function M0(Q){let W=await U3.glob("tailwind.config.*",{cwd:Q,deep:2,ignore:h});if(!W.length)return null;return W[0]}async function H0(Q){let W=await V0(Q);if(W?.resultType==="failed"||!Object.keys(W.paths).length)return null;let z={};for(let[q,Z]of Object.entries(W.paths)){let U=q.replace(/\/\*$/,"/");if(Z.some((L)=>L.includes("/app/*")))z.appPrefix=U;else if(Z.some((L)=>L.includes("/components/*")))z.componentsPrefix=U;else if(Z.some((L)=>L.includes("/utils/*")))z.utilsPrefix=U;else if(Z.some((L)=>L.includes("/styles/*")))z.stylesPrefix=U;else if(Z.some((L)=>L.includes("./*")||L.includes("/src/*")))z.srcPrefix=U}return z||null}function o(Q){let W=G0(Q),z=j0.sync(["tailwind.config.*","**/globals.css","**/{layout,_app,main}.tsx","package.json"],{cwd:Q,deep:4,absolute:!0,onlyFiles:!0,ignore:h}),q={tailwindFile:z.find((Z)=>Z.includes("tailwind.config.")),cssFile:z.find((Z)=>Z.includes("globals.css")),layoutFile:z.find((Z)=>Z.includes("layout")),appFile:z.find((Z)=>Z.includes("_app")),mainFile:z.find((Z)=>Z.includes("main")),packageJson:z.find((Z)=>Z.includes("package.json")),tsConfig:W?.resultType==="success"?W?.configFileAbsolutePath:void 0};if(W.resultType==="failed")throw new Error(`Failed to load tsconfig.json. ${W.message??""}`.trim());return q}function t(Q,W,z={},q=""){if(Q.includes("components")){if(z?.componentsPrefix)return Q.replace(/@\/components\//,E3.posix.join(z?.componentsPrefix,W?W.replace(/components\//,""):"","/"));if(W){let Z=z?.srcPrefix?E3.posix.join(z?.srcPrefix,W,"/"):q;return Q.replace(/@\/components\//,Z)}}if(Q.includes("app")&&z?.appPrefix)return Q.replace(/^@\/app\//,z?.appPrefix);if(Q.includes("utils")&&z?.utilsPrefix)return Q.replace(/^@\/utils\//,z?.utilsPrefix);if(Q.includes("styles")&&z?.stylesPrefix)return Q.replace(/^@\/styles\//,z?.stylesPrefix);if(z?.srcPrefix)return Q.replace(/^@\//,z?.srcPrefix);return Q}function C(){if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("yarn"))return"yarn";if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("pnpm"))return"pnpm";if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("bun"))return"bun";return"npm"}function e(){switch(C()){case"yarn":return"yarn";case"pnpm":return"pnpx";case"bun":return"bunx";default:return"npx"}}function n3(){switch(C()){case"yarn":return"yarn dev";case"pnpm":return"pnpm dev";case"bun":return"bun dev";default:return"npm run dev"}}function b3(Q){return Q.replace(/^[ \t]*\/\/\s*(TODO:|collapse-(start|end)).*\r?\n?|[ \t]*{\s*\/\*\s*(TODO:|collapse-(start|end)).*?\*\/\s*}\r?\n?/gm,"")}var I0=D.join(R0.homedir(),".untitledui"),c=D.join(I0,"config.json"),K={components:[],path:"",type:void 0,license:""};if(F.existsSync(c)){let Q=JSON.parse(F.readFileSync(c,"utf-8"));K.license=Q.license}var V3=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
3
- `),process.exit(1)},i3=new v0().name("add").description("add a component to your project").argument("[components...]","the components to add").option("-a, --all","add all available components",!1).option("-o, --overwrite","overwrite existing files.",!1).option("-p, --path <path>","the path to add the component to.").option("-d, --dir <directory>","the directory where the project is located.").option("-t, --type <base|marketing|shared-assets|application|foundations>","the type of the component to add.").action(async(Q,W)=>{if(Q)K.components=Q;if(W)K.all=W.all,K.dir=W.dir,K.path=W.path,K.overwrite=W.overwrite,K.license=W.license||K.license;try{await A3(K)}catch(z){console.error(N.red(z))}});async function A3(Q){if(Q)K={...K,...Q};let W=Y3().start(),z=D.posix.join(process.cwd(),K.dir||"");if(!F.existsSync(D.resolve(z,"package.json")))W.warn("This command should be run in a project directory."),process.exit(1);let Z=await p(z);if(K.license){if(!await X3(K.license))W.fail("Invalid license key"),process.exit(1);if(!F.existsSync(c)){let X=D.dirname(c);F.mkdirSync(X,{recursive:!0}),F.writeFileSync(c,JSON.stringify({license:K.license},null,2))}if(JSON.parse(F.readFileSync(c,"utf-8")).license!==K.license)F.writeFileSync(c,JSON.stringify({license:K.license},null,2),"utf-8")}W.stop();let U=[];if(K.components.length){let $=await I3(K.type,K.components,K.license);if($&&$.pro&&$.pro.length>0){if(console.log(),$.pro.length===1){let Y=$.pro[0]?.split("/")[1]||$.pro[0];console.log(N.yellow(`\uD83D\uDD12 The ${N.cyan(Y)} component requires PRO access.`))}else console.log(N.yellow("\uD83D\uDD12 The following components require PRO access:")),$.pro.forEach((Y)=>{let X=Y?.split("/")[1]||Y;console.log(` • ${N.cyan(X)}`)});console.log(),console.log("To access PRO components:"),console.log(` ${N.green("→")} If you've already purchased: ${N.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${N.green("→")} To purchase PRO components: ${N.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(!$?.components.length)console.log("No components found"),process.exit(1);U.push(...$.components)}if(!K?.type&&!K?.components.length){let $=await a3(K.license);if(!$)console.log("No component types found"),process.exit(1);let Y=await Z3({type:"select",name:"type",onState:V3,message:`What type of ${N.cyan("component")} are you adding?`,choices:$?.types.map((X)=>({title:X,value:X}))});K.type=Y.type}if(!K?.path){let $=await Z3({type:"text",name:"path",onState:V3,message:`Where would you like to add the ${N.cyan("components")}?`,initial:"components"});K.path=$.path}if(!K?.components.length){let $=await c3(K?.type,K.license);if(!$)console.log("No components found"),process.exit(1);let Y=await Z3({type:"multiselect",name:"components",onState:V3,message:`Which ${N.cyan("components")} would you like to add?`,choices:$?.components?.map((J)=>({title:J?.name+(J?.count?` (${J?.count} variants)`:"")||"example",value:J||"example",selected:K.components.includes(J.name)})),instructions:!1,hint:"- Space to select. Return to submit"});if(!Y.components||!Y.components.length)console.log("No option selected. Exiting..."),process.exit(1);let X=Y.components.filter((J)=>J?.type==="file").map((J)=>J.name),b=Y.components.filter((J)=>J?.type==="dir").map((J)=>J.name),S=[];if(b.length){let J=await l3(K?.type,K.license,b);if(J&&J.components.length)for(let x of J.components){let[I,g]=Object.entries(x)[0]||[],u=await Z3({type:"select",name:"component",onState:V3,message:`Which ${N.cyan("variant")} from ${N.cyan(I)} would you like to add?`,choices:g?.map((A)=>({title:A?.name||"example",value:A?.name||"example",selected:K.components.includes(A.name)})),instructions:!1,hint:"- Space to select. Return to submit"});if(!u.component)console.log("No variant selected for "+N.cyan(I));S.push(I+"/"+u.component)}else console.log("No variants found")}K.components=[...S,...X]}if(!K.components?.length)W.warn("No components selected. Exiting."),process.exit(1);let L=o(z),H=new Set,V=new Set,E=new Set,T=new u0({tsConfigFilePath:L?.tsConfig});if(K.type&&K.components.length){let $=await I3(K.type,K.components,K.license);if(!$?.components.length)console.log("No components found"),process.exit(1);U.push(...$.components)}if(U.forEach(($)=>{let Y=Y3(`Adding ${$.name}...`).start(),X=$.files;$.dependencies.forEach((b)=>V.add(b)),$.devDependencies.forEach((b)=>E.add(b));try{if(X?.forEach(async({path:b,code:S})=>{let J=D.posix.join(z,`${Z?.isSrcDir&&"src"}`,b.replace(/components\//,K.path+"/")),x=Z?.framework==="vite"?S.replace(`"use client";
2
+ import{Command as n3}from"commander";import r0 from"async-retry";import N from"chalk";import{Command as v3}from"commander";import{execa as J0}from"execa";import*as F from"fs";import Y0 from"ora";import R3 from"os";import*as D from"path";import Z0 from"prompts";import{Project as u3}from"ts-morph";import h0 from"node-fetch";import{Readable as q3,pipeline as X3}from"stream";import{x as B3}from"tar";import{promisify as K3}from"util";var U3=K3(X3);async function f0(Q,W){try{let z=await b3(W);await U3(z,B3({cwd:Q,strip:1}))}catch(z){throw new Error(`Failed to download or extract repository from API: ${z instanceof Error?z.message:z}`)}}async function b3(Q){let W=`https://www.untitledui.com/react/api/download-repo?template=${Q.template}`;try{let z=await h0(W,{method:"GET",headers:{"Content-Type":"application/json",Accept:"application/octet-stream"}});if(z.status===403||z.status===404)throw new Error("Repository not found");if(!z.ok)throw new Error(`Failed to download from API. Status: ${z.status} ${z.statusText}`);if(!z.body)throw new Error("Response body is empty");return q3.from(z.body)}catch(z){throw new Error(`Error downloading tarball: ${z instanceof Error?z.message:z}`)}}async function X0(Q){let W=`https://www.untitledui.com/react/api/validate-key?key=${Q}`;try{return(await h0(W)).status===200}catch{return!1}}import J3 from"node-fetch";var m0={invalid_key:"Invalid key provided",no_components_found:"No components found",no_components_provided:"No components provided"};async function I0(Q,W,z){try{let Z=await J3("https://www.untitledui.com/react/api/components",{method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json"},body:JSON.stringify({type:Q,components:W,key:z})});if(!Z.ok)console.log(m0?.[Z.statusText]||m0.no_components_found),process.exit(1);return await Z.json()}catch(Z){return null}}import N0 from"node-fetch";var i={invalid_key:"Invalid key provided",no_components_found:"No components found",no_components_provided:"No components provided"};async function c0(Q,W=""){let z=`https://www.untitledui.com/react/api/components/list?key=${W}&type=${Q}`;try{let q=await N0(z),Z=await q.json();if(!q.ok)console.log(i?.[q.statusText]||i.no_components_found),process.exit(1);if(!Z?.components?.length)return null;return Z}catch(q){return console.error(q),null}}async function l0(Q,W="",z){let q=`https://www.untitledui.com/react/api/components/list?key=${W}&type=${Q}&subfolders=${z.join(",")}`;try{let Z=await N0(q);if(!Z.ok)console.log(i?.[Z.statusText]||i.no_components_found),process.exit(1);let U=await Z.json();if(!U?.components?.length)return null;return U}catch(Z){return console.error(Z),null}}async function a0(Q=""){let W=`https://www.untitledui.com/react/api/components/list?key=${Q}`;try{let z=await N0(W);if(!z.ok)console.log(i?.[z.statusText]||i.no_components_found),process.exit(1);let q=await z.json();if(!q?.types?.length)return null;return q}catch(z){return console.error(z),null}}import j3 from"fast-glob";import*as E0 from"path";import{Project as V1}from"ts-morph";import{loadConfig as G3}from"tsconfig-paths";import $1 from"prettier";import U0 from"fast-glob";import*as B0 from"fs";import*as K0 from"path";import{loadConfig as V3}from"tsconfig-paths";var h=["**/node_modules/**",".next","public","dist","build"],s0={"next-app":"Next.js (App)","next-pages":"Next.js (Pages)",vite:"Vite",other:"Other"};async function p(Q){let W=B0.existsSync(K0.resolve(Q,"src")),z=B0.existsSync(K0.resolve(Q,`${W?"src/":""}app`)),[q,Z,U,L]=await Promise.all([U0.glob("**/{next,vite,astro}.config.*|gatsby-config.*",{cwd:Q,deep:2,ignore:h}),L3(Q),M3(Q),H3(Q)]),H={framework:"other",isTsx:Z,tailwindFile:U||null,aliasPrefix:L,isSrcDir:W,isUsingAppDir:z};if(q.find((V)=>V.startsWith("next.config."))?.length)return H.framework=z?"next-app":"next-pages",H;else if(q.find((V)=>V.startsWith("vite.config."))?.length)return H.framework="vite",H;else if(q?.length||B0.existsSync(K0.resolve(Q,"package.json")))return H.framework="other",H;return null}async function L3(Q){return(await U0.glob("tsconfig.*",{cwd:Q,deep:2,ignore:h})).length>0}async function M3(Q){let W=await U0.glob("tailwind.config.*",{cwd:Q,deep:2,ignore:h});if(!W.length)return null;return W[0]}async function H3(Q){let W=await V3(Q);if(W?.resultType==="failed"||!Object.keys(W.paths).length)return null;let z={};for(let[q,Z]of Object.entries(W.paths)){let U=q.replace(/\/\*$/,"/");if(Z.some((L)=>L.includes("/app/*")))z.appPrefix=U;else if(Z.some((L)=>L.includes("/components/*")))z.componentsPrefix=U;else if(Z.some((L)=>L.includes("/utils/*")))z.utilsPrefix=U;else if(Z.some((L)=>L.includes("/styles/*")))z.stylesPrefix=U;else if(Z.some((L)=>L.includes("./*")||L.includes("/src/*")))z.srcPrefix=U}return z||null}function o(Q){let W=G3(Q),z=j3.sync(["tailwind.config.*","**/globals.css","**/{layout,_app,main}.tsx","package.json"],{cwd:Q,deep:4,absolute:!0,onlyFiles:!0,ignore:h}),q={tailwindFile:z.find((Z)=>Z.includes("tailwind.config.")),cssFile:z.find((Z)=>Z.includes("globals.css")),layoutFile:z.find((Z)=>Z.includes("layout")),appFile:z.find((Z)=>Z.includes("_app")),mainFile:z.find((Z)=>Z.includes("main")),packageJson:z.find((Z)=>Z.includes("package.json")),tsConfig:W?.resultType==="success"?W?.configFileAbsolutePath:void 0};if(W.resultType==="failed")throw new Error(`Failed to load tsconfig.json. ${W.message??""}`.trim());return q}function t(Q,W,z={},q=""){if(Q.includes("components")){if(z?.componentsPrefix)return Q.replace(/@\/components\//,E0.posix.join(z?.componentsPrefix,W?W.replace(/components\//,""):"","/"));if(W){let Z=z?.srcPrefix?E0.posix.join(z?.srcPrefix,W,"/"):q;return Q.replace(/@\/components\//,Z)}}if(Q.includes("app")&&z?.appPrefix)return Q.replace(/^@\/app\//,z?.appPrefix);if(Q.includes("utils")&&z?.utilsPrefix)return Q.replace(/^@\/utils\//,z?.utilsPrefix);if(Q.includes("styles")&&z?.stylesPrefix)return Q.replace(/^@\/styles\//,z?.stylesPrefix);if(z?.srcPrefix)return Q.replace(/^@\//,z?.srcPrefix);return Q}function C(){if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("yarn"))return"yarn";if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("pnpm"))return"pnpm";if("bun/1.2.15 npm/? node/v22.6.0 darwin arm64".startsWith("bun"))return"bun";return"npm"}function e(){switch(C()){case"yarn":return"yarn";case"pnpm":return"pnpx";case"bun":return"bunx";default:return"npx"}}function n0(){switch(C()){case"yarn":return"yarn dev";case"pnpm":return"pnpm dev";case"bun":return"bun dev";default:return"npm run dev"}}function b0(Q){return Q.replace(/^[ \t]*\/\/\s*(TODO:|collapse-(start|end)).*\r?\n?|[ \t]*{\s*\/\*\s*(TODO:|collapse-(start|end)).*?\*\/\s*}\r?\n?/gm,"")}var I3=D.join(R3.homedir(),".untitledui"),c=D.join(I3,"config.json"),K={components:[],path:"",type:void 0,license:""};if(F.existsSync(c)){let Q=JSON.parse(F.readFileSync(c,"utf-8"));K.license=Q.license}var V0=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
3
+ `),process.exit(1)},i0=new v3().name("add").description("add a component to your project").argument("[components...]","the components to add").option("-a, --all","add all available components",!1).option("-o, --overwrite","overwrite existing files.",!1).option("-p, --path <path>","the path to add the component to.").option("-d, --dir <directory>","the directory where the project is located.").option("-t, --type <base|marketing|shared-assets|application|foundations>","the type of the component to add.").action(async(Q,W)=>{if(Q)K.components=Q;if(W)K.all=W.all,K.dir=W.dir,K.path=W.path,K.overwrite=W.overwrite,K.license=W.license||K.license;try{await A0(K)}catch(z){console.error(N.red(z))}});async function A0(Q){if(Q)K={...K,...Q};let W=Y0().start(),z=D.posix.join(process.cwd(),K.dir||"");if(!F.existsSync(D.resolve(z,"package.json")))W.warn("This command should be run in a project directory."),process.exit(1);let Z=await p(z);if(K.license){if(!await X0(K.license))W.fail("Invalid license key"),process.exit(1);if(!F.existsSync(c)){let X=D.dirname(c);F.mkdirSync(X,{recursive:!0}),F.writeFileSync(c,JSON.stringify({license:K.license},null,2))}if(JSON.parse(F.readFileSync(c,"utf-8")).license!==K.license)F.writeFileSync(c,JSON.stringify({license:K.license},null,2),"utf-8")}W.stop();let U=[];if(K.components.length){let $=await I0(K.type,K.components,K.license);if($&&$.pro&&$.pro.length>0){if(console.log(),$.pro.length===1){let Y=$.pro[0]?.split("/")[1]||$.pro[0];console.log(N.yellow(`\uD83D\uDD12 The ${N.cyan(Y)} component requires PRO access.`))}else console.log(N.yellow("\uD83D\uDD12 The following components require PRO access:")),$.pro.forEach((Y)=>{let X=Y?.split("/")[1]||Y;console.log(` • ${N.cyan(X)}`)});console.log(),console.log("To access PRO components:"),console.log(` ${N.green("→")} If you've already purchased: ${N.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${N.green("→")} To purchase PRO components: ${N.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(!$?.components.length)console.log("No components found"),process.exit(1);U.push(...$.components)}if(!K?.type&&!K?.components.length){let $=await a0(K.license);if(!$)console.log("No component types found"),process.exit(1);let Y=await Z0({type:"select",name:"type",onState:V0,message:`What type of ${N.cyan("component")} are you adding?`,choices:$?.types.map((X)=>({title:X,value:X}))});K.type=Y.type}if(!K?.path){let $=await Z0({type:"text",name:"path",onState:V0,message:`Where would you like to add the ${N.cyan("components")}?`,initial:"components"});K.path=$.path}if(!K?.components.length){let $=await c0(K?.type,K.license);if(!$)console.log("No components found"),process.exit(1);let Y=await Z0({type:"multiselect",name:"components",onState:V0,message:`Which ${N.cyan("components")} would you like to add?`,choices:$?.components?.map((J)=>({title:J?.name+(J?.count?` (${J?.count} variants)`:"")||"example",value:J||"example",selected:K.components.includes(J.name)})),instructions:!1,hint:"- Space to select. Return to submit"});if(!Y.components||!Y.components.length)console.log("No option selected. Exiting..."),process.exit(1);let X=Y.components.filter((J)=>J?.type==="file").map((J)=>J.name),b=Y.components.filter((J)=>J?.type==="dir").map((J)=>J.name),S=[];if(b.length){let J=await l0(K?.type,K.license,b);if(J&&J.components.length)for(let x of J.components){let[I,g]=Object.entries(x)[0]||[],u=await Z0({type:"select",name:"component",onState:V0,message:`Which ${N.cyan("variant")} from ${N.cyan(I)} would you like to add?`,choices:g?.map((A)=>({title:A?.name||"example",value:A?.name||"example",selected:K.components.includes(A.name)})),instructions:!1,hint:"- Space to select. Return to submit"});if(!u.component)console.log("No variant selected for "+N.cyan(I));S.push(I+"/"+u.component)}else console.log("No variants found")}K.components=[...S,...X]}if(!K.components?.length)W.warn("No components selected. Exiting."),process.exit(1);let L=o(z),H=new Set,V=new Set,E=new Set,T=new u3({tsConfigFilePath:L?.tsConfig});if(K.type&&K.components.length){let $=await I0(K.type,K.components,K.license);if(!$?.components.length)console.log("No components found"),process.exit(1);U.push(...$.components)}if(U.forEach(($)=>{let Y=Y0(`Adding ${$.name}...`).start(),X=$.files;$.dependencies.forEach((b)=>V.add(b)),$.devDependencies.forEach((b)=>E.add(b));try{if(X?.forEach(async({path:b,code:S})=>{let J=D.posix.join(z,`${Z?.isSrcDir?"src":""}`,b.replace(/components\//,K.path+"/")),x=Z?.framework==="vite"?S.replace(`"use client";
4
4
 
5
- `,""):S,I=b3(x),g=D.dirname(J);if(F.existsSync(J)&&!K.overwrite){if(F.readFileSync(J,"utf-8")!==I)H.add({code:I,path:J})}else{F.mkdirSync(g,{recursive:!0}),F.writeFileSync(J,I);let u=D.relative(D.resolve(z,`${Z?.isSrcDir&&"src"}`,K.path),J).split("/").length,A=u===1?"./":"../".repeat(u-1),k=T.addSourceFileAtPath(D.resolve(J));k.getImportDeclarations().forEach((P)=>{let W3=P.getModuleSpecifierValue();P.setModuleSpecifier(t(W3,K.path,Z?.aliasPrefix,A))}),await k.save()}}),H.size)Y.warn(`Some files of ${N.yellow($.name)} already exist`);else Y.succeed(`${N.green($.name)} is added successfully`)}catch(b){Y.fail(`
5
+ `,""):S,I=b0(x),g=D.dirname(J);if(F.existsSync(J)&&!K.overwrite){if(F.readFileSync(J,"utf-8")!==I)H.add({code:I,path:J})}else{F.mkdirSync(g,{recursive:!0}),F.writeFileSync(J,I);let u=D.relative(D.resolve(z,`${Z?.isSrcDir?"src":""}`,K.path),J).split("/").length,A=u===1?"./":"../".repeat(u-1),k=T.addSourceFileAtPath(D.resolve(J));k.getImportDeclarations().forEach((P)=>{let W0=P.getModuleSpecifierValue();P.setModuleSpecifier(t(W0,K.path,Z?.aliasPrefix,A))}),await k.save()}}),H.size)Y.warn(`Some files of ${N.yellow($.name)} already exist`);else Y.succeed(`${N.green($.name)} is added successfully`)}catch(b){Y.fail(`
6
6
  Failed to add the component ${N.red($.name)}`),console.error(N.red(b)),process.exit(1)}}),H.size&&!K?.overwrite)if(console.log(`
7
- Following files already exist in the directory.`),H.forEach((Y)=>{console.log(N.green(`- ${D.relative(z,Y.path)}`))}),(await Z3({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let Y=Y3("Overwriting files").start();H.forEach((X)=>{let b=D.relative(D.resolve(z,`${Z?.isSrcDir&&"src"}`,K.path),X.path).split("/").length,S=b===1?"./":"../".repeat(b-1),J=T.addSourceFileAtPath(D.resolve(X.path));J.replaceWithText(X.code),J.getImportDeclarations().forEach((x)=>{let I=x.getModuleSpecifierValue();x.setModuleSpecifier(t(I,K.path,Z?.aliasPrefix,S))}),J.saveSync()}),Y.succeed("Files are overwritten")}else console.log(`Use ${N.cyan("--overwrite")} or ${N.cyan("-o")} to overwrite existing files, or refer to the documentation ${N.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`),process.exit(1);let R=C();if(V?.size){let $=Y3("Installing component dependencies").start();await r3(()=>J3(R,[R==="npm"?"install":"add",...V],{cwd:z}).catch(async(Y)=>{if(Y.message.includes("peer"))$.warn("Component dependencies conflict detected. Retrying with --legacy-peer-deps..."),$.start("Installing component dependencies with --legacy-peer-deps flag"),await J3(R,[R==="npm"?"install":"add",...V,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),$.succeed("Component dependencies are installed")}if(E?.size){let $=Y3("Installing component devDependencies").start();await r3(()=>J3(R,[R==="npm"?"install":"add","-D",...E],{cwd:z}).catch(async(Y)=>{if(Y.message.includes("peer"))$.warn("Component devDependencies conflict detected. Retrying with --legacy-peer-deps..."),$.start("Installing component devDependencies with --legacy-peer-deps flag"),await J3(R,[R==="npm"?"install":"add","-D",...E,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),$.succeed("Component devDependencies are installed")}if(K.message)console.log(K.message);process.exit(0)}import D3 from"chalk";import{Command as y0}from"commander";import*as f from"fs";import _0 from"http";import D0 from"open";import w0 from"ora";import T0 from"os";import*as T3 from"path";import{URL as S0}from"url";import*as L3 from"fs";import*as l from"path";import{fileURLToPath as N0}from"url";var E0=N0(import.meta.url),y3=l.dirname(E0);function A0(){let Q=[l.join(y3,"..","templates","auth-template.html"),l.join(y3,"templates","auth-template.html"),l.join(process.cwd(),"node_modules","untitledui","templates","auth-template.html"),l.join(y3,"..","..","templates","auth-template.html")];for(let W of Q)if(L3.existsSync(W))return W;throw new Error("Auth template file not found. Please ensure the CLI package is properly installed.")}function p3(){try{let Q=A0();return L3.readFileSync(Q,"utf-8")}catch(Q){return console.warn("Warning: Using fallback auth template. Some styling may be missing."),`<!doctype html>
7
+ Following files already exist in the directory.`),H.forEach((Y)=>{console.log(N.green(`- ${D.relative(z,Y.path)}`))}),(await Z0({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let Y=Y0("Overwriting files").start();H.forEach((X)=>{let b=D.relative(D.resolve(z,`${Z?.isSrcDir?"src":""}`,K.path),X.path).split("/").length,S=b===1?"./":"../".repeat(b-1),J=T.addSourceFileAtPath(D.resolve(X.path));J.replaceWithText(X.code),J.getImportDeclarations().forEach((x)=>{let I=x.getModuleSpecifierValue();x.setModuleSpecifier(t(I,K.path,Z?.aliasPrefix,S))}),J.saveSync()}),Y.succeed("Files are overwritten")}else console.log(`Use ${N.cyan("--overwrite")} or ${N.cyan("-o")} to overwrite existing files, or refer to the documentation ${N.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`),process.exit(1);let R=C();if(V?.size){let $=Y0("Installing component dependencies").start();await r0(()=>J0(R,[R==="npm"?"install":"add",...V],{cwd:z}).catch(async(Y)=>{if(Y.message.includes("peer"))$.warn("Component dependencies conflict detected. Retrying with --legacy-peer-deps..."),$.start("Installing component dependencies with --legacy-peer-deps flag"),await J0(R,[R==="npm"?"install":"add",...V,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),$.succeed("Component dependencies are installed")}if(E?.size){let $=Y0("Installing component devDependencies").start();await r0(()=>J0(R,[R==="npm"?"install":"add","-D",...E],{cwd:z}).catch(async(Y)=>{if(Y.message.includes("peer"))$.warn("Component devDependencies conflict detected. Retrying with --legacy-peer-deps..."),$.start("Installing component devDependencies with --legacy-peer-deps flag"),await J0(R,[R==="npm"?"install":"add","-D",...E,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),$.succeed("Component devDependencies are installed")}if(K.message)console.log(K.message);process.exit(0)}import D0 from"chalk";import{Command as y3}from"commander";import*as f from"fs";import _3 from"http";import D3 from"open";import w3 from"ora";import T3 from"os";import*as T0 from"path";import{URL as S3}from"url";import*as L0 from"fs";import*as l from"path";import{fileURLToPath as N3}from"url";var E3=N3(import.meta.url),y0=l.dirname(E3);function A3(){let Q=[l.join(y0,"..","templates","auth-template.html"),l.join(y0,"templates","auth-template.html"),l.join(process.cwd(),"node_modules","untitledui","templates","auth-template.html"),l.join(y0,"..","..","templates","auth-template.html")];for(let W of Q)if(L0.existsSync(W))return W;throw new Error("Auth template file not found. Please ensure the CLI package is properly installed.")}function p0(){try{let Q=A3();return L0.readFileSync(Q,"utf-8")}catch(Q){return console.warn("Warning: Using fallback auth template. Some styling may be missing."),`<!doctype html>
8
8
  <html lang="en">
9
9
  <head>
10
10
  <meta charset="UTF-8" />
@@ -50,29 +50,29 @@ Following files already exist in the directory.`),H.forEach((Y)=>{console.log(N.
50
50
  {{AUTO_CLOSE_SCRIPT}}
51
51
  </div>
52
52
  </body>
53
- </html>`}}function o3(){return p3().replace("{{TITLE}}","Authentication successful").replace("{{HEADING}}","Authentication successful").replace("{{DESCRIPTION}}","You can now close this tab and return to your terminal.").replace("{{AUTO_CLOSE_SCRIPT}}","<script>setTimeout(() => window.close(), 10000);</script>")}function M3(Q){return p3().replace("{{TITLE}}","Authentication failed").replace("{{HEADING}}","Authentication failed").replace("{{DESCRIPTION}}",Q).replace("{{AUTO_CLOSE_SCRIPT}}","")}var w3=T3.join(T0.homedir(),".untitledui"),_3=T3.join(w3,"config.json"),t3=new y0().name("login").description("authenticate with Untitled UI to access PRO components").action(async()=>{let Q=w0("Starting authentication...").start();try{await x0(Q),Q.succeed("Authentication completed successfully!"),console.log(D3.green(`
54
- ✨ You can now access PRO components with the CLI!`)),process.exit(0)}catch(W){Q.fail(`Authentication failed: ${W instanceof Error?W.message:W}`),process.exit(1)}});async function x0(Q){return new Promise((W,z)=>{let q=_0.createServer((Z,U)=>{let L=new S0(Z.url,"http://localhost");if(L.pathname==="/callback"){let H=L.searchParams.get("apiKey"),V=L.searchParams.get("error");if(V){U.writeHead(400,{"Content-Type":"text/html"}),U.end(M3(decodeURIComponent(V))),q.close(),z(new Error(decodeURIComponent(V)));return}if(!H){U.writeHead(400,{"Content-Type":"text/html"}),U.end(M3("No Access Token received")),q.close(),z(new Error("No Access Token received"));return}try{C0(H),U.writeHead(200,{"Content-Type":"text/html"}),U.end(o3()),q.close(),W()}catch(E){U.writeHead(500,{"Content-Type":"text/html"}),U.end(M3("Failed to save authentication data")),q.close(),z(E)}}else U.writeHead(404),U.end("Not found")});q.listen(0,"localhost",()=>{let L=`https://www.untitledui.com/react/api/cli-auth?port=${q.address().port}`;Q.text="Opening browser for authentication...",D0(L).catch((H)=>{console.log(D3.yellow(`
55
- Failed to open browser automatically: ${H.message}`)),console.log(D3.cyan(`Please manually open: ${L}
56
- `))}),Q.text="Waiting for authentication in browser..."}),setTimeout(()=>{q.close(),z(new Error("Authentication timeout. Please try again."))},300000)})}function C0(Q){if(!f.existsSync(w3))f.mkdirSync(w3,{recursive:!0});let W={};if(f.existsSync(_3))try{W=JSON.parse(f.readFileSync(_3,"utf-8"))}catch{W={}}W.license=Q,f.writeFileSync(_3,JSON.stringify(W,null,2),"utf-8")}import g3 from"async-retry";import M from"chalk";import{Command as f0}from"commander";import{execa as u3}from"execa";import*as w from"fs";import q3 from"ora";import m0 from"os";import*as G from"path";import n from"prompts";import{Project as c0}from"ts-morph";import F0 from"node-fetch";async function H3(Q,W){try{let q=await F0("https://www.untitledui.com/react/api/components/example",{method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json"},body:JSON.stringify({example:Q,key:W})});if(!q.ok){if(q.status===401||q.status===403)return{type:"error",status:q.status,message:"PRO access required"};return console.error(`API error: ${q.status} - ${q.statusText}`),null}return await q.json()}catch(q){return console.error(q?.message||"Error fetching example data."),null}}import $3 from"async-retry";import y from"chalk";import{Command as k0}from"commander";import{execa as a}from"execa";import v3 from"fast-glob";import _ from"fs";import z3 from"ora";import P0 from"os";import*as v from"path";import R3 from"prompts";import{Project as g0}from"ts-morph";import{fileURLToPath as O0}from"url";import*as j3 from"fs";import*as e3 from"path";function S3(Q,W){let z=e3.join(Q,"package.json");if(!j3.existsSync(z))return W;let q=JSON.parse(j3.readFileSync(z,"utf-8")),Z={...q.dependencies,...q.devDependencies},U=[];for(let L of W){let H=Z[L];if(!H){U.push(L);continue}if(L==="tailwindcss"){let V=H.match(/\d+/);if((V?parseInt(V[0],10):0)<4)U.push(L)}}return U}import x3 from"chalk";import*as m from"fs";import*as G3 from"path";function C3(Q){if(!m.existsSync(G3.resolve(Q)))console.log(x3.red(`Error: CSS file not found at ${Q}`)),process.exit(1);let W=m.readFileSync(G3.resolve(Q),"utf-8"),z=/(--color-[a-zA-Z-]+-\d{1,3}):\s*(rgb\([^)]+\))/g,q={},Z;while((Z=z.exec(W))!==null)if(Z[1]&&Z[2])q[Z[1]]=Z[2];return q}function F3(Q,W,z){let q=G3.resolve(z);if(!m.existsSync(q)){console.log(x3.red(`Error: CSS file not found at ${q}`));return}let Z=m.readFileSync(q,"utf-8"),U=C3(z),L={},H={};for(let[E,T]of Object.entries(U))if(E.startsWith(`--color-${Q}-`)){let R=E.replace(`--color-${Q}-`,"");L[R]=E}else if(E.startsWith(`--color-${W}-`)){let R=E.replace(`--color-${W}-`,"");H[R]=T}let V=!1;for(let[E,T]of Object.entries(L))if(H[E]){let R=H[E],$=new RegExp(`(${T}):\\s*rgb\\([^)]*\\);?`,"g");if($.test(Z))Z=Z.replace($,`$1: ${R};`),V=!0;else console.log(x3.yellow(`No match found for ${T}`))}if(V)m.writeFileSync(q,Z,"utf-8")}var d0=O0(import.meta.url),z0=v.dirname(d0),h0=v.join(P0.homedir(),".untitledui"),s=v.join(h0,"config.json"),W0="vite",Y0="nextjs",Q0={[Y0]:"Next.js",[W0]:"Vite"},d="",j={color:"",template:"",framework:void 0};if(_.existsSync(s)){let Q=JSON.parse(_.readFileSync(s,"utf-8"));j.license=Q.license}var k3=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
57
- `),process.exit(1)},Z0=new k0().name("init").description("initialize a new project or adjust an existing one").argument("[directory]").usage("[directory] [options]").helpOption("-h, --help","display this help message.").option("--vite","initialize a Vite project.",!1).option("--next","initialize a Next.js project.",!1).option("-o, --overwrite","overwrite existing files.",!1).option("--colors-list","show the colors list.",!1).option("-c, --color <color-name>","specify a color for the project.").action(async(Q,W)=>{if(Q)d=Q;if(W){if(j.color=W.color,j.template=W.template,j.overwrite=W.overwrite,j.colorsList=W.colorsList,j.license=W.license||j.license,j.vite=W.vite,j.next=W.next,W.vite)j.framework=W0;if(W.next)j.framework=Y0}try{await P3(W),process.exit(0)}catch(z){console.error(y.red(z)),process.exit(1)}});async function P3(Q,W=null){let z=process.cwd(),q=_.existsSync(v.resolve(z,"package.json")),Z=v.resolve(v.join(z0,"../config/styles","theme.css")),U=C3(Z??""),L=Array.from(new Set(Object.keys(U).map(($)=>$?.split("--color-")?.[1]?.replace(/-\d{1,3}/,"")))),H=z3().start(),V=await p(z),E=q?v3.sync(["**/**/theme.css"],{cwd:z,absolute:!0,onlyFiles:!0,ignore:h}):[],T=E?.[0]&&_.readFileSync(E[0],"utf-8").match(/(--color-brand+-\d{1,3}):\s*(rgb\([^)]+\))/g)?.[1]||void 0;if(j.license){if(!_.existsSync(s)){let Y=v.dirname(s);_.mkdirSync(Y,{recursive:!0}),_.writeFileSync(s,JSON.stringify({license:j.license},null,2))}if(JSON.parse(_.readFileSync(s,"utf-8")).license!==j.license)_.writeFileSync(s,JSON.stringify({license:j.license},null,2))}if(!q){if(H.stop(),!d){let $=await R3({onState:k3,type:"text",name:"path",message:"What is your project named?",initial:"untitled-ui"});if(typeof $.path==="string")d=$.path.trim()}if(W)W.projectPath=d;if(_.existsSync(v.resolve(v.posix.join(z,d))))H.fail(y.red("Directory already exists!")),process.exit(1);if(j.vite&&j.next||!j.framework){let $=await R3({type:"select",name:"framework",onState:k3,message:`Which ${y.cyan("framework")} would you like to use?`,choices:Object.entries(Q0).map(([Y,X])=>({title:X,value:Y}))});j.framework=$.framework}H.succeed("Framework is selected: "+y.green(Q0[j.framework]))}else if(V?.framework==="other")H.fail("Unsupported project framework"),console.log(`Please refer to the documentation ${y.cyan("https://www.untitled.com/docs")} for supported frameworks or proceed with manual installation.`),process.exit(1);else if(V?.framework.startsWith("next")||V?.framework.startsWith("vite"))if(!W&&!T)H.succeed(y.yellow(`Detected ${s3[V.framework]} project, proceeding with the setup...`));else H.stop();if(j.colorsList||!j.color&&!T){let $=await R3({type:"select",name:"color",onState:k3,initial:Q.color??"",message:`Which ${y.cyan("color")} would you like to use as the ${y.cyanBright("brand")} color?`,choices:L.map((Y)=>({title:Y,value:Y}))});j.color=$.color}let R=v.posix.join(z,d||"");if(d&&!q){let $=v.resolve(d);console.log(`
58
- Creating a new project in ${y.blue(d)}`);let Y=z3("Downloading and extracting the repository...").start();try{_.mkdirSync($,{recursive:!0}),await $3(()=>f3($,{template:j.framework}),{retries:2}),Y.succeed("Files are downloaded and extracted successfully!");let X=z3({text:"Installing dependencies..."}).start(),b=v3.sync(["**/styles/theme.css"],{cwd:$,absolute:!0,onlyFiles:!0})[0];if(F3("brand",j.color||"",b??""),await $3(()=>a(C(),["install"],{cwd:R}).catch(async(S)=>{if(S.message.includes("peer"))X.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),X.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),["install","--legacy-peer-deps"],{cwd:R})}),{retries:1}),await $3(()=>a("git",["init"],{cwd:R}),{retries:1}),X.succeed("Dependencies are installed"),!W)console.log(`
53
+ </html>`}}function o0(){return p0().replace("{{TITLE}}","Authentication successful").replace("{{HEADING}}","Authentication successful").replace("{{DESCRIPTION}}","You can now close this tab and return to your terminal.").replace("{{AUTO_CLOSE_SCRIPT}}","<script>setTimeout(() => window.close(), 10000);</script>")}function M0(Q){return p0().replace("{{TITLE}}","Authentication failed").replace("{{HEADING}}","Authentication failed").replace("{{DESCRIPTION}}",Q).replace("{{AUTO_CLOSE_SCRIPT}}","")}var w0=T0.join(T3.homedir(),".untitledui"),_0=T0.join(w0,"config.json"),t0=new y3().name("login").description("authenticate with Untitled UI to access PRO components").action(async()=>{let Q=w3("Starting authentication...").start();try{await x3(Q),Q.succeed("Authentication completed successfully!"),console.log(D0.green(`
54
+ ✨ You can now access PRO components with the CLI!`)),process.exit(0)}catch(W){Q.fail(`Authentication failed: ${W instanceof Error?W.message:W}`),process.exit(1)}});async function x3(Q){return new Promise((W,z)=>{let q=_3.createServer((Z,U)=>{let L=new S3(Z.url,"http://localhost");if(L.pathname==="/callback"){let H=L.searchParams.get("apiKey"),V=L.searchParams.get("error");if(V){U.writeHead(400,{"Content-Type":"text/html"}),U.end(M0(decodeURIComponent(V))),q.close(),z(new Error(decodeURIComponent(V)));return}if(!H){U.writeHead(400,{"Content-Type":"text/html"}),U.end(M0("No Access Token received")),q.close(),z(new Error("No Access Token received"));return}try{C3(H),U.writeHead(200,{"Content-Type":"text/html"}),U.end(o0()),q.close(),W()}catch(E){U.writeHead(500,{"Content-Type":"text/html"}),U.end(M0("Failed to save authentication data")),q.close(),z(E)}}else U.writeHead(404),U.end("Not found")});q.listen(0,"localhost",()=>{let L=`https://www.untitledui.com/react/api/cli-auth?port=${q.address().port}`;Q.text="Opening browser for authentication...",D3(L).catch((H)=>{console.log(D0.yellow(`
55
+ Failed to open browser automatically: ${H.message}`)),console.log(D0.cyan(`Please manually open: ${L}
56
+ `))}),Q.text="Waiting for authentication in browser..."}),setTimeout(()=>{q.close(),z(new Error("Authentication timeout. Please try again."))},300000)})}function C3(Q){if(!f.existsSync(w0))f.mkdirSync(w0,{recursive:!0});let W={};if(f.existsSync(_0))try{W=JSON.parse(f.readFileSync(_0,"utf-8"))}catch{W={}}W.license=Q,f.writeFileSync(_0,JSON.stringify(W,null,2),"utf-8")}import g0 from"async-retry";import M from"chalk";import{Command as f3}from"commander";import{execa as u0}from"execa";import*as w from"fs";import q0 from"ora";import m3 from"os";import*as G from"path";import n from"prompts";import{Project as c3}from"ts-morph";import F3 from"node-fetch";async function H0(Q,W){try{let q=await F3("https://www.untitledui.com/react/api/components/example",{method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json"},body:JSON.stringify({example:Q,key:W})});if(!q.ok){if(q.status===401||q.status===403)return{type:"error",status:q.status,message:"PRO access required"};return console.error(`API error: ${q.status} - ${q.statusText}`),null}return await q.json()}catch(q){return console.error(q?.message||"Error fetching example data."),null}}import $0 from"async-retry";import y from"chalk";import{Command as k3}from"commander";import{execa as a}from"execa";import v0 from"fast-glob";import _ from"fs";import z0 from"ora";import P3 from"os";import*as v from"path";import R0 from"prompts";import{Project as g3}from"ts-morph";import{fileURLToPath as O3}from"url";import*as j0 from"fs";import*as e0 from"path";function S0(Q,W){let z=e0.join(Q,"package.json");if(!j0.existsSync(z))return W;let q=JSON.parse(j0.readFileSync(z,"utf-8")),Z={...q.dependencies,...q.devDependencies},U=[];for(let L of W){let H=Z[L];if(!H){U.push(L);continue}if(L==="tailwindcss"){let V=H.match(/\d+/);if((V?parseInt(V[0],10):0)<4)U.push(L)}}return U}import x0 from"chalk";import*as m from"fs";import*as G0 from"path";function C0(Q){if(!m.existsSync(G0.resolve(Q)))console.log(x0.red(`Error: CSS file not found at ${Q}`)),process.exit(1);let W=m.readFileSync(G0.resolve(Q),"utf-8"),z=/(--color-[a-zA-Z-]+-\d{1,3}):\s*(rgb\([^)]+\))/g,q={},Z;while((Z=z.exec(W))!==null)if(Z[1]&&Z[2])q[Z[1]]=Z[2];return q}function F0(Q,W,z){let q=G0.resolve(z);if(!m.existsSync(q)){console.log(x0.red(`Error: CSS file not found at ${q}`));return}let Z=m.readFileSync(q,"utf-8"),U=C0(z),L={},H={};for(let[E,T]of Object.entries(U))if(E.startsWith(`--color-${Q}-`)){let R=E.replace(`--color-${Q}-`,"");L[R]=E}else if(E.startsWith(`--color-${W}-`)){let R=E.replace(`--color-${W}-`,"");H[R]=T}let V=!1;for(let[E,T]of Object.entries(L))if(H[E]){let R=H[E],$=new RegExp(`(${T}):\\s*rgb\\([^)]*\\);?`,"g");if($.test(Z))Z=Z.replace($,`$1: ${R};`),V=!0;else console.log(x0.yellow(`No match found for ${T}`))}if(V)m.writeFileSync(q,Z,"utf-8")}var d3=O3(import.meta.url),z3=v.dirname(d3),h3=v.join(P3.homedir(),".untitledui"),s=v.join(h3,"config.json"),W3="vite",Y3="nextjs",Q3={[Y3]:"Next.js",[W3]:"Vite"},d="",j={color:"",template:"",framework:void 0};if(_.existsSync(s)){let Q=JSON.parse(_.readFileSync(s,"utf-8"));j.license=Q.license}var k0=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
57
+ `),process.exit(1)},Z3=new k3().name("init").description("initialize a new project or adjust an existing one").argument("[directory]").usage("[directory] [options]").helpOption("-h, --help","display this help message.").option("--vite","initialize a Vite project.",!1).option("--next","initialize a Next.js project.",!1).option("-o, --overwrite","overwrite existing files.",!1).option("--colors-list","show the colors list.",!1).option("-c, --color <color-name>","specify a color for the project.").action(async(Q,W)=>{if(Q)d=Q;if(W){if(j.color=W.color,j.template=W.template,j.overwrite=W.overwrite,j.colorsList=W.colorsList,j.license=W.license||j.license,j.vite=W.vite,j.next=W.next,W.vite)j.framework=W3;if(W.next)j.framework=Y3}try{await P0(W),process.exit(0)}catch(z){console.error(y.red(z)),process.exit(1)}});async function P0(Q,W=null){let z=process.cwd(),q=_.existsSync(v.resolve(z,"package.json")),Z=v.resolve(v.join(z3,"../config/styles","theme.css")),U=C0(Z??""),L=Array.from(new Set(Object.keys(U).map(($)=>$?.split("--color-")?.[1]?.replace(/-\d{1,3}/,"")))),H=z0().start(),V=await p(z),E=q?v0.sync(["**/**/theme.css"],{cwd:z,absolute:!0,onlyFiles:!0,ignore:h}):[],T=E?.[0]&&_.readFileSync(E[0],"utf-8").match(/(--color-brand+-\d{1,3}):\s*(rgb\([^)]+\))/g)?.[1]||void 0;if(j.license){if(!_.existsSync(s)){let Y=v.dirname(s);_.mkdirSync(Y,{recursive:!0}),_.writeFileSync(s,JSON.stringify({license:j.license},null,2))}if(JSON.parse(_.readFileSync(s,"utf-8")).license!==j.license)_.writeFileSync(s,JSON.stringify({license:j.license},null,2))}if(!q){if(H.stop(),!d){let $=await R0({onState:k0,type:"text",name:"path",message:"What is your project named?",initial:"untitled-ui"});if(typeof $.path==="string")d=$.path.trim()}if(W)W.projectPath=d;if(_.existsSync(v.resolve(v.posix.join(z,d))))H.fail(y.red("Directory already exists!")),process.exit(1);if(j.vite&&j.next||!j.framework){let $=await R0({type:"select",name:"framework",onState:k0,message:`Which ${y.cyan("framework")} would you like to use?`,choices:Object.entries(Q3).map(([Y,X])=>({title:X,value:Y}))});j.framework=$.framework}H.succeed("Framework is selected: "+y.green(Q3[j.framework]))}else if(V?.framework==="other")H.fail("Unsupported project framework"),console.log(`Please refer to the documentation ${y.cyan("https://www.untitled.com/docs")} for supported frameworks or proceed with manual installation.`),process.exit(1);else if(V?.framework.startsWith("next")||V?.framework.startsWith("vite"))if(!W&&!T)H.succeed(y.yellow(`Detected ${s0[V.framework]} project, proceeding with the setup...`));else H.stop();if(j.colorsList||!j.color&&!T){let $=await R0({type:"select",name:"color",onState:k0,initial:Q.color??"",message:`Which ${y.cyan("color")} would you like to use as the ${y.cyanBright("brand")} color?`,choices:L.map((Y)=>({title:Y,value:Y}))});j.color=$.color}let R=v.posix.join(z,d||"");if(d&&!q){let $=v.resolve(d);console.log(`
58
+ Creating a new project in ${y.blue(d)}`);let Y=z0("Downloading and extracting the repository...").start();try{_.mkdirSync($,{recursive:!0}),await $0(()=>f0($,{template:j.framework}),{retries:2}),Y.succeed("Files are downloaded and extracted successfully!");let X=z0({text:"Installing dependencies..."}).start(),b=v0.sync(["**/styles/theme.css"],{cwd:$,absolute:!0,onlyFiles:!0})[0];if(F0("brand",j.color||"",b??""),await $0(()=>a(C(),["install"],{cwd:R}).catch(async(S)=>{if(S.message.includes("peer"))X.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),X.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),["install","--legacy-peer-deps"],{cwd:R})}),{retries:1}),await $0(()=>a("git",["init"],{cwd:R}),{retries:1}),X.succeed("Dependencies are installed"),!W)console.log(`
59
59
  Your project is ready, to get started run the following commands:
60
60
 
61
61
  cd ${y.cyan(d)}
62
- ${y.cyan(n3())}`)}catch(X){if(Y.fail(y.red(`
62
+ ${y.cyan(n0())}`)}catch(X){if(Y.fail(y.red(`
63
63
  Failed to download and extract the repository`)),X instanceof Error)console.error(X.message);else console.error(`
64
- `);_.rmdirSync($,{recursive:!0}),process.exit(1)}}else{let $=z3(),Y=new Set,X=o(z),b=v.resolve(v.join(z0,"../config")),S=v3.sync(["**"],{cwd:b,onlyFiles:!0,ignore:h}),J=S3(z,["tailwindcss","tailwindcss-animate","@tailwindcss/typography","tailwindcss-react-aria-components"]),x=S3(z,["@tailwindcss/postcss","postcss"]);if(!W&&!T)$.start("Copying files to the project directory");if(S.forEach((u)=>{let A=u.includes("postcss.config"),k=v.posix.join(v.posix.join(b),u),P=v.posix.join(z,A?u:`${V?.isSrcDir?"src":""}/${u}`);if(_.existsSync(P)){if(j?.overwrite)_.copyFileSync(k,P);else{let W3=_.readFileSync(P,"utf-8"),O=_.readFileSync(k,"utf-8");if(W3!==O){if(u.endsWith("theme.css")&&T)return;Y.add({targetFile:P,sourceFile:k})}}return}_.mkdirSync(v.dirname(P),{recursive:!0}),_.writeFileSync(P,""),_.copyFileSync(k,P)}),$.stop(),Y.size&&!j?.overwrite)if(console.log(`
65
- `),$.fail("Following files already exist in the directory."),Y.forEach((A)=>{console.log(`- ${y.green(A.targetFile)}`)}),(await R3({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let A=z3("Overwriting files").start();Y.forEach((k)=>{_.copyFileSync(k.sourceFile,k.targetFile)}),A.succeed("Files are overwritten")}else console.log(`Use ${y.cyan("--overwrite")} or ${y.cyan("-o")} to overwrite existing files, or refer to the documentation ${y.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`);if(X?.tailwindFile)console.log(`
64
+ `);_.rmdirSync($,{recursive:!0}),process.exit(1)}}else{let $=z0(),Y=new Set,X=o(z),b=v.resolve(v.join(z3,"../config")),S=v0.sync(["**"],{cwd:b,onlyFiles:!0,ignore:h}),J=S0(z,["tailwindcss","tailwindcss-animate","@tailwindcss/typography","tailwindcss-react-aria-components"]),x=S0(z,["@tailwindcss/postcss","postcss"]);if(!W&&!T)$.start("Copying files to the project directory");if(S.forEach((u)=>{let A=u.includes("postcss.config"),k=v.posix.join(v.posix.join(b),u),P=v.posix.join(z,A?u:`${V?.isSrcDir?"src":""}/${u}`);if(_.existsSync(P)){if(j?.overwrite)_.copyFileSync(k,P);else{let W0=_.readFileSync(P,"utf-8"),O=_.readFileSync(k,"utf-8");if(W0!==O){if(u.endsWith("theme.css")&&T)return;Y.add({targetFile:P,sourceFile:k})}}return}_.mkdirSync(v.dirname(P),{recursive:!0}),_.writeFileSync(P,""),_.copyFileSync(k,P)}),$.stop(),Y.size&&!j?.overwrite)if(console.log(`
65
+ `),$.fail("Following files already exist in the directory."),Y.forEach((A)=>{console.log(`- ${y.green(A.targetFile)}`)}),(await R0({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let A=z0("Overwriting files").start();Y.forEach((k)=>{_.copyFileSync(k.sourceFile,k.targetFile)}),A.succeed("Files are overwritten")}else console.log(`Use ${y.cyan("--overwrite")} or ${y.cyan("-o")} to overwrite existing files, or refer to the documentation ${y.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`);if(X?.tailwindFile)console.log(`
66
66
  Tailwind config file exists in the project directory. You can add it to your globals.css as follows:`),console.log(`
67
- ${y.cyan(`@config "../${V?.isSrcDir&&"../"}${v.relative(z,X.tailwindFile)}";`)}
67
+ ${y.cyan(`@config "../${V?.isSrcDir?"../":""}${v.relative(z,X.tailwindFile)}";`)}
68
68
  `);let I=X?.layoutFile||X?.appFile||V?.framework==="vite"&&X?.mainFile||"";if(!I)console.log(`Import following files to your main file:
69
- `),S.forEach((u)=>{console.log(y.cyan(u))});else{let A=new g0({tsConfigFilePath:v.resolve(X?.tsConfig||"")}).addSourceFileAtPath(v.resolve(I)),k="globals.css";A.getImportDeclarations().filter((O)=>O.getModuleSpecifierValue().includes("globals.css")).forEach((O)=>O.remove());let P=v.relative(v.resolve(z,`${V?.isSrcDir&&"src"}`),I).split("/").length,W3=V?.aliasPrefix?.stylesPrefix||V?.aliasPrefix?.srcPrefix||(P===1?"./":"../".repeat(P-1));A.addImportDeclarations(S.filter((O)=>O.includes("globals.css")).map((O)=>({moduleSpecifier:`${W3}${V?.aliasPrefix?.stylesPrefix?O?.split("styles/")[1]:O}`}))),A.saveSync()}let g=v3.sync(["**/styles/theme.css"],{cwd:z,absolute:!0,onlyFiles:!0,ignore:h});if(!g?.length)return $.fail(`Failed to copy ${y.cyan("theme.css")} file.
70
- Ensure that the ${y.cyan("theme.css")} file exists in the project directory under ${y.yellow("styles/")} folder.`);if((j.color||!T)&&F3("brand",j.color||"brand",g[0]??""),J.length||x.length){let u=z3().start("Installing dependencies");J.length&&await $3(()=>a(C(),[C()==="npm"?"install":"add",...J],{cwd:R}).catch(async(A)=>{if(A.message.includes("peer"))u.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),u.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),[C()==="npm"?"install":"add",...J,"--legacy-peer-deps"],{cwd:R})}),{retries:1}),x.length&&await $3(()=>a(C(),[C()==="npm"?"install":"add","-D",...x],{cwd:R}).catch(async(A)=>{if(A.message.includes("peer"))u.warn("DevDependency conflict detected. Retrying with --legacy-peer-deps..."),u.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),[C()==="npm"?"install":"add","-D",...x,"--legacy-peer-deps"],{cwd:R})}),{retries:1}),u.succeed("Dependencies are installed")}if(!W&&!T)$.succeed(y.green("Project setup is completed!"));if(W&&q)return;else console.log(`
71
- Your project is ready, you can now start adding components.`)}}var l0=G.join(m0.homedir(),".untitledui"),r=G.join(l0,"config.json"),B={path:"",example:"",license:"",components:[]},O3={};if(w.existsSync(r)){let Q=JSON.parse(w.readFileSync(r,"utf-8"));B.license=Q.license}var Q3=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
72
- `),process.exit(1)},$0=new f0().name("example").description("add an example to the project").argument("[example]","the example to add").option("-o, --overwrite","overwrite existing files.",!1).option("-p, --path <path>","the path to add the component to.").option("-e, --example-path <example-path>","the path to add the example file to.").action(async(Q,W)=>{if(Q)B.example=Q;if(W)B.path=W.path,B.overwrite=W.overwrite,B.examplePath=W.examplePath,B.license=W.license||B.license;try{await P3(W,O3),await a0(B)}catch(z){console.error(M.red(z))}});async function a0(Q){let W=q3().start(),z=G.posix.join(process.cwd(),O3?.projectPath||"");if(!w.existsSync(G.posix.join(G.resolve(z,"package.json"))))W.warn("This command should be run in a project directory."),process.exit(1);let Z=await p(z);if(B.license){if(!await X3(B.license))W.fail("Invalid license key"),process.exit(1);if(!w.existsSync(r)){let b=G.dirname(r);w.mkdirSync(b,{recursive:!0}),w.writeFileSync(r,JSON.stringify({license:B.license},null,2))}if(JSON.parse(w.readFileSync(r,"utf-8")).license!==B.license)w.writeFileSync(r,JSON.stringify({license:B.license},null,2),"utf-8")}if(W.stop(),!B.example){let Y=await n({type:"select",name:"example",onState:Q3,message:"Select which type of example you want to add",choices:[{title:"Application",value:"application"},{title:"Marketing",value:"marketing"}]});B.example=Y.example}let U=null;if(B.example){let Y=await H3(B.example,B.license);if(Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(B.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1);if(Y?.type==="directory"){let X=await n({type:"select",name:"example",onState:Q3,message:`Select a folder or file in "${B.example}"`,choices:Y.results.map((b)=>({title:b,value:b}))});if(!X.example)return;if(B.example=X.example,Y=await H3(X.example,B.license),Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(X.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(Y?.type==="json-files"){let X=await n({type:"select",name:"example",onState:Q3,message:`Select which example you want to add from "${B.example}"`,choices:Y.results.map((b)=>({title:b,value:`${B.example}/${b}`}))});if(!X.example)return;if(B.example=X.example,Y=await H3(X.example,B.license),Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(X.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(Y?.type==="json-file")U=Y.content}if(!U)W.fail("No example found"),process.exit(1);if(!B?.examplePath){let Y=Z?.isUsingAppDir?"app":"pages",X=Z?.isSrcDir?G.posix.join("src",Y):Y,b=await n({type:"text",name:"examplePath",onState:Q3,message:`Where would you like to add the ${M.cyan(B?.example)} example?`,initial:X});B.examplePath=b.examplePath}else if(!w.existsSync(G.posix.join(z,B.examplePath)))w.mkdirSync(G.posix.join(z,B.examplePath),{recursive:!0}),console.log(M.green(`Created directory ${B.examplePath}`));if(!B?.path){let Y=await n({type:"text",name:"path",onState:Q3,message:`Where would you like to add the ${M.cyan("components")}?`,initial:"components"});B.path=Y.path}let L=U.components.filter((Y)=>!w.existsSync(G.posix.join(z,`${Z?.isSrcDir&&"src"}`,Y?.path?.replace(/components\//,B.path+"/"))));if(L?.length){let Y=await n({type:"multiselect",name:"components",onState:Q3,message:`Select which components you want to add from ${M.cyan(U.name)} example`,choices:L.map((X)=>({title:X?.name,value:X?.name,selected:!0})),instructions:!1,hint:"- Space to select. Return to submit"});if(B.components=Y.components,!L.length&&!Y.components?.length)W.warn("No components selected")}let H=o(z),V=new Set,E=new c0({tsConfigFilePath:H?.tsConfig}),T=q3(`Adding ${B?.example}...`).start(),R="";try{if(U.files?.forEach(async({path:Y,code:X})=>{let b=G.posix.join(z,`${Z?.isSrcDir&&"src"}`,Y.replace(/components\//,B.path+"/")),S=Z?.framework==="vite"?X.replace(`"use client";
69
+ `),S.forEach((u)=>{console.log(y.cyan(u))});else{let A=new g3({tsConfigFilePath:v.resolve(X?.tsConfig||"")}).addSourceFileAtPath(v.resolve(I)),k="globals.css";A.getImportDeclarations().filter((O)=>O.getModuleSpecifierValue().includes("globals.css")).forEach((O)=>O.remove());let P=v.relative(v.resolve(z,`${V?.isSrcDir?"src":""}`),I).split("/").length,W0=V?.aliasPrefix?.stylesPrefix||V?.aliasPrefix?.srcPrefix||(P===1?"./":"../".repeat(P-1));A.addImportDeclarations(S.filter((O)=>O.includes("globals.css")).map((O)=>({moduleSpecifier:`${W0}${V?.aliasPrefix?.stylesPrefix?O?.split("styles/")[1]:O}`}))),A.saveSync()}let g=v0.sync(["**/styles/theme.css"],{cwd:z,absolute:!0,onlyFiles:!0,ignore:h});if(!g?.length)return $.fail(`Failed to copy ${y.cyan("theme.css")} file.
70
+ Ensure that the ${y.cyan("theme.css")} file exists in the project directory under ${y.yellow("styles/")} folder.`);if((j.color||!T)&&F0("brand",j.color||"brand",g[0]??""),J.length||x.length){let u=z0().start("Installing dependencies");J.length&&await $0(()=>a(C(),[C()==="npm"?"install":"add",...J],{cwd:R}).catch(async(A)=>{if(A.message.includes("peer"))u.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),u.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),[C()==="npm"?"install":"add",...J,"--legacy-peer-deps"],{cwd:R})}),{retries:1}),x.length&&await $0(()=>a(C(),[C()==="npm"?"install":"add","-D",...x],{cwd:R}).catch(async(A)=>{if(A.message.includes("peer"))u.warn("DevDependency conflict detected. Retrying with --legacy-peer-deps..."),u.start("Installing dependencies with --legacy-peer-deps flag"),await a(C(),[C()==="npm"?"install":"add","-D",...x,"--legacy-peer-deps"],{cwd:R})}),{retries:1}),u.succeed("Dependencies are installed")}if(!W&&!T)$.succeed(y.green("Project setup is completed!"));if(W&&q)return;else console.log(`
71
+ Your project is ready, you can now start adding components.`)}}var l3=G.join(m3.homedir(),".untitledui"),r=G.join(l3,"config.json"),B={path:"",example:"",license:"",components:[]},O0={};if(w.existsSync(r)){let Q=JSON.parse(w.readFileSync(r,"utf-8"));B.license=Q.license}var Q0=(Q)=>{if(Q.aborted)process.stdout.write("\x1B[?25h"),process.stdout.write(`
72
+ `),process.exit(1)},$3=new f3().name("example").description("add an example to the project").argument("[example]","the example to add").option("-o, --overwrite","overwrite existing files.",!1).option("-p, --path <path>","the path to add the component to.").option("-e, --example-path <example-path>","the path to add the example file to.").action(async(Q,W)=>{if(Q)B.example=Q;if(W)B.path=W.path,B.overwrite=W.overwrite,B.examplePath=W.examplePath,B.license=W.license||B.license;try{await P0(W,O0),await a3(B)}catch(z){console.error(M.red(z))}});async function a3(Q){let W=q0().start(),z=G.posix.join(process.cwd(),O0?.projectPath||"");if(!w.existsSync(G.posix.join(G.resolve(z,"package.json"))))W.warn("This command should be run in a project directory."),process.exit(1);let Z=await p(z);if(B.license){if(!await X0(B.license))W.fail("Invalid license key"),process.exit(1);if(!w.existsSync(r)){let b=G.dirname(r);w.mkdirSync(b,{recursive:!0}),w.writeFileSync(r,JSON.stringify({license:B.license},null,2))}if(JSON.parse(w.readFileSync(r,"utf-8")).license!==B.license)w.writeFileSync(r,JSON.stringify({license:B.license},null,2),"utf-8")}if(W.stop(),!B.example){let Y=await n({type:"select",name:"example",onState:Q0,message:"Select which type of example you want to add",choices:[{title:"Application",value:"application"},{title:"Marketing",value:"marketing"}]});B.example=Y.example}let U=null;if(B.example){let Y=await H0(B.example,B.license);if(Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(B.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1);if(Y?.type==="directory"){let X=await n({type:"select",name:"example",onState:Q0,message:`Select a folder or file in "${B.example}"`,choices:Y.results.map((b)=>({title:b,value:b}))});if(!X.example)return;if(B.example=X.example,Y=await H0(X.example,B.license),Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(X.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(Y?.type==="json-files"){let X=await n({type:"select",name:"example",onState:Q0,message:`Select which example you want to add from "${B.example}"`,choices:Y.results.map((b)=>({title:b,value:`${B.example}/${b}`}))});if(!X.example)return;if(B.example=X.example,Y=await H0(X.example,B.license),Y?.type==="error"&&(Y.status===401||Y.status===403))console.log(),console.log(M.yellow(`\uD83D\uDD12 The ${M.cyan(X.example)} example requires PRO access.`)),console.log(),console.log("To access PRO examples:"),console.log(` ${M.green("→")} If you've already purchased: ${M.cyan(`${e()} untitledui@latest login`)}`),console.log(` ${M.green("→")} To purchase PRO examples: ${M.cyan("https://www.untitledui.com/buy/react")}`),console.log(),process.exit(1)}if(Y?.type==="json-file")U=Y.content}if(!U)W.fail("No example found"),process.exit(1);if(!B?.examplePath){let Y=Z?.isUsingAppDir?"app":"pages",X=Z?.isSrcDir?G.posix.join("src",Y):Y,b=await n({type:"text",name:"examplePath",onState:Q0,message:`Where would you like to add the ${M.cyan(B?.example)} example?`,initial:X});B.examplePath=b.examplePath}else if(!w.existsSync(G.posix.join(z,B.examplePath)))w.mkdirSync(G.posix.join(z,B.examplePath),{recursive:!0}),console.log(M.green(`Created directory ${B.examplePath}`));if(!B?.path){let Y=await n({type:"text",name:"path",onState:Q0,message:`Where would you like to add the ${M.cyan("components")}?`,initial:"components"});B.path=Y.path}let L=U.components.filter((Y)=>!w.existsSync(G.posix.join(z,`${Z?.isSrcDir?"src":""}`,Y?.path?.replace(/components\//,B.path+"/"))));if(L?.length){let Y=await n({type:"multiselect",name:"components",onState:Q0,message:`Select which components you want to add from ${M.cyan(U.name)} example`,choices:L.map((X)=>({title:X?.name,value:X?.name,selected:!0})),instructions:!1,hint:"- Space to select. Return to submit"});if(B.components=Y.components,!L.length&&!Y.components?.length)W.warn("No components selected")}let H=o(z),V=new Set,E=new c3({tsConfigFilePath:H?.tsConfig}),T=q0(`Adding ${B?.example}...`).start(),R="";try{if(U.files?.forEach(async({path:Y,code:X})=>{let b=G.posix.join(z,`${Z?.isSrcDir?"src":""}`,Y.replace(/components\//,B.path+"/")),S=Z?.framework==="vite"?X.replace(`"use client";
73
73
 
74
- `,""):X,J=b3(S);if(Y.includes("examples")){let I=G.basename(Y);b=G.posix.join(z,B?.examplePath??"",I),R=G.posix.join(B?.examplePath??"",I)}let x=G.dirname(b);if(w.existsSync(b)&&!B.overwrite){if(w.readFileSync(b,"utf-8")!==J)V.add({code:J,path:b})}else{w.mkdirSync(x,{recursive:!0}),w.writeFileSync(b,J);let I=G.relative(G.resolve(z,`${Z?.isSrcDir&&"src"}`,B.path),b).split("/").length,g=I===1?"./":"../".repeat(I-1),u=E.addSourceFileAtPath(G.resolve(b));u.getImportDeclarations().forEach((A)=>{let k=A.getModuleSpecifierValue();A.setModuleSpecifier(t(k,B.path,Z?.aliasPrefix,g))}),await u.save()}}),V.size)T.warn(`Some files of ${M.yellow(B?.example)} already exist`);else T.succeed(`${M.green(B?.example)} is added successfully`)}catch(Y){T.fail(`
74
+ `,""):X,J=b0(S);if(Y.includes("examples")){let I=G.basename(Y);b=G.posix.join(z,B?.examplePath??"",I),R=G.posix.join(B?.examplePath??"",I)}let x=G.dirname(b);if(w.existsSync(b)&&!B.overwrite){if(w.readFileSync(b,"utf-8")!==J)V.add({code:J,path:b})}else{w.mkdirSync(x,{recursive:!0}),w.writeFileSync(b,J);let I=G.relative(G.resolve(z,`${Z?.isSrcDir?"src":""}`,B.path),b).split("/").length,g=I===1?"./":"../".repeat(I-1),u=E.addSourceFileAtPath(G.resolve(b));u.getImportDeclarations().forEach((A)=>{let k=A.getModuleSpecifierValue();A.setModuleSpecifier(t(k,B.path,Z?.aliasPrefix,g))}),await u.save()}}),V.size)T.warn(`Some files of ${M.yellow(B?.example)} already exist`);else T.succeed(`${M.green(B?.example)} is added successfully`)}catch(Y){T.fail(`
75
75
  Failed to add the component ${M.red(B?.example)}`),console.error(M.red(Y)),process.exit(1)}if(V.size&&!B?.overwrite)if(console.log(`
76
- Following files already exist in the directory.`),V.forEach((X)=>{console.log(M.green(`- ${G.relative(z,X.path)}`))}),(await n({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let X=q3("Overwriting files").start();V.forEach((b)=>{let S=G.relative(G.resolve(z,`${Z?.isSrcDir&&"src"}`,B.path),b.path).split("/").length,J=S===1?"./":"../".repeat(S-1),x=E.addSourceFileAtPath(G.resolve(b.path));x.replaceWithText(b.code),x.getImportDeclarations().forEach((I)=>{let g=I.getModuleSpecifierValue();I.setModuleSpecifier(t(g,B.path,Z?.aliasPrefix,J))}),x.saveSync()}),X.succeed("Files are overwritten")}else console.log(`Use ${M.cyan("--overwrite")} or ${M.cyan("-o")} to overwrite existing files, or refer to the documentation ${M.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`),process.exit(1);let $=C();if(U?.dependencies?.length){let Y=q3("Installing example dependencies").start();await g3(()=>u3($,[$==="npm"?"install":"add",...U.dependencies],{cwd:z}).catch(async(X)=>{if(X.message.includes("peer"))Y.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),Y.start("Installing dependencies with --legacy-peer-deps flag"),await u3($,[$==="npm"?"install":"add",...U.dependencies,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),Y.succeed("Example dependencies are installed")}if(U?.devDependencies?.length){let Y=q3("Installing example devDependencies").start();await g3(()=>u3($,[$==="npm"?"install":"add","-D",...U.devDependencies],{cwd:z}).catch(async(X)=>{if(X.message.includes("peer"))Y.warn("DevDependency conflict detected. Retrying with --legacy-peer-deps..."),Y.start("Installing devDependencies with --legacy-peer-deps flag"),await u3($,[$==="npm"?"install":"add","-D",...U.devDependencies,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),Y.succeed("Example devDependencies are installed")}if(B?.components?.length)await g3(()=>A3({components:B.components,dir:O3?.projectPath||"",path:B.path,message:`
76
+ Following files already exist in the directory.`),V.forEach((X)=>{console.log(M.green(`- ${G.relative(z,X.path)}`))}),(await n({type:"confirm",name:"overwrite",message:"Do you want to overwrite the existing files?",initial:!0})).overwrite){let X=q0("Overwriting files").start();V.forEach((b)=>{let S=G.relative(G.resolve(z,`${Z?.isSrcDir?"src":""}`,B.path),b.path).split("/").length,J=S===1?"./":"../".repeat(S-1),x=E.addSourceFileAtPath(G.resolve(b.path));x.replaceWithText(b.code),x.getImportDeclarations().forEach((I)=>{let g=I.getModuleSpecifierValue();I.setModuleSpecifier(t(g,B.path,Z?.aliasPrefix,J))}),x.saveSync()}),X.succeed("Files are overwritten")}else console.log(`Use ${M.cyan("--overwrite")} or ${M.cyan("-o")} to overwrite existing files, or refer to the documentation ${M.cyan("https://www.untitled.com/docs")} for manual installation. The rest of the files are added.`),process.exit(1);let $=C();if(U?.dependencies?.length){let Y=q0("Installing example dependencies").start();await g0(()=>u0($,[$==="npm"?"install":"add",...U.dependencies],{cwd:z}).catch(async(X)=>{if(X.message.includes("peer"))Y.warn("Dependency conflict detected. Retrying with --legacy-peer-deps..."),Y.start("Installing dependencies with --legacy-peer-deps flag"),await u0($,[$==="npm"?"install":"add",...U.dependencies,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),Y.succeed("Example dependencies are installed")}if(U?.devDependencies?.length){let Y=q0("Installing example devDependencies").start();await g0(()=>u0($,[$==="npm"?"install":"add","-D",...U.devDependencies],{cwd:z}).catch(async(X)=>{if(X.message.includes("peer"))Y.warn("DevDependency conflict detected. Retrying with --legacy-peer-deps..."),Y.start("Installing devDependencies with --legacy-peer-deps flag"),await u0($,[$==="npm"?"install":"add","-D",...U.devDependencies,"--legacy-peer-deps"],{cwd:z})}),{retries:1}),Y.succeed("Example devDependencies are installed")}if(B?.components?.length)await g0(()=>A0({components:B.components,dir:O0?.projectPath||"",path:B.path,message:`
77
77
  \uD83C\uDF89 Example ${M.green(B.example)} has been added to ${M.green(R)}`}),{retries:1});console.log(`
78
- \uD83C\uDF89 Example ${M.green(B.example)} has been added to ${M.green(R)}`),process.exit(0)}var d3={name:"untitledui",version:"0.1.33",main:"dist/index.mjs",description:"The Untitled UI CLI tool helps you quickly scaffold projects with Untitled UI React and add components and page examples to your existing projects with an interactive interface in seconds.",type:"module",publishConfig:{access:"public"},scripts:{test:'echo "Error: no test specified" && exit 1',dev:"bun build --entrypoints ./index.ts --entry-naming=[name].mjs --outdir=dist --target=node --minify --packages=external --env=inline --define=process.env.API_URL=http://localhost:3000/react/api --watch",build:"bun build --entrypoints ./index.ts --entry-naming=[name].mjs --outdir=dist --target=node --minify --packages=external --env=inline --define=process.env.API_URL=https://www.untitledui.com/react/api","publish:npm":"bun run build && npm publish --access public",start:"node dist/index.mjs"},bugs:{url:"https://github.com/untitleduico/react/issues"},homepage:"https://github.com/untitleduico/react#readme",keywords:["untitledui","untitled-ui","untitledui","untitledui-cli","untitledui-react","untitledui-components","untitledui-examples","untitledui-vite","untitledui-nextjs","cli","tailwindcss","nextjs","react","components","examples","vite"],files:["dist","config","templates","README.md"],author:{name:"Untitled UI",url:"https://www.untitledui.com/react"},contributors:[{name:"Dilshod Turobov",url:"https://x.com/deebovv"},{name:"Jordan Hughes",url:"https://x.com/jordanphughes"}],license:"MIT",bin:{untitledui:"dist/index.mjs"},exports:"./dist/index.mjs",dependencies:{"async-retry":"^1.3.3",chalk:"^5.4.1",commander:"^13.1.0",execa:"^7.0.0","fast-glob":"^3.3.3","node-fetch":"^3.3.2",open:"^10.1.0",ora:"^8.2.0",prettier:"^3.5.3",prompts:"^2.4.2",tar:"^7.4.3","ts-morph":"^25.0.1","tsconfig-paths":"^4.2.0","update-check":"^1.5.4"},devDependencies:{"@types/async-retry":"^1.4.9","@types/prompts":"^2.4.9","@types/tar":"^6.1.13","type-fest":"^4.37.0",typescript:"^5.8.2"}};process.on("SIGINT",()=>process.exit(0));process.on("SIGTERM",()=>process.exit(0));async function r0(){let Q=new n0().name(d3.name).version(d3.version);Q.addCommand(Z0).addCommand(i3).addCommand($0).addCommand(t3),Q.parse()}r0();
78
+ \uD83C\uDF89 Example ${M.green(B.example)} has been added to ${M.green(R)}`),process.exit(0)}var d0={name:"untitledui",version:"0.1.35",main:"dist/index.mjs",description:"The Untitled UI CLI tool helps you quickly scaffold projects with Untitled UI React and add components and page examples to your existing projects with an interactive interface in seconds.",type:"module",publishConfig:{access:"public"},scripts:{test:'echo "Error: no test specified" && exit 1',dev:"bun build --entrypoints ./index.ts --entry-naming=[name].mjs --outdir=dist --target=node --minify --packages=external --env=inline --define=process.env.API_URL=http://localhost:3000/react/api --watch",build:"bun build --entrypoints ./index.ts --entry-naming=[name].mjs --outdir=dist --target=node --minify --packages=external --env=inline --define=process.env.API_URL=https://www.untitledui.com/react/api","publish:npm":"bun run build && npm publish --access public",start:"node dist/index.mjs"},bugs:{url:"https://github.com/untitleduico/react/issues"},homepage:"https://github.com/untitleduico/react#readme",keywords:["untitledui","untitled-ui","untitledui","untitledui-cli","untitledui-react","untitledui-components","untitledui-examples","untitledui-vite","untitledui-nextjs","cli","tailwindcss","nextjs","react","components","examples","vite"],files:["dist","config","templates","README.md"],author:{name:"Untitled UI",url:"https://www.untitledui.com/react"},contributors:[{name:"Dilshod Turobov",url:"https://x.com/deebovv"},{name:"Jordan Hughes",url:"https://x.com/jordanphughes"}],license:"MIT",bin:{untitledui:"dist/index.mjs"},exports:"./dist/index.mjs",dependencies:{"async-retry":"^1.3.3",chalk:"^5.4.1",commander:"^13.1.0",execa:"^7.0.0","fast-glob":"^3.3.3","node-fetch":"^3.3.2",open:"^10.1.0",ora:"^8.2.0",prettier:"^3.5.3",prompts:"^2.4.2",tar:"^7.4.3","ts-morph":"^25.0.1","tsconfig-paths":"^4.2.0","update-check":"^1.5.4"},devDependencies:{"@types/async-retry":"^1.4.9","@types/prompts":"^2.4.9","@types/tar":"^6.1.13","type-fest":"^4.37.0",typescript:"^5.8.2"}};process.on("SIGINT",()=>process.exit(0));process.on("SIGTERM",()=>process.exit(0));async function r3(){let Q=new n3().name(d0.name).version(d0.version);Q.addCommand(Z3).addCommand(i0).addCommand($3).addCommand(t0),Q.parse()}r3();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "untitledui",
3
- "version": "0.1.33",
3
+ "version": "0.1.35",
4
4
  "main": "dist/index.mjs",
5
5
  "description": "The Untitled UI CLI tool helps you quickly scaffold projects with Untitled UI React and add components and page examples to your existing projects with an interactive interface in seconds.",
6
6
  "type": "module",