grix-connector 3.26.13 → 3.27.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (29) hide show
  1. package/dist/adapter/claude/claude-bridge-server.js +1 -1
  2. package/dist/adapter/claude/claude-tools.js +1 -1
  3. package/dist/adapter/claude/claude-worker-client.js +1 -1
  4. package/dist/adapter/claude/mcp-http-launcher.js +2 -2
  5. package/dist/adapter/claude/result-timeout.js +1 -1
  6. package/dist/adapter/deepseek-harness/catalog-cache.js +1 -0
  7. package/dist/adapter/deepseek-harness/event-mapper.js +1 -1
  8. package/dist/adapter/deepseek-harness/index.js +1 -1
  9. package/dist/adapter/deepseek-harness/jsonrpc-adapter.js +2 -2
  10. package/dist/adapter/deepseek-harness/runtime-ensure.js +1 -0
  11. package/dist/adapter/deepseek-harness/toolbar-state.js +1 -1
  12. package/dist/adapter/deepseek-harness/usage.js +1 -1
  13. package/dist/assets/dsh-bridge/grix-dsh-bridge-3.27.0.tgz +0 -0
  14. package/dist/assets/dsh-bridge/manifest.json +6 -6
  15. package/dist/audit/adapters/deepseek-harness/deepseek-harness-audit-adapter.js +2 -2
  16. package/dist/bridge/bridge.js +7 -7
  17. package/dist/core/access/allowlist-store.js +1 -1
  18. package/dist/core/aibot/binding-card-meta-cache.js +1 -1
  19. package/dist/core/file-ops/list-files.js +1 -1
  20. package/dist/core/persistence/session-binding-store.js +1 -1
  21. package/dist/log.js +2 -2
  22. package/dist/mcp/stream-http/config.js +1 -1
  23. package/dist/mcp/stream-http/connection-binding.js +1 -1
  24. package/dist/mcp/stream-http/security.js +1 -1
  25. package/dist/mcp/stream-http/tool-executor.js +1 -1
  26. package/dist/mcp/stream-http/tool-registry.js +1 -1
  27. package/dist/mcp/stream-http/tool-schemas.js +1 -1
  28. package/package.json +1 -1
  29. package/dist/assets/dsh-bridge/grix-dsh-bridge-3.26.13.tgz +0 -0
@@ -1 +1 @@
1
- import{readJSONFile as o,writeJSONFileAtomic as e}from"../util/json-file.js";function n(t){const r=o(t);return r&&typeof r=="object"&&"owners"in r&&Array.isArray(r.owners)?r.owners.filter(i=>typeof i=="string"&&i.trim().length>0):[]}async function s(t,r){await e(t,{owners:r})}export{n as readAllowlist,s as writeAllowlist};
1
+ import{readJSONFile as o,writeJSONFileAtomic as i}from"../util/json-file.js";function n(t){const r=o(t);return r&&typeof r=="object"&&"owners"in r&&Array.isArray(r.owners)?r.owners.filter(e=>typeof e=="string"&&e.trim().length>0):[]}async function s(t,r){await i(t,{owners:r})}export{n as readAllowlist,s as writeAllowlist};
@@ -1 +1 @@
1
- const c=["available_models","available_modes","available_presets","available_profiles","model_id","mode_id","agent_preset_id","agent_preset_locked","dsh_profile","dsh_profile_locked","dsh_profile_create","dsh_plugins","dsh_plugin_restart_required","available_efforts","effort","reasoning_effort","currentEffort","currentModelId","currentModeId","availableModels","availableModes","models","modes"],_=["available_presets","available_profiles","agent_preset_id","agent_preset_locked","dsh_profile","dsh_profile_locked","dsh_profile_create"],p=[["model_id","currentModelId"],["mode_id","currentModeId"],["effort","reasoning_effort"]];function d(s,o,e){for(const t of o)t in s&&(e[t]=s[t])}function f(s,o){return Object.prototype.hasOwnProperty.call(s,o)&&Array.isArray(s[o])}class b{toolbarMetaBySession=new Map;merge(o,e){if(!o)return e;if(e&&f(e,"available_models")){const r=this.toolbarMetaBySession.get(o),l={};if(d(e,c,l),r)for(const i of _)!(i in l)&&i in r&&(l[i]=r[i]);return this.toolbarMetaBySession.set(o,l),e}if(e&&f(e,"available_profiles")){const r=this.toolbarMetaBySession.get(o)??{};d(e,_,r),this.toolbarMetaBySession.set(o,r)}const t=this.toolbarMetaBySession.get(o);if(!t)return e;if(e)for(const[r,l]of p){const i=e[r],n=e[l],a=typeof i=="string"&&i||typeof n=="string"&&n||null;a&&(t[r]=a,t[l]=a)}return{...t,...e??{}}}delete(o){this.toolbarMetaBySession.delete(o)}}export{b as BindingCardMetaCache};
1
+ const c=["available_models","available_providers","available_modes","available_presets","available_profiles","model_id","provider_id","mode_id","agent_preset_id","agent_preset_locked","dsh_profile","dsh_profile_locked","dsh_profile_create","dsh_plugins","dsh_plugin_restart_required","available_efforts","effort","reasoning_effort","currentEffort","currentModelId","currentModeId","availableModels","availableModes","models","modes"],d=["available_presets","available_profiles","available_providers","agent_preset_id","agent_preset_locked","provider_id","dsh_profile","dsh_profile_locked","dsh_profile_create"],p=[["model_id","currentModelId"],["mode_id","currentModeId"],["effort","reasoning_effort"]];function _(a,o,e){for(const i of o)i in a&&(e[i]=a[i])}function f(a,o){return Object.prototype.hasOwnProperty.call(a,o)&&Array.isArray(a[o])}class b{toolbarMetaBySession=new Map;merge(o,e){if(!o)return e;if(e&&f(e,"available_models")){const r=this.toolbarMetaBySession.get(o),t={};if(_(e,c,t),r)for(const l of d)!(l in t)&&l in r&&(t[l]=r[l]);return this.toolbarMetaBySession.set(o,t),e}if(e&&f(e,"available_profiles")){const r=this.toolbarMetaBySession.get(o)??{};_(e,d,r),this.toolbarMetaBySession.set(o,r)}const i=this.toolbarMetaBySession.get(o);if(!i)return e;if(e)for(const[r,t]of p){const l=e[r],n=e[t],s=typeof l=="string"&&l||typeof n=="string"&&n||null;s&&(i[r]=s,i[t]=s)}return{...i,...e??{}}}delete(o){this.toolbarMetaBySession.delete(o)}}export{b as BindingCardMetaCache};
@@ -1 +1 @@
1
- import{readdir as r,stat as m}from"node:fs/promises";import{join as l,extname as d}from"node:path";const x={pdf:"application/pdf",doc:"application/msword",docx:"application/vnd.openxmlformats-officedocument.wordprocessingml.document",xls:"application/vnd.ms-excel",xlsx:"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",ppt:"application/vnd.ms-powerpoint",pptx:"application/vnd.openxmlformats-officedocument.presentationml.presentation",txt:"text/plain",md:"text/markdown",csv:"text/csv",json:"application/json",xml:"application/xml",yaml:"text/yaml",yml:"text/yaml",html:"text/html",css:"text/css",js:"text/javascript",ts:"text/typescript",zip:"application/zip",rar:"application/x-rar-compressed","7z":"application/x-7z-compressed",tar:"application/x-tar",gz:"application/gzip",jpg:"image/jpeg",jpeg:"image/jpeg",png:"image/png",gif:"image/gif",webp:"image/webp",svg:"image/svg+xml",mp4:"video/mp4",mov:"video/quicktime",avi:"video/x-msvideo",mkv:"video/x-matroska",webm:"video/webm",mp3:"audio/mpeg",wav:"audio/wav",flac:"audio/flac",aac:"audio/aac"};function n(a){const p=d(a).slice(1).toLowerCase();return x[p]}async function f(a,p=!1){const c=await r(a,{withFileTypes:!0}),s=[];for(const t of c){if(!p&&t.name.startsWith("."))continue;const i=l(a,t.name),e={id:i,name:t.name,is_directory:t.isDirectory()};try{if(t.isDirectory()){const o=await m(i);e.modified_at=o.mtime.toISOString()}else{const o=await m(i);e.size=o.size,e.modified_at=o.mtime.toISOString(),e.mime_type=n(t.name)}}catch{}s.push(e)}return s.sort((t,i)=>t.is_directory!==i.is_directory?t.is_directory?-1:1:t.name.localeCompare(i.name)),s}export{f as listFiles,n as resolveMimeType};
1
+ import{readdir as r,stat as m}from"node:fs/promises";import{join as l,extname as d}from"node:path";const x={pdf:"application/pdf",doc:"application/msword",docx:"application/vnd.openxmlformats-officedocument.wordprocessingml.document",xls:"application/vnd.ms-excel",xlsx:"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",ppt:"application/vnd.ms-powerpoint",pptx:"application/vnd.openxmlformats-officedocument.presentationml.presentation",txt:"text/plain",md:"text/markdown",csv:"text/csv",json:"application/json",xml:"application/xml",yaml:"text/yaml",yml:"text/yaml",html:"text/html",css:"text/css",js:"text/javascript",ts:"text/typescript",zip:"application/zip",rar:"application/x-rar-compressed","7z":"application/x-7z-compressed",tar:"application/x-tar",gz:"application/gzip",jpg:"image/jpeg",jpeg:"image/jpeg",png:"image/png",gif:"image/gif",webp:"image/webp",svg:"image/svg+xml",mp4:"video/mp4",mov:"video/quicktime",avi:"video/x-msvideo",mkv:"video/x-matroska",webm:"video/webm",mp3:"audio/mpeg",wav:"audio/wav",flac:"audio/flac",aac:"audio/aac"};function n(a){const p=d(a).slice(1).toLowerCase();return x[p]}async function f(a,p=!1){const c=await r(a,{withFileTypes:!0}),s=[];for(const i of c){if(!p&&i.name.startsWith("."))continue;const t=l(a,i.name),e={id:t,name:i.name,is_directory:i.isDirectory()};try{if(i.isDirectory()){const o=await m(t);e.modified_at=o.mtime.toISOString()}else{const o=await m(t);e.size=o.size,e.modified_at=o.mtime.toISOString(),e.mime_type=n(i.name)}}catch{}s.push(e)}return s.sort((i,t)=>i.is_directory!==t.is_directory?i.is_directory?-1:1:i.name.localeCompare(t.name)),s}export{f as listFiles,n as resolveMimeType};
@@ -1,2 +1,2 @@
1
- import{readJSONFile as I,writeJSONFileAtomic as m}from"../util/json-file.js";import{log as o}from"../log/index.js";import{SESSION_MODE_IDS as l}from"../../adapter/claude/protocol-contract.js";import{normalizeClaudeEffort as a}from"../config/claude-direct-env.js";import{chmodSync as x,copyFileSync as p,existsSync as h,renameSync as S,rmSync as M,writeFileSync as b}from"node:fs";import{randomUUID as y}from"node:crypto";const P=l.fullAuto;function n(g){const e=String(g??"").trim().toLowerCase();return e===l.approval||e===l.fullAuto?e:P}class E{bindings=new Map;filePath;legacyFilePath;writePromise=Promise.resolve();constructor(e,t){this.filePath=e??null,this.legacyFilePath=t&&t!==e?t:null}load(){if(!this.filePath)return;const e=h(this.filePath);let t=I(this.filePath),i=!1;if(e&&!Array.isArray(t)){const d=this.quarantineUnreadablePrimary();throw new Error(`Refusing to start with unreadable session bindings: primary=${this.filePath}`+(d?` quarantined=${d}`:"")+(this.legacyFilePath?` legacy=${this.legacyFilePath}`:"")+" (legacy fallback disabled to avoid clobbering newer bindings)")}if(!e&&this.legacyFilePath){i=h(this.legacyFilePath);const d=I(this.legacyFilePath);Array.isArray(d)&&(this.writeMigratedSnapshot(d),t=d,o.info("session-binding-store",`Migrated legacy bindings from ${this.legacyFilePath} to ${this.filePath}; legacy file retained`))}if(!Array.isArray(t)){if(e||i)throw new Error(`Refusing to start with unreadable session bindings: primary=${this.filePath}${this.legacyFilePath?` legacy=${this.legacyFilePath}`:""}`);return}this.bindings.clear();for(const d of t)d.aibotSessionId&&this.bindings.set(d.aibotSessionId,{...d,modeId:n(d.modeId),effort:a(d.effort),dshProviderId:typeof d.dshProviderId=="string"&&d.dshProviderId.trim()?d.dshProviderId.trim():void 0,dshModelId:typeof d.dshModelId=="string"&&d.dshModelId.trim()?d.dshModelId.trim():void 0,dshModeId:d.dshModeId===void 0?void 0:d.dshModeId==="full_auto"?"full_auto":"approval",dshMaxTokens:Number.isSafeInteger(d.dshMaxTokens)&&Number(d.dshMaxTokens)>0?Number(d.dshMaxTokens):void 0,dshAgentPreset:typeof d.dshAgentPreset=="string"&&d.dshAgentPreset.trim()?d.dshAgentPreset.trim():void 0,dshSettingsRevision:d.dshSettingsRevision===void 0?void 0:Number.isSafeInteger(d.dshSettingsRevision)&&Number(d.dshSettingsRevision)>=0?Number(d.dshSettingsRevision):0,dshProfileName:typeof d.dshProfileName=="string"&&d.dshProfileName.trim()?d.dshProfileName.trim():void 0,dshProfileSessionId:typeof d.dshProfileSessionId=="string"&&d.dshProfileSessionId.trim()?d.dshProfileSessionId.trim():void 0,dshProfileSessionCreated:d.dshProfileSessionCreated===!0,dshProfileEventCursor:Number.isSafeInteger(d.dshProfileEventCursor)&&Number(d.dshProfileEventCursor)>=0?Number(d.dshProfileEventCursor):0})}set(e,t,i){const d=this.bindings.get(e),s=n(i?.modeId??d?.modeId),r=t!==void 0?t:d?.cwd;this.bindings.set(e,{aibotSessionId:e,cwd:r,acpSessionId:d?.acpSessionId,claudeSessionId:d?.claudeSessionId,codexThreadId:d?.codexThreadId,codexModelId:d?.codexModelId,codexModeId:d?.codexModeId,codewhaleThreadId:d?.codewhaleThreadId,agyConversationId:d?.agyConversationId,codexReasoningEffort:d?.codexReasoningEffort,codexServiceTier:d?.codexServiceTier,codexSandboxMode:d?.codexSandboxMode,piSessionPath:d?.piSessionPath,modeId:s,modelId:d?.modelId,effort:d?.effort,cursorModeId:d?.cursorModeId,acpModelId:d?.acpModelId,acpModeId:d?.acpModeId,dshProviderId:d?.dshProviderId,dshModelId:d?.dshModelId,dshModeId:d?.dshModeId,dshMaxTokens:d?.dshMaxTokens,dshAgentPreset:d?.dshAgentPreset,dshSettingsRevision:d?.dshSettingsRevision,dshSettingsUpdatedAt:d?.dshSettingsUpdatedAt,dshProfileName:d?.dshProfileName,dshProfileSessionId:d?.dshProfileSessionId,dshProfileSessionCreated:d?.dshProfileSessionCreated,dshProfileEventCursor:d?.dshProfileEventCursor,updatedAt:Date.now()}),this.scheduleWrite()}setAcpSessionId(e,t){this.updateBinding(e,{acpSessionId:t})}setClaudeSessionId(e,t){this.updateBinding(e,{claudeSessionId:t})}getClaudeSessionId(e){return this.bindings.get(e)?.claudeSessionId}setCodexThreadId(e,t){this.updateBinding(e,{codexThreadId:t})}getCodexThreadId(e){return this.bindings.get(e)?.codexThreadId}setAgyConversationId(e,t){this.updateBinding(e,{agyConversationId:t})}getAgyConversationId(e){return this.bindings.get(e)?.agyConversationId}setCodexContext(e,t){this.updateBinding(e,{codexModelId:t.modelId,codexModeId:t.modeId,codexReasoningEffort:t.reasoningEffort,codexServiceTier:t.serviceTier,codexSandboxMode:t.sandboxMode})}getCodexModelId(e){return this.bindings.get(e)?.codexModelId}setCodexModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexModelId===d||(this.bindings.set(e,{...i,codexModelId:d,updatedAt:Date.now()}),this.scheduleWrite())}setCodexModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexModeId===d||(this.bindings.set(e,{...i,codexModeId:d,updatedAt:Date.now()}),this.scheduleWrite())}setCodexServiceTier(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexServiceTier===d||(this.bindings.set(e,{...i,codexServiceTier:d,updatedAt:Date.now()}),this.scheduleWrite())}getCodexModeId(e){return this.bindings.get(e)?.codexModeId}getCodexReasoningEffort(e){return this.bindings.get(e)?.codexReasoningEffort}getCodexServiceTier(e){return this.bindings.get(e)?.codexServiceTier}getCodexSandboxMode(e){return this.bindings.get(e)?.codexSandboxMode}setPiSessionPath(e,t){this.updateBinding(e,{piSessionPath:t})}getPiSessionPath(e){return this.bindings.get(e)?.piSessionPath}setCodeWhaleThreadId(e,t){this.updateBinding(e,{codewhaleThreadId:t})}getCodeWhaleThreadId(e){return this.bindings.get(e)?.codewhaleThreadId}setModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=n(t);i.modeId!==d&&(this.bindings.set(e,{...i,modeId:d,updatedAt:Date.now()}),this.scheduleWrite())}ensureModeId(e,t=P){const i=this.bindings.get(e);i&&(i.modeId||(this.bindings.set(e,{...i,modeId:n(t),updatedAt:Date.now()}),this.scheduleWrite()))}getAcpSessionId(e){return this.bindings.get(e)?.acpSessionId}getModeId(e){const t=this.bindings.get(e)?.modeId;return t?n(t):void 0}setModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=t.trim();i.modelId!==d&&(this.bindings.set(e,{...i,modelId:d,updatedAt:Date.now()}),this.scheduleWrite())}getModelId(e){return this.bindings.get(e)?.modelId}setEffort(e,t){const i=this.bindings.get(e);if(!i)return;const d=a(t);d&&i.effort!==d&&(this.bindings.set(e,{...i,effort:d,updatedAt:Date.now()}),this.scheduleWrite())}getEffort(e){return a(this.bindings.get(e)?.effort)}setCursorModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim().toLowerCase(),s=d===""?void 0:d;i.cursorModeId!==s&&(this.bindings.set(e,{...i,cursorModeId:s,updatedAt:Date.now()}),this.scheduleWrite())}getCursorModeId(e){return this.bindings.get(e)?.cursorModeId}setAcpModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim(),s=d===""?void 0:d;i.acpModelId!==s&&(this.bindings.set(e,{...i,acpModelId:s,updatedAt:Date.now()}),this.scheduleWrite())}getAcpModelId(e){return this.bindings.get(e)?.acpModelId}setAcpModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim(),s=d===""?void 0:d;i.acpModeId!==s&&(this.bindings.set(e,{...i,acpModeId:s,updatedAt:Date.now()}),this.scheduleWrite())}getAcpModeId(e){return this.bindings.get(e)?.acpModeId}getDshSettings(e){const t=this.bindings.get(e);if(t)return{...t.dshProviderId?{providerId:t.dshProviderId}:{},...t.dshModelId?{modelId:t.dshModelId}:{},modeId:t.dshModeId==="full_auto"?"full_auto":"approval",...t.dshMaxTokens?{maxTokens:t.dshMaxTokens}:{},...t.dshAgentPreset?{agentPreset:t.dshAgentPreset}:{},revision:t.dshSettingsRevision??0,...t.dshSettingsUpdatedAt?{updatedAt:t.dshSettingsUpdatedAt}:{}}}updateDshSettings(e,t){const i=this.bindings.get(e);if(!i)return;const d=Object.prototype.hasOwnProperty.call(t,"providerId")?String(t.providerId??"").trim()||void 0:i.dshProviderId,s=Object.prototype.hasOwnProperty.call(t,"modelId")?String(t.modelId??"").trim()||void 0:i.dshModelId,r=Object.prototype.hasOwnProperty.call(t,"modeId")?t.modeId==="full_auto"?"full_auto":"approval":i.dshModeId==="full_auto"?"full_auto":"approval",f=Object.prototype.hasOwnProperty.call(t,"maxTokens")?Number.isSafeInteger(t.maxTokens)&&Number(t.maxTokens)>0?Number(t.maxTokens):void 0:i.dshMaxTokens;if(d===i.dshProviderId&&s===i.dshModelId&&r===(i.dshModeId==="full_auto"?"full_auto":"approval")&&f===i.dshMaxTokens)return i.dshSettingsRevision??0;const u=Date.now(),c=(i.dshSettingsRevision??0)+1;return this.bindings.set(e,{...i,dshProviderId:d,dshModelId:s,dshModeId:r,dshMaxTokens:f,dshSettingsRevision:c,dshSettingsUpdatedAt:u,updatedAt:u}),this.scheduleWrite(),c}getDshSelectedProfile(e){const t=this.bindings.get(e)?.dshProfileName;return typeof t=="string"&&t.trim()?t.trim():void 0}isDshProfileLocked(e){return this.bindings.get(e)?.dshProfileSessionCreated===!0}setDshSelectedProfile(e,t){const i=this.bindings.get(e);if(!i)return!1;const d=String(t??"").trim();return d?i.dshProfileName===d?!0:i.dshProfileSessionCreated===!0?!1:(this.bindings.set(e,{...i,dshProfileName:d,dshProfileSessionId:void 0,dshProfileSessionCreated:!1,dshProfileEventCursor:0,updatedAt:Date.now()}),this.scheduleWrite(),!0):!1}getDshAgentPreset(e){const t=this.bindings.get(e)?.dshAgentPreset;return typeof t=="string"&&t.trim()?t.trim():void 0}isDshAgentPresetLocked(e){return this.bindings.get(e)?.dshProfileSessionCreated===!0}setDshAgentPreset(e,t){const i=this.bindings.get(e);if(!i||i.dshProfileSessionCreated===!0)return!1;const d=String(t??"").trim();return!d||i.dshAgentPreset===d?i.dshAgentPreset===d:(this.bindings.set(e,{...i,dshAgentPreset:d,updatedAt:Date.now()}),this.scheduleWrite(),!0)}getDshProfileBinding(e,t){const i=this.bindings.get(e);if(!(!i?.dshProfileSessionId||i.dshProfileName!==t))return{profileName:t,sessionId:i.dshProfileSessionId,sessionCreated:i.dshProfileSessionCreated===!0,eventCursor:i.dshProfileEventCursor??0}}setDshProfileBinding(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t.profileName).trim(),s=String(t.sessionId).trim();if(!d||!s)return;const r=Number.isSafeInteger(t.eventCursor)&&t.eventCursor>=0?t.eventCursor:0;i.dshProfileName===d&&i.dshProfileSessionId===s&&i.dshProfileSessionCreated===t.sessionCreated&&(i.dshProfileEventCursor??0)===r||(this.bindings.set(e,{...i,dshProfileName:d,dshProfileSessionId:s,dshProfileSessionCreated:t.sessionCreated,dshProfileEventCursor:r,updatedAt:Date.now()}),this.scheduleWrite())}get(e){return this.bindings.get(e)}getMostRecentlyUpdatedSessionId(e){const t=e?.requireCwd!==!1;let i,d=-1;for(const s of this.bindings.values())t&&!String(s.cwd??"").trim()||s.updatedAt>d&&(d=s.updatedAt,i=s.aibotSessionId);return i}delete(e){const t=this.bindings.get(e);t&&(o.info("session-binding-store",`delete binding session_id=${e} cwd=${t.cwd??""} codexThreadId=${t.codexThreadId??""}`),this.bindings.delete(e),this.scheduleWrite())}quarantineUnreadablePrimary(){if(!this.filePath||!h(this.filePath))return;const e=`${this.filePath}.corrupt.${Date.now()}`;try{return p(this.filePath,e),o.error("session-binding-store",`Copied unreadable primary bindings to ${e} (original retained to block legacy clobber)`),e}catch(t){o.error("session-binding-store",`Failed to copy unreadable primary ${this.filePath}: ${t instanceof Error?t.message:String(t)}`);return}}entries(){return this.bindings.entries()}async flush(){await this.writePromise}scheduleWrite(){this.filePath&&(this.writePromise=this.writePromise.then(()=>this.write()).catch(e=>{o.error("session-binding-store",`Persist failed: ${e instanceof Error?e.message:e}`)}))}async write(){if(!this.filePath)return;const e=Array.from(this.bindings.values());await m(this.filePath,e)}writeMigratedSnapshot(e){if(!this.filePath)return;const t=`${this.filePath}.${y()}.migration.tmp`;try{b(t,`${JSON.stringify(e,null,2)}
1
+ import{readJSONFile as I,writeJSONFileAtomic as m}from"../util/json-file.js";import{log as o}from"../log/index.js";import{SESSION_MODE_IDS as l}from"../../adapter/claude/protocol-contract.js";import{normalizeClaudeEffort as a}from"../config/claude-direct-env.js";import{chmodSync as x,copyFileSync as p,existsSync as h,renameSync as S,rmSync as M,writeFileSync as b}from"node:fs";import{randomUUID as y}from"node:crypto";const P=l.fullAuto;function n(g){const e=String(g??"").trim().toLowerCase();return e===l.approval||e===l.fullAuto?e:P}class E{bindings=new Map;filePath;legacyFilePath;writePromise=Promise.resolve();constructor(e,t){this.filePath=e??null,this.legacyFilePath=t&&t!==e?t:null}load(){if(!this.filePath)return;const e=h(this.filePath);let t=I(this.filePath),i=!1;if(e&&!Array.isArray(t)){const d=this.quarantineUnreadablePrimary();throw new Error(`Refusing to start with unreadable session bindings: primary=${this.filePath}`+(d?` quarantined=${d}`:"")+(this.legacyFilePath?` legacy=${this.legacyFilePath}`:"")+" (legacy fallback disabled to avoid clobbering newer bindings)")}if(!e&&this.legacyFilePath){i=h(this.legacyFilePath);const d=I(this.legacyFilePath);Array.isArray(d)&&(this.writeMigratedSnapshot(d),t=d,o.info("session-binding-store",`Migrated legacy bindings from ${this.legacyFilePath} to ${this.filePath}; legacy file retained`))}if(!Array.isArray(t)){if(e||i)throw new Error(`Refusing to start with unreadable session bindings: primary=${this.filePath}${this.legacyFilePath?` legacy=${this.legacyFilePath}`:""}`);return}this.bindings.clear();for(const d of t)d.aibotSessionId&&this.bindings.set(d.aibotSessionId,{...d,modeId:n(d.modeId),effort:a(d.effort),dshProviderId:typeof d.dshProviderId=="string"&&d.dshProviderId.trim()?d.dshProviderId.trim():void 0,dshModelId:typeof d.dshModelId=="string"&&d.dshModelId.trim()?d.dshModelId.trim():void 0,dshModeId:d.dshModeId===void 0?void 0:d.dshModeId==="full_auto"?"full_auto":"approval",dshMaxTokens:Number.isSafeInteger(d.dshMaxTokens)&&Number(d.dshMaxTokens)>0?Number(d.dshMaxTokens):void 0,dshAgentPreset:typeof d.dshAgentPreset=="string"&&d.dshAgentPreset.trim()?d.dshAgentPreset.trim():void 0,dshSettingsRevision:d.dshSettingsRevision===void 0?void 0:Number.isSafeInteger(d.dshSettingsRevision)&&Number(d.dshSettingsRevision)>=0?Number(d.dshSettingsRevision):0,dshProfileName:typeof d.dshProfileName=="string"&&d.dshProfileName.trim()?d.dshProfileName.trim():void 0,dshProfileSessionId:typeof d.dshProfileSessionId=="string"&&d.dshProfileSessionId.trim()?d.dshProfileSessionId.trim():void 0,dshProfileSessionCreated:d.dshProfileSessionCreated===!0,dshProfileEventCursor:Number.isSafeInteger(d.dshProfileEventCursor)&&Number(d.dshProfileEventCursor)>=0?Number(d.dshProfileEventCursor):0})}set(e,t,i){const d=this.bindings.get(e),s=n(i?.modeId??d?.modeId),r=t!==void 0?t:d?.cwd;this.bindings.set(e,{aibotSessionId:e,cwd:r,acpSessionId:d?.acpSessionId,claudeSessionId:d?.claudeSessionId,codexThreadId:d?.codexThreadId,codexModelId:d?.codexModelId,codexModeId:d?.codexModeId,codewhaleThreadId:d?.codewhaleThreadId,agyConversationId:d?.agyConversationId,codexReasoningEffort:d?.codexReasoningEffort,codexServiceTier:d?.codexServiceTier,codexSandboxMode:d?.codexSandboxMode,piSessionPath:d?.piSessionPath,modeId:s,modelId:d?.modelId,effort:d?.effort,cursorModeId:d?.cursorModeId,acpModelId:d?.acpModelId,acpModeId:d?.acpModeId,dshProviderId:d?.dshProviderId,dshModelId:d?.dshModelId,dshModeId:d?.dshModeId,dshMaxTokens:d?.dshMaxTokens,dshAgentPreset:d?.dshAgentPreset,dshSettingsRevision:d?.dshSettingsRevision,dshSettingsUpdatedAt:d?.dshSettingsUpdatedAt,dshProfileName:d?.dshProfileName,dshProfileSessionId:d?.dshProfileSessionId,dshProfileSessionCreated:d?.dshProfileSessionCreated,dshProfileEventCursor:d?.dshProfileEventCursor,updatedAt:Date.now()}),this.scheduleWrite()}setAcpSessionId(e,t){this.updateBinding(e,{acpSessionId:t})}setClaudeSessionId(e,t){this.updateBinding(e,{claudeSessionId:t})}getClaudeSessionId(e){return this.bindings.get(e)?.claudeSessionId}setCodexThreadId(e,t){this.updateBinding(e,{codexThreadId:t})}getCodexThreadId(e){return this.bindings.get(e)?.codexThreadId}setAgyConversationId(e,t){this.updateBinding(e,{agyConversationId:t})}getAgyConversationId(e){return this.bindings.get(e)?.agyConversationId}setCodexContext(e,t){this.updateBinding(e,{codexModelId:t.modelId,codexModeId:t.modeId,codexReasoningEffort:t.reasoningEffort,codexServiceTier:t.serviceTier,codexSandboxMode:t.sandboxMode})}getCodexModelId(e){return this.bindings.get(e)?.codexModelId}setCodexModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexModelId===d||(this.bindings.set(e,{...i,codexModelId:d,updatedAt:Date.now()}),this.scheduleWrite())}setCodexModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexModeId===d||(this.bindings.set(e,{...i,codexModeId:d,updatedAt:Date.now()}),this.scheduleWrite())}setCodexServiceTier(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim();!d||i.codexServiceTier===d||(this.bindings.set(e,{...i,codexServiceTier:d,updatedAt:Date.now()}),this.scheduleWrite())}getCodexModeId(e){return this.bindings.get(e)?.codexModeId}getCodexReasoningEffort(e){return this.bindings.get(e)?.codexReasoningEffort}getCodexServiceTier(e){return this.bindings.get(e)?.codexServiceTier}getCodexSandboxMode(e){return this.bindings.get(e)?.codexSandboxMode}setPiSessionPath(e,t){this.updateBinding(e,{piSessionPath:t})}getPiSessionPath(e){return this.bindings.get(e)?.piSessionPath}setCodeWhaleThreadId(e,t){this.updateBinding(e,{codewhaleThreadId:t})}getCodeWhaleThreadId(e){return this.bindings.get(e)?.codewhaleThreadId}setModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=n(t);i.modeId!==d&&(this.bindings.set(e,{...i,modeId:d,updatedAt:Date.now()}),this.scheduleWrite())}ensureModeId(e,t=P){const i=this.bindings.get(e);i&&(i.modeId||(this.bindings.set(e,{...i,modeId:n(t),updatedAt:Date.now()}),this.scheduleWrite()))}getAcpSessionId(e){return this.bindings.get(e)?.acpSessionId}getModeId(e){const t=this.bindings.get(e)?.modeId;return t?n(t):void 0}setModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=t.trim();i.modelId!==d&&(this.bindings.set(e,{...i,modelId:d,updatedAt:Date.now()}),this.scheduleWrite())}getModelId(e){return this.bindings.get(e)?.modelId}setEffort(e,t){const i=this.bindings.get(e);if(!i)return;const d=a(t);d&&i.effort!==d&&(this.bindings.set(e,{...i,effort:d,updatedAt:Date.now()}),this.scheduleWrite())}getEffort(e){return a(this.bindings.get(e)?.effort)}setCursorModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim().toLowerCase(),s=d===""?void 0:d;i.cursorModeId!==s&&(this.bindings.set(e,{...i,cursorModeId:s,updatedAt:Date.now()}),this.scheduleWrite())}getCursorModeId(e){return this.bindings.get(e)?.cursorModeId}setAcpModelId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim(),s=d===""?void 0:d;i.acpModelId!==s&&(this.bindings.set(e,{...i,acpModelId:s,updatedAt:Date.now()}),this.scheduleWrite())}getAcpModelId(e){return this.bindings.get(e)?.acpModelId}setAcpModeId(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t??"").trim(),s=d===""?void 0:d;i.acpModeId!==s&&(this.bindings.set(e,{...i,acpModeId:s,updatedAt:Date.now()}),this.scheduleWrite())}getAcpModeId(e){return this.bindings.get(e)?.acpModeId}getDshSettings(e){const t=this.bindings.get(e);if(t)return{...t.dshProviderId?{providerId:t.dshProviderId}:{},...t.dshModelId?{modelId:t.dshModelId}:{},modeId:t.dshModeId==="full_auto"?"full_auto":"approval",...t.dshMaxTokens?{maxTokens:t.dshMaxTokens}:{},...t.dshAgentPreset?{agentPreset:t.dshAgentPreset}:{},revision:t.dshSettingsRevision??0,...t.dshSettingsUpdatedAt?{updatedAt:t.dshSettingsUpdatedAt}:{}}}updateDshSettings(e,t){const i=this.bindings.get(e);if(!i)return;const d=Object.prototype.hasOwnProperty.call(t,"providerId")?String(t.providerId??"").trim()||void 0:i.dshProviderId,s=Object.prototype.hasOwnProperty.call(t,"modelId")?String(t.modelId??"").trim()||void 0:i.dshModelId,r=Object.prototype.hasOwnProperty.call(t,"modeId")?t.modeId==="full_auto"?"full_auto":"approval":i.dshModeId,f=Object.prototype.hasOwnProperty.call(t,"maxTokens")?Number.isSafeInteger(t.maxTokens)&&Number(t.maxTokens)>0?Number(t.maxTokens):void 0:i.dshMaxTokens;if(d===i.dshProviderId&&s===i.dshModelId&&r===i.dshModeId&&f===i.dshMaxTokens)return i.dshSettingsRevision??0;const c=Date.now(),u=(i.dshSettingsRevision??0)+1;return this.bindings.set(e,{...i,dshProviderId:d,dshModelId:s,dshModeId:r,dshMaxTokens:f,dshSettingsRevision:u,dshSettingsUpdatedAt:c,updatedAt:c}),this.scheduleWrite(),u}getDshSelectedProfile(e){const t=this.bindings.get(e)?.dshProfileName;return typeof t=="string"&&t.trim()?t.trim():void 0}isDshProfileLocked(e){return this.bindings.get(e)?.dshProfileSessionCreated===!0}setDshSelectedProfile(e,t){const i=this.bindings.get(e);if(!i)return!1;const d=String(t??"").trim();return d?i.dshProfileName===d?!0:i.dshProfileSessionCreated===!0?!1:(this.bindings.set(e,{...i,dshProfileName:d,dshProfileSessionId:void 0,dshProfileSessionCreated:!1,dshProfileEventCursor:0,updatedAt:Date.now()}),this.scheduleWrite(),!0):!1}getDshAgentPreset(e){const t=this.bindings.get(e)?.dshAgentPreset;return typeof t=="string"&&t.trim()?t.trim():void 0}isDshAgentPresetLocked(e){return this.bindings.get(e)?.dshProfileSessionCreated===!0}setDshAgentPreset(e,t){const i=this.bindings.get(e);if(!i||i.dshProfileSessionCreated===!0)return!1;const d=String(t??"").trim();return!d||i.dshAgentPreset===d?i.dshAgentPreset===d:(this.bindings.set(e,{...i,dshAgentPreset:d,updatedAt:Date.now()}),this.scheduleWrite(),!0)}getDshProfileBinding(e,t){const i=this.bindings.get(e);if(!(!i?.dshProfileSessionId||i.dshProfileName!==t))return{profileName:t,sessionId:i.dshProfileSessionId,sessionCreated:i.dshProfileSessionCreated===!0,eventCursor:i.dshProfileEventCursor??0}}setDshProfileBinding(e,t){const i=this.bindings.get(e);if(!i)return;const d=String(t.profileName).trim(),s=String(t.sessionId).trim();if(!d||!s)return;const r=Number.isSafeInteger(t.eventCursor)&&t.eventCursor>=0?t.eventCursor:0;i.dshProfileName===d&&i.dshProfileSessionId===s&&i.dshProfileSessionCreated===t.sessionCreated&&(i.dshProfileEventCursor??0)===r||(this.bindings.set(e,{...i,dshProfileName:d,dshProfileSessionId:s,dshProfileSessionCreated:t.sessionCreated,dshProfileEventCursor:r,updatedAt:Date.now()}),this.scheduleWrite())}get(e){return this.bindings.get(e)}getMostRecentlyUpdatedSessionId(e){const t=e?.requireCwd!==!1;let i,d=-1;for(const s of this.bindings.values())t&&!String(s.cwd??"").trim()||s.updatedAt>d&&(d=s.updatedAt,i=s.aibotSessionId);return i}delete(e){const t=this.bindings.get(e);t&&(o.info("session-binding-store",`delete binding session_id=${e} cwd=${t.cwd??""} codexThreadId=${t.codexThreadId??""}`),this.bindings.delete(e),this.scheduleWrite())}quarantineUnreadablePrimary(){if(!this.filePath||!h(this.filePath))return;const e=`${this.filePath}.corrupt.${Date.now()}`;try{return p(this.filePath,e),o.error("session-binding-store",`Copied unreadable primary bindings to ${e} (original retained to block legacy clobber)`),e}catch(t){o.error("session-binding-store",`Failed to copy unreadable primary ${this.filePath}: ${t instanceof Error?t.message:String(t)}`);return}}entries(){return this.bindings.entries()}async flush(){await this.writePromise}scheduleWrite(){this.filePath&&(this.writePromise=this.writePromise.then(()=>this.write()).catch(e=>{o.error("session-binding-store",`Persist failed: ${e instanceof Error?e.message:e}`)}))}async write(){if(!this.filePath)return;const e=Array.from(this.bindings.values());await m(this.filePath,e)}writeMigratedSnapshot(e){if(!this.filePath)return;const t=`${this.filePath}.${y()}.migration.tmp`;try{b(t,`${JSON.stringify(e,null,2)}
2
2
  `,{encoding:"utf8",mode:384,flag:"wx"}),S(t,this.filePath);try{x(this.filePath,384)}catch{}}catch(i){if(h(t))try{M(t)}catch{}throw new Error(`Failed to migrate legacy session bindings from ${this.legacyFilePath} to ${this.filePath}: ${i instanceof Error?i.message:String(i)}`)}}updateBinding(e,t){const i=this.bindings.get(e),d={aibotSessionId:e,acpSessionId:Object.prototype.hasOwnProperty.call(t,"acpSessionId")?t.acpSessionId:i?.acpSessionId,claudeSessionId:Object.prototype.hasOwnProperty.call(t,"claudeSessionId")?t.claudeSessionId:i?.claudeSessionId,codexThreadId:Object.prototype.hasOwnProperty.call(t,"codexThreadId")?t.codexThreadId:i?.codexThreadId,codexModelId:Object.prototype.hasOwnProperty.call(t,"codexModelId")?t.codexModelId:i?.codexModelId,codexModeId:Object.prototype.hasOwnProperty.call(t,"codexModeId")?t.codexModeId:i?.codexModeId,codewhaleThreadId:Object.prototype.hasOwnProperty.call(t,"codewhaleThreadId")?t.codewhaleThreadId:i?.codewhaleThreadId,agyConversationId:Object.prototype.hasOwnProperty.call(t,"agyConversationId")?t.agyConversationId:i?.agyConversationId,codexReasoningEffort:Object.prototype.hasOwnProperty.call(t,"codexReasoningEffort")?t.codexReasoningEffort:i?.codexReasoningEffort,codexServiceTier:Object.prototype.hasOwnProperty.call(t,"codexServiceTier")?t.codexServiceTier:i?.codexServiceTier,codexSandboxMode:Object.prototype.hasOwnProperty.call(t,"codexSandboxMode")?t.codexSandboxMode:i?.codexSandboxMode,piSessionPath:Object.prototype.hasOwnProperty.call(t,"piSessionPath")?t.piSessionPath:i?.piSessionPath,cwd:i?.cwd,modeId:n(i?.modeId),modelId:i?.modelId,effort:Object.prototype.hasOwnProperty.call(t,"effort")?a(t.effort):a(i?.effort),cursorModeId:i?.cursorModeId,acpModelId:i?.acpModelId,acpModeId:i?.acpModeId,dshProviderId:i?.dshProviderId,dshModelId:i?.dshModelId,dshModeId:i?.dshModeId,dshMaxTokens:i?.dshMaxTokens,dshAgentPreset:i?.dshAgentPreset,dshSettingsRevision:i?.dshSettingsRevision,dshSettingsUpdatedAt:i?.dshSettingsUpdatedAt,dshProfileName:i?.dshProfileName,dshProfileSessionId:i?.dshProfileSessionId,dshProfileSessionCreated:i?.dshProfileSessionCreated,dshProfileEventCursor:i?.dshProfileEventCursor,updatedAt:Date.now()};this.bindings.set(e,d),this.scheduleWrite()}}export{E as SessionBindingStore};
package/dist/log.js CHANGED
@@ -1,3 +1,3 @@
1
- import{createWriteStream as g,mkdirSync as l,existsSync as f}from"node:fs";import{join as t}from"node:path";import{homedir as m}from"node:os";const i=t(m(),".grix"),s={base:i,config:t(i,"config"),log:t(i,"log"),data:t(i,"data")};function S(){for(const o of Object.values(s))f(o)||l(o,{recursive:!0})}let a=null;function $(){const o=new Date().toISOString().slice(0,10),r=t(s.log,`grix-acp-${o}.log`);a=g(r,{flags:"a"})}function c(){return new Date().toISOString().slice(11,19)}const u={info(o,r,...n){const e=`${c()} [${o}] ${r}${n.length?" "+n.map(String).join(" "):""}`;console.log(e),a?.write(e+`
2
- `)},error(o,r,...n){const e=`${c()} [${o}] ERROR ${r}${n.length?" "+n.map(String).join(" "):""}`;console.error(e),a?.write(e+`
1
+ import{createWriteStream as g,mkdirSync as l,existsSync as f}from"node:fs";import{join as i}from"node:path";import{homedir as m}from"node:os";const n=i(m(),".grix"),s={base:n,config:i(n,"config"),log:i(n,"log"),data:i(n,"data")};function S(){for(const o of Object.values(s))f(o)||l(o,{recursive:!0})}let a=null;function $(){const o=new Date().toISOString().slice(0,10),r=i(s.log,`grix-acp-${o}.log`);a=g(r,{flags:"a"})}function c(){return new Date().toISOString().slice(11,19)}const u={info(o,r,...t){const e=`${c()} [${o}] ${r}${t.length?" "+t.map(String).join(" "):""}`;console.log(e),a?.write(e+`
2
+ `)},error(o,r,...t){const e=`${c()} [${o}] ERROR ${r}${t.length?" "+t.map(String).join(" "):""}`;console.error(e),a?.write(e+`
3
3
  `)}};export{s as GRIX_PATHS,S as ensureGrixDirs,$ as initLogger,u as log};
@@ -1 +1 @@
1
- import*as i from"node:net";const e={bind:"127.0.0.1",port:0,endpoint:"/mcp",sessionTimeoutMs:18e5,invokeTimeoutMs:3e4};function n(o){const u={bind:o?.bind??e.bind,port:o?.port??e.port,endpoint:o?.endpoint??e.endpoint,sessionTimeoutMs:o?.sessionTimeoutMs??e.sessionTimeoutMs,invokeTimeoutMs:o?.invokeTimeoutMs??e.invokeTimeoutMs,allowedOrigins:o?.allowedOrigins,allowedHosts:o?.allowedHosts};return s(u.bind),u.port!==0&&t(u.port),r(u.sessionTimeoutMs),u}function s(o){if(!o||!i.isIPv4(o)&&!i.isIPv6(o))throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: bind \u5730\u5740 "${o}" \u4E0D\u662F\u5408\u6CD5\u7684 IPv4 \u6216 IPv6 \u5730\u5740`)}function t(o){if(!Number.isInteger(o)||o<1||o>65535)throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: port \u503C ${o} \u4E0D\u5728\u5408\u6CD5\u8303\u56F4 1-65535 \u5185\u6216\u4E0D\u662F\u6574\u6570`)}function r(o){if(!Number.isInteger(o)||o<1e3||o>864e5)throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: session_timeout_ms \u503C ${o} \u4E0D\u5728\u5408\u6CD5\u8303\u56F4 1000-86400000 \u5185`)}export{n as createDefaultGatewayConfig};
1
+ import*as n from"node:net";const i={bind:"127.0.0.1",port:0,endpoint:"/mcp",sessionTimeoutMs:18e5,invokeTimeoutMs:3e4};function s(u){const e={bind:u?.bind??i.bind,port:u?.port??i.port,endpoint:u?.endpoint??i.endpoint,sessionTimeoutMs:u?.sessionTimeoutMs??i.sessionTimeoutMs,invokeTimeoutMs:u?.invokeTimeoutMs??i.invokeTimeoutMs,allowedOrigins:u?.allowedOrigins,allowedHosts:u?.allowedHosts};return t(e.bind),e.port!==0&&o(e.port),r(e.sessionTimeoutMs),e}function t(u){if(!u||!n.isIPv4(u)&&!n.isIPv6(u))throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: bind \u5730\u5740 "${u}" \u4E0D\u662F\u5408\u6CD5\u7684 IPv4 \u6216 IPv6 \u5730\u5740`)}function o(u){if(!Number.isInteger(u)||u<1||u>65535)throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: port \u503C ${u} \u4E0D\u5728\u5408\u6CD5\u8303\u56F4 1-65535 \u5185\u6216\u4E0D\u662F\u6574\u6570`)}function r(u){if(!Number.isInteger(u)||u<1e3||u>864e5)throw new Error(`\u914D\u7F6E\u6821\u9A8C\u5931\u8D25: session_timeout_ms \u503C ${u} \u4E0D\u5728\u5408\u6CD5\u8303\u56F4 1000-86400000 \u5185`)}export{s as createDefaultGatewayConfig};
@@ -1 +1 @@
1
- const r=3e4;class c{connectionManager;onDisconnected;bindings=new Map;constructor(n,i){this.connectionManager=n,this.onDisconnected=i}async bind(n,i){if(this.bindings.has(n))throw new Error(`Session ${n} is already bound to a connection`);const e=await this.connectWithTimeout(i),t=[],s=e.onDisconnected(()=>{this.removeBinding(n),this.onDisconnected(n)});return t.push(s),this.bindings.set(n,{sessionId:n,handle:e,subscriptions:t}),e}getHandle(n){return this.bindings.get(n)?.handle}unbind(n){const i=this.bindings.get(n);if(i){this.bindings.delete(n);for(const e of i.subscriptions)e();i.handle.disconnect()}}unbindAll(){const n=[...this.bindings.keys()];for(const i of n)this.unbind(i)}connectWithTimeout(n){return new Promise((i,e)=>{let t=!1;const s=setTimeout(()=>{t||(t=!0,e(new Error("Connection bind timeout after 30000ms")))},3e4);this.connectionManager.connect({agentId:n.agentId,apiKey:n.apiKey,url:n.wsUrl,clientType:n.clientType,capabilities:["agent_invoke"],adapterHint:`${n.clientType}/base`},{maxRetries:0}).then(o=>{t?o.disconnect():(t=!0,clearTimeout(s),i(o))}).catch(o=>{t||(t=!0,clearTimeout(s),e(o))})})}removeBinding(n){const i=this.bindings.get(n);if(i){this.bindings.delete(n);for(const e of i.subscriptions)e()}}}export{c as ConnectionBindingImpl};
1
+ const a=3e4;class c{connectionManager;onDisconnected;bindings=new Map;constructor(n,i){this.connectionManager=n,this.onDisconnected=i}async bind(n,i){if(this.bindings.has(n))throw new Error(`Session ${n} is already bound to a connection`);const e=await this.connectWithTimeout(i),t=[],s=e.onDisconnected(()=>{this.removeBinding(n),this.onDisconnected(n)});return t.push(s),this.bindings.set(n,{sessionId:n,handle:e,subscriptions:t}),e}getHandle(n){return this.bindings.get(n)?.handle}unbind(n){const i=this.bindings.get(n);if(i){this.bindings.delete(n);for(const e of i.subscriptions)e();i.handle.disconnect()}}unbindAll(){const n=[...this.bindings.keys()];for(const i of n)this.unbind(i)}connectWithTimeout(n){return new Promise((i,e)=>{let t=!1;const s=setTimeout(()=>{t||(t=!0,e(new Error("Connection bind timeout after 30000ms")))},3e4);this.connectionManager.connect({agentId:n.agentId,apiKey:n.apiKey,url:n.wsUrl,clientType:n.clientType,capabilities:["agent_invoke"],adapterHint:`${n.clientType}/base`},{maxRetries:0}).then(o=>{t?o.disconnect():(t=!0,clearTimeout(s),i(o))}).catch(o=>{t||(t=!0,clearTimeout(s),e(o))})})}removeBinding(n){const i=this.bindings.get(n);if(i){this.bindings.delete(n);for(const e of i.subscriptions)e()}}}export{c as ConnectionBindingImpl};
@@ -1 +1 @@
1
- function a(o){const e=new Set([`http://127.0.0.1:${o.serverPort}`,`http://localhost:${o.serverPort}`,...o.allowedOrigins]),t=new Set([`127.0.0.1:${o.serverPort}`,`localhost:${o.serverPort}`,...o.allowedHosts]);return{validateRequest(s){const r=i(s,e);if(!r.ok)return r;const n=l(s,t);return n.ok?{ok:!0}:n}}}function i(o,e){const t=o.headers.origin;return t?e.has(t)?{ok:!0}:{ok:!1,statusCode:403,message:`Origin not allowed: ${t}`}:{ok:!0}}function l(o,e){const t=o.headers.host;return t?e.has(t)?{ok:!0}:{ok:!1,statusCode:403,message:`Host not allowed: ${t}`}:{ok:!1,statusCode:403,message:"Missing Host header"}}export{a as createSecurityPolicy};
1
+ function a(t){const o=new Set([`http://127.0.0.1:${t.serverPort}`,`http://localhost:${t.serverPort}`,...t.allowedOrigins]),e=new Set([`127.0.0.1:${t.serverPort}`,`localhost:${t.serverPort}`,...t.allowedHosts]);return{validateRequest(s){const r=i(s,o);if(!r.ok)return r;const n=l(s,e);return n.ok?{ok:!0}:n}}}function i(t,o){const e=t.headers.origin;return e?o.has(e)?{ok:!0}:{ok:!1,statusCode:403,message:`Origin not allowed: ${e}`}:{ok:!0}}function l(t,o){const e=t.headers.host;return e?o.has(e)?{ok:!0}:{ok:!1,statusCode:403,message:`Host not allowed: ${e}`}:{ok:!1,statusCode:403,message:"Missing Host header"}}export{a as createSecurityPolicy};
@@ -1 +1 @@
1
- import{toolCallToInvoke as i}from"../../core/mcp/tools.js";import{ToolRegistryImpl as l}from"./tool-registry.js";import{validateToolArgs as a}from"./tool-schemas.js";import{isEventTool as p,executeEventTool as d}from"./event-tool-executor.js";class y{registry;constructor(){this.registry=new l}async execute(t,e,r,n){if(!this.registry.hasTool(e))return this.errorResult(`\u672A\u77E5\u5DE5\u5177: ${e}`);const s=a(e,r);if(!s.valid)return this.errorResult(`\u53C2\u6570\u6821\u9A8C\u5931\u8D25: ${s.error}`);if(t.status!=="ready")return this.errorResult(`\u8FDE\u63A5\u4E0D\u53EF\u7528: \u5F53\u524D\u72B6\u6001\u4E3A ${t.status}`);if(p(e))return this.executeEventTool(t,e,r);const o=i(e,r);try{const u=await t.agentInvoke(o.action,o.params,n);return this.normalizeResult(u)}catch(u){const c=u instanceof Error?u.message:String(u);return c.toLowerCase().includes("timeout")?this.errorResult(`\u8C03\u7528\u8D85\u65F6: ${c}`):this.errorResult(`\u8C03\u7528\u5931\u8D25: ${c}`)}}normalizeResult(t){if(t==null||typeof t!="object")return this.successResult(t??null);const e=t,r=typeof e.code=="number"?e.code:0;if(r===0){const s="data"in e?e.data:null;return this.successResult(s??null)}const n=typeof e.msg=="string"?e.msg:"\u672A\u77E5\u9519\u8BEF";return this.errorResult(`\u4E0A\u6E38\u9519\u8BEF [code=${r}]: ${n}`)}successResult(t){return{content:[{type:"text",text:JSON.stringify(t)}],isError:!1}}errorResult(t){return{content:[{type:"text",text:t}],isError:!0}}async executeEventTool(t,e,r){return e==="grix_access_control"?this.executeAccessControl(t,r):d(t,e,r)}async executeAccessControl(t,e){const r=String(e.action??""),n={pair_approve:"pair_approve",pair_deny:"pair_deny",allow_sender:"sender_allow",remove_sender:"sender_remove",set_policy:"policy_set"}[r];if(!n)return this.errorResult(`\u672A\u77E5 access_control action: ${r}`);const s={};e.code!=null&&(s.code=e.code),e.sender_id!=null&&(s.sender_id=e.sender_id),e.policy!=null&&(s.policy=e.policy);try{const o=await t.agentInvoke("claude_access_control",{verb:n,payload:s},3e4);return this.successResult(o)}catch(o){const u=o instanceof Error?o.message:String(o);return this.errorResult(`access_control \u8C03\u7528\u5931\u8D25: ${u}`)}}}export{y as ToolExecutorImpl};
1
+ import{toolCallToInvoke as i}from"../../core/mcp/tools.js";import{ToolRegistryImpl as l}from"./tool-registry.js";import{validateToolArgs as a}from"./tool-schemas.js";import{isEventTool as p,executeEventTool as d}from"./event-tool-executor.js";class y{registry;constructor(){this.registry=new l}async execute(r,e,t,n){if(!this.registry.hasTool(e))return this.errorResult(`\u672A\u77E5\u5DE5\u5177: ${e}`);const s=a(e,t);if(!s.valid)return this.errorResult(`\u53C2\u6570\u6821\u9A8C\u5931\u8D25: ${s.error}`);if(r.status!=="ready")return this.errorResult(`\u8FDE\u63A5\u4E0D\u53EF\u7528: \u5F53\u524D\u72B6\u6001\u4E3A ${r.status}`);if(p(e))return this.executeEventTool(r,e,t);const o=i(e,t);try{const u=await r.agentInvoke(o.action,o.params,n);return this.normalizeResult(u)}catch(u){const c=u instanceof Error?u.message:String(u);return c.toLowerCase().includes("timeout")?this.errorResult(`\u8C03\u7528\u8D85\u65F6: ${c}`):this.errorResult(`\u8C03\u7528\u5931\u8D25: ${c}`)}}normalizeResult(r){if(r==null||typeof r!="object")return this.successResult(r??null);const e=r,t=typeof e.code=="number"?e.code:0;if(t===0){const s="data"in e?e.data:null;return this.successResult(s??null)}const n=typeof e.msg=="string"?e.msg:"\u672A\u77E5\u9519\u8BEF";return this.errorResult(`\u4E0A\u6E38\u9519\u8BEF [code=${t}]: ${n}`)}successResult(r){return{content:[{type:"text",text:JSON.stringify(r)}],isError:!1}}errorResult(r){return{content:[{type:"text",text:r}],isError:!0}}async executeEventTool(r,e,t){return e==="grix_access_control"?this.executeAccessControl(r,t):d(r,e,t)}async executeAccessControl(r,e){const t=String(e.action??""),n={pair_approve:"pair_approve",pair_deny:"pair_deny",allow_sender:"sender_allow",remove_sender:"sender_remove",set_policy:"policy_set"}[t];if(!n)return this.errorResult(`\u672A\u77E5 access_control action: ${t}`);const s={};e.code!=null&&(s.code=e.code),e.sender_id!=null&&(s.sender_id=e.sender_id),e.policy!=null&&(s.policy=e.policy);try{const o=await r.agentInvoke("claude_access_control",{verb:n,payload:s},3e4);return this.successResult(o)}catch(o){const u=o instanceof Error?o.message:String(o);return this.errorResult(`access_control \u8C03\u7528\u5931\u8D25: ${u}`)}}}export{y as ToolExecutorImpl};
@@ -1 +1 @@
1
- import{TOOLS as s,EVENT_TOOLS as t}from"../../core/mcp/tools.js";const e=new Set(["grix_query","grix_group","grix_message_send","grix_message_unsend","grix_admin"]),r=new Set(["grix_reply","grix_complete","grix_event_ack","grix_composing","grix_access_control","grix_status"]);class a{tools;toolMap;constructor(){this.tools=[...s.filter(o=>e.has(o.name)),...t.filter(o=>r.has(o.name))],this.toolMap=new Map(this.tools.map(o=>[o.name,o]))}getTools(){return this.tools}getTool(o){return this.toolMap.get(o)}hasTool(o){return this.toolMap.has(o)}}export{a as ToolRegistryImpl};
1
+ import{TOOLS as o,EVENT_TOOLS as s}from"../../core/mcp/tools.js";const e=new Set(["grix_query","grix_group","grix_message_send","grix_message_unsend","grix_admin"]),r=new Set(["grix_reply","grix_complete","grix_event_ack","grix_composing","grix_access_control","grix_status"]);class a{tools;toolMap;constructor(){this.tools=[...o.filter(t=>e.has(t.name)),...s.filter(t=>r.has(t.name))],this.toolMap=new Map(this.tools.map(t=>[t.name,t]))}getTools(){return this.tools}getTool(t){return this.toolMap.get(t)}hasTool(t){return this.toolMap.has(t)}}export{a as ToolRegistryImpl};
@@ -1 +1 @@
1
- const o={required:["action"],properties:{action:{type:"string",enum:["contact_search","session_search","message_history","message_search"]},id:{type:"string"},keyword:{type:"string",maxLength:200},limit:{type:"integer",minimum:1,maximum:100},offset:{type:"integer",minimum:0},sessionId:{type:"string"},beforeId:{type:"string"}}},a={required:["action"],properties:{action:{type:"string",enum:["create","detail","leave","add_members","remove_members","update_member_role","update_all_members_muted","update_member_speaking","dissolve"]},sessionId:{type:"string"},name:{type:"string",maxLength:128},memberIds:{type:"array",items:{type:"string"},maxItems:100},memberTypes:{type:"array",items:{type:"integer",enum:[1,2]}},memberId:{type:"string"},role:{type:"integer",enum:[1,2]},memberType:{type:"integer"},allMembersMuted:{type:"boolean"},isSpeakMuted:{type:"boolean"},canSpeakWhenAllMuted:{type:"boolean"}}},p={required:["sessionId","content"],properties:{sessionId:{type:"string"},content:{type:"string",maxLength:1e4},msgType:{type:"integer"},quotedMessageId:{type:"string"},threadId:{type:"string"}}},m={required:["sessionId","msgId"],properties:{sessionId:{type:"string"},msgId:{type:"string"}}},g={required:["action"],properties:{action:{type:"string",enum:["create_agent","list_categories","create_category","update_category","assign_category","rotate_api_key"]},agentName:{type:"string"},introduction:{type:"string"},isMain:{type:"boolean"},agentId:{type:"string"},categoryId:{type:"string"},name:{type:"string"},parentId:{type:"string"},sortOrder:{type:"integer"}}},y={required:["session_id","text"],properties:{event_id:{type:"string"},session_id:{type:"string"},text:{type:"string",maxLength:5e4},quoted_message_id:{type:"string"},is_final:{type:"boolean"}}},d={required:["event_id","status"],properties:{event_id:{type:"string"},status:{type:"string",enum:["responded","canceled","failed"]},msg:{type:"string",maxLength:500}}},c={required:["event_id"],properties:{event_id:{type:"string"},session_id:{type:"string"}}},l={required:["session_id","active"],properties:{session_id:{type:"string"},active:{type:"boolean"},event_id:{type:"string"}}},_={required:["action"],properties:{action:{type:"string",enum:["pair_approve","pair_deny","allow_sender","remove_sender","set_policy"]},code:{type:"string"},sender_id:{type:"string"},policy:{type:"string",enum:["allowlist","open","disabled"]}}},f={required:[],properties:{}},C={grix_query:o,grix_group:a,grix_message_send:p,grix_message_unsend:m,grix_admin:g,grix_reply:y,grix_complete:d,grix_event_ack:c,grix_composing:l,grix_access_control:_,grix_status:f};function B(u,t){const e=C[u];if(!e)return{valid:!1,error:`\u672A\u77E5\u5DE5\u5177: ${u}`};for(const i of e.required)if(t[i]===void 0||t[i]===null)return{valid:!1,error:`\u7F3A\u5C11\u5FC5\u586B\u53C2\u6570: ${i}`};for(const[i,r]of Object.entries(t)){if(r==null)continue;const n=e.properties[i];if(!n)continue;const s=$(i,r,n);if(s)return{valid:!1,error:s}}return{valid:!0}}function $(u,t,e){switch(e.type){case"string":if(typeof t!="string")return`\u53C2\u6570 ${u} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B string\uFF0C\u5B9E\u9645 ${typeof t}`;if(e.maxLength!==void 0&&t.length>e.maxLength)return`\u53C2\u6570 ${u} \u8D85\u8FC7\u6700\u5927\u957F\u5EA6 ${e.maxLength}\uFF0C\u5B9E\u9645 ${t.length}`;if(e.enum&&!e.enum.includes(t))return`\u53C2\u6570 ${u} \u503C "${t}" \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.enum.join(", ")}]`;break;case"integer":if(typeof t!="number"||!Number.isInteger(t))return`\u53C2\u6570 ${u} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B integer\uFF0C\u5B9E\u9645 ${typeof t=="number"?"\u6D6E\u70B9\u6570":typeof t}`;if(e.minimum!==void 0&&t<e.minimum)return`\u53C2\u6570 ${u} \u503C ${t} \u5C0F\u4E8E\u6700\u5C0F\u503C ${e.minimum}`;if(e.maximum!==void 0&&t>e.maximum)return`\u53C2\u6570 ${u} \u503C ${t} \u5927\u4E8E\u6700\u5927\u503C ${e.maximum}`;if(e.enum&&!e.enum.includes(t))return`\u53C2\u6570 ${u} \u503C ${t} \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.enum.join(", ")}]`;break;case"boolean":if(typeof t!="boolean")return`\u53C2\u6570 ${u} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B boolean\uFF0C\u5B9E\u9645 ${typeof t}`;break;case"array":if(!Array.isArray(t))return`\u53C2\u6570 ${u} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B array\uFF0C\u5B9E\u9645 ${typeof t}`;if(e.maxItems!==void 0&&t.length>e.maxItems)return`\u53C2\u6570 ${u} \u8D85\u8FC7\u6700\u5927\u5143\u7D20\u6570 ${e.maxItems}\uFF0C\u5B9E\u9645 ${t.length}`;if(e.items)for(let i=0;i<t.length;i++){const r=t[i];if(e.items.type==="string"&&typeof r!="string")return`\u53C2\u6570 ${u}[${i}] \u7C7B\u578B\u9519\u8BEF: \u671F\u671B string\uFF0C\u5B9E\u9645 ${typeof r}`;if(e.items.type==="integer"){if(typeof r!="number"||!Number.isInteger(r))return`\u53C2\u6570 ${u}[${i}] \u7C7B\u578B\u9519\u8BEF: \u671F\u671B integer\uFF0C\u5B9E\u9645 ${typeof r}`;if(e.items.enum&&!e.items.enum.includes(r))return`\u53C2\u6570 ${u}[${i}] \u503C ${r} \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.items.enum.join(", ")}]`}}break}}export{B as validateToolArgs};
1
+ const o={required:["action"],properties:{action:{type:"string",enum:["contact_search","session_search","message_history","message_search"]},id:{type:"string"},keyword:{type:"string",maxLength:200},limit:{type:"integer",minimum:1,maximum:100},offset:{type:"integer",minimum:0},sessionId:{type:"string"},beforeId:{type:"string"}}},a={required:["action"],properties:{action:{type:"string",enum:["create","detail","leave","add_members","remove_members","update_member_role","update_all_members_muted","update_member_speaking","dissolve"]},sessionId:{type:"string"},name:{type:"string",maxLength:128},memberIds:{type:"array",items:{type:"string"},maxItems:100},memberTypes:{type:"array",items:{type:"integer",enum:[1,2]}},memberId:{type:"string"},role:{type:"integer",enum:[1,2]},memberType:{type:"integer"},allMembersMuted:{type:"boolean"},isSpeakMuted:{type:"boolean"},canSpeakWhenAllMuted:{type:"boolean"}}},p={required:["sessionId","content"],properties:{sessionId:{type:"string"},content:{type:"string",maxLength:1e4},msgType:{type:"integer"},quotedMessageId:{type:"string"},threadId:{type:"string"}}},m={required:["sessionId","msgId"],properties:{sessionId:{type:"string"},msgId:{type:"string"}}},g={required:["action"],properties:{action:{type:"string",enum:["create_agent","list_categories","create_category","update_category","assign_category","rotate_api_key"]},agentName:{type:"string"},introduction:{type:"string"},isMain:{type:"boolean"},agentId:{type:"string"},categoryId:{type:"string"},name:{type:"string"},parentId:{type:"string"},sortOrder:{type:"integer"}}},y={required:["session_id","text"],properties:{event_id:{type:"string"},session_id:{type:"string"},text:{type:"string",maxLength:5e4},quoted_message_id:{type:"string"},is_final:{type:"boolean"}}},d={required:["event_id","status"],properties:{event_id:{type:"string"},status:{type:"string",enum:["responded","canceled","failed"]},msg:{type:"string",maxLength:500}}},c={required:["event_id"],properties:{event_id:{type:"string"},session_id:{type:"string"}}},l={required:["session_id","active"],properties:{session_id:{type:"string"},active:{type:"boolean"},event_id:{type:"string"}}},_={required:["action"],properties:{action:{type:"string",enum:["pair_approve","pair_deny","allow_sender","remove_sender","set_policy"]},code:{type:"string"},sender_id:{type:"string"},policy:{type:"string",enum:["allowlist","open","disabled"]}}},f={required:[],properties:{}},C={grix_query:o,grix_group:a,grix_message_send:p,grix_message_unsend:m,grix_admin:g,grix_reply:y,grix_complete:d,grix_event_ack:c,grix_composing:l,grix_access_control:_,grix_status:f};function B(r,t){const e=C[r];if(!e)return{valid:!1,error:`\u672A\u77E5\u5DE5\u5177: ${r}`};for(const i of e.required)if(t[i]===void 0||t[i]===null)return{valid:!1,error:`\u7F3A\u5C11\u5FC5\u586B\u53C2\u6570: ${i}`};for(const[i,u]of Object.entries(t)){if(u==null)continue;const n=e.properties[i];if(!n)continue;const s=$(i,u,n);if(s)return{valid:!1,error:s}}return{valid:!0}}function $(r,t,e){switch(e.type){case"string":if(typeof t!="string")return`\u53C2\u6570 ${r} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B string\uFF0C\u5B9E\u9645 ${typeof t}`;if(e.maxLength!==void 0&&t.length>e.maxLength)return`\u53C2\u6570 ${r} \u8D85\u8FC7\u6700\u5927\u957F\u5EA6 ${e.maxLength}\uFF0C\u5B9E\u9645 ${t.length}`;if(e.enum&&!e.enum.includes(t))return`\u53C2\u6570 ${r} \u503C "${t}" \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.enum.join(", ")}]`;break;case"integer":if(typeof t!="number"||!Number.isInteger(t))return`\u53C2\u6570 ${r} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B integer\uFF0C\u5B9E\u9645 ${typeof t=="number"?"\u6D6E\u70B9\u6570":typeof t}`;if(e.minimum!==void 0&&t<e.minimum)return`\u53C2\u6570 ${r} \u503C ${t} \u5C0F\u4E8E\u6700\u5C0F\u503C ${e.minimum}`;if(e.maximum!==void 0&&t>e.maximum)return`\u53C2\u6570 ${r} \u503C ${t} \u5927\u4E8E\u6700\u5927\u503C ${e.maximum}`;if(e.enum&&!e.enum.includes(t))return`\u53C2\u6570 ${r} \u503C ${t} \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.enum.join(", ")}]`;break;case"boolean":if(typeof t!="boolean")return`\u53C2\u6570 ${r} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B boolean\uFF0C\u5B9E\u9645 ${typeof t}`;break;case"array":if(!Array.isArray(t))return`\u53C2\u6570 ${r} \u7C7B\u578B\u9519\u8BEF: \u671F\u671B array\uFF0C\u5B9E\u9645 ${typeof t}`;if(e.maxItems!==void 0&&t.length>e.maxItems)return`\u53C2\u6570 ${r} \u8D85\u8FC7\u6700\u5927\u5143\u7D20\u6570 ${e.maxItems}\uFF0C\u5B9E\u9645 ${t.length}`;if(e.items)for(let i=0;i<t.length;i++){const u=t[i];if(e.items.type==="string"&&typeof u!="string")return`\u53C2\u6570 ${r}[${i}] \u7C7B\u578B\u9519\u8BEF: \u671F\u671B string\uFF0C\u5B9E\u9645 ${typeof u}`;if(e.items.type==="integer"){if(typeof u!="number"||!Number.isInteger(u))return`\u53C2\u6570 ${r}[${i}] \u7C7B\u578B\u9519\u8BEF: \u671F\u671B integer\uFF0C\u5B9E\u9645 ${typeof u}`;if(e.items.enum&&!e.items.enum.includes(u))return`\u53C2\u6570 ${r}[${i}] \u503C ${u} \u4E0D\u5728\u5141\u8BB8\u8303\u56F4 [${e.items.enum.join(", ")}]`}}break}}export{B as validateToolArgs};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "grix-connector",
3
- "version": "3.26.13",
3
+ "version": "3.27.0",
4
4
  "description": "Connect local AI coding agents (Claude, Codex, Gemini, Qwen, DeepSeek, Cursor, OpenCode, Pi, OpenHuman, Reasonix) to the Grix scheduling platform. Also serves as an OpenClaw plugin for Grix channel transport.",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",