@goffy-ai/coding-helper 0.0.7 → 0.0.8
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.
|
@@ -1 +1 @@
|
|
|
1
|
-
import{existsSync as e,mkdirSync as t,readFileSync as r,writeFileSync as n}from"fs";import{join as s,dirname as o}from"path";import{homedir as a}from"os";import{logger as i}from"../utils/logger.js";export class ClaudeCodeManager{static instance;settingsPath;mcpConfigPath;constructor(){this.settingsPath=s(a(),".claude","settings.json"),this.mcpConfigPath=s(a(),".claude.json")}static getInstance(){return ClaudeCodeManager.instance||(ClaudeCodeManager.instance=new ClaudeCodeManager),ClaudeCodeManager.instance}ensureConfigDir(r){const n=o(r);e(n)||t(n,{recursive:!0})}getSettings(){try{if(e(this.settingsPath)){const e=r(this.settingsPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read Claude Code settings:",e),i.logError("ClaudeCodeManager.getSettings",e)}return{}}saveSettings(e){try{this.ensureConfigDir(this.settingsPath),n(this.settingsPath,JSON.stringify(e,null,2),"utf-8")}catch(e){throw Error("Failed to save Claude Code settings: "+e)}}getMCPConfig(){try{if(e(this.mcpConfigPath)){const e=r(this.mcpConfigPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read Claude Code MCP config:",e),i.logError("ClaudeCodeManager.getMCPConfig",e)}return{}}saveMCPConfig(e){try{this.ensureConfigDir(this.mcpConfigPath),n(this.mcpConfigPath,JSON.stringify(e,null,2),"utf-8")}catch(e){throw Error("Failed to save Claude Code MCP config: "+e)}}loadGFFConfig(e,t){this.ensureOnboardingCompleted(),this.cleanupShellEnvVars();const r=this.getSettings(),n=r.env||{},{ANTHROPIC_API_KEY:s,...o}=n,a={...r,env:{...o,ANTHROPIC_AUTH_TOKEN:t,ANTHROPIC_BASE_URL:"https://api.goffy.tech",API_TIMEOUT_MS:"3000000",CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC:1,ANTHROPIC_DEFAULT_HAIKU_MODEL:"
|
|
1
|
+
import{existsSync as e,mkdirSync as t,readFileSync as r,writeFileSync as n}from"fs";import{join as s,dirname as o}from"path";import{homedir as a}from"os";import{logger as i}from"../utils/logger.js";export class ClaudeCodeManager{static instance;settingsPath;mcpConfigPath;constructor(){this.settingsPath=s(a(),".claude","settings.json"),this.mcpConfigPath=s(a(),".claude.json")}static getInstance(){return ClaudeCodeManager.instance||(ClaudeCodeManager.instance=new ClaudeCodeManager),ClaudeCodeManager.instance}ensureConfigDir(r){const n=o(r);e(n)||t(n,{recursive:!0})}getSettings(){try{if(e(this.settingsPath)){const e=r(this.settingsPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read Claude Code settings:",e),i.logError("ClaudeCodeManager.getSettings",e)}return{}}saveSettings(e){try{this.ensureConfigDir(this.settingsPath),n(this.settingsPath,JSON.stringify(e,null,2),"utf-8")}catch(e){throw Error("Failed to save Claude Code settings: "+e)}}getMCPConfig(){try{if(e(this.mcpConfigPath)){const e=r(this.mcpConfigPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read Claude Code MCP config:",e),i.logError("ClaudeCodeManager.getMCPConfig",e)}return{}}saveMCPConfig(e){try{this.ensureConfigDir(this.mcpConfigPath),n(this.mcpConfigPath,JSON.stringify(e,null,2),"utf-8")}catch(e){throw Error("Failed to save Claude Code MCP config: "+e)}}loadGFFConfig(e,t){this.ensureOnboardingCompleted(),this.cleanupShellEnvVars();const r=this.getSettings(),n=r.env||{},{ANTHROPIC_API_KEY:s,...o}=n,a={...r,env:{...o,ANTHROPIC_AUTH_TOKEN:t,ANTHROPIC_BASE_URL:"https://api.goffy.tech",API_TIMEOUT_MS:"3000000",CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC:1,ANTHROPIC_DEFAULT_HAIKU_MODEL:"goffy-fast",ANTHROPIC_DEFAULT_SONNET_MODEL:"goffy-code-1.0",ANTHROPIC_DEFAULT_OPUS_MODEL:"goffy-pro-1.0"}};this.saveSettings(a)}ensureOnboardingCompleted(){try{const e=this.getMCPConfig();e.hasCompletedOnboarding||this.saveMCPConfig({...e,hasCompletedOnboarding:!0})}catch(e){console.warn("Failed to ensure onboarding completed:",e),i.logError("ClaudeCodeManager.ensureOnboardingCompleted",e)}}cleanupShellEnvVars(){if(process.env.ANTHROPIC_API_KEY||process.env.ANTHROPIC_BASE_URL)try{const t=this.getShellRcFilePath();if(!t||!e(t))return;let s=r(t,"utf-8");const o=s,a=[/^\s*export\s+ANTHROPIC_BASE_URL=.*$/gm,/^\s*export\s+ANTHROPIC_API_KEY=.*$/gm,/^\s*#\s*Claude Code environment variables\s*$/gm];for(const e of a)s=s.replace(e,"");s!==o&&(n(t,s,"utf-8"),console.log("Cleaned up ANTHROPIC_* environment variables from "+t),setTimeout(()=>{},1e3))}catch(e){console.warn("Failed to cleanup shell environment variables:",e),i.logError("ClaudeCodeManager.cleanupShellEnvVars",e),setTimeout(()=>{},1e3)}}getShellRcFilePath(){const e=a();if("win32"===process.platform)return null;switch((process.env.SHELL||"").split("/").pop()||""){case"bash":return s(e,".bashrc");case"zsh":return s(e,".zshrc");case"fish":return s(e,".config","fish","config.fish");default:return s(e,".profile")}}unloadGFFConfig(){const e=this.getSettings();if(!e.env)return;const{ANTHROPIC_AUTH_TOKEN:t,ANTHROPIC_BASE_URL:r,API_TIMEOUT_MS:n,CLAUDE_CODE_DISABLE_NONESSENTIAL_TRAFFIC:s,ANTHROPIC_DEFAULT_HAIKU_MODEL:o,ANTHROPIC_DEFAULT_SONNET_MODEL:a,ANTHROPIC_DEFAULT_OPUS_MODEL:i,...l}=e.env,c={...e,env:l};c.env&&0===Object.keys(c.env).length&&delete c.env,this.saveSettings(c)}isMCPInstalled(e){try{const t=this.getMCPConfig().mcpServers;return!!t&&e in t}catch{return!1}}installMCP(e,t,r){try{const n=this.getMCPConfig(),s=n.mcpServers||{};let o;if("stdio"===e.protocol){let n={};e.envTemplate&&r?n={...e.envTemplate[r]||{}}:e.env&&(n={...e.env}),e.requiresAuth&&t&&(n.GOFFY_API_KEY=t),o={type:"stdio",command:e.command||"npx",args:e.args||[],env:n}}else{if("sse"!==e.protocol&&"streamable-http"!==e.protocol)throw Error("Unsupported protocol: "+e.protocol);{let n="";if(e.urlTemplate&&r)n=e.urlTemplate[r]||"";else{if(!e.url)throw Error(`MCP ${e.id} missing url or urlTemplate`);n=e.url}o={type:"sse"==e.protocol?"sse":"http",url:n,headers:{...e.headers||{}}},e.requiresAuth&&t&&(o.headers.Authorization="Bearer "+t)}}s[e.id]=o,n.mcpServers=s,this.saveMCPConfig(n)}catch(t){throw Error(`Failed to install MCP ${e.name}: ${t}`)}}uninstallMCP(e){try{const t=this.getMCPConfig(),r=t.mcpServers;if(!r)return;delete r[e],this.saveMCPConfig(t)}catch(t){throw Error(`Failed to uninstall MCP ${e}: ${t}`)}}getInstalledMCPs(){try{const e=this.getMCPConfig().mcpServers;return e?Object.keys(e):[]}catch{return[]}}getMCPStatus(e){const t=new Map;for(const r of e)t.set(r.id,this.isMCPInstalled(r.id));return t}getOtherMCPs(e){try{const t=this.getMCPConfig().mcpServers;if(!t)return[];const r=[];for(const[n,s]of Object.entries(t))e.includes(n)||r.push({id:n,config:s});return r}catch{return[]}}getAllMCPServers(){try{return this.getMCPConfig().mcpServers||{}}catch{return{}}}detectCurrentConfig(){try{const e=this.getSettings().env||{};if(!e.ANTHROPIC_AUTH_TOKEN)return{plan:null,apiKey:null};const t=e.ANTHROPIC_AUTH_TOKEN,r=e.ANTHROPIC_BASE_URL;let n=null;return"https://api.goffy.tech"===r&&(n="goffy_coding"),{plan:n,apiKey:t}}catch{return{plan:null,apiKey:null}}}}export const claudeCodeManager=ClaudeCodeManager.getInstance();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{existsSync as e,mkdirSync as t,readFileSync as n,writeFileSync as o}from"fs";import{join as r,dirname as i}from"path";import{homedir as s}from"os";import{logger as a}from"../utils/logger.js";export class OpenCodeManager{static instance;configPath;constructor(){this.configPath=r(s(),".config","opencode","opencode.json")}static getInstance(){return OpenCodeManager.instance||(OpenCodeManager.instance=new OpenCodeManager),OpenCodeManager.instance}ensureConfigDir(){const n=i(this.configPath);e(n)||t(n,{recursive:!0})}getConfig(){try{if(e(this.configPath)){const e=n(this.configPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read OpenCode config:",e),a.logError("OpenCodeManager.getConfig",e)}return{}}saveConfig(e){try{this.ensureConfigDir(),o(this.configPath,JSON.stringify(e,null,4),"utf-8")}catch(e){throw Error("Failed to save OpenCode config: "+e)}}getProviderName(e){return"goffy-coding-plan"}loadGFFConfig(e,t){const n=this.getConfig(),o=this.getProviderName(e),{provider:r,...i}=n,s={};if(r)for(const[e,t]of Object.entries(r))"goffy-coding-plan"!==e&&(s[e]=t);s[o]={options:{apiKey:t}};const a={$schema:"https://opencode.ai/config.json",...i,provider:s,model:o+"/goffy-code-1.0",small_model:o+"/goffy-
|
|
1
|
+
import{existsSync as e,mkdirSync as t,readFileSync as n,writeFileSync as o}from"fs";import{join as r,dirname as i}from"path";import{homedir as s}from"os";import{logger as a}from"../utils/logger.js";export class OpenCodeManager{static instance;configPath;constructor(){this.configPath=r(s(),".config","opencode","opencode.json")}static getInstance(){return OpenCodeManager.instance||(OpenCodeManager.instance=new OpenCodeManager),OpenCodeManager.instance}ensureConfigDir(){const n=i(this.configPath);e(n)||t(n,{recursive:!0})}getConfig(){try{if(e(this.configPath)){const e=n(this.configPath,"utf-8");return JSON.parse(e)}}catch(e){console.warn("Failed to read OpenCode config:",e),a.logError("OpenCodeManager.getConfig",e)}return{}}saveConfig(e){try{this.ensureConfigDir(),o(this.configPath,JSON.stringify(e,null,4),"utf-8")}catch(e){throw Error("Failed to save OpenCode config: "+e)}}getProviderName(e){return"goffy-coding-plan"}loadGFFConfig(e,t){const n=this.getConfig(),o=this.getProviderName(e),{provider:r,...i}=n,s={};if(r)for(const[e,t]of Object.entries(r))"goffy-coding-plan"!==e&&(s[e]=t);s[o]={options:{apiKey:t}};const a={$schema:"https://opencode.ai/config.json",...i,provider:s,model:o+"/goffy-code-1.0",small_model:o+"/goffy-fast"};this.saveConfig(a)}unloadGFFConfig(){const e=this.getConfig();e.provider&&(delete e.provider["goffy-coding-plan"],0===Object.keys(e.provider).length&&delete e.provider),e.model?.includes("coding-plan")&&delete e.model,e.small_model?.includes("coding-plan")&&delete e.small_model,this.saveConfig(e)}isMCPInstalled(e){try{const t=this.getConfig().mcp;return!!t&&e in t}catch{return!1}}installMCP(e,t,n){try{const o=this.getConfig(),r=o.mcp||{};let i;if("stdio"===e.protocol){let o={};e.envTemplate&&n?o={...e.envTemplate[n]||{}}:e.env&&(o={...e.env}),e.requiresAuth&&t&&(o.GOFFY_API_KEY=t),i={type:"local",command:[e.command||"npx",...e.args||[]],environment:o}}else{if("streamable-http"!==e.protocol)throw Error("Unsupported protocol: "+e.protocol);{let o="";if(e.urlTemplate&&n)o=e.urlTemplate[n]||"";else{if(!e.url)throw Error(`MCP ${e.id} missing url or urlTemplate`);o=e.url}i={type:"remote",url:o,headers:{...e.headers||{}}},e.requiresAuth&&t&&((i.headers||{}).Authorization="Bearer "+t)}}r[e.id]=i,o.mcp=r,this.saveConfig(o)}catch(t){throw Error(`Failed to install MCP ${e.name}: ${t}`)}}uninstallMCP(e){try{const t=this.getConfig(),n=t.mcp;if(!n)return;delete n[e],this.saveConfig(t)}catch(t){throw Error(`Failed to uninstall MCP ${e}: ${t}`)}}getInstalledMCPs(){try{const e=this.getConfig().mcp;return e?Object.keys(e):[]}catch{return[]}}getMCPStatus(e){const t=new Map;for(const n of e)t.set(n.id,this.isMCPInstalled(n.id));return t}getOtherMCPs(e){try{const t=this.getConfig().mcp;if(!t)return[];const n=[];for(const[o,r]of Object.entries(t))e.includes(o)||n.push({id:o,config:r});return n}catch{return[]}}getAllMCPServers(){try{return this.getConfig().mcp||{}}catch{return{}}}detectCurrentConfig(){try{const e=this.getConfig().provider;if(!e)return{plan:null,apiKey:null};const t=e["goffy-coding-plan"];let n=null,o=null;if(t){n="goffy_coding";const e=t.options;o=e?.apiKey||null}return{plan:n,apiKey:o}}catch{return{plan:null,apiKey:null}}}}export const openCodeManager=OpenCodeManager.getInstance();
|