@iamharshil/aix-cli 3.2.2 β†’ 3.2.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -42,7 +42,14 @@ No API keys. No cloud calls. No data leaving your machine.
42
42
  - πŸš€ **GPU-accelerated** β€” Take advantage of your local GPU for fast inference.
43
43
  - πŸ”€ **Multi-backend** β€” Use LM Studio or Ollama as your model server.
44
44
  - πŸ› οΈ **Multi-provider** β€” Switch between Claude Code and OpenCode with a single flag.
45
- - ⚑ **Zero config** β€” Just run `aix-cli run` and start coding.
45
+ - ⚑ **Zero config** β€” Just run `aix-cli run` and start coding. OpenCode is launched using an OpenAI-compatible endpoint with `openai-compatible/<model>` so you don’t need to manually register models in `opencode.json`.
46
+
47
+ ### Compatibility notes
48
+
49
+ Both providers can be launched with either backend, but compatibility ultimately depends on what API shape the provider expects:
50
+
51
+ - **OpenCode** works with **LM Studio** and **Ollama** by pointing at their OpenAI-compatible `/v1` endpoints.
52
+ - **Claude Code** is configured via `ANTHROPIC_BASE_URL` and works best with backends that expose an Anthropic-compatible API at `/v1` (LM Studio supports this). If your Ollama setup does not provide an Anthropic-compatible `/v1`, Claude Code may fail even though AIX can launch it.
46
53
 
47
54
  ---
48
55
 
@@ -112,8 +119,9 @@ aix-cli run
112
119
  aix-cli run -b ollama -m qwen2.5-coder:14b
113
120
  aix-cli run -b lmstudio -m llama-3-8b
114
121
 
115
- # Use OpenCode instead of Claude Code
116
- aix-cli run --provider opencode
122
+ # Choose provider explicitly
123
+ aix-cli run -p claude
124
+ aix-cli run -p opencode
117
125
 
118
126
  # Pass a prompt directly
119
127
  aix-cli run -b ollama -m qwen2.5-coder:14b -- "Refactor auth middleware"
@@ -289,7 +297,7 @@ Install the missing provider globally:
289
297
  npm install -g @anthropic-ai/claude-code
290
298
 
291
299
  # OpenCode
292
- npm install -g opencode
300
+ npm install -g opencode-ai
293
301
  ```
294
302
 
295
303
  Then re-run `aix-cli doctor` to confirm.
package/dist/bin/aix.js CHANGED
@@ -1,11 +1,12 @@
1
1
  #!/usr/bin/env node
2
- var we=Object.defineProperty;var be=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,o)=>(typeof require<"u"?require:e)[o]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var O=(t,e)=>()=>(t&&(e=t(t=0)),e);var L=(t,e)=>{for(var o in e)we(t,o,{get:e[o],enumerable:!0})};var ae={};L(ae,{ConfigService:()=>D,configService:()=>l});import Me from"conf";var D,l,M=O(()=>{"use strict";D=class{store;constructor(){this.store=new Me({projectName:"aix",defaults:{lmStudioUrl:"http://localhost",lmStudioPort:1234,ollamaUrl:"http://localhost",ollamaPort:11434,defaultTimeout:3e4,autoStartServer:!1},clearInvalidConfig:!0})}get(e){return this.store.get(e)}set(e,o){this.store.set(e,o)}setModel(e){this.store.set("model",e)}getLastUsedModel(){return this.store.get("model")}setDefaultProvider(e){this.store.set("defaultProvider",e)}getDefaultProvider(){return this.store.get("defaultProvider")}setDefaultBackend(e){this.store.set("defaultBackend",e)}getDefaultBackend(){return this.store.get("defaultBackend")}getLMStudioUrl(){let e=this.store.get("lmStudioUrl"),o=this.store.get("lmStudioPort");return`${e}:${o}`}getOllamaUrl(){let e=this.store.get("ollamaUrl"),o=this.store.get("ollamaPort");return`${e}:${o}`}reset(){this.store.clear()}},l=new D});var ce={};L(ce,{LMStudioService:()=>T,lmStudioService:()=>h});import{execa as z}from"execa";import se from"ora";import le from"chalk";var de,T,h,A=O(()=>{"use strict";M();de=[1234,1235,1236,1237],T=class{baseUrl;constructor(){this.baseUrl=l.getLMStudioUrl()}getApiUrl(e){return`${this.baseUrl}${e}`}async checkStatus(){try{return(await fetch(this.getApiUrl("/api/status"),{method:"GET",signal:AbortSignal.timeout(3e3)})).ok}catch{return!1}}async getAvailableModels(){let e=["/api/v1/models","/api/models","/v1/models","/api/ls-model/list"];for(let o of e)try{let i=await fetch(this.getApiUrl(o),{method:"GET",signal:AbortSignal.timeout(1e4)});if(!i.ok)continue;let n=await i.json(),r=[];return Array.isArray(n)?r=n:n.models&&Array.isArray(n.models)?r=n.models:n.data&&Array.isArray(n.data)&&(r=n.data),r.map(a=>{let d=a;return{id:String(d.key||d.id||d.model||""),name:String(d.display_name||d.name||d.id||d.model||""),size:Number(d.size_bytes||d.size||d.file_size||0),quantization:String(d.quantization?typeof d.quantization=="object"?d.quantization.name:d.quantization:"")}}).filter(a=>a.id&&a.name)}catch{continue}return[]}async getStatus(){if(!await this.checkStatus())return{running:!1,port:l.get("lmStudioPort"),models:[]};try{let o=await fetch(this.getApiUrl("/api/status"),{method:"GET",signal:AbortSignal.timeout(1e4)});if(!o.ok)return{running:!1,port:l.get("lmStudioPort"),models:[]};let i=await o.json();return{running:!0,port:l.get("lmStudioPort"),models:i.models??[],activeModel:i.active_model}}catch{return{running:!1,port:l.get("lmStudioPort"),models:[]}}}async loadModel(e,o){let i=o??se({text:`Loading model: ${le.cyan(e)}`,color:"cyan"}).start();try{let n=await fetch(this.getApiUrl("/api/model/load"),{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({model:e}),signal:AbortSignal.timeout(3e5)});if(!n.ok)throw new Error(`Failed to load model: ${n.statusText}`);return i.succeed(`Model ${le.green(e)} loaded successfully`),l.setModel(e),{loadSpinner:i}}catch(n){throw i.fail(`Failed to load model: ${n instanceof Error?n.message:"Unknown error"}`),n}}async startServer(e){let o=e??se({text:"Starting LM Studio server...",color:"cyan"}).start();try{let i=process.platform==="darwin",n=process.platform==="linux",r=process.platform==="win32",a;if(i){let d=["/Applications/LM Studio.app",`${process.env.HOME}/Applications/LM Studio.app`];for(let u of d)try{let{existsSync:m}=await import("fs");if(m(u)){a=`open "${u}" --args --server`;break}}catch{}if(a?.startsWith("open")){await z("open",[d.find(u=>{try{let{existsSync:m}=be("fs");return m(u)}catch{return!1}})||"/Applications/LM Studio.app","--args","--server"],{detached:!0,stdio:"ignore"}),o.succeed("LM Studio server started"),await this.waitForServer(6e4);return}}else n?a=await this.findLinuxBinary():r&&(a=await this.findWindowsExecutable());if(!a)throw o.fail("LM Studio not found. Please install it from https://lmstudio.ai"),new Error("LM Studio not installed");await z(a,["--server"],{detached:!0,stdio:"ignore",env:{...process.env,LM_STUDIO_SERVER_PORT:String(l.get("lmStudioPort"))}}),o.succeed("LM Studio server started"),await this.waitForServer(6e4)}catch(i){throw o.fail(`Failed to start LM Studio: ${i instanceof Error?i.message:"Unknown error"}`),i}}async findLinuxBinary(){let e=["/usr/bin/lm-studio","/usr/local/bin/lm-studio",`${process.env.HOME}/.local/bin/lm-studio`];for(let o of e)try{return await z("test",["-x",o]),o}catch{continue}}async findWindowsExecutable(){let e=process.env.LOCALAPPDATA,o=process.env.PROGRAMFILES,i=[e?`${e}\\Programs\\LM Studio\\lm-studio.exe`:"",o?`${o}\\LM Studio\\lm-studio.exe`:""].filter(Boolean);for(let n of i)try{return await z("cmd",["/c","if exist",`"${n}"`,"echo","yes"]),n}catch{continue}}async waitForServer(e=6e4){let o=Date.now();for(;Date.now()-o<e;){if(await this.checkStatus())return!0;await this.sleep(2e3)}return!1}sleep(e){return new Promise(o=>setTimeout(o,e))}async findAvailablePort(){for(let e of de)try{if((await fetch(`http://localhost:${e}/api/status`,{method:"GET",signal:AbortSignal.timeout(1e3)})).ok)return e}catch{return l.set("lmStudioPort",e),e}return de[0]??1234}},h=new T});var ue={};L(ue,{OllamaService:()=>j,ollamaService:()=>y});var j,y,E=O(()=>{"use strict";M();j=class{getBaseUrl(){return l.getOllamaUrl()}getApiUrl(e){return`${this.getBaseUrl()}${e}`}async checkStatus(){try{return(await fetch(this.getApiUrl("/api/tags"),{method:"GET",signal:AbortSignal.timeout(3e3)})).ok}catch{return!1}}async getAvailableModels(){try{let e=await fetch(this.getApiUrl("/api/tags"),{method:"GET",signal:AbortSignal.timeout(1e4)});return e.ok?((await e.json()).models??[]).map(n=>{let r=n.details??{};return{id:String(n.name??n.model??""),name:String(n.name??n.model??""),size:Number(n.size??0),quantization:String(r.quantization_level??""),family:String(r.family??""),parameterSize:String(r.parameter_size??"")}}).filter(n=>n.id&&n.name):[]}catch{return[]}}async getRunningModels(){try{let e=await fetch(this.getApiUrl("/api/ps"),{method:"GET",signal:AbortSignal.timeout(5e3)});return e.ok?((await e.json()).models??[]).map(n=>String(n.name??n.model??"")).filter(Boolean):[]}catch{return[]}}async getStatus(){if(!await this.checkStatus())return{running:!1,port:l.get("ollamaPort"),models:[],runningModels:[]};let[o,i]=await Promise.all([this.getAvailableModels(),this.getRunningModels()]);return{running:!0,port:l.get("ollamaPort"),models:o,runningModels:i}}},y=new j});var ge={};L(ge,{ClaudeService:()=>K,claudeService:()=>R});import{execa as J}from"execa";import xe from"chalk";var K,R,Q=O(()=>{"use strict";M();K=class{async isClaudeCodeInstalled(){try{return await J("claude",["--version"],{stdio:"ignore"}),!0}catch{return!1}}async run(e){let{model:o,args:i=[],verbose:n=!1}=e,r=this.extractProvider(o),a=this.extractModelName(o);if(!r||!a)throw new Error(`Invalid model format: ${o}. Expected format: provider/model-name`);let d=["--model",a,...i];n&&console.log(xe.dim(`
2
+ #!/usr/bin/env node
3
+ var we=Object.defineProperty;var be=(t=>typeof require<"u"?require:typeof Proxy<"u"?new Proxy(t,{get:(e,o)=>(typeof require<"u"?require:e)[o]}):t)(function(t){if(typeof require<"u")return require.apply(this,arguments);throw Error('Dynamic require of "'+t+'" is not supported')});var O=(t,e)=>()=>(t&&(e=t(t=0)),e);var L=(t,e)=>{for(var o in e)we(t,o,{get:e[o],enumerable:!0})};var ae={};L(ae,{ConfigService:()=>D,configService:()=>l});import Me from"conf";var D,l,M=O(()=>{"use strict";D=class{store;constructor(){this.store=new Me({projectName:"aix",defaults:{lmStudioUrl:"http://localhost",lmStudioPort:1234,ollamaUrl:"http://localhost",ollamaPort:11434,defaultTimeout:3e4,autoStartServer:!1},clearInvalidConfig:!0})}get(e){return this.store.get(e)}set(e,o){this.store.set(e,o)}setModel(e){this.store.set("model",e)}getLastUsedModel(){return this.store.get("model")}setDefaultProvider(e){this.store.set("defaultProvider",e)}getDefaultProvider(){return this.store.get("defaultProvider")}setDefaultBackend(e){this.store.set("defaultBackend",e)}getDefaultBackend(){return this.store.get("defaultBackend")}getLMStudioUrl(){let e=this.store.get("lmStudioUrl"),o=this.store.get("lmStudioPort");return`${e}:${o}`}getOllamaUrl(){let e=this.store.get("ollamaUrl"),o=this.store.get("ollamaPort");return`${e}:${o}`}reset(){this.store.clear()}},l=new D});var ce={};L(ce,{LMStudioService:()=>_,lmStudioService:()=>v});import{execa as z}from"execa";import se from"ora";import le from"chalk";var de,_,v,A=O(()=>{"use strict";M();de=[1234,1235,1236,1237],_=class{baseUrl;constructor(){this.baseUrl=l.getLMStudioUrl()}getApiUrl(e){return`${this.baseUrl}${e}`}async checkStatus(){try{return(await fetch(this.getApiUrl("/api/status"),{method:"GET",signal:AbortSignal.timeout(3e3)})).ok}catch{return!1}}async getAvailableModels(){let e=["/api/v1/models","/api/models","/v1/models","/api/ls-model/list"];for(let o of e)try{let i=await fetch(this.getApiUrl(o),{method:"GET",signal:AbortSignal.timeout(1e4)});if(!i.ok)continue;let n=await i.json(),r=[];return Array.isArray(n)?r=n:n.models&&Array.isArray(n.models)?r=n.models:n.data&&Array.isArray(n.data)&&(r=n.data),r.map(a=>{let d=a;return{id:String(d.key||d.id||d.model||""),name:String(d.display_name||d.name||d.id||d.model||""),size:Number(d.size_bytes||d.size||d.file_size||0),quantization:String(d.quantization?typeof d.quantization=="object"?d.quantization.name:d.quantization:"")}}).filter(a=>a.id&&a.name)}catch{continue}return[]}async getStatus(){if(!await this.checkStatus())return{running:!1,port:l.get("lmStudioPort"),models:[]};try{let o=await fetch(this.getApiUrl("/api/status"),{method:"GET",signal:AbortSignal.timeout(1e4)});if(!o.ok)return{running:!1,port:l.get("lmStudioPort"),models:[]};let i=await o.json();return{running:!0,port:l.get("lmStudioPort"),models:i.models??[],activeModel:i.active_model}}catch{return{running:!1,port:l.get("lmStudioPort"),models:[]}}}async loadModel(e,o){let i=o??se({text:`Loading model: ${le.cyan(e)}`,color:"cyan"}).start();try{let n=await fetch(this.getApiUrl("/api/model/load"),{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({model:e}),signal:AbortSignal.timeout(3e5)});if(!n.ok)throw new Error(`Failed to load model: ${n.statusText}`);return i.succeed(`Model ${le.green(e)} loaded successfully`),l.setModel(e),{loadSpinner:i}}catch(n){throw i.fail(`Failed to load model: ${n instanceof Error?n.message:"Unknown error"}`),n}}async startServer(e){let o=e??se({text:"Starting LM Studio server...",color:"cyan"}).start();try{let i=process.platform==="darwin",n=process.platform==="linux",r=process.platform==="win32",a;if(i){let d=["/Applications/LM Studio.app",`${process.env.HOME}/Applications/LM Studio.app`];for(let u of d)try{let{existsSync:m}=await import("fs");if(m(u)){a=`open "${u}" --args --server`;break}}catch{}if(a?.startsWith("open")){await z("open",[d.find(u=>{try{let{existsSync:m}=be("fs");return m(u)}catch{return!1}})||"/Applications/LM Studio.app","--args","--server"],{detached:!0,stdio:"ignore"}),o.succeed("LM Studio server started"),await this.waitForServer(6e4);return}}else n?a=await this.findLinuxBinary():r&&(a=await this.findWindowsExecutable());if(!a)throw o.fail("LM Studio not found. Please install it from https://lmstudio.ai"),new Error("LM Studio not installed");await z(a,["--server"],{detached:!0,stdio:"ignore",env:{...process.env,LM_STUDIO_SERVER_PORT:String(l.get("lmStudioPort"))}}),o.succeed("LM Studio server started"),await this.waitForServer(6e4)}catch(i){throw o.fail(`Failed to start LM Studio: ${i instanceof Error?i.message:"Unknown error"}`),i}}async findLinuxBinary(){let e=["/usr/bin/lm-studio","/usr/local/bin/lm-studio",`${process.env.HOME}/.local/bin/lm-studio`];for(let o of e)try{return await z("test",["-x",o]),o}catch{continue}}async findWindowsExecutable(){let e=process.env.LOCALAPPDATA,o=process.env.PROGRAMFILES,i=[e?`${e}\\Programs\\LM Studio\\lm-studio.exe`:"",o?`${o}\\LM Studio\\lm-studio.exe`:""].filter(Boolean);for(let n of i)try{return await z("cmd",["/c","if exist",`"${n}"`,"echo","yes"]),n}catch{continue}}async waitForServer(e=6e4){let o=Date.now();for(;Date.now()-o<e;){if(await this.checkStatus())return!0;await this.sleep(2e3)}return!1}sleep(e){return new Promise(o=>setTimeout(o,e))}async findAvailablePort(){for(let e of de)try{if((await fetch(`http://localhost:${e}/api/status`,{method:"GET",signal:AbortSignal.timeout(1e3)})).ok)return e}catch{return l.set("lmStudioPort",e),e}return de[0]??1234}},v=new _});var ue={};L(ue,{OllamaService:()=>T,ollamaService:()=>y});var T,y,E=O(()=>{"use strict";M();T=class{getBaseUrl(){return l.getOllamaUrl()}getApiUrl(e){return`${this.getBaseUrl()}${e}`}async checkStatus(){try{return(await fetch(this.getApiUrl("/api/tags"),{method:"GET",signal:AbortSignal.timeout(3e3)})).ok}catch{return!1}}async getAvailableModels(){try{let e=await fetch(this.getApiUrl("/api/tags"),{method:"GET",signal:AbortSignal.timeout(1e4)});return e.ok?((await e.json()).models??[]).map(n=>{let r=n.details??{};return{id:String(n.name??n.model??""),name:String(n.name??n.model??""),size:Number(n.size??0),quantization:String(r.quantization_level??""),family:String(r.family??""),parameterSize:String(r.parameter_size??"")}}).filter(n=>n.id&&n.name):[]}catch{return[]}}async getRunningModels(){try{let e=await fetch(this.getApiUrl("/api/ps"),{method:"GET",signal:AbortSignal.timeout(5e3)});return e.ok?((await e.json()).models??[]).map(n=>String(n.name??n.model??"")).filter(Boolean):[]}catch{return[]}}async getStatus(){if(!await this.checkStatus())return{running:!1,port:l.get("ollamaPort"),models:[],runningModels:[]};let[o,i]=await Promise.all([this.getAvailableModels(),this.getRunningModels()]);return{running:!0,port:l.get("ollamaPort"),models:o,runningModels:i}}},y=new T});var ge={};L(ge,{ClaudeService:()=>G,claudeService:()=>R});import{execa as J}from"execa";import xe from"chalk";var G,R,Q=O(()=>{"use strict";M();G=class{async isClaudeCodeInstalled(){try{return await J("claude",["--version"],{stdio:"ignore"}),!0}catch{return!1}}async run(e){let{model:o,args:i=[],verbose:n=!1}=e,r=this.extractProvider(o),a=this.extractModelName(o);if(!r||!a)throw new Error(`Invalid model format: ${o}. Expected format: provider/model-name`);let d=["--model",a,...i];n&&console.log(xe.dim(`
3
4
  Running: claude ${d.join(" ")}
4
- `));let m=`${r==="ollama"?l.getOllamaUrl():l.getLMStudioUrl()}/v1`;try{await J("claude",d,{stdio:"inherit",env:{...process.env,ANTHROPIC_MODEL:a,ANTHROPIC_BASE_URL:m,ANTHROPIC_API_KEY:"lmstudio",ANTHROPIC_AUTH_TOKEN:"lmstudio"}})}catch(c){if(c instanceof Error&&"exitCode"in c){let v=c.exitCode;process.exit(v??1)}throw c}}extractProvider(e){return e.split("/")[0]}extractModelName(e){let o=e.split("/");if(!(o.length<2))return o.slice(1).join("/")}async getVersion(){try{return(await J("claude",["--version"])).stdout}catch{return}}},R=new K});var pe={};L(pe,{OpenCodeService:()=>W,openCodeService:()=>U});import{execa as Z}from"execa";import Oe from"chalk";var W,U,ee=O(()=>{"use strict";M();W=class{async isOpenCodeInstalled(){try{return await Z("opencode",["--version"],{stdio:"ignore"}),!0}catch{return!1}}async run(e){let{model:o,args:i=[],verbose:n=!1}=e,r=this.extractProvider(o),a=this.extractModelName(o);if(!r||!a)throw new Error(`Invalid model format: ${o}. Expected format: provider/model-name`);let u=["--model",`openai/${a}`,...i];n&&console.log(Oe.dim(`
5
+ `));let m=`${r==="ollama"?l.getOllamaUrl():l.getLMStudioUrl()}/v1`;try{await J("claude",d,{stdio:"inherit",env:{...process.env,ANTHROPIC_MODEL:a,ANTHROPIC_BASE_URL:m,ANTHROPIC_API_KEY:"lmstudio",ANTHROPIC_AUTH_TOKEN:"lmstudio"}})}catch(c){if(c instanceof Error&&"exitCode"in c){let S=c.exitCode;process.exit(S??1)}throw c}}extractProvider(e){return e.split("/")[0]}extractModelName(e){let o=e.split("/");if(!(o.length<2))return o.slice(1).join("/")}async getVersion(){try{return(await J("claude",["--version"])).stdout}catch{return}}},R=new G});var pe={};L(pe,{OpenCodeService:()=>W,openCodeService:()=>U});import{execa as Z}from"execa";import Oe from"chalk";var W,U,ee=O(()=>{"use strict";M();W=class{async isOpenCodeInstalled(){try{return await Z("opencode",["--version"],{stdio:"ignore"}),!0}catch{return!1}}async run(e){let{model:o,args:i=[],verbose:n=!1}=e,r=this.extractProvider(o),a=this.extractModelName(o);if(!r||!a)throw new Error(`Invalid model format: ${o}. Expected format: provider/model-name`);let u=["--model",`openai-compatible/${a}`,...i];n&&console.log(Oe.dim(`
5
6
  Running: opencode ${u.join(" ")}
6
- `));let c=`${r==="ollama"?l.getOllamaUrl():l.getLMStudioUrl()}/v1`;try{await Z("opencode",u,{stdio:"inherit",env:{...process.env,OPENCODE_MODEL_NAME:a,OPENCODE_MODEL_PROVIDER:"openai",OPENAI_BASE_URL:c,OPENAI_API_KEY:"local-no-key-required"}})}catch(v){if(v instanceof Error&&"exitCode"in v){let P=v.exitCode;process.exit(P??1)}throw v}}extractProvider(e){return e.split("/")[0]}extractModelName(e){let o=e.split("/");if(!(o.length<2))return o.slice(1).join("/")}async getVersion(){try{return(await Z("opencode",["--version"])).stdout}catch{return}}},U=new W});import{Command as De}from"commander";import g from"chalk";A();E();M();import F from"ora";import f from"chalk";import G from"inquirer";import me from"inquirer";async function k(t,e){let o=t.map(r=>({name:`${r.name} (${r.id})`,value:r,short:r.name})),i=e?o.findIndex(r=>r.value.id===e):0;return(await me.prompt([{type:"list",name:"model",message:"Select a model to load:",choices:o,default:Math.max(0,i),pageSize:Math.min(t.length,15)}])).model}async function _(t,e=!0){return(await me.prompt([{type:"confirm",name:"confirm",message:t,default:e}])).confirm}import H from"chalk";function C(t){if(t===0)return"0 B";let e=1024,o=["B","KB","MB","GB","TB"],i=Math.floor(Math.log(t)/Math.log(e));return`${parseFloat((t/Math.pow(e,i)).toFixed(2))} ${o[i]}`}function w(t){console.log(H.green("\u2713")+" "+t)}function X(t){console.error(H.red("\u2717")+" "+t)}function q(t){console.log(H.blue("\u2139")+" "+t)}function p(t,e=1){X(t),process.exit(e)}async function $e(){let t=l.getDefaultBackend(),{backendSelection:e}=await G.prompt([{type:"list",name:"backendSelection",message:"Select model backend:",default:t??"lmstudio",choices:[{name:"\u{1F5A5}\uFE0F LM Studio",value:"lmstudio"},{name:"\u{1F999} Ollama",value:"ollama"}]}]),{saveDefault:o}=await G.prompt([{type:"confirm",name:"saveDefault",message:"Save as default backend?",default:!1}]);return o&&(l.setDefaultBackend(e),w(`Default backend set to ${f.cyan(e)}`)),e}async function Pe(t){let e=l.getDefaultProvider(),o=t==="ollama"?[{name:"OpenCode",value:"opencode"}]:[{name:"Claude Code",value:"claude"},{name:"OpenCode",value:"opencode"}],i=t==="ollama"?"opencode":e??"claude",{providerSelection:n}=await G.prompt([{type:"list",name:"providerSelection",message:"Select coding tool:",default:i,choices:o}]),{saveDefault:r}=await G.prompt([{type:"confirm",name:"saveDefault",message:"Save as default coding tool?",default:!1}]);return r&&(l.setDefaultProvider(n),w(`Default coding tool set to ${f.cyan(n)}`)),n}async function ke(t,e){let o=F({text:"Checking LM Studio status...",color:"cyan"}).start(),i=await h.checkStatus();i||(o.info("LM Studio server not running"),o.stop(),await _("Would you like to start the LM Studio server?")||p("LM Studio server must be running. Start it manually or use the Server tab in LM Studio."),await h.startServer(),i=!0),o.succeed("Connected to LM Studio");let n=F({text:"Fetching available models...",color:"cyan"}).start(),r=await h.getAvailableModels();r.length===0&&(n.fail("No models found. Download some models in LM Studio first."),p("No models available")),n.succeed(`Found ${f.bold(r.length)} model${r.length===1?"":"s"}`),console.log(),console.log(f.bold("Available Models:")),console.log(f.dim("\u2500".repeat(process.stdout.columns||80))),r.forEach((c,v)=>{let P=C(c.size),$=c.loaded?f.green(" [LOADED]"):"";console.log(` ${f.dim(String(v+1).padStart(2))}. ${c.name} ${f.dim(`(${P})`)}${$}`)}),console.log();let a=l.getLastUsedModel(),d=t.model,u=d?r.find(c=>c.id===d||c.name.includes(d)):await k(r,a);u||p("No model selected"),await h.loadModel(u.id,o);let m=u.id.replace("/","--");w(f.bold(`
7
- Model ready: ${u.name}`)),console.log(),console.log("Start your interactive coding session:"),console.log(` ${f.cyan(`aix-cli run --provider ${e} --backend lmstudio --model ${m}`)}`),console.log()}async function Ce(t,e){let o=F({text:"Checking Ollama status...",color:"cyan"}).start();await y.checkStatus()||(o.fail("Ollama is not running"),p("Ollama must be running. Start it with: ollama serve")),o.succeed("Connected to Ollama");let n=F({text:"Fetching available models...",color:"cyan"}).start(),r=await y.getAvailableModels();r.length===0&&(n.fail("No models found. Pull a model first: ollama pull <model>"),p("No models available")),n.succeed(`Found ${f.bold(r.length)} model${r.length===1?"":"s"}`);let a=await y.getRunningModels();console.log(),console.log(f.bold("Available Models:")),console.log(f.dim("\u2500".repeat(process.stdout.columns||80))),r.forEach((c,v)=>{let P=C(c.size),V=a.includes(c.id)?f.green(" [RUNNING]"):"",ye=c.parameterSize?f.dim(` ${c.parameterSize}`):"";console.log(` ${f.dim(String(v+1).padStart(2))}. ${c.name}${ye} ${f.dim(`(${P})`)}${V}`)}),console.log();let d=l.getLastUsedModel(),u=t.model,m=u?r.find(c=>c.id===u||c.name.includes(u)):await k(r,d);m||p("No model selected"),l.setModel(m.id),w(f.bold(`
8
- Model selected: ${m.name}`)),console.log(),console.log("Start your interactive coding session:"),console.log(` ${f.cyan(`aix-cli run --provider ${e} --backend ollama --model ${m.id}`)}`),console.log()}async function Y(t={}){let e=t.backend??await $e(),o=t.provider??await Pe(e);e==="ollama"&&o==="claude"&&p("Claude Code requires an Anthropic-compatible API. LM Studio supports this natively, but Ollama does not. Please select OpenCode for Ollama, or switch to LM Studio."),e==="ollama"?await Ce(t,o):await ke(t,o)}A();E();Q();ee();M();import x from"ora";import fe from"chalk";import ve from"inquirer";async function Le(t){if(t==="claude")return"lmstudio";let e=l.getDefaultBackend();if(e)return e;let{backendSelection:o}=await ve.prompt([{type:"list",name:"backendSelection",message:"Select model backend:",choices:[{name:"\u{1F5A5}\uFE0F LM Studio",value:"lmstudio"},{name:"\u{1F999} Ollama",value:"ollama"}]}]);return o}async function Ae(){let t=await R.isClaudeCodeInstalled(),e=await U.isOpenCodeInstalled(),o=[];if(t&&o.push({name:"Claude Code",value:"claude"}),e&&o.push({name:"OpenCode",value:"opencode"}),o.length===0&&p("Neither Claude Code nor OpenCode is installed."),o.length===1)return o[0].value;let{providerSelection:i}=await ve.prompt([{type:"list",name:"providerSelection",message:"Select coding tool:",choices:o}]);return i}function I(t){return t==="opencode"?"OpenCode":"Claude Code"}async function Ee(t,e){let o=x({text:"Checking LM Studio status...",color:"cyan"}).start(),i=await h.checkStatus();i||(o.info("LM Studio server not running"),o.stop(),await _("Would you like to start the LM Studio server?")||p("LM Studio server must be running. Start it manually or use the Server tab in LM Studio."),await h.startServer(),i=!0),o.succeed("Connected to LM Studio");let n=x({text:"Fetching available models...",color:"cyan"}).start(),r=await h.getAvailableModels();r.length===0&&(n.fail("No models found. Download some models in LM Studio first."),p("No models available")),n.stop();let a;if(t.model){let c=r.find(v=>v.id===t.model||v.name.toLowerCase().includes(t.model.toLowerCase()));c||p(`Model "${t.model}" not found. Available models: ${r.map(v=>v.name).join(", ")}`),a=c.id}else{let c=l.getLastUsedModel();a=(await k(r,c)).id}let d=x({text:`Loading model: ${fe.cyan(a)}`,color:"cyan"}).start();await h.loadModel(a,d);let m=`lmstudio/${a.replace("/","--")}`;await he(e,m,t)}async function Re(t,e){let o=x({text:"Checking Ollama status...",color:"cyan"}).start();await y.checkStatus()||(o.fail("Ollama is not running"),p("Ollama must be running. Start it with: ollama serve")),o.succeed("Connected to Ollama");let n=x({text:"Fetching available models...",color:"cyan"}).start(),r=await y.getAvailableModels();r.length===0&&(n.fail("No models found. Pull a model first: ollama pull <model>"),p("No models available")),n.stop();let a;if(t.model){let u=r.find(m=>m.id===t.model||m.name.toLowerCase().includes(t.model.toLowerCase()));u||p(`Model "${t.model}" not found. Available models: ${r.map(m=>m.name).join(", ")}`),a=u.id}else{let u=l.getLastUsedModel();a=(await k(r,u)).id}l.setModel(a);let d=`ollama/${a}`;await he(e,d,t)}async function he(t,e,o){let i=I(t);w(fe.green(`
7
+ `));let c=`${r==="ollama"?l.getOllamaUrl():l.getLMStudioUrl()}/v1`;try{await Z("opencode",u,{stdio:"inherit",env:{...process.env,OPENCODE_MODEL_NAME:a,OPENCODE_MODEL_PROVIDER:"openai-compatible",OPENAI_BASE_URL:c,OPENAI_API_KEY:"local-no-key-required",OPENAI_COMPATIBLE_BASE_URL:c,OPENAI_COMPATIBLE_API_KEY:"local-no-key-required"}})}catch(S){if(S instanceof Error&&"exitCode"in S){let P=S.exitCode;process.exit(P??1)}throw S}}extractProvider(e){return e.split("/")[0]}extractModelName(e){let o=e.split("/");if(!(o.length<2))return o.slice(1).join("/")}async getVersion(){try{return(await Z("opencode",["--version"])).stdout}catch{return}}},U=new W});import{Command as De}from"commander";import g from"chalk";A();E();M();import F from"ora";import p from"chalk";import K from"inquirer";import me from"inquirer";async function k(t,e){let o=t.map(r=>({name:`${r.name} (${r.id})`,value:r,short:r.name})),i=e?o.findIndex(r=>r.value.id===e):0;return(await me.prompt([{type:"list",name:"model",message:"Select a model to load:",choices:o,default:Math.max(0,i),pageSize:Math.min(t.length,15)}])).model}async function j(t,e=!0){return(await me.prompt([{type:"confirm",name:"confirm",message:t,default:e}])).confirm}import H from"chalk";function C(t){if(t===0)return"0 B";let e=1024,o=["B","KB","MB","GB","TB"],i=Math.floor(Math.log(t)/Math.log(e));return`${parseFloat((t/Math.pow(e,i)).toFixed(2))} ${o[i]}`}function w(t){console.log(H.green("\u2713")+" "+t)}function X(t){console.error(H.red("\u2717")+" "+t)}function q(t){console.log(H.blue("\u2139")+" "+t)}function f(t,e=1){X(t),process.exit(e)}async function $e(){let t=l.getDefaultBackend(),{backendSelection:e}=await K.prompt([{type:"list",name:"backendSelection",message:"Select model backend:",default:t??"lmstudio",choices:[{name:"\u{1F5A5}\uFE0F LM Studio",value:"lmstudio"},{name:"\u{1F999} Ollama",value:"ollama"}]}]),{saveDefault:o}=await K.prompt([{type:"confirm",name:"saveDefault",message:"Save as default backend?",default:!1}]);return o&&(l.setDefaultBackend(e),w(`Default backend set to ${p.cyan(e)}`)),e}async function Pe(t){let e=l.getDefaultProvider(),o=[{name:"Claude Code",value:"claude"},{name:"OpenCode",value:"opencode"}],i=e??"claude",{providerSelection:n}=await K.prompt([{type:"list",name:"providerSelection",message:"Select coding tool:",default:i,choices:o}]),{saveDefault:r}=await K.prompt([{type:"confirm",name:"saveDefault",message:"Save as default coding tool?",default:!1}]);return r&&(l.setDefaultProvider(n),w(`Default coding tool set to ${p.cyan(n)}`)),n}async function ke(t,e){let o=F({text:"Checking LM Studio status...",color:"cyan"}).start(),i=await v.checkStatus();i||(o.info("LM Studio server not running"),o.stop(),await j("Would you like to start the LM Studio server?")||f("LM Studio server must be running. Start it manually or use the Server tab in LM Studio."),await v.startServer(),i=!0),o.succeed("Connected to LM Studio");let n=F({text:"Fetching available models...",color:"cyan"}).start(),r=await v.getAvailableModels();r.length===0&&(n.fail("No models found. Download some models in LM Studio first."),f("No models available")),n.succeed(`Found ${p.bold(r.length)} model${r.length===1?"":"s"}`),console.log(),console.log(p.bold("Available Models:")),console.log(p.dim("\u2500".repeat(process.stdout.columns||80))),r.forEach((c,S)=>{let P=C(c.size),$=c.loaded?p.green(" [LOADED]"):"";console.log(` ${p.dim(String(S+1).padStart(2))}. ${c.name} ${p.dim(`(${P})`)}${$}`)}),console.log();let a=l.getLastUsedModel(),d=t.model,u=d?r.find(c=>c.id===d||c.name.includes(d)):await k(r,a);u||f("No model selected"),await v.loadModel(u.id,o);let m=u.id.replace("/","--");w(p.bold(`
8
+ Model ready: ${u.name}`)),console.log(),console.log("Start your interactive coding session:"),console.log(` ${p.cyan(`aix-cli run --provider ${e} --backend lmstudio --model ${m}`)}`),console.log()}async function Ce(t,e){let o=F({text:"Checking Ollama status...",color:"cyan"}).start();await y.checkStatus()||(o.fail("Ollama is not running"),f("Ollama must be running. Start it with: ollama serve")),o.succeed("Connected to Ollama");let n=F({text:"Fetching available models...",color:"cyan"}).start(),r=await y.getAvailableModels();r.length===0&&(n.fail("No models found. Pull a model first: ollama pull <model>"),f("No models available")),n.succeed(`Found ${p.bold(r.length)} model${r.length===1?"":"s"}`);let a=await y.getRunningModels();console.log(),console.log(p.bold("Available Models:")),console.log(p.dim("\u2500".repeat(process.stdout.columns||80))),r.forEach((c,S)=>{let P=C(c.size),V=a.includes(c.id)?p.green(" [RUNNING]"):"",ye=c.parameterSize?p.dim(` ${c.parameterSize}`):"";console.log(` ${p.dim(String(S+1).padStart(2))}. ${c.name}${ye} ${p.dim(`(${P})`)}${V}`)}),console.log();let d=l.getLastUsedModel(),u=t.model,m=u?r.find(c=>c.id===u||c.name.includes(u)):await k(r,d);m||f("No model selected"),l.setModel(m.id),w(p.bold(`
9
+ Model selected: ${m.name}`)),console.log(),console.log("Start your interactive coding session:"),console.log(` ${p.cyan(`aix-cli run --provider ${e} --backend ollama --model ${m.id}`)}`),console.log()}async function Y(t={}){let e=t.backend??await $e(),o=t.provider??await Pe(e);e==="ollama"?await Ce(t,o):await ke(t,o)}A();E();Q();ee();M();import x from"ora";import fe from"chalk";import ve from"inquirer";async function Le(t){let e=l.getDefaultBackend();if(e)return e;let{backendSelection:o}=await ve.prompt([{type:"list",name:"backendSelection",message:"Select model backend:",choices:[{name:"\u{1F5A5}\uFE0F LM Studio",value:"lmstudio"},{name:"\u{1F999} Ollama",value:"ollama"}]}]);return o}async function Ae(){let t=await R.isClaudeCodeInstalled(),e=await U.isOpenCodeInstalled(),o=[{name:"Claude Code",value:"claude",disabled:t?!1:"Not installed (install: npm i -g @anthropic-ai/claude-code)"},{name:"OpenCode",value:"opencode",disabled:e?!1:"Not installed (install: npm i -g opencode-ai)"}];if(!t&&!e&&f("Neither Claude Code nor OpenCode is installed."),t&&!e)return"claude";if(!t&&e)return"opencode";let{providerSelection:i}=await ve.prompt([{type:"list",name:"providerSelection",message:"Select coding tool:",choices:o}]);return i}function I(t){return t==="opencode"?"OpenCode":"Claude Code"}async function Ee(t,e){let o=x({text:"Checking LM Studio status...",color:"cyan"}).start(),i=await v.checkStatus();i||(o.info("LM Studio server not running"),o.stop(),await j("Would you like to start the LM Studio server?")||f("LM Studio server must be running. Start it manually or use the Server tab in LM Studio."),await v.startServer(),i=!0),o.succeed("Connected to LM Studio");let n=x({text:"Fetching available models...",color:"cyan"}).start(),r=await v.getAvailableModels();r.length===0&&(n.fail("No models found. Download some models in LM Studio first."),f("No models available")),n.stop();let a;if(t.model){let m=r.find(c=>c.id===t.model||c.name.toLowerCase().includes(t.model.toLowerCase()));m||f(`Model "${t.model}" not found. Available models: ${r.map(c=>c.name).join(", ")}`),a=m.id}else{let m=l.getLastUsedModel();a=(await k(r,m)).id}let d=x({text:`Loading model: ${fe.cyan(a)}`,color:"cyan"}).start();await v.loadModel(a,d);let u=`lmstudio/${a}`;await Se(e,u,t)}async function Re(t,e){let o=x({text:"Checking Ollama status...",color:"cyan"}).start();await y.checkStatus()||(o.fail("Ollama is not running"),f("Ollama must be running. Start it with: ollama serve")),o.succeed("Connected to Ollama");let n=x({text:"Fetching available models...",color:"cyan"}).start(),r=await y.getAvailableModels();r.length===0&&(n.fail("No models found. Pull a model first: ollama pull <model>"),f("No models available")),n.stop();let a;if(t.model){let u=r.find(m=>m.id===t.model||m.name.toLowerCase().includes(t.model.toLowerCase()));u||f(`Model "${t.model}" not found. Available models: ${r.map(m=>m.name).join(", ")}`),a=u.id}else{let u=l.getLastUsedModel();a=(await k(r,u)).id}l.setModel(a);let d=`ollama/${a}`;await Se(e,d,t)}async function Se(t,e,o){let i=I(t);w(fe.green(`
9
10
  Starting ${i} with model: ${e}
10
- `));try{t==="opencode"?await U.run({model:e,args:o.args??[],verbose:o.verbose}):await R.run({model:e,args:o.args??[],verbose:o.verbose})}catch(n){p(`Failed to run ${i}: ${n instanceof Error?n.message:"Unknown error"}`)}}async function oe(t={}){let e;if(t.provider)e=t.provider;else{let r=l.getDefaultProvider();r?e=r:e=await Ae()}let o=x({text:`Checking ${I(e)} installation...`,color:"cyan"}).start();(e==="opencode"?await U.isOpenCodeInstalled():await R.isClaudeCodeInstalled())||(o.fail(`${I(e)} is not installed.`),p(`Please install ${I(e)} first.`)),o.succeed(`${I(e)} is installed`);let n=t.backend??await Le(e);n==="ollama"&&e==="claude"&&p("Claude Code requires an Anthropic-compatible API. LM Studio supports this natively, but Ollama does not. Please select OpenCode for Ollama, or switch to LM Studio."),n==="ollama"?await Re(t,e):await Ee(t,e)}A();E();import s from"chalk";async function te(){let[t,e]=await Promise.all([h.getStatus(),y.getStatus()]);console.log(),console.log(s.bold("LM Studio")),console.log(s.dim("\u2500".repeat(50))),console.log(` ${t.running?s.green("\u25CF"):s.red("\u25CB")} Server: ${t.running?s.green("Running"):s.red("Stopped")}`),console.log(` ${s.dim("\u25B8")} Port: ${s.cyan(String(t.port))}`),console.log(` ${s.dim("\u25B8")} URL: ${s.cyan(`http://localhost:${t.port}`)}`),t.activeModel&&console.log(` ${s.dim("\u25B8")} Active Model: ${s.green(t.activeModel)}`),t.running&&t.models.length>0?(console.log(),console.log(s.bold(" Models")),t.models.forEach((o,i)=>{let n=C(o.size),r=o.id===t.activeModel?` ${s.green("[LOADED]")}`:"";console.log(` ${s.dim(String(i+1)+".")} ${o.name}${r}`),console.log(` ${s.dim("ID:")} ${o.id}`),console.log(` ${s.dim("Size:")} ${n}`),o.quantization&&console.log(` ${s.dim("Quantization:")} ${o.quantization}`)})):t.running&&console.log(` ${s.dim("No models available")}`),console.log(),console.log(s.bold("Ollama")),console.log(s.dim("\u2500".repeat(50))),console.log(` ${e.running?s.green("\u25CF"):s.red("\u25CB")} Server: ${e.running?s.green("Running"):s.red("Stopped")}`),console.log(` ${s.dim("\u25B8")} Port: ${s.cyan(String(e.port))}`),console.log(` ${s.dim("\u25B8")} URL: ${s.cyan(`http://localhost:${e.port}`)}`),e.running&&e.runningModels.length>0&&console.log(` ${s.dim("\u25B8")} Running: ${s.green(e.runningModels.join(", "))}`),e.running&&e.models.length>0?(console.log(),console.log(s.bold(" Models")),e.models.forEach((o,i)=>{let n=C(o.size),a=e.runningModels.includes(o.id)?` ${s.green("[RUNNING]")}`:"",d=o.parameterSize?` ${s.dim(o.parameterSize)}`:"";console.log(` ${s.dim(String(i+1)+".")} ${o.name}${d}${a}`),console.log(` ${s.dim("Size:")} ${n}`),o.family&&console.log(` ${s.dim("Family:")} ${o.family}`),o.quantization&&console.log(` ${s.dim("Quantization:")} ${o.quantization}`)})):e.running&&console.log(` ${s.dim("No models available")}`),console.log()}import Ue from"ora";import N from"chalk";import{execa as Se}from"execa";import{readFileSync as Ie}from"fs";import{fileURLToPath as Ne}from"url";function ne(){try{let t=Ne(new URL("../../package.json",import.meta.url)),e=JSON.parse(Ie(t,"utf8"));return String(e.version)}catch{return"unknown"}}async function re(){let t=Ue({text:"Checking for updates...",color:"cyan"}).start();try{let e=ne();if(e==="unknown"){t.fail("Could not determine current version.");return}let{stdout:o}=await Se("npm",["view","@iamharshil/aix-cli","version"]),i=o.trim();if(e===i){t.succeed(`You're already on the latest version: ${N.green(`v${e}`)}`);return}t.text=`Updating: ${N.yellow(`v${e}`)} \u2192 ${N.green(`v${i}`)}...`,await Se("npm",["install","-g","@iamharshil/aix-cli@latest"]),t.succeed(`Successfully updated to ${N.green(`v${i}`)}! \u{1F680}`),q(`Restart your terminal or run ${N.cyan("aix-cli --help")} to see what's new.`)}catch(e){t.fail("Failed to update."),X(e instanceof Error?e.message:String(e))}}M();import S from"chalk";import Be from"inquirer";async function ie(t,e,o){if(t==="reset"){let{confirm:n}=await Be.prompt([{type:"confirm",name:"confirm",message:"Are you sure you want to completely reset all configuration to defaults?",default:!1}]);n?(l.reset(),w("Configuration has been reset to defaults.")):q("Reset cancelled.");return}if(t==="set"&&e&&o){let n=o;o==="true"?n=!0:o==="false"?n=!1:Number.isNaN(Number(o))||(n=Number(o)),l.set(e,n),w(`Set ${S.cyan(e)} to ${S.green(o)}`);return}console.log(),console.log(S.bold.cyan("\u2699\uFE0F AIX CLI Configuration")),console.log(S.dim("\u2500".repeat(40))),["defaultBackend","defaultProvider","model","lmStudioUrl","lmStudioPort","ollamaUrl","ollamaPort","defaultTimeout","autoStartServer"].forEach(n=>{let r=l.get(n);console.log(r!==void 0?` ${S.bold(n)}: ${S.green(r)}`:` ${S.bold(n)}: ${S.dim("not set")}`)}),console.log(),console.log(S.dim("Commands:")),console.log(S.dim(" aix-cli config set <key> <value>")),console.log(S.dim(" aix-cli config reset")),console.log()}var b=new De;b.name("aix-cli").description("Run Claude Code or OpenCode with local AI models from LM Studio or Ollama").version(ne()).option("--ollama","Shortcut to use Ollama backend").option("--lmstudio","Shortcut to use LM Studio backend").showHelpAfterError();function B(t=0){console.log(),console.log(g.dim(t===0?"\u{1F44B} Goodbye!":"\u274C Cancelled.")),process.exit(t)}process.on("SIGINT",()=>B(0));process.on("SIGTERM",()=>B(0));process.on("uncaughtException",t=>{t.message?.includes("ExitPromptError")||t.message?.includes("User force closed")||t.message?.includes("prompt")?B(0):(console.error(g.red("Error:"),t.message),process.exit(1))});process.on("unhandledRejection",t=>{let e=String(t);(e.includes("ExitPromptError")||e.includes("User force closed")||e.includes("prompt"))&&B(0)});b.command("init",{isDefault:!1}).aliases(["i","load"]).description("Select a backend, load a model, and configure your provider").option("-m, --model <name>","Model name or ID to load").option("-p, --provider <provider>","Coding tool to use (claude or opencode)").option("-b, --backend <backend>","Model backend to use (lmstudio or ollama)").action(t=>{let e=b.opts();return e.ollama&&(t.backend="ollama"),e.lmstudio&&(t.backend="lmstudio"),Y(t)});b.command("run",{isDefault:!1}).aliases(["r"]).description("Run Claude Code or OpenCode with a model from LM Studio or Ollama").option("-m, --model <name>","Model name or ID to use").option("-p, --provider <provider>","Coding tool to use (claude or opencode)").option("-b, --backend <backend>","Model backend to use (lmstudio or ollama)").option("-v, --verbose","Show verbose output").argument("[args...]","Additional arguments for the provider").action(async(t,e)=>{let o=b.opts();o.ollama&&(e.backend="ollama"),o.lmstudio&&(e.backend="lmstudio"),await oe({...e,args:t})});b.command("status",{isDefault:!1}).aliases(["s","stats"]).description("Show LM Studio and Ollama status and available models").action(te);b.command("doctor",{isDefault:!1}).aliases(["d","check"]).description("Check system requirements and configuration").action(async()=>{let{lmStudioService:t}=await Promise.resolve().then(()=>(A(),ce)),{ollamaService:e}=await Promise.resolve().then(()=>(E(),ue)),{claudeService:o}=await Promise.resolve().then(()=>(Q(),ge)),{openCodeService:i}=await Promise.resolve().then(()=>(ee(),pe)),{configService:n}=await Promise.resolve().then(()=>(M(),ae));console.log(g.bold.cyan("\u{1F527} AIX CLI System Check")),console.log(g.dim("\u2500".repeat(40)));let[r,a,d,u]=await Promise.all([t.checkStatus(),e.checkStatus(),o.isClaudeCodeInstalled(),i.isOpenCodeInstalled()]),m=n.getDefaultProvider(),c=n.getDefaultBackend(),v=n.get("lmStudioPort"),P=n.get("ollamaPort");console.log(),console.log(g.bold("Backends")),console.log(` ${r?"\u2705":"\u26A0\uFE0F"} LM Studio: ${r?g.green("Running"):g.yellow("Not running")} ${g.dim(`(port ${v})`)}`),console.log(` ${a?"\u2705":"\u26A0\uFE0F"} Ollama: ${a?g.green("Running"):g.yellow("Not running")} ${g.dim(`(port ${P})`)}`),console.log(),console.log(g.bold("Coding Tools")),console.log(` ${d?"\u2705":"\u274C"} Claude Code: ${d?g.green("Installed"):g.red("Not installed")}`),console.log(` ${u?"\u2705":"\u274C"} OpenCode: ${u?g.green("Installed"):g.red("Not installed")}`),console.log(),console.log(g.bold("Defaults")),console.log(` \u{1F4CC} Backend: ${g.cyan(c??"not set")}`),console.log(` \u{1F4CC} Coding tool: ${g.cyan(m??"not set")}`);let $=[];d||$.push(` \u2192 ${g.cyan("npm install -g @anthropic-ai/claude-code")}`),u||$.push(` \u2192 ${g.cyan("npm install -g opencode")}`),!r&&!a&&$.push(` \u2192 Start LM Studio or run ${g.cyan("ollama serve")}`),$.length>0&&(console.log(),console.log(g.bold("\u{1F4CB} Next Steps:")),$.forEach(V=>console.log(V))),console.log()});b.command("update",{isDefault:!1}).aliases(["upgrade","u"]).description("Update AIX CLI to the latest version").action(re);b.command("config [action] [key] [value]",{isDefault:!1}).aliases(["c","settings"]).description("View, set, or reset AIX CLI configuration constraints").action(ie);b.parse();
11
+ `));try{t==="opencode"?await U.run({model:e,args:o.args??[],verbose:o.verbose}):await R.run({model:e,args:o.args??[],verbose:o.verbose})}catch(n){f(`Failed to run ${i}: ${n instanceof Error?n.message:"Unknown error"}`)}}async function oe(t={}){let e;if(t.provider)e=t.provider;else{let r=l.getDefaultProvider();r?e=r:e=await Ae()}let o=x({text:`Checking ${I(e)} installation...`,color:"cyan"}).start();(e==="opencode"?await U.isOpenCodeInstalled():await R.isClaudeCodeInstalled())||(o.fail(`${I(e)} is not installed.`),f(`Please install ${I(e)} first.`)),o.succeed(`${I(e)} is installed`);let n=t.backend??await Le(e);n==="ollama"&&e==="claude"&&f("Claude Code requires an Anthropic-compatible API. LM Studio supports this natively, but Ollama does not. Please select OpenCode for Ollama, or switch to LM Studio."),n==="ollama"?await Re(t,e):await Ee(t,e)}A();E();import s from"chalk";async function te(){let[t,e]=await Promise.all([v.getStatus(),y.getStatus()]);console.log(),console.log(s.bold("LM Studio")),console.log(s.dim("\u2500".repeat(50))),console.log(` ${t.running?s.green("\u25CF"):s.red("\u25CB")} Server: ${t.running?s.green("Running"):s.red("Stopped")}`),console.log(` ${s.dim("\u25B8")} Port: ${s.cyan(String(t.port))}`),console.log(` ${s.dim("\u25B8")} URL: ${s.cyan(`http://localhost:${t.port}`)}`),t.activeModel&&console.log(` ${s.dim("\u25B8")} Active Model: ${s.green(t.activeModel)}`),t.running&&t.models.length>0?(console.log(),console.log(s.bold(" Models")),t.models.forEach((o,i)=>{let n=C(o.size),r=o.id===t.activeModel?` ${s.green("[LOADED]")}`:"";console.log(` ${s.dim(String(i+1)+".")} ${o.name}${r}`),console.log(` ${s.dim("ID:")} ${o.id}`),console.log(` ${s.dim("Size:")} ${n}`),o.quantization&&console.log(` ${s.dim("Quantization:")} ${o.quantization}`)})):t.running&&console.log(` ${s.dim("No models available")}`),console.log(),console.log(s.bold("Ollama")),console.log(s.dim("\u2500".repeat(50))),console.log(` ${e.running?s.green("\u25CF"):s.red("\u25CB")} Server: ${e.running?s.green("Running"):s.red("Stopped")}`),console.log(` ${s.dim("\u25B8")} Port: ${s.cyan(String(e.port))}`),console.log(` ${s.dim("\u25B8")} URL: ${s.cyan(`http://localhost:${e.port}`)}`),e.running&&e.runningModels.length>0&&console.log(` ${s.dim("\u25B8")} Running: ${s.green(e.runningModels.join(", "))}`),e.running&&e.models.length>0?(console.log(),console.log(s.bold(" Models")),e.models.forEach((o,i)=>{let n=C(o.size),a=e.runningModels.includes(o.id)?` ${s.green("[RUNNING]")}`:"",d=o.parameterSize?` ${s.dim(o.parameterSize)}`:"";console.log(` ${s.dim(String(i+1)+".")} ${o.name}${d}${a}`),console.log(` ${s.dim("Size:")} ${n}`),o.family&&console.log(` ${s.dim("Family:")} ${o.family}`),o.quantization&&console.log(` ${s.dim("Quantization:")} ${o.quantization}`)})):e.running&&console.log(` ${s.dim("No models available")}`),console.log()}import Ue from"ora";import N from"chalk";import{execa as he}from"execa";import{readFileSync as Ie}from"fs";import{fileURLToPath as Ne}from"url";function ne(){try{let t=Ne(new URL("../../package.json",import.meta.url)),e=JSON.parse(Ie(t,"utf8"));return String(e.version)}catch{return"unknown"}}async function re(){let t=Ue({text:"Checking for updates...",color:"cyan"}).start();try{let e=ne();if(e==="unknown"){t.fail("Could not determine current version.");return}let{stdout:o}=await he("npm",["view","@iamharshil/aix-cli","version"]),i=o.trim();if(e===i){t.succeed(`You're already on the latest version: ${N.green(`v${e}`)}`);return}t.text=`Updating: ${N.yellow(`v${e}`)} \u2192 ${N.green(`v${i}`)}...`,await he("npm",["install","-g","@iamharshil/aix-cli@latest"]),t.succeed(`Successfully updated to ${N.green(`v${i}`)}! \u{1F680}`),q(`Restart your terminal or run ${N.cyan("aix-cli --help")} to see what's new.`)}catch(e){t.fail("Failed to update."),X(e instanceof Error?e.message:String(e))}}M();import h from"chalk";import Be from"inquirer";async function ie(t,e,o){if(t==="reset"){let{confirm:n}=await Be.prompt([{type:"confirm",name:"confirm",message:"Are you sure you want to completely reset all configuration to defaults?",default:!1}]);n?(l.reset(),w("Configuration has been reset to defaults.")):q("Reset cancelled.");return}if(t==="set"&&e&&o){let n=o;o==="true"?n=!0:o==="false"?n=!1:Number.isNaN(Number(o))||(n=Number(o)),l.set(e,n),w(`Set ${h.cyan(e)} to ${h.green(o)}`);return}console.log(),console.log(h.bold.cyan("\u2699\uFE0F AIX CLI Configuration")),console.log(h.dim("\u2500".repeat(40))),["defaultBackend","defaultProvider","model","lmStudioUrl","lmStudioPort","ollamaUrl","ollamaPort","defaultTimeout","autoStartServer"].forEach(n=>{let r=l.get(n);console.log(r!==void 0?` ${h.bold(n)}: ${h.green(r)}`:` ${h.bold(n)}: ${h.dim("not set")}`)}),console.log(),console.log(h.dim("Commands:")),console.log(h.dim(" aix-cli config set <key> <value>")),console.log(h.dim(" aix-cli config reset")),console.log()}var b=new De;b.name("aix-cli").description("Run Claude Code or OpenCode with local AI models from LM Studio or Ollama").version(ne()).option("--ollama","Shortcut to use Ollama backend").option("--lmstudio","Shortcut to use LM Studio backend").showHelpAfterError();function B(t=0){console.log(),console.log(g.dim(t===0?"\u{1F44B} Goodbye!":"\u274C Cancelled.")),process.exit(t)}process.on("SIGINT",()=>B(0));process.on("SIGTERM",()=>B(0));process.on("uncaughtException",t=>{t.message?.includes("ExitPromptError")||t.message?.includes("User force closed")||t.message?.includes("prompt")?B(0):(console.error(g.red("Error:"),t.message),process.exit(1))});process.on("unhandledRejection",t=>{let e=String(t);(e.includes("ExitPromptError")||e.includes("User force closed")||e.includes("prompt"))&&B(0)});b.command("init",{isDefault:!1}).aliases(["i","load"]).description("Select a backend, load a model, and configure your provider").option("-m, --model <name>","Model name or ID to load").option("-p, --provider <provider>","Coding tool to use (claude or opencode)").option("-b, --backend <backend>","Model backend to use (lmstudio or ollama)").action(t=>{let e=b.opts();return e.ollama&&(t.backend="ollama"),e.lmstudio&&(t.backend="lmstudio"),Y(t)});b.command("run",{isDefault:!1}).aliases(["r"]).description("Run Claude Code or OpenCode with a model from LM Studio or Ollama").option("-m, --model <name>","Model name or ID to use").option("-p, --provider <provider>","Coding tool to use (claude or opencode)").option("-b, --backend <backend>","Model backend to use (lmstudio or ollama)").option("-v, --verbose","Show verbose output").argument("[args...]","Additional arguments for the provider").action(async(t,e)=>{let o=b.opts();o.ollama&&(e.backend="ollama"),o.lmstudio&&(e.backend="lmstudio"),await oe({...e,args:t})});b.command("status",{isDefault:!1}).aliases(["s","stats"]).description("Show LM Studio and Ollama status and available models").action(te);b.command("doctor",{isDefault:!1}).aliases(["d","check"]).description("Check system requirements and configuration").action(async()=>{let{lmStudioService:t}=await Promise.resolve().then(()=>(A(),ce)),{ollamaService:e}=await Promise.resolve().then(()=>(E(),ue)),{claudeService:o}=await Promise.resolve().then(()=>(Q(),ge)),{openCodeService:i}=await Promise.resolve().then(()=>(ee(),pe)),{configService:n}=await Promise.resolve().then(()=>(M(),ae));console.log(g.bold.cyan("\u{1F527} AIX CLI System Check")),console.log(g.dim("\u2500".repeat(40)));let[r,a,d,u]=await Promise.all([t.checkStatus(),e.checkStatus(),o.isClaudeCodeInstalled(),i.isOpenCodeInstalled()]),m=n.getDefaultProvider(),c=n.getDefaultBackend(),S=n.get("lmStudioPort"),P=n.get("ollamaPort");console.log(),console.log(g.bold("Backends")),console.log(` ${r?"\u2705":"\u26A0\uFE0F"} LM Studio: ${r?g.green("Running"):g.yellow("Not running")} ${g.dim(`(port ${S})`)}`),console.log(` ${a?"\u2705":"\u26A0\uFE0F"} Ollama: ${a?g.green("Running"):g.yellow("Not running")} ${g.dim(`(port ${P})`)}`),console.log(),console.log(g.bold("Coding Tools")),console.log(` ${d?"\u2705":"\u274C"} Claude Code: ${d?g.green("Installed"):g.red("Not installed")}`),console.log(` ${u?"\u2705":"\u274C"} OpenCode: ${u?g.green("Installed"):g.red("Not installed")}`),console.log(),console.log(g.bold("Defaults")),console.log(` \u{1F4CC} Backend: ${g.cyan(c??"not set")}`),console.log(` \u{1F4CC} Coding tool: ${g.cyan(m??"not set")}`);let $=[];d||$.push(` \u2192 ${g.cyan("npm install -g @anthropic-ai/claude-code")}`),u||$.push(` \u2192 ${g.cyan("npm install -g opencode-ai")}`),!r&&!a&&$.push(` \u2192 Start LM Studio or run ${g.cyan("ollama serve")}`),$.length>0&&(console.log(),console.log(g.bold("\u{1F4CB} Next Steps:")),$.forEach(V=>console.log(V))),console.log()});b.command("update",{isDefault:!1}).aliases(["upgrade","u"]).description("Update AIX CLI to the latest version").action(re);b.command("config [action] [key] [value]",{isDefault:!1}).aliases(["c","settings"]).description("View, set, or reset AIX CLI configuration constraints").action(ie);b.parse();
11
12
  //# sourceMappingURL=aix.js.map