@microi.net/cli 4.6.7 → 4.6.9

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.
@@ -8,27 +8,27 @@ XaFX8UgCFE4d4pvK6IvQsWunm+WfYqgrSzBMS1LH1fstmZB0wnVUX1uGROaZTKGZ
8
8
  1rS/MVn4i6CsPgP9Q7nFV6dZvbxro1byH/E3CV/Q1CgCDeue9FzQUlWQ+UZld8Jg
9
9
  1DsI9VJ7gTHGL3R7sQIDAQAB
10
10
  -----END PUBLIC KEY-----`;var de=G(require("fs")),z=G(require("path")),Wt=require("child_process");var yn="# Microi VS Code extension local runtime files";function ft(a){let e="",t=0;for(;t<a.length;)if(a[t]==='"'){let n=t;for(t++;t<a.length&&a[t]!=='"';)a[t]==="\\"&&t++,t++;t++,e+=a.slice(n,t)}else if(a[t]==="/"&&a[t+1]==="/")for(;t<a.length&&a[t]!==`
11
- `;)t++;else if(a[t]==="/"&&a[t+1]==="*"){for(t+=2;t<a.length&&!(a[t]==="*"&&a[t+1]==="/");)t++;t+=2}else e+=a[t],t++;return JSON.parse(e)}function te(a){de.existsSync(a)||de.mkdirSync(a,{recursive:!0})}function Sn(a){return a.replace(/\\/g,"/").replace(/^\.\//,"")}function Cn(a){let e=a;for(;;){let t=z.join(e,".git");if(de.existsSync(t))try{let i=de.statSync(t);if(i.isDirectory())return{gitDir:t,workTreeRoot:e};if(i.isFile()){let o=de.readFileSync(t,"utf-8").match(/^gitdir:\s*(.+)$/m);if(o?.[1])return{gitDir:z.isAbsolute(o[1])?o[1]:z.resolve(e,o[1]),workTreeRoot:e}}}catch{return null}let n=z.dirname(e);if(n===e)return null;e=n}}function ve(a,e){try{let t=Cn(a);if(!t)return;let n=z.join(t.gitDir,"info");te(n);let i=z.join(n,"exclude"),r=Sn(z.relative(t.workTreeRoot,a)),o=e.map(u=>u.trim()).filter(Boolean).map(u=>Sn(u.replace(/^\/+/,""))).map(u=>r?`${r}/${u}`:u),s=de.existsSync(i)?de.readFileSync(i,"utf-8"):"",c=new Set(s.split(/\r?\n/).map(u=>u.trim())),d=o.filter(u=>!c.has(u));if(!d.length)return;let m=s.length>0&&!s.endsWith(`
11
+ `;)t++;else if(a[t]==="/"&&a[t+1]==="*"){for(t+=2;t<a.length&&!(a[t]==="*"&&a[t+1]==="/");)t++;t+=2}else e+=a[t],t++;return JSON.parse(e)}function te(a){de.existsSync(a)||de.mkdirSync(a,{recursive:!0})}function Sn(a){return a.replace(/\\/g,"/").replace(/^\.\//,"")}function Cn(a){let e=a;for(;;){let t=z.join(e,".git");if(de.existsSync(t))try{let i=de.statSync(t);if(i.isDirectory())return{gitDir:t,workTreeRoot:e};if(i.isFile()){let o=de.readFileSync(t,"utf-8").match(/^gitdir:\s*(.+)$/m);if(o?.[1])return{gitDir:z.isAbsolute(o[1])?o[1]:z.resolve(e,o[1]),workTreeRoot:e}}}catch{return null}let n=z.dirname(e);if(n===e)return null;e=n}}function ve(a,e){try{let t=Cn(a);if(!t)return;let n=z.join(t.gitDir,"info");te(n);let i=z.join(n,"exclude"),r=Sn(z.relative(t.workTreeRoot,a)),o=e.map(u=>u.trim()).filter(Boolean).map(u=>Sn(u.replace(/^\/+/,""))).map(u=>r?`${r}/${u}`:u),s=de.existsSync(i)?de.readFileSync(i,"utf-8"):"",c=new Set(s.split(/\r?\n/).map(u=>u.trim())),l=o.filter(u=>!c.has(u));if(!l.length)return;let m=s.length>0&&!s.endsWith(`
12
12
  `),g=s.includes(yn)?"":`${yn}
13
- `,l=`${m?`
14
- `:""}${g}${d.join(`
13
+ `,d=`${m?`
14
+ `:""}${g}${l.join(`
15
15
  `)}
16
- `;de.appendFileSync(i,l,"utf-8")}catch{}}function Be(a){if(process.platform==="win32")try{let e=Cn(a);if(!e)return;try{if((0,Wt.execFileSync)("git",["config","--get","core.longpaths"],{cwd:e.workTreeRoot,encoding:"utf-8",stdio:["ignore","pipe","ignore"],windowsHide:!0}).trim().toLowerCase()==="true")return}catch{}(0,Wt.execFileSync)("git",["config","core.longpaths","true"],{cwd:e.workTreeRoot,stdio:"ignore",windowsHide:!0})}catch{}}function K(a){let e=String(a||"").replace(/[<>:"/\\|?*\x00-\x1F]/g,"_").replace(/[. ]+$/g,""),t=!e||e==="."||e===".."?"_":e;return/^(con|prn|aux|nul|com[1-9]|lpt[1-9])(?:\..*)?$/i.test(t)?`_${t}`:t}function Gt(a){return encodeURIComponent(String(a||"")).replace(/[!'()*]/g,e=>`%${e.charCodeAt(0).toString(16).toUpperCase()}`)}function li(a){try{return decodeURIComponent(String(a||""))}catch{return String(a||"")}}function Ce(a){let e=a.indexOf(Kt);return e!==-1?a.substring(e+Kt.length):a}function di(a){let e=a||"";if(!e.trim())return!1;let t=e.trimStart();return t.startsWith("var ")||t.startsWith("let ")||t.startsWith("const ")||t.startsWith("function")||t.startsWith("return")||t.startsWith("//")||t.startsWith("/*")||e.includes("V8.")||e.includes("return ")||e.includes("=>")||e.includes("console.")||e.includes(";")||e.includes("{")||e.includes(`
17
- `)}function zt(a){let e=a||"",t=e.trim();if(!t||t.length%4!==0||!/^[A-Za-z0-9+/]+={0,2}$/.test(t))return e;try{let n=Buffer.from(t,"base64").toString("utf8");if(!n||n.includes("\uFFFD"))return e;let i=t.replace(/=+$/,""),r=Buffer.from(n,"utf8").toString("base64").replace(/=+$/,"");return i!==r?e:di(n)?n:e}catch{return e}}function Tn(a,e){let n=z.relative(e,a).split(z.sep);if(n.length>=5&&(n[2]===Ve||n[2]==="api-engine")){let i=n[1],r=i.split(".")[0];if(n.length===5&&n[4]?.endsWith(".js")){let o=n[4].replace(".js",""),s=o.match(/\(([^)]+)\)$/);return s?{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:li(s[1])}:{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:o}}if(n.length>=6&&n[5]?.endsWith(".js"))return{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:n[5].replace(".js","")}}return null}function vn(a,e){let n=z.relative(e,a).split(z.sep),i=r=>{let o=r.match(/[((]([^))]+)[))]\s*$/);return o?o[1]:r};if(n.length>=6&&n[2]===Te&&n[4]===ut){let r=n[1],o=r.split(".")[0],s=i(n[3]),c=n[5].replace(/\.js$/i,""),d=i(c);return{serverDir:n[0],osClientDir:r,osClient:o,formEngineKey:s,eventType:d}}if(n.length>=5&&(n[2]===un||n[2]==="v8-event"||n[2]==="v8-events")){let r=n[1],o=r.split(".")[0],s=i(n[3]);return{serverDir:n[0],osClientDir:r,osClient:o,formEngineKey:s,eventType:n[4].replace(/\.js$/i,"")}}return null}function me(a){return(a||new Date).toISOString().replace("T"," ").substring(0,19)}function En(a,e){let n=z.relative(e,a).split(z.sep);if(n.length<7||n[2]!==Te||n[4]!==Je)return null;let i=g=>{let l=g.match(/[((]([^))]+)[))]\s*$/);return l?l[1]:g},r=n[1],o=r.split(".")[0],s=i(n[3]),c=i(n[5]),d=n[6].replace(/\.js$/i,""),m=i(d);return{serverDir:n[0],osClientDir:r,osClient:o,tableName:s,fieldName:c,v8Key:m}}function wn(a,e){let n=z.relative(e,a).split(z.sep);if(n[2]!==ke)return null;let i=g=>{let l=g.match(/[((]([^))]+)[))]\s*$/);return l?l[1]:g},r=g=>g.replace(/[((][^))]+[))]\s*$/,"").trim()||g,o=n[1],s=o.split(".")[0],c=n.findIndex((g,l)=>l>2&&Object.prototype.hasOwnProperty.call($e,i(g)));if(c<=3)return null;let d=i(n[c-1]),m=i(n[c]);if(n.length>c+1&&n[c+1].endsWith(".js")){let g=n[c+1].replace(/\.js$/i,""),l=i(g),u=r(g).replace(/_显隐判断$/,"")||r(g),p=g.includes("\u663E\u9690\u5224\u65AD")?"V8CodeShow":"V8Code";return{serverDir:n[0],osClientDir:o,osClient:s,moduleId:d,btnField:m,btnId:l,btnName:u,v8SubField:p}}if(n.length>c+2&&n[c+2].endsWith(".js")){let g=i(n[c+1]),l=r(n[c+1]),u=n[c+2].replace(/\.js$/i,""),p=i(u);return p!=="V8Code"&&p!=="V8CodeShow"?null:{serverDir:n[0],osClientDir:o,osClient:s,moduleId:d,btnField:m,btnId:g,btnName:l,v8SubField:p}}return null}function bn(a,e){let n=z.relative(e,a).split(z.sep),i=n[n.length-1];if(n.length<5||n[2]!==ke||!i?.endsWith(".js"))return null;let r=d=>{let m=d.match(/[((]([^))]+)[))]\s*$/);return m?m[1]:d},o=r(i.replace(/\.js$/i,""));if(!Object.prototype.hasOwnProperty.call(qe,o))return null;let s=r(n[n.length-2]);if(!s)return null;let c=n[1];return{serverDir:n[0],osClientDir:c,osClient:c.split(".")[0],moduleId:s,scriptField:o}}function kn(a){let e=[],t=[{label:"tokens truncated",regex:/(?:\.\.\.|…)\s*[\d,.]+\s+tokens?\s+truncated\s*(?:\.\.\.|…)/i},{label:"Exit code",regex:/^\s*Exit code:\s*-?\d+\s*$/i},{label:"Process exited with code",regex:/^\s*Process exited with code\s+-?\d+\s*$/i},{label:"Chunk ID",regex:/^\s*Chunk ID:\s*\S+\s*$/i},{label:"Wall time",regex:/^\s*Wall time:\s*[\d.]+\s*(?:s|sec(?:ond)?s?)\s*$/i}];return a.replace(/\r\n/g,`
16
+ `;de.appendFileSync(i,d,"utf-8")}catch{}}function Be(a){if(process.platform==="win32")try{let e=Cn(a);if(!e)return;try{if((0,Wt.execFileSync)("git",["config","--get","core.longpaths"],{cwd:e.workTreeRoot,encoding:"utf-8",stdio:["ignore","pipe","ignore"],windowsHide:!0}).trim().toLowerCase()==="true")return}catch{}(0,Wt.execFileSync)("git",["config","core.longpaths","true"],{cwd:e.workTreeRoot,stdio:"ignore",windowsHide:!0})}catch{}}function K(a){let e=String(a||"").replace(/[<>:"/\\|?*\x00-\x1F]/g,"_").replace(/[. ]+$/g,""),t=!e||e==="."||e===".."?"_":e;return/^(con|prn|aux|nul|com[1-9]|lpt[1-9])(?:\..*)?$/i.test(t)?`_${t}`:t}function Gt(a){return encodeURIComponent(String(a||"")).replace(/[!'()*]/g,e=>`%${e.charCodeAt(0).toString(16).toUpperCase()}`)}function li(a){try{return decodeURIComponent(String(a||""))}catch{return String(a||"")}}function Ce(a){let e=a.indexOf(Kt);return e!==-1?a.substring(e+Kt.length):a}function di(a){let e=a||"";if(!e.trim())return!1;let t=e.trimStart();return t.startsWith("var ")||t.startsWith("let ")||t.startsWith("const ")||t.startsWith("function")||t.startsWith("return")||t.startsWith("//")||t.startsWith("/*")||e.includes("V8.")||e.includes("return ")||e.includes("=>")||e.includes("console.")||e.includes(";")||e.includes("{")||e.includes(`
17
+ `)}function zt(a){let e=a||"",t=e.trim();if(!t||t.length%4!==0||!/^[A-Za-z0-9+/]+={0,2}$/.test(t))return e;try{let n=Buffer.from(t,"base64").toString("utf8");if(!n||n.includes("\uFFFD"))return e;let i=t.replace(/=+$/,""),r=Buffer.from(n,"utf8").toString("base64").replace(/=+$/,"");return i!==r?e:di(n)?n:e}catch{return e}}function Tn(a,e){let n=z.relative(e,a).split(z.sep);if(n.length>=5&&(n[2]===Ve||n[2]==="api-engine")){let i=n[1],r=i.split(".")[0];if(n.length===5&&n[4]?.endsWith(".js")){let o=n[4].replace(".js",""),s=o.match(/\(([^)]+)\)$/);return s?{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:li(s[1])}:{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:o}}if(n.length>=6&&n[5]?.endsWith(".js"))return{serverDir:n[0],osClientDir:i,osClient:r,category:n[3],apiEngineKey:n[5].replace(".js","")}}return null}function vn(a,e){let n=z.relative(e,a).split(z.sep),i=r=>{let o=r.match(/[((]([^))]+)[))]\s*$/);return o?o[1]:r};if(n.length>=6&&n[2]===Te&&n[4]===ut){let r=n[1],o=r.split(".")[0],s=i(n[3]),c=n[5].replace(/\.js$/i,""),l=i(c);return{serverDir:n[0],osClientDir:r,osClient:o,formEngineKey:s,eventType:l}}if(n.length>=5&&(n[2]===un||n[2]==="v8-event"||n[2]==="v8-events")){let r=n[1],o=r.split(".")[0],s=i(n[3]);return{serverDir:n[0],osClientDir:r,osClient:o,formEngineKey:s,eventType:n[4].replace(/\.js$/i,"")}}return null}function me(a){return(a||new Date).toISOString().replace("T"," ").substring(0,19)}function En(a,e){let n=z.relative(e,a).split(z.sep);if(n.length<7||n[2]!==Te||n[4]!==Je)return null;let i=g=>{let d=g.match(/[((]([^))]+)[))]\s*$/);return d?d[1]:g},r=n[1],o=r.split(".")[0],s=i(n[3]),c=i(n[5]),l=n[6].replace(/\.js$/i,""),m=i(l);return{serverDir:n[0],osClientDir:r,osClient:o,tableName:s,fieldName:c,v8Key:m}}function wn(a,e){let n=z.relative(e,a).split(z.sep);if(n[2]!==ke)return null;let i=g=>{let d=g.match(/[((]([^))]+)[))]\s*$/);return d?d[1]:g},r=g=>g.replace(/[((][^))]+[))]\s*$/,"").trim()||g,o=n[1],s=o.split(".")[0],c=n.findIndex((g,d)=>d>2&&Object.prototype.hasOwnProperty.call($e,i(g)));if(c<=3)return null;let l=i(n[c-1]),m=i(n[c]);if(n.length>c+1&&n[c+1].endsWith(".js")){let g=n[c+1].replace(/\.js$/i,""),d=i(g),u=r(g).replace(/_显隐判断$/,"")||r(g),p=g.includes("\u663E\u9690\u5224\u65AD")?"V8CodeShow":"V8Code";return{serverDir:n[0],osClientDir:o,osClient:s,moduleId:l,btnField:m,btnId:d,btnName:u,v8SubField:p}}if(n.length>c+2&&n[c+2].endsWith(".js")){let g=i(n[c+1]),d=r(n[c+1]),u=n[c+2].replace(/\.js$/i,""),p=i(u);return p!=="V8Code"&&p!=="V8CodeShow"?null:{serverDir:n[0],osClientDir:o,osClient:s,moduleId:l,btnField:m,btnId:g,btnName:d,v8SubField:p}}return null}function bn(a,e){let n=z.relative(e,a).split(z.sep),i=n[n.length-1];if(n.length<5||n[2]!==ke||!i?.endsWith(".js"))return null;let r=l=>{let m=l.match(/[((]([^))]+)[))]\s*$/);return m?m[1]:l},o=r(i.replace(/\.js$/i,""));if(!Object.prototype.hasOwnProperty.call(qe,o))return null;let s=r(n[n.length-2]);if(!s)return null;let c=n[1];return{serverDir:n[0],osClientDir:c,osClient:c.split(".")[0],moduleId:s,scriptField:o}}function kn(a){let e=[],t=[{label:"tokens truncated",regex:/(?:\.\.\.|…)\s*[\d,.]+\s+tokens?\s+truncated\s*(?:\.\.\.|…)/i},{label:"Exit code",regex:/^\s*Exit code:\s*-?\d+\s*$/i},{label:"Process exited with code",regex:/^\s*Process exited with code\s+-?\d+\s*$/i},{label:"Chunk ID",regex:/^\s*Chunk ID:\s*\S+\s*$/i},{label:"Wall time",regex:/^\s*Wall time:\s*[\d.]+\s*(?:s|sec(?:ond)?s?)\s*$/i}];return a.replace(/\r\n/g,`
18
18
  `).split(`
19
- `).forEach((n,i)=>{for(let r of t)if(r.regex.test(n)){e.push({line:i+1,marker:r.label});break}}),e}function Dn(a,e){let n=z.relative(e,a).split(z.sep);if(n.length<7||n[2]!==Oe||n[4]!==mt||!n[6]?.endsWith(".js"))return null;let i=m=>{let g=m.match(/[((]([^))]+)[))]\s*$/);return g?g[1]:m},r=n[1],o=r.split(".")[0],s=i(n[3]),c=i(n[5]),d=i(n[6].replace(/\.js$/i,""));return{serverDir:n[0],osClientDir:r,osClient:o,flowDesignId:s,nodeId:c,eventType:d}}function Ye(a){return String(a).padStart(2,"0")}function In(a=new Date){return`${a.getFullYear()}-${Ye(a.getMonth()+1)}-${Ye(a.getDate())} ${Ye(a.getHours())}:${Ye(a.getMinutes())}:${Ye(a.getSeconds())}`}function Ie(a,e,t){let n=String(t??"").trim();!n||e.has(n)||(e.add(n),a.push(n))}function Xe(a){if(typeof a=="string")return a.trim()||"\u672A\u77E5\u9519\u8BEF";if(!a||typeof a!="object")return String(a??"\u672A\u77E5\u9519\u8BEF");let e=a,t=[],n=new Set;return Ie(t,n,e.message),Ie(t,n,e.code),Ie(t,n,e.syscall),e.address&&Ie(t,n,`address=${e.address}`),e.port!==void 0&&e.port!==null&&e.port!==""&&Ie(t,n,`port=${e.port}`),(Array.isArray(e.errors)?e.errors:[]).forEach(r=>Ie(t,n,Xe(r))),t.length||Ie(t,n,e.name),t.join(" | ")||"\u672A\u77E5\u9519\u8BEF"}var Y=class a{static init(){a._channel||(a._channel=oe.createOutputChannel("Microi \u543E\u7801"))}static get channel(){return a._channel}static log(e,t){a.init();let n=In();a._channel.appendLine(`[${n}] [${e}] ${t}`)}static appendLine(e){a.init(),a._channel.appendLine(e)}static show(e){a._channel.show(e)}static dispose(){a._channel?.dispose()}};function gi(a){return typeof a=="string"?a:a&&typeof a=="object"&&"title"in a?String(a.title||""):""}function Jt(a,e){return a.then(t=>{let n=gi(t);return n&&Y.log("\u901A\u77E5/\u64CD\u4F5C",`${e}\u901A\u77E5\u9009\u62E9\uFF1A${n}`),t})}var _=class{static info(e,...t){return Y.log("\u901A\u77E5/\u4FE1\u606F",e),Jt(oe.showInformationMessage(e,...t),"\u4FE1\u606F")}static warn(e,...t){return Y.log("\u901A\u77E5/\u8B66\u544A",e),Jt(oe.showWarningMessage(e,...t),"\u8B66\u544A")}static error(e,...t){return Y.log("\u901A\u77E5/\u9519\u8BEF",e),Jt(oe.showErrorMessage(e,...t),"\u9519\u8BEF")}};var I=class a{constructor(){this._activeProfileIndex=-1;this._syncDirCasingWarningShown=!1;this.defaultSettings={apiBaseUrl:"",osClient:"",localDir:"",showConsoleOnExecute:!0,profiles:[]}}static getInstance(){return a._instance||(a._instance=new a),a._instance}getWorkspaceConfigPath(){let e=this.getWorkspaceRoot();if(e)return pe.join(this.getDefaultSyncRootDir(e),dn)}getWorkspaceStateFilePath(e){let t=this.getWorkspaceRoot();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");return pe.join(this.getDefaultSyncRootDir(t),e)}readWorkspaceConfig(){let e=this.getWorkspaceConfigPath();if(!e||!H.existsSync(e))return{};try{let t=JSON.parse(H.readFileSync(e,"utf-8"));return t&&typeof t=="object"?t:{}}catch{return{}}}readWorkspaceConfigForUpdate(e){if(!H.existsSync(e))return{};let t;try{t=JSON.parse(H.readFileSync(e,"utf-8"))}catch(n){throw new Error(`Microi \u914D\u7F6E\u6587\u4EF6\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${e}\uFF08${n instanceof Error?n.message:String(n)}\uFF09`)}if(!t||typeof t!="object"||Array.isArray(t))throw new Error(`Microi \u914D\u7F6E\u6587\u4EF6\u5FC5\u987B\u662F JSON \u5BF9\u8C61\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${e}`);return t}writeWorkspaceConfig(e,t){H.mkdirSync(pe.dirname(e),{recursive:!0});let n=`${e}.${process.pid}.${Date.now()}.tmp`;try{H.writeFileSync(n,`${JSON.stringify(t,null,2)}
20
- `,"utf-8"),H.renameSync(n,e)}finally{try{H.existsSync(n)&&H.unlinkSync(n)}catch{}}}async mutateWorkspaceConfig(e){let t=this.getWorkspaceConfigPath();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");H.mkdirSync(pe.dirname(t),{recursive:!0});let n=`${t}.lock`,i=Date.now()+3e3,r;for(;r===void 0;)try{r=H.openSync(n,"wx",384),H.writeFileSync(r,JSON.stringify({pid:process.pid,createdAt:Date.now()}),"utf-8")}catch(o){if(o.code!=="EEXIST")throw o;try{Date.now()-H.statSync(n).mtimeMs>3e4&&H.unlinkSync(n)}catch{}if(Date.now()>=i)throw new Error("Microi \u914D\u7F6E\u6B63\u5728\u88AB CLI \u6216 VS Code \u63D2\u4EF6\u4FEE\u6539\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5");await new Promise(c=>setTimeout(c,40))}try{let o=this.readWorkspaceConfigForUpdate(t),s=this.normalizeSettings(e(o));return this.writeWorkspaceConfig(t,s),this.normalizeSettings(s)}finally{try{H.closeSync(r)}catch{}try{H.unlinkSync(n)}catch{}}}normalizeSettings(e){return{...this.defaultSettings,...e,profiles:Array.isArray(e.profiles)?e.profiles:[],showConsoleOnExecute:e.showConsoleOnExecute??this.defaultSettings.showConsoleOnExecute}}getSettings(){return this.normalizeSettings(this.readWorkspaceConfig())}async updateSettings(e){await this.mutateWorkspaceConfig(t=>({...t,...e}))}getProfiles(){return this.getSettings().profiles}async addProfile(e){await this.upsertProfiles([e])}async upsertProfiles(e){await this.mutateWorkspaceConfig(t=>{let n=Array.isArray(t.profiles)?[...t.profiles]:[];for(let i of e){let r=this.profileIdentity(i),o=n.findIndex(s=>this.profileIdentity(s)===r);if(o>=0){let s=n[o];n[o]={...s,...i,apiBaseUrl:s.apiBaseUrl,osClient:s.osClient}}else n.push(i)}return{...t,profiles:n}})}async removeProfile(e){let t=await this.mutateWorkspaceConfig(n=>{let i=Array.isArray(n.profiles)?[...n.profiles]:[];return i.splice(e,1),{...n,profiles:i}});this._activeProfileIndex>=t.profiles.length&&(this._activeProfileIndex=t.profiles.length-1)}profileIdentity(e){let t=String(e.apiBaseUrl||"").trim().replace(/\/+$/,""),n=t;try{let i=new URL(t);n=`${i.protocol.toLowerCase()}//${i.host.toLowerCase()}${i.pathname.replace(/\/+$/,"")}`}catch{n=t.toLowerCase()}return`${n}|${String(e.osClient||"").trim().toLowerCase()}`}setActiveProfile(e){this._activeProfileIndex=e}get activeProfileIndex(){return this._activeProfileIndex}getActiveProfile(){let e=this.getProfiles();if(this._activeProfileIndex>=0&&this._activeProfileIndex<e.length)return e[this._activeProfileIndex];let t=this.getSettings();return t.apiBaseUrl?{label:"",apiBaseUrl:t.apiBaseUrl,osClient:t.osClient}:e[0]}getWorkspaceRoot(){return Ge.workspaceFolders?.[0]?.uri.fsPath}getDefaultSyncRootDir(e){return this.ensureDefaultSyncDirCasing(e),pe.join(e,be)}ensureDefaultSyncDirCasing(e){try{if(!H.existsSync(e))return;let t=H.readdirSync(e,{withFileTypes:!0}).filter(s=>s.isDirectory());if(t.some(s=>s.name===be))return;let n=t.find(s=>s.name.toLowerCase()===be.toLowerCase());if(!n)return;let i=pe.join(e,n.name),r=pe.join(e,be),o=pe.join(e,`${be}.case-rename-${Date.now()}`);H.renameSync(i,o);try{H.renameSync(o,r)}catch(s){try{H.renameSync(o,i)}catch{}throw s}}catch{this._syncDirCasingWarningShown||(this._syncDirCasingWarningShown=!0,_.warn(`Microi: \u65E0\u6CD5\u5C06\u65E7\u540C\u6B65\u76EE\u5F55\u91CD\u547D\u540D\u4E3A ${be}\uFF0C\u8BF7\u5173\u95ED\u6B63\u5728\u5360\u7528 microi-v8-engine \u7684\u6587\u4EF6\u3001\u7EC8\u7AEF\u6216\u6269\u5C55\u7A97\u53E3\u540E\u91CD\u542F VS Code\uFF0C\u6216\u624B\u52A8\u6539\u540D\u3002`))}}getWorkspaceSecretKey(e){let t=this.getWorkspaceRoot()||"no-workspace",n=pe.resolve(t).toLowerCase(),i=Rn.createHash("sha256").update(n).digest("hex").slice(0,16);return`${e}.workspace.${i}`}getSyncRootDir(){let e=this.getSettings();if(e.localDir)return e.localDir;let t=this.getWorkspaceRoot();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");return this.getDefaultSyncRootDir(t)}getEngineDir(){return this.getSyncRootDir()}getEventDir(){return this.getSyncRootDir()}buildServerDirName(e,t){let n=t;try{n=new URL(t).host}catch{}return K(`${e||"\u672A\u547D\u540D"} (${n})`)}buildOsClientDirName(e,t,n){return K([e||"default",t||"default",n||"default"].join("."))}getApiBaseUrl(){let e=this.getActiveProfile();return e?.apiBaseUrl?e.apiBaseUrl:this.getSettings().apiBaseUrl||""}getOsClient(){let e=this.getActiveProfile();return e?.osClient?e.osClient:this.getSettings().osClient||""}};function _n(a){if(a?.Code===1001||a?.Code===1002)return!0;let e=String(a?.DataAppend?.ReasonCode||"").trim();if(/^(MissingToken|MalformedToken|MissingClaims|TenantMismatch|AuthVersionChanged|JwtExpired|SessionExpired|SessionMissing|TokenReplaced|SignatureMismatch)$/i.test(e))return!0;let t=[a?.Msg,a?.DataAppend?.UserMessage,a?.DataAppend?.AppendMsg].filter(Boolean).join(" ");return/Token签名|Token.*(无效|失效|过期)|登录.*(无效|失效|过期)|invalid\s*token|token\s*invalid|signature\s*mismatch/i.test(t)}function Ze(a){if(!_n(a))return!1;let e=String(a?.DataAppend?.ReasonCode||"").trim();if(/^(InvalidTenant|InvalidOsClient|TenantNotFound|TenantDisabled)$/i.test(e))return!0;let t=[a?.Msg,a?.DataAppend?.UserMessage,a?.DataAppend?.Hint].filter(Boolean).join(" ");return/无效的租户标识|租户不存在|租户.*未启用|invalid\s+(tenant|osclient)|tenant\s+not\s+found|unknown\s+tenant/i.test(t)}function yt(a){return _n(a)&&!Ze(a)}function Nn(a){return/^[a-f0-9]{64}$/i.test(String(a||"").trim())}function Pn(a){try{let t=String(a||"").replace(/^Bearer\s+/i,"").trim().split(".");if(t.length<2)return;let n=t[1].replace(/-/g,"+").replace(/_/g,"/"),i=JSON.parse(Buffer.from(n,"base64").toString("utf-8")),r=Number(i.MicroiTokenIssuedAt??i.iat);return Number.isFinite(r)&&r>0?r:void 0}catch{return}}function qt(a,e,t=!1){let n=String(a||"").trim(),i=String(e||"").trim();if(!n)return i;if(!i||i===n)return n;let r=Pn(n),o=Pn(i);return r!==void 0&&o!==void 0&&r!==o?o>r?i:n:r===void 0&&o!==void 0?i:o===void 0&&r!==void 0?n:t?i:n}var ht=class{constructor(){this.inFlight=new Map}async run(e,t){let n=this.inFlight.get(e);if(n)return n;let i=Promise.resolve().then(t);this.inFlight.set(e,i);try{return await i}finally{this.inFlight.get(e)===i&&this.inFlight.delete(e)}}};var Mn="microi.authTokenMap",L=class a{constructor(){this._token="";this._tokenMap={};this._authRecoveryGate=new ht}static getInstance(){return a._instance||(a._instance=new a),a._instance}setSecretStorage(e){this._secretStorage=e}setAuthRecoveryHandler(e){this._authRecoveryHandler=e}setTokenStateChangedHandler(e){this._tokenStateChangedHandler=e}async notifyTokenStateChanged(){if(this._tokenStateChangedHandler)try{await this._tokenStateChangedHandler()}catch{}}getDeviceId(){let e=Ge.workspaceFile?.fsPath||Ge.workspaceFolders?.map(n=>n.uri.fsPath).sort().join("|")||At.sessionId||"empty-window",t=Tt.createHash("sha256").update(e.toLowerCase()).digest("hex").slice(0,16);return`VSCode:${At.machineId||"Unknown"}:${t}`}tokenKey(e,t,n,i){return t?[e,t,n||"",i||""].join("|"):e}legacyCompactTokenKey(e,t,n,i){return[e,t,n,i].filter(Boolean).join("|")}legacyTokenScope(e,t){try{let n=e.trim().replace(/\/+$/,"").toLowerCase(),i=String(t||"").trim().toLowerCase(),r=I.getInstance().getProfiles().filter(s=>String(s.apiBaseUrl||"").trim().replace(/\/+$/,"").toLowerCase()===n);return{tenantKeyUnambiguous:r.filter(s=>String(s.osClient||"").trim().toLowerCase()===i).length<=1,apiKeyUnambiguous:r.length<=1}}catch{return{tenantKeyUnambiguous:!0,apiKeyUnambiguous:!0}}}tokenLookupKeys(e,t,n,i){let r=[],o=this.legacyTokenScope(e,t);if(t){let s=this.tokenKey(e,t,n,i),c=this.legacyCompactTokenKey(e,t,n,i);r.push(s),(c===s||o.tenantKeyUnambiguous)&&r.push(c),n&&o.tenantKeyUnambiguous&&r.push(this.legacyCompactTokenKey(e,t,n)),o.tenantKeyUnambiguous&&r.push(this.legacyCompactTokenKey(e,t))}return(!t||o.apiKeyUnambiguous)&&r.push(e),Array.from(new Set(r))}async persistTokens(){if(!this._secretStorage)return;let e=I.getInstance(),t=e.getWorkspaceSecretKey(Ht),n=e.getWorkspaceSecretKey(Mn);this._token?await this._secretStorage.store(t,this._token):await this._secretStorage.delete(t),Object.keys(this._tokenMap).length>0?await this._secretStorage.store(n,JSON.stringify(this._tokenMap)):await this._secretStorage.delete(n)}async setToken(e,t,n,i,r){this._token=e,t&&(this._tokenMap[this.tokenKey(t,n,i,r)]=e),await this.persistTokens(),await this.notifyTokenStateChanged()}async loadToken(){if(this._token)return this._token;if(this._secretStorage){let e=I.getInstance();this._token=await this._secretStorage.get(e.getWorkspaceSecretKey(Ht))||"";try{let t=await this._secretStorage.get(e.getWorkspaceSecretKey(Mn));t&&(this._tokenMap=JSON.parse(t))}catch{}}return this._token}getTokenForServer(e,t,n,i){for(let r of this.tokenLookupKeys(e,t,n,i))if(this._tokenMap[r])return this._tokenMap[r];return""}getExactTokenForServer(e,t,n,i){return this._tokenMap[this.tokenKey(e,t,n,i)]||""}async adoptTokenFromSharedFile(e,t,n,i,r){this._token=e,this._tokenMap[this.tokenKey(t,n,i,r)]=e,await this.persistTokens()}async clearTokenForServer(e,t,n,i,r){let o=!1;for(let s of this.tokenLookupKeys(e,t,n,i))this._tokenMap[s]&&(!r||this._tokenMap[s]===r)&&(delete this._tokenMap[s],o=!0);this._token&&(!r||this._token===r)&&(this._token="",o=!0),o&&(await this.persistTokens(),await this.notifyTokenStateChanged())}async clearToken(){this._token="",this._tokenMap={},await this.persistTokens(),await this.notifyTokenStateChanged()}get hasToken(){return!!this._token||Object.keys(this._tokenMap).length>0}isInvalidRefreshToken(e,t){if(t===401||t===403)return!0;let n=String(e?.DataAppend?.ReasonCode||"");if(/^(MissingToken|MalformedToken|MissingClaims|TenantMismatch|AuthVersionChanged|JwtExpired|SessionExpired|SessionMissing|TokenReplaced)$/i.test(n))return!0;let i=e?.Msg||"";return e?.Code!==1&&/无效.*Token|Token.*无效|Token.*过期|登录.*过期|租户.*不一致|invalid\s*token|token\s*invalid/i.test(i)}serializeRequestBody(e,t){if(t==="form"){let n=new URLSearchParams;if(e&&typeof e=="object"&&!Array.isArray(e))for(let[i,r]of Object.entries(e))r!=null&&n.append(i,typeof r=="object"?JSON.stringify(r):String(r));return n.toString()}return JSON.stringify(e)}maskSensitiveBody(e){if(!e||typeof e!="object")return e;if(Array.isArray(e))return e.map(n=>this.maskSensitiveBody(n));let t={};for(let[n,i]of Object.entries(e))/^(pwd|password|authorization|token)$/i.test(n)?t[n]="***":i&&typeof i=="object"?t[n]=this.maskSensitiveBody(i):t[n]=i;return t}async refreshTokenForRequest(e,t,n){if(!t)return!1;let i=I.getInstance(),r=e.osClient||i.getOsClient()||"",o=new URL(n),c=o.pathname.replace(/\/+$/,"")+x.REFRESH_TOKEN,d=o.protocol==="https:",m=d?St:Ct,g=JSON.stringify({authorization:t,OsClient:r||void 0,_ClientType:"VSCode"}),l={hostname:o.hostname,port:o.port||(d?443:80),path:c,method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json",Authorization:`Bearer ${t}`,did:this.getDeviceId(),"Content-Length":Buffer.byteLength(g),...r?{OsClient:r}:{}},timeout:e.timeout||3e4,rejectUnauthorized:!1};return Y.log("API",`\u{1F504} RefreshToken ${n}${c}`),new Promise(u=>{let p=m.request(l,h=>{let f=[];h.on("data",y=>f.push(y)),h.on("end",async()=>{let y=Buffer.concat(f).toString("utf-8"),S;try{S=JSON.parse(y)}catch{}let C=h.headers,w=h.statusCode||0,R=C.authorization||"";if(S?.Code===1&&R){await this.setToken(R,e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork),Y.log("API","\u2705 Token \u5DF2\u4EE5\u65E7\u6362\u65B0"),u(!0);return}this.isInvalidRefreshToken(S,w)&&await this.clearTokenForServer(e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork,t),Y.log("API",`\u26A0\uFE0F RefreshToken \u5931\u8D25: ${S?.Msg||y.slice(0,120)}`),u(!1)})});p.on("error",h=>{Y.log("API",`\u274C RefreshToken Error: ${h.message}`),u(!1)}),p.on("timeout",()=>{p.destroy(),u(!1)}),p.write(g),p.end()})}async recoverAuthForRequest(e,t){if(!this._authRecoveryHandler)return!1;let n=I.getInstance(),i={apiBaseUrl:e.apiBaseUrl||t,osClient:e.osClient||n.getOsClient()||void 0,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork},r=this.tokenKey(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork);return this._authRecoveryGate.run(r,()=>this._authRecoveryHandler(i))}async request(e){let t=I.getInstance(),n=e.apiBaseUrl||t.getApiBaseUrl();if(!n)throw new Error('\u672A\u914D\u7F6E API \u5730\u5740\uFF0C\u8BF7\u5148\u6267\u884C "Microi: \u914D\u7F6E\u8FDE\u63A5"');let i=new URL(n),o=i.pathname.replace(/\/+$/,"")+e.path;if(e.params){let f=new URLSearchParams;for(let[S,C]of Object.entries(e.params))C!==void 0&&C!==""&&f.append(S,C);let y=f.toString();y&&(o+=`?${y}`)}let s=i.protocol==="https:",c=s?St:Ct,d=e.bodyFormat||"json",m=e.body!==void 0?this.serializeRequestBody(e.body,d):void 0,g={hostname:i.hostname,port:i.port||(s?443:80),path:o,method:e.method,headers:{"Content-Type":d==="form"?"application/x-www-form-urlencoded":"application/json",Accept:"application/json",did:this.getDeviceId()},timeout:e.timeout||3e4,rejectUnauthorized:!1};m!==void 0&&(g.headers["Content-Length"]=Buffer.byteLength(m));let l=e.allowAuthRetry!==!1,u=e.osClient||t.getOsClient()||"";u&&(g.headers.OsClient=u);let p=e.apiBaseUrl?this.getTokenForServer(e.apiBaseUrl,e.osClient,e.osClientType,e.osClientNetwork):await this.loadToken();p&&(g.headers.Authorization=`Bearer ${p}`);let h=`${n}${o}`;if(e.silent||Y.log("API",`\u27A1\uFE0F ${e.method} ${h}`),e.body&&!e.silent){let f=JSON.stringify(this.maskSensitiveBody(e.body));Y.appendLine(` Body: ${f.length>500?f.substring(0,500)+"...(truncated)":f}`)}return new Promise((f,y)=>{let S=c.request(g,w=>{let R=[];w.on("data",E=>R.push(E)),w.on("end",async()=>{let E=Buffer.concat(R).toString("utf-8"),b=w.statusCode||0;if(!e.silent){Y.log("API",`\u2B05\uFE0F ${b} ${e.method} ${e.path}`);let U=E.length>500?E.substring(0,500)+"...(truncated)":E;Y.appendLine(` Response: ${U}`)}let V;try{V=JSON.parse(E)}catch{}if(V){let U={};for(let[P,O]of Object.entries(w.headers))typeof O=="string"&&(U[P.toLowerCase()]=O);V._headers=U;let A=U.authorization||"";if(A&&A!==p&&await this.setToken(A,e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork),l&&Ze(V))Y.log("API",`\u26A0\uFE0F \u79DF\u6237\u8FDE\u63A5\u914D\u7F6E\u65E0\u6548\uFF0C\u5DF2\u505C\u6B62 token \u5237\u65B0\u4E0E\u9759\u9ED8\u91CD\u767B: ${V.Msg||""}`);else if(l&&yt(V)&&(Y.log("API",`\u{1F510} \u8EAB\u4EFD\u5DF2\u8FC7\u671F\uFF0C\u5C1D\u8BD5\u4F7F\u7528\u65E7 token \u5237\u65B0\u540E\u91CD\u8BD5: ${V.Msg||""}`),await this.refreshTokenForRequest(e,p,n)||await this.recoverAuthForRequest(e,n))){try{f(await this.request({...e,allowAuthRetry:!1}))}catch(F){y(F)}return}f(V)}else if(b===401||b===403){if(l&&(await this.refreshTokenForRequest(e,p,n)||await this.recoverAuthForRequest(e,n))){try{f(await this.request({...e,allowAuthRetry:!1}))}catch(P){y(P)}return}y(new Error(`\u8EAB\u4EFD\u9A8C\u8BC1\u5931\u8D25 (HTTP ${b})\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55`))}else if(b>=400){let U=E.replace(/<[^>]+>/g," ").replace(/\s+/g," ").trim().substring(0,120);y(new Error(`\u670D\u52A1\u5668\u9519\u8BEF (HTTP ${b}): ${U||"\u672A\u77E5\u9519\u8BEF"}`))}else y(new Error(`\u54CD\u5E94\u89E3\u6790\u5931\u8D25 (HTTP ${b}): ${E.substring(0,200)}`))})}),C=!1;S.on("error",w=>{if(C)return;let R=Xe(w);e.silent||Y.log("API",`\u274C ${e.method} ${e.path} Error: ${R}`),y(new Error(`\u8BF7\u6C42\u5931\u8D25: ${R}`))}),S.on("timeout",()=>{C=!0,S.destroy(),e.silent||Y.log("API",`\u23F0 ${e.method} ${e.path} Timeout`),y(new Error("\u8BF7\u6C42\u8D85\u65F6"))}),m!==void 0&&S.write(m),S.end()})}async get(e,t,n,i){return this.request({method:"GET",path:e,params:t,apiBaseUrl:n,osClient:i?.osClient,osClientType:i?.osClientType,osClientNetwork:i?.osClientNetwork})}async post(e,t,n,i,r,o,s){return this.request({method:"POST",path:e,body:t,params:n,apiBaseUrl:i,osClient:r?.osClient,osClientType:r?.osClientType,osClientNetwork:r?.osClientNetwork,timeout:o,silent:s})}async getRaw(e,t,n){let i=I.getInstance(),r=n||i.getApiBaseUrl();if(!r)throw new Error("\u672A\u914D\u7F6E API \u5730\u5740");let o=new URL(r),c=o.pathname.replace(/\/+$/,"")+e;if(t){let l=new URLSearchParams;for(let[p,h]of Object.entries(t))h!==void 0&&h!==""&&l.append(p,h);let u=l.toString();u&&(c+=`?${u}`)}let d=o.protocol==="https:",m=d?St:Ct,g={hostname:o.hostname,port:o.port||(d?443:80),path:c,method:"GET",timeout:15e3,rejectUnauthorized:!1};return new Promise((l,u)=>{let p=m.request(g,h=>{let f=[];h.on("data",y=>f.push(y)),h.on("end",()=>{let y=Buffer.concat(f),S=h.headers.captchaid||"";l({data:y,captchaId:S,statusCode:h.statusCode||0,contentType:String(h.headers["content-type"]||"")})})});p.on("error",h=>u(new Error(`\u8BF7\u6C42\u5931\u8D25: ${h.message}`))),p.on("timeout",()=>{p.destroy(),u(new Error("\u8BF7\u6C42\u8D85\u65F6"))}),p.end()})}async postMultipartFile(e,t,n,i,r,o,s=30*60*1e3){let c=Ue.realpathSync(n),d=Ue.lstatSync(c);if(!d.isFile()||d.isSymbolicLink())throw new Error(`\u4E0A\u4F20\u8D44\u4EA7\u5FC5\u987B\u662F\u666E\u901A\u6587\u4EF6\u4E14\u4E0D\u80FD\u662F\u7B26\u53F7\u94FE\u63A5\uFF1A${n}`);if(!i||/[\r\n"]/u.test(i))throw new Error("\u4E0A\u4F20\u6587\u4EF6\u540D\u4E0D\u5408\u6CD5");let m=String(r||"").replace(/\/+$/,""),g=new URL(m),l=`----microi-vscode-${Tt.randomBytes(24).toString("hex")}`,u=Object.entries(t).map(([E,b])=>Buffer.from(`--${l}\r
19
+ `).forEach((n,i)=>{for(let r of t)if(r.regex.test(n)){e.push({line:i+1,marker:r.label});break}}),e}function Dn(a,e){let n=z.relative(e,a).split(z.sep);if(n.length<7||n[2]!==Oe||n[4]!==mt||!n[6]?.endsWith(".js"))return null;let i=m=>{let g=m.match(/[((]([^))]+)[))]\s*$/);return g?g[1]:m},r=n[1],o=r.split(".")[0],s=i(n[3]),c=i(n[5]),l=i(n[6].replace(/\.js$/i,""));return{serverDir:n[0],osClientDir:r,osClient:o,flowDesignId:s,nodeId:c,eventType:l}}function Ye(a){return String(a).padStart(2,"0")}function In(a=new Date){return`${a.getFullYear()}-${Ye(a.getMonth()+1)}-${Ye(a.getDate())} ${Ye(a.getHours())}:${Ye(a.getMinutes())}:${Ye(a.getSeconds())}`}function Ie(a,e,t){let n=String(t??"").trim();!n||e.has(n)||(e.add(n),a.push(n))}function Xe(a){if(typeof a=="string")return a.trim()||"\u672A\u77E5\u9519\u8BEF";if(!a||typeof a!="object")return String(a??"\u672A\u77E5\u9519\u8BEF");let e=a,t=[],n=new Set;return Ie(t,n,e.message),Ie(t,n,e.code),Ie(t,n,e.syscall),e.address&&Ie(t,n,`address=${e.address}`),e.port!==void 0&&e.port!==null&&e.port!==""&&Ie(t,n,`port=${e.port}`),(Array.isArray(e.errors)?e.errors:[]).forEach(r=>Ie(t,n,Xe(r))),t.length||Ie(t,n,e.name),t.join(" | ")||"\u672A\u77E5\u9519\u8BEF"}var Y=class a{static init(){a._channel||(a._channel=oe.createOutputChannel("Microi \u543E\u7801"))}static get channel(){return a._channel}static log(e,t){a.init();let n=In();a._channel.appendLine(`[${n}] [${e}] ${t}`)}static appendLine(e){a.init(),a._channel.appendLine(e)}static show(e){a._channel.show(e)}static dispose(){a._channel?.dispose()}};function gi(a){return typeof a=="string"?a:a&&typeof a=="object"&&"title"in a?String(a.title||""):""}function Jt(a,e){return a.then(t=>{let n=gi(t);return n&&Y.log("\u901A\u77E5/\u64CD\u4F5C",`${e}\u901A\u77E5\u9009\u62E9\uFF1A${n}`),t})}var _=class{static info(e,...t){return Y.log("\u901A\u77E5/\u4FE1\u606F",e),Jt(oe.showInformationMessage(e,...t),"\u4FE1\u606F")}static warn(e,...t){return Y.log("\u901A\u77E5/\u8B66\u544A",e),Jt(oe.showWarningMessage(e,...t),"\u8B66\u544A")}static error(e,...t){return Y.log("\u901A\u77E5/\u9519\u8BEF",e),Jt(oe.showErrorMessage(e,...t),"\u9519\u8BEF")}};var I=class a{constructor(){this._activeProfileIndex=-1;this._syncDirCasingWarningShown=!1;this.defaultSettings={apiBaseUrl:"",osClient:"",localDir:"",showConsoleOnExecute:!0,profiles:[]}}static getInstance(){return a._instance||(a._instance=new a),a._instance}getWorkspaceConfigPath(){let e=this.getWorkspaceRoot();if(e)return pe.join(this.getDefaultSyncRootDir(e),dn)}getWorkspaceStateFilePath(e){let t=this.getWorkspaceRoot();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");return pe.join(this.getDefaultSyncRootDir(t),e)}readWorkspaceConfig(){let e=this.getWorkspaceConfigPath();if(!e||!H.existsSync(e))return{};try{let t=JSON.parse(H.readFileSync(e,"utf-8"));return t&&typeof t=="object"?t:{}}catch{return{}}}readWorkspaceConfigForUpdate(e){if(!H.existsSync(e))return{};let t;try{t=JSON.parse(H.readFileSync(e,"utf-8"))}catch(n){throw new Error(`Microi \u914D\u7F6E\u6587\u4EF6\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${e}\uFF08${n instanceof Error?n.message:String(n)}\uFF09`)}if(!t||typeof t!="object"||Array.isArray(t))throw new Error(`Microi \u914D\u7F6E\u6587\u4EF6\u5FC5\u987B\u662F JSON \u5BF9\u8C61\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${e}`);return t}writeWorkspaceConfig(e,t){H.mkdirSync(pe.dirname(e),{recursive:!0});let n=`${e}.${process.pid}.${Date.now()}.tmp`;try{H.writeFileSync(n,`${JSON.stringify(t,null,2)}
20
+ `,"utf-8"),H.renameSync(n,e)}finally{try{H.existsSync(n)&&H.unlinkSync(n)}catch{}}}async mutateWorkspaceConfig(e){let t=this.getWorkspaceConfigPath();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");H.mkdirSync(pe.dirname(t),{recursive:!0});let n=`${t}.lock`,i=Date.now()+3e3,r;for(;r===void 0;)try{r=H.openSync(n,"wx",384),H.writeFileSync(r,JSON.stringify({pid:process.pid,createdAt:Date.now()}),"utf-8")}catch(o){if(o.code!=="EEXIST")throw o;try{Date.now()-H.statSync(n).mtimeMs>3e4&&H.unlinkSync(n)}catch{}if(Date.now()>=i)throw new Error("Microi \u914D\u7F6E\u6B63\u5728\u88AB CLI \u6216 VS Code \u63D2\u4EF6\u4FEE\u6539\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5");await new Promise(c=>setTimeout(c,40))}try{let o=this.readWorkspaceConfigForUpdate(t),s=this.normalizeSettings(e(o));return this.writeWorkspaceConfig(t,s),this.normalizeSettings(s)}finally{try{H.closeSync(r)}catch{}try{H.unlinkSync(n)}catch{}}}normalizeSettings(e){return{...this.defaultSettings,...e,profiles:Array.isArray(e.profiles)?e.profiles:[],showConsoleOnExecute:e.showConsoleOnExecute??this.defaultSettings.showConsoleOnExecute}}getSettings(){return this.normalizeSettings(this.readWorkspaceConfig())}async updateSettings(e){await this.mutateWorkspaceConfig(t=>({...t,...e}))}getProfiles(){return this.getSettings().profiles}findProfileByIdentity(e,t){let n=this.profileIdentity({apiBaseUrl:e,osClient:t});return this.getProfiles().find(i=>this.profileIdentity(i)===n)}async addProfile(e){await this.upsertProfiles([e])}async upsertProfiles(e){await this.mutateWorkspaceConfig(t=>{let n=Array.isArray(t.profiles)?[...t.profiles]:[];for(let i of e){let r=this.profileIdentity(i),o=n.findIndex(s=>this.profileIdentity(s)===r);if(o>=0){let s=n[o];n[o]={...s,...i,apiBaseUrl:s.apiBaseUrl,osClient:s.osClient}}else n.push(i)}return{...t,profiles:n}})}async removeProfile(e){let t=await this.mutateWorkspaceConfig(n=>{let i=Array.isArray(n.profiles)?[...n.profiles]:[];return i.splice(e,1),{...n,profiles:i}});this._activeProfileIndex>=t.profiles.length&&(this._activeProfileIndex=t.profiles.length-1)}profileIdentity(e){let t=String(e.apiBaseUrl||"").trim().replace(/\/+$/,""),n=t;try{let i=new URL(t);n=`${i.protocol.toLowerCase()}//${i.host.toLowerCase()}${i.pathname.replace(/\/+$/,"")}`}catch{n=t.toLowerCase()}return`${n}|${String(e.osClient||"").trim().toLowerCase()}`}setActiveProfile(e){this._activeProfileIndex=e}get activeProfileIndex(){return this._activeProfileIndex}getActiveProfile(){let e=this.getProfiles();if(this._activeProfileIndex>=0&&this._activeProfileIndex<e.length)return e[this._activeProfileIndex];let t=this.getSettings();return t.apiBaseUrl?{label:"",apiBaseUrl:t.apiBaseUrl,osClient:t.osClient}:e[0]}getWorkspaceRoot(){return Ge.workspaceFolders?.[0]?.uri.fsPath}getDefaultSyncRootDir(e){return this.ensureDefaultSyncDirCasing(e),pe.join(e,be)}ensureDefaultSyncDirCasing(e){try{if(!H.existsSync(e))return;let t=H.readdirSync(e,{withFileTypes:!0}).filter(s=>s.isDirectory());if(t.some(s=>s.name===be))return;let n=t.find(s=>s.name.toLowerCase()===be.toLowerCase());if(!n)return;let i=pe.join(e,n.name),r=pe.join(e,be),o=pe.join(e,`${be}.case-rename-${Date.now()}`);H.renameSync(i,o);try{H.renameSync(o,r)}catch(s){try{H.renameSync(o,i)}catch{}throw s}}catch{this._syncDirCasingWarningShown||(this._syncDirCasingWarningShown=!0,_.warn(`Microi: \u65E0\u6CD5\u5C06\u65E7\u540C\u6B65\u76EE\u5F55\u91CD\u547D\u540D\u4E3A ${be}\uFF0C\u8BF7\u5173\u95ED\u6B63\u5728\u5360\u7528 microi-v8-engine \u7684\u6587\u4EF6\u3001\u7EC8\u7AEF\u6216\u6269\u5C55\u7A97\u53E3\u540E\u91CD\u542F VS Code\uFF0C\u6216\u624B\u52A8\u6539\u540D\u3002`))}}getWorkspaceSecretKey(e){let t=this.getWorkspaceRoot()||"no-workspace",n=pe.resolve(t).toLowerCase(),i=Rn.createHash("sha256").update(n).digest("hex").slice(0,16);return`${e}.workspace.${i}`}getSyncRootDir(){let e=this.getSettings();if(e.localDir)return e.localDir;let t=this.getWorkspaceRoot();if(!t)throw new Error("\u8BF7\u5148\u6253\u5F00\u4E00\u4E2A\u5DE5\u4F5C\u533A");return this.getDefaultSyncRootDir(t)}getEngineDir(){return this.getSyncRootDir()}getEventDir(){return this.getSyncRootDir()}buildServerDirName(e,t){let n=t;try{n=new URL(t).host}catch{}return K(`${e||"\u672A\u547D\u540D"} (${n})`)}buildOsClientDirName(e,t,n){return K([e||"default",t||"default",n||"default"].join("."))}getApiBaseUrl(){let e=this.getActiveProfile();return e?.apiBaseUrl?e.apiBaseUrl:this.getSettings().apiBaseUrl||""}getOsClient(){let e=this.getActiveProfile();return e?.osClient?e.osClient:this.getSettings().osClient||""}};function _n(a){if(a?.Code===1001||a?.Code===1002)return!0;let e=String(a?.DataAppend?.ReasonCode||"").trim();if(/^(MissingToken|MalformedToken|MissingClaims|TenantMismatch|AuthVersionChanged|JwtExpired|SessionExpired|SessionMissing|TokenReplaced|SignatureMismatch)$/i.test(e))return!0;let t=[a?.Msg,a?.DataAppend?.UserMessage,a?.DataAppend?.AppendMsg].filter(Boolean).join(" ");return/Token签名|Token.*(无效|失效|过期)|登录.*(无效|失效|过期)|invalid\s*token|token\s*invalid|signature\s*mismatch/i.test(t)}function Ze(a){if(!_n(a))return!1;let e=String(a?.DataAppend?.ReasonCode||"").trim();if(/^(InvalidTenant|InvalidOsClient|TenantNotFound|TenantDisabled)$/i.test(e))return!0;let t=[a?.Msg,a?.DataAppend?.UserMessage,a?.DataAppend?.Hint].filter(Boolean).join(" ");return/无效的租户标识|租户不存在|租户.*未启用|invalid\s+(tenant|osclient)|tenant\s+not\s+found|unknown\s+tenant/i.test(t)}function yt(a){return _n(a)&&!Ze(a)}function Nn(a){return/^[a-f0-9]{64}$/i.test(String(a||"").trim())}function Pn(a){try{let t=String(a||"").replace(/^Bearer\s+/i,"").trim().split(".");if(t.length<2)return;let n=t[1].replace(/-/g,"+").replace(/_/g,"/"),i=JSON.parse(Buffer.from(n,"base64").toString("utf-8")),r=Number(i.MicroiTokenIssuedAt??i.iat);return Number.isFinite(r)&&r>0?r:void 0}catch{return}}function qt(a,e,t=!1){let n=String(a||"").trim(),i=String(e||"").trim();if(!n)return i;if(!i||i===n)return n;let r=Pn(n),o=Pn(i);return r!==void 0&&o!==void 0&&r!==o?o>r?i:n:r===void 0&&o!==void 0?i:o===void 0&&r!==void 0?n:t?i:n}var ht=class{constructor(){this.inFlight=new Map}async run(e,t){let n=this.inFlight.get(e);if(n)return n;let i=Promise.resolve().then(t);this.inFlight.set(e,i);try{return await i}finally{this.inFlight.get(e)===i&&this.inFlight.delete(e)}}};var Mn="microi.authTokenMap",L=class a{constructor(){this._token="";this._tokenMap={};this._authRecoveryGate=new ht}static getInstance(){return a._instance||(a._instance=new a),a._instance}setSecretStorage(e){this._secretStorage=e}setAuthRecoveryHandler(e){this._authRecoveryHandler=e}setTokenStateChangedHandler(e){this._tokenStateChangedHandler=e}async notifyTokenStateChanged(){if(this._tokenStateChangedHandler)try{await this._tokenStateChangedHandler()}catch{}}getDeviceId(){let e=Ge.workspaceFile?.fsPath||Ge.workspaceFolders?.map(n=>n.uri.fsPath).sort().join("|")||At.sessionId||"empty-window",t=Tt.createHash("sha256").update(e.toLowerCase()).digest("hex").slice(0,16);return`VSCode:${At.machineId||"Unknown"}:${t}`}tokenKey(e,t,n,i){return t?[e,t,n||"",i||""].join("|"):e}legacyCompactTokenKey(e,t,n,i){return[e,t,n,i].filter(Boolean).join("|")}legacyTokenScope(e,t){try{let n=e.trim().replace(/\/+$/,"").toLowerCase(),i=String(t||"").trim().toLowerCase(),r=I.getInstance().getProfiles().filter(s=>String(s.apiBaseUrl||"").trim().replace(/\/+$/,"").toLowerCase()===n);return{tenantKeyUnambiguous:r.filter(s=>String(s.osClient||"").trim().toLowerCase()===i).length<=1,apiKeyUnambiguous:r.length<=1}}catch{return{tenantKeyUnambiguous:!0,apiKeyUnambiguous:!0}}}tokenLookupKeys(e,t,n,i){let r=[],o=this.legacyTokenScope(e,t);if(t){let s=this.tokenKey(e,t,n,i),c=this.tokenKey(e,t,"",""),l=this.legacyCompactTokenKey(e,t,n,i);r.push(s),o.tenantKeyUnambiguous&&r.push(c),(l===s||o.tenantKeyUnambiguous)&&r.push(l),n&&o.tenantKeyUnambiguous&&r.push(this.legacyCompactTokenKey(e,t,n)),o.tenantKeyUnambiguous&&r.push(this.legacyCompactTokenKey(e,t))}return(!t||o.apiKeyUnambiguous)&&r.push(e),Array.from(new Set(r))}async persistTokens(){if(!this._secretStorage)return;let e=I.getInstance(),t=e.getWorkspaceSecretKey(Ht),n=e.getWorkspaceSecretKey(Mn);this._token?await this._secretStorage.store(t,this._token):await this._secretStorage.delete(t),Object.keys(this._tokenMap).length>0?await this._secretStorage.store(n,JSON.stringify(this._tokenMap)):await this._secretStorage.delete(n)}async setToken(e,t,n,i,r){this._token=e,t&&(this._tokenMap[this.tokenKey(t,n,i,r)]=e),await this.persistTokens(),await this.notifyTokenStateChanged()}async loadToken(){if(this._token)return this._token;if(this._secretStorage){let e=I.getInstance();this._token=await this._secretStorage.get(e.getWorkspaceSecretKey(Ht))||"";try{let t=await this._secretStorage.get(e.getWorkspaceSecretKey(Mn));t&&(this._tokenMap=JSON.parse(t))}catch{}}return this._token}getTokenForServer(e,t,n,i){for(let r of this.tokenLookupKeys(e,t,n,i))if(this._tokenMap[r])return this._tokenMap[r];return""}getExactTokenForServer(e,t,n,i){return this._tokenMap[this.tokenKey(e,t,n,i)]||""}async adoptTokenFromSharedFile(e,t,n,i,r){this._token=e,this._tokenMap[this.tokenKey(t,n,i,r)]=e,await this.persistTokens()}async clearTokenForServer(e,t,n,i,r){let o=!1;for(let s of this.tokenLookupKeys(e,t,n,i))this._tokenMap[s]&&(!r||this._tokenMap[s]===r)&&(delete this._tokenMap[s],o=!0);this._token&&(!r||this._token===r)&&(this._token="",o=!0),o&&(await this.persistTokens(),await this.notifyTokenStateChanged())}async clearToken(){this._token="",this._tokenMap={},await this.persistTokens(),await this.notifyTokenStateChanged()}get hasToken(){return!!this._token||Object.keys(this._tokenMap).length>0}isInvalidRefreshToken(e,t){if(t===401||t===403)return!0;let n=String(e?.DataAppend?.ReasonCode||"");if(/^(MissingToken|MalformedToken|MissingClaims|TenantMismatch|AuthVersionChanged|JwtExpired|SessionExpired|SessionMissing|TokenReplaced)$/i.test(n))return!0;let i=e?.Msg||"";return e?.Code!==1&&/无效.*Token|Token.*无效|Token.*过期|登录.*过期|租户.*不一致|invalid\s*token|token\s*invalid/i.test(i)}serializeRequestBody(e,t){if(t==="form"){let n=new URLSearchParams;if(e&&typeof e=="object"&&!Array.isArray(e))for(let[i,r]of Object.entries(e))r!=null&&n.append(i,typeof r=="object"?JSON.stringify(r):String(r));return n.toString()}return JSON.stringify(e)}maskSensitiveBody(e){if(!e||typeof e!="object")return e;if(Array.isArray(e))return e.map(n=>this.maskSensitiveBody(n));let t={};for(let[n,i]of Object.entries(e))/^(pwd|password|authorization|token)$/i.test(n)?t[n]="***":i&&typeof i=="object"?t[n]=this.maskSensitiveBody(i):t[n]=i;return t}async refreshTokenForRequest(e,t,n){if(!t)return!1;let i=I.getInstance(),r=e.osClient||i.getOsClient()||"",o=new URL(n),c=o.pathname.replace(/\/+$/,"")+x.REFRESH_TOKEN,l=o.protocol==="https:",m=l?St:Ct,g=JSON.stringify({authorization:t,OsClient:r||void 0,_ClientType:"VSCode"}),d={hostname:o.hostname,port:o.port||(l?443:80),path:c,method:"POST",headers:{"Content-Type":"application/json",Accept:"application/json",Authorization:`Bearer ${t}`,did:this.getDeviceId(),"Content-Length":Buffer.byteLength(g),...r?{OsClient:r}:{}},timeout:e.timeout||3e4,rejectUnauthorized:!1};return Y.log("API",`\u{1F504} RefreshToken ${n}${c}`),new Promise(u=>{let p=m.request(d,h=>{let f=[];h.on("data",y=>f.push(y)),h.on("end",async()=>{let y=Buffer.concat(f).toString("utf-8"),S;try{S=JSON.parse(y)}catch{}let C=h.headers,w=h.statusCode||0,R=C.authorization||"";if(S?.Code===1&&R){await this.setToken(R,e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork),Y.log("API","\u2705 Token \u5DF2\u4EE5\u65E7\u6362\u65B0"),u(!0);return}this.isInvalidRefreshToken(S,w)&&await this.clearTokenForServer(e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork,t),Y.log("API",`\u26A0\uFE0F RefreshToken \u5931\u8D25: ${S?.Msg||y.slice(0,120)}`),u(!1)})});p.on("error",h=>{Y.log("API",`\u274C RefreshToken Error: ${h.message}`),u(!1)}),p.on("timeout",()=>{p.destroy(),u(!1)}),p.write(g),p.end()})}async recoverAuthForRequest(e,t){if(!this._authRecoveryHandler)return!1;let n=I.getInstance(),i={apiBaseUrl:e.apiBaseUrl||t,osClient:e.osClient||n.getOsClient()||void 0,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork},r=this.tokenKey(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork);return this._authRecoveryGate.run(r,()=>this._authRecoveryHandler(i))}async request(e){let t=I.getInstance(),n=e.apiBaseUrl||t.getApiBaseUrl();if(!n)throw new Error('\u672A\u914D\u7F6E API \u5730\u5740\uFF0C\u8BF7\u5148\u6267\u884C "Microi: \u914D\u7F6E\u8FDE\u63A5"');let i=new URL(n),o=i.pathname.replace(/\/+$/,"")+e.path;if(e.params){let f=new URLSearchParams;for(let[S,C]of Object.entries(e.params))C!==void 0&&C!==""&&f.append(S,C);let y=f.toString();y&&(o+=`?${y}`)}let s=i.protocol==="https:",c=s?St:Ct,l=e.bodyFormat||"json",m=e.body!==void 0?this.serializeRequestBody(e.body,l):void 0,g={hostname:i.hostname,port:i.port||(s?443:80),path:o,method:e.method,headers:{"Content-Type":l==="form"?"application/x-www-form-urlencoded":"application/json",Accept:"application/json",did:this.getDeviceId()},timeout:e.timeout||3e4,rejectUnauthorized:!1};m!==void 0&&(g.headers["Content-Length"]=Buffer.byteLength(m));let d=e.allowAuthRetry!==!1,u=e.osClient||t.getOsClient()||"";u&&(g.headers.OsClient=u);let p=e.apiBaseUrl?this.getTokenForServer(e.apiBaseUrl,e.osClient,e.osClientType,e.osClientNetwork):await this.loadToken();p&&(g.headers.Authorization=`Bearer ${p}`);let h=`${n}${o}`;if(e.silent||Y.log("API",`\u27A1\uFE0F ${e.method} ${h}`),e.body&&!e.silent){let f=JSON.stringify(this.maskSensitiveBody(e.body));Y.appendLine(` Body: ${f.length>500?f.substring(0,500)+"...(truncated)":f}`)}return new Promise((f,y)=>{let S=c.request(g,w=>{let R=[];w.on("data",E=>R.push(E)),w.on("end",async()=>{let E=Buffer.concat(R).toString("utf-8"),b=w.statusCode||0;if(!e.silent){Y.log("API",`\u2B05\uFE0F ${b} ${e.method} ${e.path}`);let U=E.length>500?E.substring(0,500)+"...(truncated)":E;Y.appendLine(` Response: ${U}`)}let V;try{V=JSON.parse(E)}catch{}if(V){let U={};for(let[P,O]of Object.entries(w.headers))typeof O=="string"&&(U[P.toLowerCase()]=O);V._headers=U;let A=U.authorization||"";if(A&&A!==p&&await this.setToken(A,e.apiBaseUrl||n,e.osClient,e.osClientType,e.osClientNetwork),d&&Ze(V))Y.log("API",`\u26A0\uFE0F \u79DF\u6237\u8FDE\u63A5\u914D\u7F6E\u65E0\u6548\uFF0C\u5DF2\u505C\u6B62 token \u5237\u65B0\u4E0E\u9759\u9ED8\u91CD\u767B: ${V.Msg||""}`);else if(d&&yt(V)&&(Y.log("API",`\u{1F510} \u8EAB\u4EFD\u5DF2\u8FC7\u671F\uFF0C\u5C1D\u8BD5\u4F7F\u7528\u65E7 token \u5237\u65B0\u540E\u91CD\u8BD5: ${V.Msg||""}`),await this.refreshTokenForRequest(e,p,n)||await this.recoverAuthForRequest(e,n))){try{f(await this.request({...e,allowAuthRetry:!1}))}catch(F){y(F)}return}f(V)}else if(b===401||b===403){if(d&&(await this.refreshTokenForRequest(e,p,n)||await this.recoverAuthForRequest(e,n))){try{f(await this.request({...e,allowAuthRetry:!1}))}catch(P){y(P)}return}y(new Error(`\u8EAB\u4EFD\u9A8C\u8BC1\u5931\u8D25 (HTTP ${b})\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55`))}else if(b>=400){let U=E.replace(/<[^>]+>/g," ").replace(/\s+/g," ").trim().substring(0,120);y(new Error(`\u670D\u52A1\u5668\u9519\u8BEF (HTTP ${b}): ${U||"\u672A\u77E5\u9519\u8BEF"}`))}else y(new Error(`\u54CD\u5E94\u89E3\u6790\u5931\u8D25 (HTTP ${b}): ${E.substring(0,200)}`))})}),C=!1;S.on("error",w=>{if(C)return;let R=Xe(w);e.silent||Y.log("API",`\u274C ${e.method} ${e.path} Error: ${R}`),y(new Error(`\u8BF7\u6C42\u5931\u8D25: ${R}`))}),S.on("timeout",()=>{C=!0,S.destroy(),e.silent||Y.log("API",`\u23F0 ${e.method} ${e.path} Timeout`),y(new Error("\u8BF7\u6C42\u8D85\u65F6"))}),m!==void 0&&S.write(m),S.end()})}async get(e,t,n,i){return this.request({method:"GET",path:e,params:t,apiBaseUrl:n,osClient:i?.osClient,osClientType:i?.osClientType,osClientNetwork:i?.osClientNetwork})}async post(e,t,n,i,r,o,s){return this.request({method:"POST",path:e,body:t,params:n,apiBaseUrl:i,osClient:r?.osClient,osClientType:r?.osClientType,osClientNetwork:r?.osClientNetwork,timeout:o,silent:s})}async getRaw(e,t,n){let i=I.getInstance(),r=n||i.getApiBaseUrl();if(!r)throw new Error("\u672A\u914D\u7F6E API \u5730\u5740");let o=new URL(r),c=o.pathname.replace(/\/+$/,"")+e;if(t){let d=new URLSearchParams;for(let[p,h]of Object.entries(t))h!==void 0&&h!==""&&d.append(p,h);let u=d.toString();u&&(c+=`?${u}`)}let l=o.protocol==="https:",m=l?St:Ct,g={hostname:o.hostname,port:o.port||(l?443:80),path:c,method:"GET",timeout:15e3,rejectUnauthorized:!1};return new Promise((d,u)=>{let p=m.request(g,h=>{let f=[];h.on("data",y=>f.push(y)),h.on("end",()=>{let y=Buffer.concat(f),S=h.headers.captchaid||"";d({data:y,captchaId:S,statusCode:h.statusCode||0,contentType:String(h.headers["content-type"]||"")})})});p.on("error",h=>u(new Error(`\u8BF7\u6C42\u5931\u8D25: ${h.message}`))),p.on("timeout",()=>{p.destroy(),u(new Error("\u8BF7\u6C42\u8D85\u65F6"))}),p.end()})}async postMultipartFile(e,t,n,i,r,o,s=30*60*1e3){let c=Ue.realpathSync(n),l=Ue.lstatSync(c);if(!l.isFile()||l.isSymbolicLink())throw new Error(`\u4E0A\u4F20\u8D44\u4EA7\u5FC5\u987B\u662F\u666E\u901A\u6587\u4EF6\u4E14\u4E0D\u80FD\u662F\u7B26\u53F7\u94FE\u63A5\uFF1A${n}`);if(!i||/[\r\n"]/u.test(i))throw new Error("\u4E0A\u4F20\u6587\u4EF6\u540D\u4E0D\u5408\u6CD5");let m=String(r||"").replace(/\/+$/,""),g=new URL(m),d=`----microi-vscode-${Tt.randomBytes(24).toString("hex")}`,u=Object.entries(t).map(([E,b])=>Buffer.from(`--${d}\r
21
21
  Content-Disposition: form-data; name="${E}"\r
22
22
  \r
23
23
  ${b}\r
24
- `,"utf8")),p=Buffer.from(`--${l}\r
24
+ `,"utf8")),p=Buffer.from(`--${d}\r
25
25
  Content-Disposition: form-data; name="file"; filename="${i}"\r
26
26
  Content-Type: application/octet-stream\r
27
27
  \r
28
28
  `,"utf8"),h=Buffer.concat([...u,p]),f=Buffer.from(`\r
29
- --${l}--\r
30
- `,"utf8"),y=o?this.getTokenForServer(m,o.osClient,o.osClientType,o.osClientNetwork):await this.loadToken(),S=g.protocol==="https:",C=S?St:Ct,w=g.pathname.replace(/\/+$/,""),R={hostname:g.hostname,port:g.port||(S?443:80),path:w+e,method:"POST",timeout:s,rejectUnauthorized:!1,headers:{Accept:"application/json",...y?{Authorization:`Bearer ${y}`}:{},did:this.getDeviceId(),...o?.osClient?{OsClient:o.osClient}:{},"Content-Type":`multipart/form-data; boundary=${l}`,"Content-Length":h.length+d.size+f.length}};return new Promise((E,b)=>{let V=!1,U=O=>{V||(V=!0,b(O))},A=C.request(R,O=>{let F=[];O.on("data",k=>F.push(k)),O.on("end",async()=>{if(V)return;let k=Buffer.concat(F).toString("utf8"),$;try{$=JSON.parse(k)}catch{U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u54CD\u5E94\u4E0D\u662F JSON\uFF08HTTP ${O.statusCode||0}\uFF09`));return}let j=String(O.headers.authorization||"");j&&await this.setToken(j,m,o?.osClient,o?.osClientType,o?.osClientNetwork),V=!0,E($)})});A.on("error",O=>U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u5931\u8D25\uFF1A${Xe(O)}`))),A.on("timeout",()=>{A.destroy(),U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u8D85\u65F6\uFF08${s}ms\uFF09`))}),A.write(h);let P=Ue.createReadStream(c);P.on("error",O=>{A.destroy(),U(new Error(`\u8BFB\u53D6\u672C\u5730\u53D1\u5E03\u8D44\u4EA7\u5931\u8D25\uFF1A${Xe(O)}`))}),P.on("end",()=>A.end(f)),P.pipe(A,{end:!1})})}};var je=G(require("crypto")),B=G(require("fs")),et=G(require("path"));var ui=60*60*1e3,mi=5*60,Fn=24*60*60,pi=2*60*1e3,fi=60*1e3;function hi(a,e){let t=(e||"").trim();return t?je.publicEncrypt({key:t,padding:je.constants.RSA_PKCS1_PADDING},Buffer.from(a,"utf-8")).toString("base64"):a}var ge=class a{constructor(){this._isLoggedIn=!1;this._refreshInProgress=!1;this._mcpTokenFilePath="";this._mcpAuthRecoveryDirPath="";this._mcpAuthRecoveryInProgress=new Set;this._mcpAuthRecoveryFailureUntil=new Map;this._mcpAuthRecoveryPassInProgress=!1;this._lastAuthWarning="";this._lastAuthWarningTime=0}static getInstance(){return a._instance||(a._instance=new a),a._instance}setSecretStorage(e){this._secretStorage=e,L.getInstance().setTokenStateChangedHandler(async()=>{await this.writeMcpTokenFile()}),L.getInstance().setAuthRecoveryHandler(async t=>{let n=I.getInstance(),i=this.normalizeApiBaseUrl(t.apiBaseUrl),r=this.normalizeOsClient(t.osClient),o=this.normalizeIdentityPart(t.osClientType),s=this.normalizeIdentityPart(t.osClientNetwork),c=n.getProfiles().filter(g=>this.normalizeApiBaseUrl(g.apiBaseUrl)===i&&this.normalizeOsClient(g.osClient)===r),d=c.find(g=>this.normalizeIdentityPart(g.osClientType)===o&&this.normalizeIdentityPart(g.osClientNetwork)===s);if(!d&&!o&&!s&&c.length===1&&(d=c[0]),!d&&c.length===0&&(d={label:t.osClient||t.apiBaseUrl,apiBaseUrl:t.apiBaseUrl,osClient:t.osClient||"",osClientType:t.osClientType,osClientNetwork:t.osClientNetwork}),!d)return this.showAuthExpiredWarning("\u68C0\u6D4B\u5230\u540C\u4E00\u670D\u52A1\u5668\u4E0E\u79DF\u6237\u5B58\u5728\u591A\u4E2A\u8FDE\u63A5\u73AF\u5883\uFF0C\u65E0\u6CD5\u5B89\u5168\u5224\u65AD\u5E94\u6062\u590D\u54EA\u4E00\u4E2A\u767B\u5F55\u8EAB\u4EFD\u3002"),!1;let m=await this.reLoginForProfile(d);return m&&(this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0)),await this.writeMcpTokenFile(),m})}setMcpTokenFilePath(e){this._mcpTokenFilePath=e,this._mcpAuthRecoveryDirPath=e?`${e}.recovery`:""}get mcpTokenFilePath(){return this._mcpTokenFilePath}get mcpAuthRecoveryDirPath(){return this._mcpAuthRecoveryDirPath}async loadMcpTokenFile(){if(!this._mcpTokenFilePath||!B.existsSync(this._mcpTokenFilePath))return 0;let e;try{let r=JSON.parse(B.readFileSync(this._mcpTokenFilePath,"utf-8"));if(!r||typeof r!="object"||Array.isArray(r))return 0;e=r}catch{return 0}let t=L.getInstance(),n=I.getInstance().getProfiles(),i=0;for(let r of n){let o=this.normalizeApiBaseUrl(r.apiBaseUrl),s=this.normalizeOsClient(r.osClient),c=this.mcpRecoveryIdentity(o,s,r.osClientType,r.osClientNetwork),m=n.filter(f=>this.normalizeApiBaseUrl(f.apiBaseUrl)===o&&this.normalizeOsClient(f.osClient)===s).length===1?[[o,s,r.osClientType,r.osClientNetwork].filter(Boolean).join("|"),[o,s,r.osClientType].filter(Boolean).join("|"),s?`${o}|${s}`:o]:[],g=typeof e[c]=="string"&&String(e[c]).trim()?String(e[c]).trim():"",l=m.map(f=>e[f]).find(f=>typeof f=="string"&&f.trim()),u=t.getTokenForServer(r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),p=t.getExactTokenForServer(r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),h=qt(u,g||l,!!g&&!p);!h||p===h||(await t.adoptTokenFromSharedFile(h,r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),i+=1)}return i}get isLoggedIn(){return this._isLoggedIn}secretKey(e){return I.getInstance().getWorkspaceSecretKey(e)}normalizeApiBaseUrl(e){return(e||"").trim().replace(/\/+$/,"")}normalizeOsClient(e){return(e||"").trim()}normalizeIdentityPart(e){return(e||"").trim()}mcpRecoveryIdentity(e,t,n,i){return[this.normalizeApiBaseUrl(e),this.normalizeOsClient(t),this.normalizeIdentityPart(n),this.normalizeIdentityPart(i)].join("|")}serverSecretKey(e,t,n){return this.secretKey(`${e}.${this.normalizeApiBaseUrl(t)}|${this.normalizeOsClient(n)}`)}legacyServerSecretKey(e,t){return this.secretKey(`${e}.${this.normalizeApiBaseUrl(t)}`)}canUseLegacyCredential(e,t){let n=this.normalizeApiBaseUrl(e),i=this.normalizeOsClient(t);if(!n)return!1;let r=I.getInstance().getProfiles().filter(s=>this.normalizeApiBaseUrl(s.apiBaseUrl)===n);if(r.length===0)return!i;if(r.length===1)return!0;let o=r.filter(s=>this.normalizeOsClient(s.osClient)===i);return!!i&&o.length===r.length}async writeMcpTokenFile(){if(!this._mcpTokenFilePath)return;let e=L.getInstance(),n=I.getInstance().getProfiles(),i={},r=new Set,o=[];for(let p of n){let h=this.normalizeApiBaseUrl(p.apiBaseUrl),f=this.normalizeOsClient(p.osClient),y=this.mcpRecoveryIdentity(h,f,p.osClientType,p.osClientNetwork);r.add(y);let S=n.filter(R=>this.normalizeApiBaseUrl(R.apiBaseUrl)===h&&this.normalizeOsClient(R.osClient)===f),C=f?`${h}|${f}`:h;S.length===1&&r.add(C);let w=e.getTokenForServer(p.apiBaseUrl,p.osClient,p.osClientType,p.osClientNetwork);o.push({profile:p,exactKey:y,legacyKey:S.length===1?C:void 0,currentToken:w,currentExactToken:e.getExactTokenForServer(p.apiBaseUrl,p.osClient,p.osClientType,p.osClientNetwork)}),w&&(i[y]=w,S.length===1&&(i[C]=w))}let s=this._mcpTokenFilePath,c=et.dirname(s);B.existsSync(c)||B.mkdirSync(c,{recursive:!0});let d=`${s}.lock`,m=Date.now()+3e3,g;for(;g===void 0;)try{g=B.openSync(d,"wx",384),B.writeFileSync(g,JSON.stringify({pid:process.pid,createdAt:Date.now()}),"utf-8")}catch(p){if(p.code!=="EEXIST")throw p;try{Date.now()-B.statSync(d).mtimeMs>3e4&&B.unlinkSync(d)}catch{}if(Date.now()>=m)throw new Error("Microi MCP Token \u6587\u4EF6\u6B63\u5728\u88AB CLI \u6216 VS Code \u63D2\u4EF6\u4FEE\u6539\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5");await new Promise(h=>setTimeout(h,40))}let l=`${s}.${process.pid}.${Date.now()}.tmp`,u=[];try{let p={};if(B.existsSync(s)){let f=JSON.parse(B.readFileSync(s,"utf-8"));if(!f||typeof f!="object"||Array.isArray(f))throw new Error(`Microi MCP Token \u6587\u4EF6\u5FC5\u987B\u662F JSON \u5BF9\u8C61\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\uFF1A${s}`);p=Object.fromEntries(Object.entries(f).filter(y=>typeof y[1]=="string"&&!!y[1]))}for(let f of o){let y=p[f.exactKey]||"",S=f.legacyKey&&p[f.legacyKey]||"",C=qt(f.currentToken,y||S,!!y&&!f.currentExactToken);C&&(i[f.exactKey]=C,f.legacyKey&&(i[f.legacyKey]=C),C!==f.currentExactToken&&u.push({profile:f.profile,token:C}))}for(let f of r)delete p[f];let h={...p,...i};B.writeFileSync(l,`${JSON.stringify(h,null,2)}
31
- `,{encoding:"utf-8",mode:384}),B.renameSync(l,s)}finally{try{B.existsSync(l)&&B.unlinkSync(l)}catch{}try{B.closeSync(g)}catch{}try{B.unlinkSync(d)}catch{}}for(let p of u)await e.adoptTokenFromSharedFile(p.token,p.profile.apiBaseUrl,p.profile.osClient,p.profile.osClientType,p.profile.osClientNetwork)}tokenFingerprint(e){return je.createHash("sha256").update(String(e||"")).digest("hex")}deleteMcpAuthRecoveryRequests(e,t){let n=this._mcpAuthRecoveryDirPath;if(!n||!B.existsSync(n))return;let i=[];try{i=B.readdirSync(n).filter(r=>r.endsWith(".json")).slice(0,200)}catch{return}for(let r of i){let o=et.join(n,r);try{let s=JSON.parse(B.readFileSync(o,"utf-8")),c=this.normalizeApiBaseUrl(String(s.apiBaseUrl||"")),d=this.normalizeOsClient(String(s.osClient||"")),m=this.normalizeIdentityPart(String(s.osClientType||"")),g=this.normalizeIdentityPart(String(s.osClientNetwork||"")),l=this.mcpRecoveryIdentity(c,d,m,g);if(!m&&!g){let u=t.filter(p=>this.normalizeApiBaseUrl(p.apiBaseUrl)===c&&this.normalizeOsClient(p.osClient)===d);u.length===1&&(l=this.mcpRecoveryIdentity(u[0].apiBaseUrl,u[0].osClient,u[0].osClientType,u[0].osClientNetwork))}l===e&&B.unlinkSync(o)}catch{}}}async processMcpAuthRecoveryRequests(){let e=this._mcpAuthRecoveryDirPath;if(!(!e||!B.existsSync(e)||this._mcpAuthRecoveryPassInProgress)){this._mcpAuthRecoveryPassInProgress=!0;try{let t=[];try{t=B.readdirSync(e).filter(o=>o.endsWith(".json")).slice(0,100)}catch{return}let i=I.getInstance().getProfiles(),r=L.getInstance();for(let o of t){let s=et.join(e,o),c={};try{c=JSON.parse(B.readFileSync(s,"utf-8"))}catch{try{B.unlinkSync(s)}catch{}continue}let d=Number(c.requestedAt||0),m=this.normalizeApiBaseUrl(String(c.apiBaseUrl||"")),g=this.normalizeOsClient(String(c.osClient||"")),l=this.normalizeIdentityPart(String(c.osClientType||"")),u=this.normalizeIdentityPart(String(c.osClientNetwork||"")),p=String(c.failedTokenHash||"").trim().toLowerCase();if(Number(c.version)!==1||!m||!d||Math.abs(Date.now()-d)>pi||!Nn(p)){try{B.unlinkSync(s)}catch{}continue}let h=i.filter(S=>this.normalizeApiBaseUrl(S.apiBaseUrl)===m&&this.normalizeOsClient(S.osClient)===g),f=l||u?h.find(S=>this.normalizeIdentityPart(S.osClientType)===l&&this.normalizeIdentityPart(S.osClientNetwork)===u):h.length===1?h[0]:void 0;if(!f){try{B.unlinkSync(s)}catch{}continue}let y=this.mcpRecoveryIdentity(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);if(!this._mcpAuthRecoveryInProgress.has(y)){if((this._mcpAuthRecoveryFailureUntil.get(y)||0)>Date.now()){this.deleteMcpAuthRecoveryRequests(y,i);continue}this._mcpAuthRecoveryInProgress.add(y);try{let S=r.getTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);S&&this.tokenFingerprint(S)!==p?(this._mcpAuthRecoveryFailureUntil.delete(y),await this.writeMcpTokenFile()):(S&&await r.clearTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork,S),await this.reLoginForProfile(f)?this._mcpAuthRecoveryFailureUntil.delete(y):(this._mcpAuthRecoveryFailureUntil.set(y,Date.now()+fi),this.showAuthExpiredWarning("MCP \u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u4FDD\u5B58\u7684\u51ED\u636E\u65E0\u6CD5\u9759\u9ED8\u6062\u590D\uFF1B\u82E5\u670D\u52A1\u5668\u542F\u7528\u4E86\u9A8C\u8BC1\u7801\uFF0C\u8BF7\u5728\u63D2\u4EF6\u914D\u7F6E\u4E2D\u4EA4\u4E92\u5F0F\u91CD\u65B0\u767B\u5F55\u3002")))}finally{this._mcpAuthRecoveryInProgress.delete(y),this.deleteMcpAuthRecoveryRequests(y,i)}}}}finally{this._mcpAuthRecoveryPassInProgress=!1}}}startMcpAuthRecoveryWatcher(){this._mcpAuthRecoveryTimer||!this._mcpAuthRecoveryDirPath||(this._mcpAuthRecoveryTimer=setInterval(()=>{this.processMcpAuthRecoveryRequests()},1e3),this.processMcpAuthRecoveryRequests())}stopMcpAuthRecoveryWatcher(){this._mcpAuthRecoveryTimer&&(clearInterval(this._mcpAuthRecoveryTimer),this._mcpAuthRecoveryTimer=void 0)}async tryAutoLogin(){let e=L.getInstance(),n=I.getInstance().getProfiles(),i=!1,r=await e.loadToken(),o=await this.loadMcpTokenFile();i=!!r||o>0||e.hasToken;let s=n.filter(g=>!e.getTokenForServer(g.apiBaseUrl,g.osClient,g.osClientType,g.osClientNetwork)),c=0,d=async()=>{for(;c<s.length;){let g=s[c++];await this.reLoginForProfile(g)&&(i=!0)}},m=Math.min(4,s.length);return await Promise.all(Array.from({length:m},()=>d())),i&&(this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0),await this.writeMcpTokenFile()),i}async getSysConfig(e,t,n,i=!1){let r=L.getInstance(),o=I.getInstance();try{let s=await r.request({method:"POST",path:x.GET_SYS_CONFIG,body:{_SearchEqual:{IsEnable:1},OsClient:t||o.getOsClient()||void 0},apiBaseUrl:e,osClient:t,allowAuthRetry:!1,silent:i});if(s.Code===1&&s.Data)return s.Data;n&&(n.message=s.Code!==1?`\u670D\u52A1\u5668\u8FD4\u56DE\u9519\u8BEF (Code: ${s.Code})${s.Msg?"\uFF1A"+s.Msg:""}\uFF0C\u8BF7\u68C0\u67E5 OsClient \u662F\u5426\u6B63\u786E`:"\u670D\u52A1\u5668\u672A\u8FD4\u56DE\u914D\u7F6E\u6570\u636E")}catch(s){n&&(n.message=s instanceof Error?s.message:String(s))}return null}async getCaptcha(e,t){let n=L.getInstance(),i=I.getInstance();try{let r=await n.getRaw(x.GET_CAPTCHA,{OsClient:t||i.getOsClient()||""},e);if(r.data&&r.captchaId){let o=r.data.toString("base64");return{captchaId:r.captchaId,imageBase64:`data:image/png;base64,${o}`}}}catch{}return null}async login(e,t,n={}){let i=L.getInstance(),r=I.getInstance(),o=n.osClient||r.getOsClient(),s=n.silent??!1;try{let c=await this.getSysConfig(n.apiBaseUrl,o,void 0,s),d=c?.EnableCaptcha;if((d===!0||d===1||String(d||"").trim().toLowerCase()==="true")&&(!n.captchaId||!n.captchaValue)){let y="\u670D\u52A1\u5668\u5DF2\u5F00\u542F\u56FE\u5F62\u9A8C\u8BC1\u7801\uFF0C\u8BF7\u5728\u63D2\u4EF6\u914D\u7F6E\u4E2D\u4EA4\u4E92\u5F0F\u767B\u5F55\u3002";return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${y}`),{ok:!1,msg:y}}let g=typeof c?.LoginRsaPublicKey=="string"&&c.LoginRsaPublicKey.trim()?c.LoginRsaPublicKey:hn,l=hi(t,g),u={Account:e,Pwd:l,OsClient:o||void 0,_ClientType:"VSCode"};n.captchaId&&n.captchaValue&&(u._CaptchaId=n.captchaId,u._CaptchaValue=n.captchaValue);let p=await i.request({method:"POST",path:x.LOGIN,body:u,bodyFormat:"form",apiBaseUrl:n.apiBaseUrl,osClient:n.osClient,osClientType:n.osClientType,osClientNetwork:n.osClientNetwork,allowAuthRetry:!1,silent:s}),f=p._headers?.authorization||"";if(p.Code===1)return f&&await i.setToken(f,n.apiBaseUrl,n.osClient,n.osClientType,n.osClientNetwork),this._secretStorage&&(n.apiBaseUrl?(await this._secretStorage.store(this.serverSecretKey(ye,n.apiBaseUrl,o),e),await this._secretStorage.store(this.serverSecretKey(Se,n.apiBaseUrl,o),t)):(await this._secretStorage.store(this.secretKey(ye),e),await this._secretStorage.store(this.secretKey(Se),t))),p.Data?.OsClient&&!o&&await r.updateSettings({osClient:p.Data.OsClient}),this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0),await this.writeMcpTokenFile(),s||_.info(`Microi: \u767B\u5F55\u6210\u529F\uFF0C\u6B22\u8FCE ${p.Data?.Name||p.Data?.Account||e}`),{ok:!0,msg:""};{let y=p.Msg||"\u8BF7\u68C0\u67E5\u8D26\u53F7\u5BC6\u7801";return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${y}`),{ok:!1,msg:y}}}catch(c){let d=c instanceof Error?c.message:String(c);return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${d}`),{ok:!1,msg:d}}}async refreshAllTokens(){if(this._refreshInProgress)return;this._refreshInProgress=!0;let e=L.getInstance(),n=I.getInstance().getProfiles();try{for(let i of n){let r=e.getTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork);if(!r){await this.reLoginForProfile(i);continue}try{let l=await e.request({method:"GET",path:x.GET_STATUS,apiBaseUrl:i.apiBaseUrl,osClient:i.osClient,osClientType:i.osClientType,osClientNetwork:i.osClientNetwork,allowAuthRetry:!1,silent:!0});if(Ze(l))continue;if(yt(l)){await e.clearTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork,r),await this.reLoginForProfile(i)||this.showAuthExpiredWarning(l.Msg||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002");continue}}catch{}let o=this.readJwtClientClaims(r),s=String(o?.ClientType||"").trim(),c=s.toLowerCase()!=="vscode",d=!s||s.toLowerCase()==="empty";if(c&&(await this.reLoginForProfile(i)||!d))continue;let m=String(o?.Did||"").trim(),g=s.toLowerCase()==="vscode"&&m!==e.getDeviceId();if(!(!c&&!g&&!this.shouldRefreshToken(r,o)))try{let l=await e.request({method:"POST",path:x.REFRESH_TOKEN,body:{authorization:r,OsClient:i.osClient,_ClientType:"VSCode"},apiBaseUrl:i.apiBaseUrl,osClient:i.osClient,osClientType:i.osClientType,osClientNetwork:i.osClientNetwork,allowAuthRetry:!1,silent:!0}),p=l._headers?.authorization||"";l.Code===1&&p?await e.setToken(p,i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork):(await e.clearTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork,r),await this.reLoginForProfile(i)||this.showAuthExpiredWarning(l.Msg||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002"))}catch{await this.reLoginForProfile(i)}}}finally{this._isLoggedIn=e.hasToken,await Ne.executeCommand("setContext",xe,this._isLoggedIn),await this.writeMcpTokenFile(),this._refreshInProgress=!1}}showAuthExpiredWarning(e){let t=String(e||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002"),n=Date.now();t===this._lastAuthWarning&&n-this._lastAuthWarningTime<60*1e3||(this._lastAuthWarning=t,this._lastAuthWarningTime=n,_.warn(`Microi: ${t}`))}readJwtClientClaims(e){try{let n=e.replace(/^Bearer\s+/i,"").trim().split(".");if(n.length<2)return null;let i=n[1].replace(/-/g,"+").replace(/_/g,"/");return JSON.parse(Buffer.from(i,"base64").toString("utf-8"))}catch{return null}}shouldRefreshToken(e,t){let n=t??this.readJwtClientClaims(e),i=Number(n?.exp);if(!Number.isFinite(i)||i<=0)return!0;let r=Number(n?.MicroiTokenIssuedAt??n?.iat),o=Number.isFinite(r)&&r>0&&i>r?i-r:Fn,s=Math.min(Fn,Math.max(mi,Math.floor(o/10)));return i-Math.floor(Date.now()/1e3)<=s}async getCredentialsForProfile(e,t){if(!this._secretStorage)return null;let n=this.normalizeApiBaseUrl(e),i=this.normalizeOsClient(t),r=n?await this._secretStorage.get(this.serverSecretKey(ye,n,i)):void 0,o=n?await this._secretStorage.get(this.serverSecretKey(Se,n,i)):void 0;return(!r||!o)&&n&&this.canUseLegacyCredential(n,i)&&(r=r||await this._secretStorage.get(this.legacyServerSecretKey(ye,n)),o=o||await this._secretStorage.get(this.legacyServerSecretKey(Se,n))),(!r||!o)&&!n&&!i&&(r=r||await this._secretStorage.get(this.secretKey(ye)),o=o||await this._secretStorage.get(this.secretKey(Se))),!r||!o?null:{username:r,password:o}}async reLoginForProfile(e){if(!this._secretStorage)return!1;let t=await this.getCredentialsForProfile(e.apiBaseUrl,e.osClient);return t?(await this.login(t.username,t.password,{silent:!0,apiBaseUrl:e.apiBaseUrl,osClient:e.osClient,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork})).ok:!1}startTokenRefresh(){this.stopTokenRefresh(),this.startMcpAuthRecoveryWatcher(),this.refreshAllTokens(),this._refreshTimer=setInterval(()=>{this.refreshAllTokens()},ui),this._windowStateSubscription=oe.onDidChangeWindowState(e=>{e.focused&&this.refreshAllTokens()})}stopTokenRefresh(){this._refreshTimer&&(clearInterval(this._refreshTimer),this._refreshTimer=void 0),this._windowStateSubscription&&(this._windowStateSubscription.dispose(),this._windowStateSubscription=void 0),this.stopMcpAuthRecoveryWatcher()}async logout(){if(this.stopTokenRefresh(),await L.getInstance().clearToken(),this._secretStorage){await this._secretStorage.delete(this.secretKey(ye)),await this._secretStorage.delete(this.secretKey(Se));let t=I.getInstance().getProfiles();for(let n of t)await this._secretStorage.delete(this.serverSecretKey(ye,n.apiBaseUrl,n.osClient)),await this._secretStorage.delete(this.serverSecretKey(Se,n.apiBaseUrl,n.osClient)),await this._secretStorage.delete(this.legacyServerSecretKey(ye,n.apiBaseUrl)),await this._secretStorage.delete(this.legacyServerSecretKey(Se,n.apiBaseUrl))}this._isLoggedIn=!1,await Ne.executeCommand("setContext",xe,!1),_.info("Microi: \u5DF2\u9000\u51FA\u767B\u5F55")}};var yi=/^\s*\*?\s*Version\s*:\s*(v\d+\.\d+\.\d+)\s*$/im,An=/^v(\d+)\.(\d+)\.(\d+)$/;function vt(a){let e=(a||"").trim();if(!e)return null;let t=e.match(An);if(t)return`v${Number(t[1])}.${Number(t[2])}.${Number(t[3])}`;let n=e.match(yi);return n?vt(n[1]):null}function Vn(a){if(!a)return null;let e=a.match(An);return e?{major:Number(e[1]),minor:Number(e[2]),patch:Number(e[3])}:null}function Si(a,e){return a.major!==e.major?a.major-e.major:a.minor!==e.minor?a.minor-e.minor:a.patch-e.patch}function Ci(a){let e=null;for(let t of a){let n=Vn(t);n&&(!e||Si(n,e)>0)&&(e=n)}return e?`v${e.major}.${e.minor}.${e.patch}`:null}function Ti(a){let e=Vn(a);if(!e)return"v1.0.0";let{major:t,minor:n,patch:i}=e;return i<9?`v${t}.${n}.${i+1}`:(i=0,n<9?`v${t}.${n+1}.${i}`:(n=0,t+=1,`v${t}.${n}.${i}`))}function vi(a){let e=(a||"").trim();return e?e.replace(/\r\n/g,`
29
+ --${d}--\r
30
+ `,"utf8"),y=o?this.getTokenForServer(m,o.osClient,o.osClientType,o.osClientNetwork):await this.loadToken(),S=g.protocol==="https:",C=S?St:Ct,w=g.pathname.replace(/\/+$/,""),R={hostname:g.hostname,port:g.port||(S?443:80),path:w+e,method:"POST",timeout:s,rejectUnauthorized:!1,headers:{Accept:"application/json",...y?{Authorization:`Bearer ${y}`}:{},did:this.getDeviceId(),...o?.osClient?{OsClient:o.osClient}:{},"Content-Type":`multipart/form-data; boundary=${d}`,"Content-Length":h.length+l.size+f.length}};return new Promise((E,b)=>{let V=!1,U=O=>{V||(V=!0,b(O))},A=C.request(R,O=>{let F=[];O.on("data",k=>F.push(k)),O.on("end",async()=>{if(V)return;let k=Buffer.concat(F).toString("utf8"),$;try{$=JSON.parse(k)}catch{U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u54CD\u5E94\u4E0D\u662F JSON\uFF08HTTP ${O.statusCode||0}\uFF09`));return}let j=String(O.headers.authorization||"");j&&await this.setToken(j,m,o?.osClient,o?.osClientType,o?.osClientNetwork),V=!0,E($)})});A.on("error",O=>U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u5931\u8D25\uFF1A${Xe(O)}`))),A.on("timeout",()=>{A.destroy(),U(new Error(`\u6D41\u5F0F\u4E0A\u4F20\u8D85\u65F6\uFF08${s}ms\uFF09`))}),A.write(h);let P=Ue.createReadStream(c);P.on("error",O=>{A.destroy(),U(new Error(`\u8BFB\u53D6\u672C\u5730\u53D1\u5E03\u8D44\u4EA7\u5931\u8D25\uFF1A${Xe(O)}`))}),P.on("end",()=>A.end(f)),P.pipe(A,{end:!1})})}};var je=G(require("crypto")),B=G(require("fs")),et=G(require("path"));var ui=60*60*1e3,mi=5*60,Fn=24*60*60,pi=2*60*1e3,fi=60*1e3;function hi(a,e){let t=(e||"").trim();return t?je.publicEncrypt({key:t,padding:je.constants.RSA_PKCS1_PADDING},Buffer.from(a,"utf-8")).toString("base64"):a}var ge=class a{constructor(){this._isLoggedIn=!1;this._refreshInProgress=!1;this._mcpTokenFilePath="";this._mcpAuthRecoveryDirPath="";this._mcpAuthRecoveryInProgress=new Set;this._mcpAuthRecoveryFailureUntil=new Map;this._mcpAuthRecoveryPassInProgress=!1;this._lastAuthWarning="";this._lastAuthWarningTime=0}static getInstance(){return a._instance||(a._instance=new a),a._instance}setSecretStorage(e){this._secretStorage=e,L.getInstance().setTokenStateChangedHandler(async()=>{await this.writeMcpTokenFile()}),L.getInstance().setAuthRecoveryHandler(async t=>{let n=I.getInstance(),i=this.normalizeApiBaseUrl(t.apiBaseUrl),r=this.normalizeOsClient(t.osClient),o=this.normalizeIdentityPart(t.osClientType),s=this.normalizeIdentityPart(t.osClientNetwork),c=n.getProfiles().filter(g=>this.normalizeApiBaseUrl(g.apiBaseUrl)===i&&this.normalizeOsClient(g.osClient)===r),l=c.find(g=>this.normalizeIdentityPart(g.osClientType)===o&&this.normalizeIdentityPart(g.osClientNetwork)===s);if(!l&&!o&&!s&&c.length===1&&(l=c[0]),!l&&c.length===0&&(l={label:t.osClient||t.apiBaseUrl,apiBaseUrl:t.apiBaseUrl,osClient:t.osClient||"",osClientType:t.osClientType,osClientNetwork:t.osClientNetwork}),!l)return this.showAuthExpiredWarning("\u68C0\u6D4B\u5230\u540C\u4E00\u670D\u52A1\u5668\u4E0E\u79DF\u6237\u5B58\u5728\u591A\u4E2A\u8FDE\u63A5\u73AF\u5883\uFF0C\u65E0\u6CD5\u5B89\u5168\u5224\u65AD\u5E94\u6062\u590D\u54EA\u4E00\u4E2A\u767B\u5F55\u8EAB\u4EFD\u3002"),!1;let m=await this.reLoginForProfile(l);return m&&(this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0)),await this.writeMcpTokenFile(),m})}setMcpTokenFilePath(e){this._mcpTokenFilePath=e,this._mcpAuthRecoveryDirPath=e?`${e}.recovery`:""}get mcpTokenFilePath(){return this._mcpTokenFilePath}get mcpAuthRecoveryDirPath(){return this._mcpAuthRecoveryDirPath}async loadMcpTokenFile(){if(!this._mcpTokenFilePath||!B.existsSync(this._mcpTokenFilePath))return 0;let e;try{let r=JSON.parse(B.readFileSync(this._mcpTokenFilePath,"utf-8"));if(!r||typeof r!="object"||Array.isArray(r))return 0;e=r}catch{return 0}let t=L.getInstance(),n=I.getInstance().getProfiles(),i=0;for(let r of n){let o=this.normalizeApiBaseUrl(r.apiBaseUrl),s=this.normalizeOsClient(r.osClient),c=this.mcpRecoveryIdentity(o,s,r.osClientType,r.osClientNetwork),m=n.filter(f=>this.normalizeApiBaseUrl(f.apiBaseUrl)===o&&this.normalizeOsClient(f.osClient)===s).length===1?[[o,s,r.osClientType,r.osClientNetwork].filter(Boolean).join("|"),[o,s,r.osClientType].filter(Boolean).join("|"),s?`${o}|${s}`:o]:[],g=typeof e[c]=="string"&&String(e[c]).trim()?String(e[c]).trim():"",d=m.map(f=>e[f]).find(f=>typeof f=="string"&&f.trim()),u=t.getTokenForServer(r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),p=t.getExactTokenForServer(r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),h=qt(u,g||d,!!g&&!p);!h||p===h||(await t.adoptTokenFromSharedFile(h,r.apiBaseUrl,r.osClient,r.osClientType,r.osClientNetwork),i+=1)}return i}get isLoggedIn(){return this._isLoggedIn}secretKey(e){return I.getInstance().getWorkspaceSecretKey(e)}normalizeApiBaseUrl(e){return(e||"").trim().replace(/\/+$/,"")}normalizeOsClient(e){return(e||"").trim()}normalizeIdentityPart(e){return(e||"").trim()}mcpRecoveryIdentity(e,t,n,i){return[this.normalizeApiBaseUrl(e),this.normalizeOsClient(t),this.normalizeIdentityPart(n),this.normalizeIdentityPart(i)].join("|")}serverSecretKey(e,t,n){return this.secretKey(`${e}.${this.normalizeApiBaseUrl(t)}|${this.normalizeOsClient(n)}`)}legacyServerSecretKey(e,t){return this.secretKey(`${e}.${this.normalizeApiBaseUrl(t)}`)}canUseLegacyCredential(e,t){let n=this.normalizeApiBaseUrl(e),i=this.normalizeOsClient(t);if(!n)return!1;let r=I.getInstance().getProfiles().filter(s=>this.normalizeApiBaseUrl(s.apiBaseUrl)===n);if(r.length===0)return!i;if(r.length===1)return!0;let o=r.filter(s=>this.normalizeOsClient(s.osClient)===i);return!!i&&o.length===r.length}async writeMcpTokenFile(){if(!this._mcpTokenFilePath)return;let e=L.getInstance(),n=I.getInstance().getProfiles(),i={},r=new Set,o=[];for(let p of n){let h=this.normalizeApiBaseUrl(p.apiBaseUrl),f=this.normalizeOsClient(p.osClient),y=this.mcpRecoveryIdentity(h,f,p.osClientType,p.osClientNetwork);r.add(y);let S=n.filter(R=>this.normalizeApiBaseUrl(R.apiBaseUrl)===h&&this.normalizeOsClient(R.osClient)===f),C=f?`${h}|${f}`:h;S.length===1&&r.add(C);let w=e.getTokenForServer(p.apiBaseUrl,p.osClient,p.osClientType,p.osClientNetwork);o.push({profile:p,exactKey:y,legacyKey:S.length===1?C:void 0,currentToken:w,currentExactToken:e.getExactTokenForServer(p.apiBaseUrl,p.osClient,p.osClientType,p.osClientNetwork)}),w&&(i[y]=w,S.length===1&&(i[C]=w))}let s=this._mcpTokenFilePath,c=et.dirname(s);B.existsSync(c)||B.mkdirSync(c,{recursive:!0});let l=`${s}.lock`,m=Date.now()+3e3,g;for(;g===void 0;)try{g=B.openSync(l,"wx",384),B.writeFileSync(g,JSON.stringify({pid:process.pid,createdAt:Date.now()}),"utf-8")}catch(p){if(p.code!=="EEXIST")throw p;try{Date.now()-B.statSync(l).mtimeMs>3e4&&B.unlinkSync(l)}catch{}if(Date.now()>=m)throw new Error("Microi MCP Token \u6587\u4EF6\u6B63\u5728\u88AB CLI \u6216 VS Code \u63D2\u4EF6\u4FEE\u6539\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5");await new Promise(h=>setTimeout(h,40))}let d=`${s}.${process.pid}.${Date.now()}.tmp`,u=[];try{let p={};if(B.existsSync(s)){let f=JSON.parse(B.readFileSync(s,"utf-8"));if(!f||typeof f!="object"||Array.isArray(f))throw new Error(`Microi MCP Token \u6587\u4EF6\u5FC5\u987B\u662F JSON \u5BF9\u8C61\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\uFF1A${s}`);p=Object.fromEntries(Object.entries(f).filter(y=>typeof y[1]=="string"&&!!y[1]))}for(let f of o){let y=p[f.exactKey]||"",S=f.legacyKey&&p[f.legacyKey]||"",C=qt(f.currentToken,y||S,!!y&&!f.currentExactToken);C&&(i[f.exactKey]=C,f.legacyKey&&(i[f.legacyKey]=C),C!==f.currentExactToken&&u.push({profile:f.profile,token:C}))}for(let f of r)delete p[f];let h={...p,...i};B.writeFileSync(d,`${JSON.stringify(h,null,2)}
31
+ `,{encoding:"utf-8",mode:384}),B.renameSync(d,s)}finally{try{B.existsSync(d)&&B.unlinkSync(d)}catch{}try{B.closeSync(g)}catch{}try{B.unlinkSync(l)}catch{}}for(let p of u)await e.adoptTokenFromSharedFile(p.token,p.profile.apiBaseUrl,p.profile.osClient,p.profile.osClientType,p.profile.osClientNetwork)}tokenFingerprint(e){return je.createHash("sha256").update(String(e||"")).digest("hex")}deleteMcpAuthRecoveryRequests(e,t){let n=this._mcpAuthRecoveryDirPath;if(!n||!B.existsSync(n))return;let i=[];try{i=B.readdirSync(n).filter(r=>r.endsWith(".json")).slice(0,200)}catch{return}for(let r of i){let o=et.join(n,r);try{let s=JSON.parse(B.readFileSync(o,"utf-8")),c=this.normalizeApiBaseUrl(String(s.apiBaseUrl||"")),l=this.normalizeOsClient(String(s.osClient||"")),m=this.normalizeIdentityPart(String(s.osClientType||"")),g=this.normalizeIdentityPart(String(s.osClientNetwork||"")),d=this.mcpRecoveryIdentity(c,l,m,g);if(!m&&!g){let u=t.filter(p=>this.normalizeApiBaseUrl(p.apiBaseUrl)===c&&this.normalizeOsClient(p.osClient)===l);u.length===1&&(d=this.mcpRecoveryIdentity(u[0].apiBaseUrl,u[0].osClient,u[0].osClientType,u[0].osClientNetwork))}d===e&&B.unlinkSync(o)}catch{}}}async processMcpAuthRecoveryRequests(){let e=this._mcpAuthRecoveryDirPath;if(!(!e||!B.existsSync(e)||this._mcpAuthRecoveryPassInProgress)){this._mcpAuthRecoveryPassInProgress=!0;try{let t=[];try{t=B.readdirSync(e).filter(o=>o.endsWith(".json")).slice(0,100)}catch{return}let i=I.getInstance().getProfiles(),r=L.getInstance();for(let o of t){let s=et.join(e,o),c={};try{c=JSON.parse(B.readFileSync(s,"utf-8"))}catch{try{B.unlinkSync(s)}catch{}continue}let l=Number(c.requestedAt||0),m=this.normalizeApiBaseUrl(String(c.apiBaseUrl||"")),g=this.normalizeOsClient(String(c.osClient||"")),d=this.normalizeIdentityPart(String(c.osClientType||"")),u=this.normalizeIdentityPart(String(c.osClientNetwork||"")),p=String(c.failedTokenHash||"").trim().toLowerCase();if(Number(c.version)!==1||!m||!l||Math.abs(Date.now()-l)>pi||!Nn(p)){try{B.unlinkSync(s)}catch{}continue}let h=i.filter(S=>this.normalizeApiBaseUrl(S.apiBaseUrl)===m&&this.normalizeOsClient(S.osClient)===g),f=d||u?h.find(S=>this.normalizeIdentityPart(S.osClientType)===d&&this.normalizeIdentityPart(S.osClientNetwork)===u):h.length===1?h[0]:void 0;if(!f){try{B.unlinkSync(s)}catch{}continue}let y=this.mcpRecoveryIdentity(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);if(!this._mcpAuthRecoveryInProgress.has(y)){if((this._mcpAuthRecoveryFailureUntil.get(y)||0)>Date.now()){this.deleteMcpAuthRecoveryRequests(y,i);continue}this._mcpAuthRecoveryInProgress.add(y);try{let S=r.getTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);S&&this.tokenFingerprint(S)!==p?(this._mcpAuthRecoveryFailureUntil.delete(y),await this.writeMcpTokenFile()):(S&&await r.clearTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork,S),await this.reLoginForProfile(f)?this._mcpAuthRecoveryFailureUntil.delete(y):(this._mcpAuthRecoveryFailureUntil.set(y,Date.now()+fi),this.showAuthExpiredWarning("MCP \u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u4FDD\u5B58\u7684\u51ED\u636E\u65E0\u6CD5\u9759\u9ED8\u6062\u590D\uFF1B\u82E5\u670D\u52A1\u5668\u542F\u7528\u4E86\u9A8C\u8BC1\u7801\uFF0C\u8BF7\u5728\u63D2\u4EF6\u914D\u7F6E\u4E2D\u4EA4\u4E92\u5F0F\u91CD\u65B0\u767B\u5F55\u3002")))}finally{this._mcpAuthRecoveryInProgress.delete(y),this.deleteMcpAuthRecoveryRequests(y,i)}}}}finally{this._mcpAuthRecoveryPassInProgress=!1}}}startMcpAuthRecoveryWatcher(){this._mcpAuthRecoveryTimer||!this._mcpAuthRecoveryDirPath||(this._mcpAuthRecoveryTimer=setInterval(()=>{this.processMcpAuthRecoveryRequests()},1e3),this.processMcpAuthRecoveryRequests())}stopMcpAuthRecoveryWatcher(){this._mcpAuthRecoveryTimer&&(clearInterval(this._mcpAuthRecoveryTimer),this._mcpAuthRecoveryTimer=void 0)}async tryAutoLogin(){let e=L.getInstance(),n=I.getInstance().getProfiles(),i=!1,r=await e.loadToken(),o=await this.loadMcpTokenFile();i=!!r||o>0||e.hasToken;let s=n.filter(g=>!e.getTokenForServer(g.apiBaseUrl,g.osClient,g.osClientType,g.osClientNetwork)),c=0,l=async()=>{for(;c<s.length;){let g=s[c++];await this.reLoginForProfile(g)&&(i=!0)}},m=Math.min(4,s.length);return await Promise.all(Array.from({length:m},()=>l())),i&&(this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0),await this.writeMcpTokenFile()),i}async getSysConfig(e,t,n,i=!1){let r=L.getInstance(),o=I.getInstance();try{let s=await r.request({method:"POST",path:x.GET_SYS_CONFIG,body:{_SearchEqual:{IsEnable:1},OsClient:t||o.getOsClient()||void 0},apiBaseUrl:e,osClient:t,allowAuthRetry:!1,silent:i});if(s.Code===1&&s.Data)return s.Data;n&&(n.message=s.Code!==1?`\u670D\u52A1\u5668\u8FD4\u56DE\u9519\u8BEF (Code: ${s.Code})${s.Msg?"\uFF1A"+s.Msg:""}\uFF0C\u8BF7\u68C0\u67E5 OsClient \u662F\u5426\u6B63\u786E`:"\u670D\u52A1\u5668\u672A\u8FD4\u56DE\u914D\u7F6E\u6570\u636E")}catch(s){n&&(n.message=s instanceof Error?s.message:String(s))}return null}async getCaptcha(e,t){let n=L.getInstance(),i=I.getInstance();try{let r=await n.getRaw(x.GET_CAPTCHA,{OsClient:t||i.getOsClient()||""},e);if(r.data&&r.captchaId){let o=r.data.toString("base64");return{captchaId:r.captchaId,imageBase64:`data:image/png;base64,${o}`}}}catch{}return null}async login(e,t,n={}){let i=L.getInstance(),r=I.getInstance(),o=n.osClient||r.getOsClient(),s=n.silent??!1;try{let c=await this.getSysConfig(n.apiBaseUrl,o,void 0,s),l=c?.EnableCaptcha;if((l===!0||l===1||String(l||"").trim().toLowerCase()==="true")&&(!n.captchaId||!n.captchaValue)){let y="\u670D\u52A1\u5668\u5DF2\u5F00\u542F\u56FE\u5F62\u9A8C\u8BC1\u7801\uFF0C\u8BF7\u5728\u63D2\u4EF6\u914D\u7F6E\u4E2D\u4EA4\u4E92\u5F0F\u767B\u5F55\u3002";return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${y}`),{ok:!1,msg:y}}let g=typeof c?.LoginRsaPublicKey=="string"&&c.LoginRsaPublicKey.trim()?c.LoginRsaPublicKey:hn,d=hi(t,g),u={Account:e,Pwd:d,OsClient:o||void 0,_ClientType:"VSCode"};n.captchaId&&n.captchaValue&&(u._CaptchaId=n.captchaId,u._CaptchaValue=n.captchaValue);let p=await i.request({method:"POST",path:x.LOGIN,body:u,bodyFormat:"form",apiBaseUrl:n.apiBaseUrl,osClient:n.osClient,osClientType:n.osClientType,osClientNetwork:n.osClientNetwork,allowAuthRetry:!1,silent:s}),f=p._headers?.authorization||"";if(p.Code===1)return f&&await i.setToken(f,n.apiBaseUrl,n.osClient,n.osClientType,n.osClientNetwork),this._secretStorage&&(n.apiBaseUrl?(await this._secretStorage.store(this.serverSecretKey(ye,n.apiBaseUrl,o),e),await this._secretStorage.store(this.serverSecretKey(Se,n.apiBaseUrl,o),t)):(await this._secretStorage.store(this.secretKey(ye),e),await this._secretStorage.store(this.secretKey(Se),t))),p.Data?.OsClient&&!o&&await r.updateSettings({osClient:p.Data.OsClient}),this._isLoggedIn=!0,await Ne.executeCommand("setContext",xe,!0),await this.writeMcpTokenFile(),s||_.info(`Microi: \u767B\u5F55\u6210\u529F\uFF0C\u6B22\u8FCE ${p.Data?.Name||p.Data?.Account||e}`),{ok:!0,msg:""};{let y=p.Msg||"\u8BF7\u68C0\u67E5\u8D26\u53F7\u5BC6\u7801";return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${y}`),{ok:!1,msg:y}}}catch(c){let l=c instanceof Error?c.message:String(c);return s||_.error(`Microi: \u767B\u5F55\u5931\u8D25 - ${l}`),{ok:!1,msg:l}}}async refreshAllTokens(){if(this._refreshInProgress)return;this._refreshInProgress=!0;let e=L.getInstance(),n=I.getInstance().getProfiles();try{for(let i of n){let r=e.getTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork);if(!r){await this.reLoginForProfile(i);continue}try{let d=await e.request({method:"GET",path:x.GET_STATUS,apiBaseUrl:i.apiBaseUrl,osClient:i.osClient,osClientType:i.osClientType,osClientNetwork:i.osClientNetwork,allowAuthRetry:!1,silent:!0});if(Ze(d))continue;if(yt(d)){await e.clearTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork,r),await this.reLoginForProfile(i)||this.showAuthExpiredWarning(d.Msg||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002");continue}}catch{}let o=this.readJwtClientClaims(r),s=String(o?.ClientType||"").trim(),c=s.toLowerCase()!=="vscode",l=!s||s.toLowerCase()==="empty";if(c&&(await this.reLoginForProfile(i)||!l))continue;let m=String(o?.Did||"").trim(),g=s.toLowerCase()==="vscode"&&m!==e.getDeviceId();if(!(!c&&!g&&!this.shouldRefreshToken(r,o)))try{let d=await e.request({method:"POST",path:x.REFRESH_TOKEN,body:{authorization:r,OsClient:i.osClient,_ClientType:"VSCode"},apiBaseUrl:i.apiBaseUrl,osClient:i.osClient,osClientType:i.osClientType,osClientNetwork:i.osClientNetwork,allowAuthRetry:!1,silent:!0}),p=d._headers?.authorization||"";d.Code===1&&p?await e.setToken(p,i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork):(await e.clearTokenForServer(i.apiBaseUrl,i.osClient,i.osClientType,i.osClientNetwork,r),await this.reLoginForProfile(i)||this.showAuthExpiredWarning(d.Msg||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002"))}catch{await this.reLoginForProfile(i)}}}finally{this._isLoggedIn=e.hasToken,await Ne.executeCommand("setContext",xe,this._isLoggedIn),await this.writeMcpTokenFile(),this._refreshInProgress=!1}}showAuthExpiredWarning(e){let t=String(e||"\u5F53\u524D\u767B\u5F55\u8EAB\u4EFD\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55\u3002"),n=Date.now();t===this._lastAuthWarning&&n-this._lastAuthWarningTime<60*1e3||(this._lastAuthWarning=t,this._lastAuthWarningTime=n,_.warn(`Microi: ${t}`))}readJwtClientClaims(e){try{let n=e.replace(/^Bearer\s+/i,"").trim().split(".");if(n.length<2)return null;let i=n[1].replace(/-/g,"+").replace(/_/g,"/");return JSON.parse(Buffer.from(i,"base64").toString("utf-8"))}catch{return null}}shouldRefreshToken(e,t){let n=t??this.readJwtClientClaims(e),i=Number(n?.exp);if(!Number.isFinite(i)||i<=0)return!0;let r=Number(n?.MicroiTokenIssuedAt??n?.iat),o=Number.isFinite(r)&&r>0&&i>r?i-r:Fn,s=Math.min(Fn,Math.max(mi,Math.floor(o/10)));return i-Math.floor(Date.now()/1e3)<=s}async getCredentialsForProfile(e,t){if(!this._secretStorage)return null;let n=this.normalizeApiBaseUrl(e),i=this.normalizeOsClient(t),r=n?await this._secretStorage.get(this.serverSecretKey(ye,n,i)):void 0,o=n?await this._secretStorage.get(this.serverSecretKey(Se,n,i)):void 0;return(!r||!o)&&n&&this.canUseLegacyCredential(n,i)&&(r=r||await this._secretStorage.get(this.legacyServerSecretKey(ye,n)),o=o||await this._secretStorage.get(this.legacyServerSecretKey(Se,n))),(!r||!o)&&!n&&!i&&(r=r||await this._secretStorage.get(this.secretKey(ye)),o=o||await this._secretStorage.get(this.secretKey(Se))),!r||!o?null:{username:r,password:o}}async reLoginForProfile(e){if(!this._secretStorage)return!1;let t=await this.getCredentialsForProfile(e.apiBaseUrl,e.osClient);return t?(await this.login(t.username,t.password,{silent:!0,apiBaseUrl:e.apiBaseUrl,osClient:e.osClient,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork})).ok:!1}startTokenRefresh(){this.stopTokenRefresh(),this.startMcpAuthRecoveryWatcher(),this.refreshAllTokens(),this._refreshTimer=setInterval(()=>{this.refreshAllTokens()},ui),this._windowStateSubscription=oe.onDidChangeWindowState(e=>{e.focused&&this.refreshAllTokens()})}stopTokenRefresh(){this._refreshTimer&&(clearInterval(this._refreshTimer),this._refreshTimer=void 0),this._windowStateSubscription&&(this._windowStateSubscription.dispose(),this._windowStateSubscription=void 0),this.stopMcpAuthRecoveryWatcher()}async logout(){if(this.stopTokenRefresh(),await L.getInstance().clearToken(),this._secretStorage){await this._secretStorage.delete(this.secretKey(ye)),await this._secretStorage.delete(this.secretKey(Se));let t=I.getInstance().getProfiles();for(let n of t)await this._secretStorage.delete(this.serverSecretKey(ye,n.apiBaseUrl,n.osClient)),await this._secretStorage.delete(this.serverSecretKey(Se,n.apiBaseUrl,n.osClient)),await this._secretStorage.delete(this.legacyServerSecretKey(ye,n.apiBaseUrl)),await this._secretStorage.delete(this.legacyServerSecretKey(Se,n.apiBaseUrl))}this._isLoggedIn=!1,await Ne.executeCommand("setContext",xe,!1),_.info("Microi: \u5DF2\u9000\u51FA\u767B\u5F55")}};var yi=/^\s*\*?\s*Version\s*:\s*(v\d+\.\d+\.\d+)\s*$/im,An=/^v(\d+)\.(\d+)\.(\d+)$/;function vt(a){let e=(a||"").trim();if(!e)return null;let t=e.match(An);if(t)return`v${Number(t[1])}.${Number(t[2])}.${Number(t[3])}`;let n=e.match(yi);return n?vt(n[1]):null}function Vn(a){if(!a)return null;let e=a.match(An);return e?{major:Number(e[1]),minor:Number(e[2]),patch:Number(e[3])}:null}function Si(a,e){return a.major!==e.major?a.major-e.major:a.minor!==e.minor?a.minor-e.minor:a.patch-e.patch}function Ci(a){let e=null;for(let t of a){let n=Vn(t);n&&(!e||Si(n,e)>0)&&(e=n)}return e?`v${e.major}.${e.minor}.${e.patch}`:null}function Ti(a){let e=Vn(a);if(!e)return"v1.0.0";let{major:t,minor:n,patch:i}=e;return i<9?`v${t}.${n}.${i+1}`:(i=0,n<9?`v${t}.${n+1}.${i}`:(n=0,t+=1,`v${t}.${n}.${i}`))}function vi(a){let e=(a||"").trim();return e?e.replace(/\r\n/g,`
32
32
  `).split(`
33
33
  `).map(t=>t.trim()).filter(Boolean):["\u8BF7\u8865\u5145\u8BE5 V8 \u4EE3\u7801\u7684\u5B8C\u6574\u529F\u80FD\u8BF4\u660E\u3002"]}function Ei(a){let e=a.replace(/\r\n/g,`
34
34
  `).split(`
@@ -36,13 +36,13 @@ Content-Type: application/octet-stream\r
36
36
  `):void 0}function wi(a){let e=a.replace(/^\uFEFF/,""),t=e.match(/^\s*\/\*[\s\S]*?\*\/\s*/);if(!t)return{body:e};let n=t[0];return/Microi\s+V8|Version\s*:|ChangeLog\s*:|ApiEngineKey\s*:|TableKey\s*:|WorkflowKey\s*:/i.test(n)?{header:n,body:e.slice(n.length)}:{body:e}}function bi(a,e,t){let n=a.functionDescription||Ei(t||""),i=vi(n),r=a.kind==="ApiEngine"?"V8 ApiEngine":a.kind==="V8Event"?"V8 Event":"V8 Workflow",o=a.kind==="ApiEngine"?"ApiEngineKey":a.kind==="V8Event"?"TableKey":"WorkflowKey",s=["/*",` * ${r}`,` * ${o}: ${a.key}`];a.eventType&&s.push(` * EventType: ${a.eventType}`),s.push(` * Version: ${e}`),s.push(" * Function:");for(let c of i)s.push(` * - ${c}`);return s.push(" */"),`${s.join(`
37
37
  `)}
38
38
 
39
- `}function tt(a){let e=vt(a.currentCode),t=vt(a.remoteCode),n=vt(a.remoteVersion),i=Ci([e,t,n]),r=a.initial?i||"v1.0.0":Ti(i),{header:o,body:s}=wi(a.currentCode||""),c=`${bi(a,r,o)}${s.replace(/^\s+/,"")}`,d=(a.changeSummary||"\u540C\u6B65 V8 \u4EE3\u7801").trim();return{code:c,version:r,changeHistory:`${r} ${d}`}}var Ke=class a{static getInstance(){return a._instance||(a._instance=new a),a._instance}constructor(){}get outputChannel(){return Y.channel}log(e){Y.log("\u540C\u6B65",e)}loadMeta(e){let t=I.getInstance(),n="";try{n=t.getSyncRootDir()}catch{}if(!n)return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let i=v.join(n,e,Ae);if(!T.existsSync(i))return this.migrateFromFlatMeta(e);try{let r=JSON.parse(T.readFileSync(i,"utf-8"));if(!r||typeof r!="object"||Array.isArray(r))throw new Error("\u9876\u5C42\u5FC5\u987B\u662F JSON \u5BF9\u8C61");let o=r;return{...o,engines:o.engines||{},events:o.events||{},fields:o.fields||{},menus:o.menus||{},menuButtons:o.menuButtons||{},menuScripts:o.menuScripts||{},workflows:o.workflows||{},workflowNodeEvents:o.workflowNodeEvents||{}}}catch(r){throw new Error(`Microi \u540C\u6B65\u5143\u6570\u636E\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${i}\uFF08${r instanceof Error?r.message:String(r)}\uFF09`)}}saveMeta(e,t){let n=I.getInstance();try{let i=n.getSyncRootDir();this.ensureSyncGitExcludes(i);let r=v.join(i,t);te(r);let o=v.join(r,Ae),s=`${o}.${process.pid}.${Date.now()}.tmp`;try{T.writeFileSync(s,`${JSON.stringify(e,null,2)}
39
+ `}function tt(a){let e=vt(a.currentCode),t=vt(a.remoteCode),n=vt(a.remoteVersion),i=Ci([e,t,n]),r=a.initial?i||"v1.0.0":Ti(i),{header:o,body:s}=wi(a.currentCode||""),c=`${bi(a,r,o)}${s.replace(/^\s+/,"")}`,l=(a.changeSummary||"\u540C\u6B65 V8 \u4EE3\u7801").trim();return{code:c,version:r,changeHistory:`${r} ${l}`}}var Ke=class a{static getInstance(){return a._instance||(a._instance=new a),a._instance}constructor(){}get outputChannel(){return Y.channel}log(e){Y.log("\u540C\u6B65",e)}loadMeta(e){let t=I.getInstance(),n="";try{n=t.getSyncRootDir()}catch{}if(!n)return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let i=v.join(n,e,Ae);if(!T.existsSync(i))return this.migrateFromFlatMeta(e);try{let r=JSON.parse(T.readFileSync(i,"utf-8"));if(!r||typeof r!="object"||Array.isArray(r))throw new Error("\u9876\u5C42\u5FC5\u987B\u662F JSON \u5BF9\u8C61");let o=r;return{...o,engines:o.engines||{},events:o.events||{},fields:o.fields||{},menus:o.menus||{},menuButtons:o.menuButtons||{},menuScripts:o.menuScripts||{},workflows:o.workflows||{},workflowNodeEvents:o.workflowNodeEvents||{}}}catch(r){throw new Error(`Microi \u540C\u6B65\u5143\u6570\u636E\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u5E76\u505C\u6B62\u5199\u5165\uFF1A${i}\uFF08${r instanceof Error?r.message:String(r)}\uFF09`)}}saveMeta(e,t){let n=I.getInstance();try{let i=n.getSyncRootDir();this.ensureSyncGitExcludes(i);let r=v.join(i,t);te(r);let o=v.join(r,Ae),s=`${o}.${process.pid}.${Date.now()}.tmp`;try{T.writeFileSync(s,`${JSON.stringify(e,null,2)}
40
40
  `,"utf-8"),T.renameSync(s,o)}finally{try{T.existsSync(s)&&T.unlinkSync(s)}catch{}}}catch{}}getWorkspaceFilePath(e){let t=I.getInstance().getWorkspaceRoot();return t?v.isAbsolute(e)?e:v.join(t,e):null}normalizeCode(e){return Ce(zt(e||"")).replace(/\r\n/g,`
41
- `).trimEnd()}isLocalModified(e,t){try{if(!T.existsSync(e))return!1;let n=T.statSync(e),i=new Date(t);return isNaN(i.getTime())?!1:n.mtime.getTime()>i.getTime()+1e3}catch{return!1}}getLocalModifiedTime(e,t){try{if(!T.existsSync(e))return null;let n=T.statSync(e),i=new Date(t);return isNaN(i.getTime())?null:n.mtime.getTime()>i.getTime()+1e3?me(n.mtime):null}catch{return null}}touchSyncedFile(e,t){let n=new Date(t),i=isNaN(n.getTime())?new Date:n;try{T.utimesSync(e,i,i)}catch{}}ensureSyncGitExcludes(e){try{let t=e||I.getInstance().getSyncRootDir();Be(t),ve(t,[".backups/","**/.backups/",".microi-mcp-tokens.json","**/.microi-mcp-tokens.json"])}catch{}}shortBackupKey(e){return require("crypto").createHash("sha1").update(e||"").digest("hex").slice(0,10)}getMenuButtonMetaKey(e,t,n,i){return`${e}__${t}__${n}__${i}`}getMenuScriptMetaKey(e,t){return`${e}__${t}`}sourceHash(e){return require("crypto").createHash("sha256").update(this.normalizeCode(e||"")).digest("hex")}extractTrailingKey(e){let t=e.match(/[((]([^))]+)[))]\s*$/);return t?t[1]:e}getServerDirs(){try{let e=I.getInstance().getSyncRootDir();return T.existsSync(e)?T.readdirSync(e,{withFileTypes:!0}).filter(t=>t.isDirectory()).filter(t=>!t.name.startsWith(".")).map(t=>t.name):[]}catch{return[]}}getLocalChangeSummary(){let e={engines:0,events:0,fields:0,menuButtons:0,menuScripts:0,workflowNodeEvents:0,total:0};for(let t of this.getLocalChangeItems())t.kind==="engine"?e.engines+=1:t.kind==="event"?e.events+=1:t.kind==="field"?e.fields+=1:t.kind==="menuButton"?e.menuButtons+=1:t.kind==="menuScript"?e.menuScripts+=1:t.kind==="workflow"&&(e.workflowNodeEvents+=1);return e.total=e.engines+e.events+e.fields+e.menuButtons+e.menuScripts+e.workflowNodeEvents,e}getLocalChangeItems(){let e=[],t=(n,i,r,o,s)=>{let c=this.getWorkspaceFilePath(s.filePath);if(!c)return;let d=this.getLocalModifiedTime(c,s.updateTime);d&&e.push({kind:i,key:r,name:o,serverDir:n,filePath:c,updateTime:s.updateTime,modifiedTime:d})};for(let n of this.getServerDirs()){let i=this.loadMeta(n);for(let[r,o]of Object.entries(i.engines))t(n,"engine",r,o.apiName||r,o);for(let[r,o]of Object.entries(i.events))t(n,"event",r,`${o.description||o.formEngineKey}/${o.eventType}`,o);for(let[r,o]of Object.entries(i.fields||{}))t(n,"field",r,`${o.tableName}.${o.fieldName}/${o.v8Key}`,o);for(let[r,o]of Object.entries(i.menuButtons||{}))t(n,"menuButton",r,`${o.moduleName}/${o.btnName}/${o.v8SubField}`,o);for(let[r,o]of Object.entries(i.menuScripts||{}))t(n,"menuScript",r,`${o.moduleName}/${o.scriptField}`,o);for(let[r,o]of Object.entries(i.workflowNodeEvents||{}))t(n,"workflow",r,`${o.flowName}/${o.nodeName}/${o.eventType}`,o)}return e}async checkRemoteDifferences(e,t="all",n){let i=e?[e]:I.getInstance().getProfiles(),r=[];for(let o of i){let s=I.getInstance().buildServerDirName(o.label,o.apiBaseUrl),c=this.loadMeta(s),d=n?this.getTargetSyncKind(c,n):null;if(n&&!d)throw new Error(`\u540C\u6B65\u76EE\u6807\u4E0D\u5728\u672C\u5730\u57FA\u7EBF\u4E2D: ${n}`);(t==="all"||t==="api")&&(!n||d==="engine")&&await this.collectEngineDifferences(o,s,c,r,n),(t==="all"||t==="form")&&(!n||d==="event")&&await this.collectEventDifferences(o,s,c,r,n),(t==="all"||t==="form")&&(!n||d==="field")&&await this.collectFieldDifferences(o,s,c,r,n),(t==="all"||t==="module")&&(!n||d==="menuButton")&&await this.collectMenuButtonDifferences(o,s,c,r,n),(t==="all"||t==="module")&&(!n||d==="menuScript")&&await this.collectMenuScriptDifferences(o,s,c,r,n),(t==="all"||t==="workflow")&&(!n||d==="workflow")&&await this.collectWorkflowDifferences(o,s,c,r,n)}return r}matchesTargetFile(e,t){if(!t)return!0;let n=this.getWorkspaceFilePath(e);return!!n&&v.resolve(n).toLowerCase()===v.resolve(t).toLowerCase()}getTargetSyncKind(e,t){let n=[["engine",e.engines],["event",e.events],["field",e.fields||{}],["menuButton",e.menuButtons||{}],["menuScript",e.menuScripts||{}],["workflow",e.workflowNodeEvents||{}]];for(let[i,r]of n)if(Object.values(r).some(o=>this.matchesTargetFile(o.filePath,t)))return i;return null}classifyDifference(e,t,n,i){return n===i?null:e&&t?"conflict":e?"localModified":"remoteModified"}classifyRemoteDeletion(e,t){return this.isLocalModified(e,t)?"conflict":"remoteDeleted"}createRemoteDeletedItem(e,t,n,i,r,o){return!r||!T.existsSync(r)?null:{kind:e,status:this.classifyRemoteDeletion(r,o),name:t,key:n,serverDir:i,filePath:r,localCode:this.normalizeCode(T.readFileSync(r,"utf-8")),remoteCode:"",localUpdateTime:o,remoteUpdateTime:""}}isRemoteNewer(e,t){let n=new Date(e||"").getTime(),i=new Date(t||"").getTime();return isNaN(n)||isNaN(i)?!1:n>i+1e3}getRemoteOnlyPlaceholderPath(e,t,n,i){let r=I.getInstance(),o=n==="api"?Ve:n==="form"?Te:n==="module"?ke:Oe;return v.join(r.getSyncRootDir(),t,r.buildOsClientDirName(e.osClient,e.osClientType,e.osClientNetwork),o,"\u670D\u52A1\u5668\u65B0\u589E\u5F85\u62C9\u53D6",`${K(i)}.js`)}async collectEngineDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_ENGINE_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u63A5\u53E3\u5F15\u64CE\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map(s.Data.List.map(g=>[g.ApiEngineKey,g])),d=!1;for(let[g,l]of Object.entries(n.engines)){if(!this.matchesTargetFile(l.filePath,r))continue;let u=c.get(g),p=this.getWorkspaceFilePath(l.filePath);if(!p||!T.existsSync(p))continue;if(!u){let w=this.createRemoteDeletedItem("engine",l.apiName||g,g,t,p,l.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.ApiV8Code||""),y=this.isLocalModified(p,l.updateTime),S=this.isRemoteNewer(u.UpdateTime,l.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(l.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),d=!0);continue}let C=this.classifyDifference(y,S,h,f);C&&i.push({kind:"engine",status:C,name:u.ApiName||l.apiName||g,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:l.updateTime,remoteUpdateTime:u.UpdateTime})}if(d&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.engines).map(g=>g.toLowerCase()));for(let g of s.Data.List)!String(g.ApiV8Code||"").trim()||m.has(g.ApiEngineKey.toLowerCase())||i.push({kind:"engine",status:"remoteModified",name:g.ApiName||g.ApiEngineKey,key:g.ApiEngineKey,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"api",g.ApiEngineKey),localCode:"",remoteCode:this.normalizeCode(g.ApiV8Code||""),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}async collectEventDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_EVENT_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u8868\u5355\u4E8B\u4EF6\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map;for(let g of s.Data.List){let l=`${g.FormEngineKey}__${g.EventType}`;c.set(l,g),c.set(l.toLowerCase(),g)}let d=!1;for(let[g,l]of Object.entries(n.events)){if(!this.matchesTargetFile(l.filePath,r))continue;let u=c.get(g)||c.get(g.toLowerCase()),p=this.getWorkspaceFilePath(l.filePath);if(!p||!T.existsSync(p))continue;if(!u){let w=this.createRemoteDeletedItem("event",`${l.description||l.formEngineKey}/${l.eventType}`,g,t,p,l.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.V8Code||""),y=this.isLocalModified(p,l.updateTime),S=this.isRemoteNewer(u.UpdateTime,l.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(l.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),d=!0);continue}let C=this.classifyDifference(y,S,h,f);C&&i.push({kind:"event",status:C,name:`${u.Description||l.formEngineKey}/${l.eventType}`,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:l.updateTime,remoteUpdateTime:u.UpdateTime})}if(d&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.events).map(g=>g.toLowerCase()));for(let g of s.Data.List){let l=`${g.FormEngineKey}__${g.EventType}`;!String(g.V8Code||"").trim()||m.has(l.toLowerCase())||i.push({kind:"event",status:"remoteModified",name:`${g.Description||g.FormEngineKey}/${g.EventType}`,key:l,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"form",l),localCode:"",remoteCode:this.normalizeCode(g.V8Code||""),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}}async collectFieldDifferences(e,t,n,i,r){let o=L.getInstance(),s=new Map;for(let d of Object.entries(n.fields||{})){if(!this.matchesTargetFile(d[1].filePath,r))continue;let m=s.get(d[1].tableId||d[1].tableName)||[];m.push(d),s.set(d[1].tableId||d[1].tableName,m)}let c=!1;await this.runInBatches([...s.values()],r?1:2,async d=>{let m=d[0][1],g=await o.get(x.GET_FIELD_LIST,{osClient:e.osClient,tableId:m.tableId,tableName:m.tableName},e.apiBaseUrl,e);if(g.Code!==1||!Array.isArray(g.Data?.List))throw new Error(`\u83B7\u53D6\u5B57\u6BB5\u540C\u6B65\u72B6\u6001\u5931\u8D25[${m.tableName}]: ${g.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let l=new Map(g.Data.List.map(u=>[String(u.Name||"").toLowerCase(),u]));for(let[u,p]of d){let h=l.get(p.fieldName.toLowerCase()),f=this.getWorkspaceFilePath(p.filePath);if(!f||!T.existsSync(f))continue;if(!h||!String(h[p.v8Key]||"").trim()){let b=this.createRemoteDeletedItem("field",`${p.tableName}.${p.fieldName}/${p.v8Key}`,u,t,f,p.updateTime);b&&i.push(b);continue}let y=this.normalizeCode(T.readFileSync(f,"utf-8")),S=this.normalizeCode(String(h[p.v8Key]||"")),C=String(h.UpdateTime||""),w=this.isLocalModified(f,p.updateTime),R=this.isRemoteNewer(C,p.updateTime);if(y===S){(w||R)&&C&&(p.updateTime=C,this.touchSyncedFile(f,C),c=!0);continue}let E=this.classifyDifference(w,R,y,S);E&&i.push({kind:"field",status:E,name:`${p.tableName}.${p.fieldName}/${p.v8Key}`,key:u,serverDir:t,filePath:f,localCode:y,remoteCode:S,localUpdateTime:p.updateTime,remoteUpdateTime:C})}}),c&&this.saveMeta(n,t)}async collectMenuButtonDifferences(e,t,n,i,r){let o=L.getInstance(),s=new Map;if(!r)for(let l of Object.keys(n.menus||{}))s.set(l,[]);for(let l of Object.entries(n.menuButtons||{})){if(!this.matchesTargetFile(l[1].filePath,r))continue;let u=s.get(l[1].moduleId)||[];u.push(l),s.set(l[1].moduleId,u)}let c=[];if(!r){let l=await o.get(x.LIST_MODULES,{osClient:e.osClient},e.apiBaseUrl,e);if(l.Code!==1||!Array.isArray(l.Data?.List))throw new Error(`\u83B7\u53D6\u6A21\u5757\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${l.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);c=l.Data.List}let d=new Set(c.map(l=>String(l.ParentId||"")).filter(Boolean)),m=new Map(c.map(l=>[l.Id,l]));for(let l of c){if(d.has(l.Id)||n.menus?.[l.Id])continue;let u=l.Label||l.Name||l.Id;i.push({kind:"menuButton",status:"remoteModified",name:`${u}/\u670D\u52A1\u5668\u65B0\u589E\u6A21\u5757`,key:l.Id,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"module",l.Id),localCode:"",remoteCode:JSON.stringify(l,null,2),localUpdateTime:"",remoteUpdateTime:String(l.UpdateTime||"")})}let g=!1;await this.runInBatches([...s.entries()],r?1:2,async([l,u])=>{let p=()=>{for(let[R,E]of u){let b=this.getWorkspaceFilePath(E.filePath);if(!b)continue;let V=this.createRemoteDeletedItem("menuButton",`${E.moduleName}/${E.btnName}/${E.v8SubField}`,R,t,b,E.updateTime);V&&i.push(V)}};if(!r&&!m.has(l)){p();return}let h=await o.get(x.GET_MODULE,{osClient:e.osClient,moduleId:l},e.apiBaseUrl,e);if(h.Code!==1||!h.Data){if(/不存在|not\s*found/i.test(String(h.Msg||""))){p();return}throw new Error(`\u83B7\u53D6\u6A21\u5757\u6309\u94AE\u540C\u6B65\u72B6\u6001\u5931\u8D25[${l}]: ${h.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`)}let f=h.Data,y=String(f.UpdateTime||""),S=new Map;for(let R of Object.keys($e)){let E=[];try{let b=f[R];E=typeof b=="string"?JSON.parse(b):Array.isArray(b)?b:[],Array.isArray(E)||(E=[])}catch{E=[]}S.set(R,new Map(E.map(b=>[String(b.Id||""),b])))}for(let[R,E]of u){let b=S.get(E.btnField)?.get(E.btnId),V=this.getWorkspaceFilePath(E.filePath);if(!V||!T.existsSync(V))continue;if(!b||!String(b[E.v8SubField]||"").trim()){let k=this.createRemoteDeletedItem("menuButton",`${E.moduleName}/${E.btnName}/${E.v8SubField}`,R,t,V,E.updateTime);k&&i.push(k);continue}let U=this.normalizeCode(T.readFileSync(V,"utf-8")),A=this.normalizeCode(String(b[E.v8SubField]||"")),P=this.isLocalModified(V,E.updateTime),O=this.isRemoteNewer(y,E.updateTime);if(U===A){(P||O)&&y&&(E.updateTime=y,this.touchSyncedFile(V,y),g=!0);continue}let F=this.classifyDifference(P,O,U,A);F&&i.push({kind:"menuButton",status:F,name:`${E.moduleName}/${E.btnName}/${E.v8SubField}`,key:R,serverDir:t,filePath:V,localCode:U,remoteCode:A,localUpdateTime:E.updateTime,remoteUpdateTime:y})}if(r)return;let C=new Set(u.map(([R])=>R)),w=n.menus?.[l]?.moduleName||m.get(l)?.Label||m.get(l)?.Name||l;for(let[R,E]of S)for(let[b,V]of E){if(!b)continue;let U=String(V.Name||b);for(let A of["V8Code","V8CodeShow"]){let P=String(V[A]||""),O=this.getMenuButtonMetaKey(l,R,b,A);!P.trim()||C.has(O)||i.push({kind:"menuButton",status:"remoteModified",name:`${w}/${U}/${A}`,key:O,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"module",O),localCode:"",remoteCode:this.normalizeCode(P),localUpdateTime:"",remoteUpdateTime:y})}}}),g&&this.saveMeta(n,t)}async collectMenuScriptDifferences(e,t,n,i,r){let o=L.getInstance(),s=Object.entries(n.menuScripts||{}).filter(([,d])=>this.matchesTargetFile(d.filePath,r)),c=!1;await this.runInBatches(s,r?1:2,async([d,m])=>{let g=this.getWorkspaceFilePath(m.filePath);if(!g||!T.existsSync(g))return;let l=await o.get(x.GET_MODULE,{osClient:e.osClient,moduleId:m.moduleId},e.apiBaseUrl,e);if(l.Code!==1||!l.Data){if(/不存在|not\s*found/i.test(String(l.Msg||""))){let w=this.createRemoteDeletedItem("menuScript",`${m.moduleName}/${m.scriptField}`,d,t,g,m.updateTime);w&&i.push(w);return}throw new Error(`\u83B7\u53D6\u6A21\u5757 Join/Where \u540C\u6B65\u72B6\u6001\u5931\u8D25[${m.moduleId}]: ${l.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`)}let u=l.Data,p=this.normalizeCode(String(u[m.scriptField]||"")),h=this.normalizeCode(T.readFileSync(g,"utf-8")),f=String(u.UpdateTime||""),y=this.isLocalModified(g,m.updateTime),S=this.sourceHash(p)!==m.codeHash;if(h===p){(y||S||f&&f!==m.updateTime)&&(m.codeHash=this.sourceHash(p),m.updateTime=f||m.updateTime,this.touchSyncedFile(g,m.updateTime),c=!0);return}let C=this.classifyDifference(y,S,h,p);C&&i.push({kind:"menuScript",status:C,name:`${m.moduleName}/${m.scriptField}`,key:d,serverDir:t,filePath:g,localCode:h,remoteCode:p,localUpdateTime:m.updateTime,remoteUpdateTime:f})}),c&&this.saveMeta(n,t)}async runInBatches(e,t,n){for(let i=0;i<e.length;i+=t)await Promise.all(e.slice(i,i+t).map(r=>n(r))),i+t<e.length&&await new Promise(r=>setTimeout(r,120))}async collectWorkflowDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_WORKFLOW_V8_EVENT_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u6D41\u7A0B\u4E8B\u4EF6\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map(s.Data.List.map(g=>[`${g.FlowDesignId}__${g.NodeId}__${g.EventType}`,g])),d=!1;for(let[g,l]of Object.entries(n.workflowNodeEvents||{})){if(!this.matchesTargetFile(l.filePath,r))continue;let u=c.get(g),p=this.getWorkspaceFilePath(l.filePath);if(!p||!T.existsSync(p))continue;if(!u||!String(u.V8Code||u.Code||"").trim()){let w=this.createRemoteDeletedItem("workflow",`${l.flowName}/${l.nodeName}/${l.eventType}`,g,t,p,l.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.V8Code||u.Code||""),y=this.isLocalModified(p,l.updateTime),S=this.isRemoteNewer(u.UpdateTime,l.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(l.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),d=!0);continue}let C=this.classifyDifference(y,S,h,f);if(C){let w=`${u.FlowName||l.flowName}/${u.NodeName||l.nodeName}/${u.EventType||l.eventType}`;i.push({kind:"workflow",status:C,name:w,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:l.updateTime,remoteUpdateTime:u.UpdateTime})}}if(d&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.workflowNodeEvents||{}));for(let g of s.Data.List){let l=`${g.FlowDesignId}__${g.NodeId}__${g.EventType}`,u=g.V8Code||g.Code||"";if(!u.trim()||m.has(l))continue;let p=`${g.FlowName||g.FlowDesignId}/${g.NodeName||g.NodeId}/${g.EventType}`;i.push({kind:"workflow",status:"remoteModified",name:p,key:l,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"workflow",l),localCode:"",remoteCode:this.normalizeCode(u),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}}migrateFromFlatMeta(e){let t=I.getInstance();try{let n=t.getSyncRootDir(),i=v.join(n,Ae);if(!T.existsSync(i))return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let r=t.getWorkspaceRoot();if(!r)return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let o=JSON.parse(T.readFileSync(i,"utf-8")),s=o.engines||{},c=o.events||{},d={engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};for(let[m,g]of Object.entries(s)){let l=g;if(l.filePath){let u=v.join(r,l.filePath);v.relative(n,u).split(v.sep)[0]===e&&(d.engines[m]=l)}}for(let[m,g]of Object.entries(c)){let l=g;if(l.filePath){let u=v.join(r,l.filePath);v.relative(n,u).split(v.sep)[0]===e&&(d.events[m]=l)}}return(Object.keys(d.engines).length>0||Object.keys(d.events).length>0)&&this.saveMeta(d,e),d}catch{return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}}}}async pullEngines(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0){_.warn("Microi: \u6CA1\u6709\u5DF2\u8FDE\u63A5\u7684\u670D\u52A1\u5668\uFF0C\u8BF7\u5148\u5728\u8BBE\u7F6E\u4E2D\u6DFB\u52A0\u8FDE\u63A5\u5E76\u767B\u5F55");return}for(let n of t)try{await this.pullEnginesForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`),_.error(`Microi: \u62C9\u53D6 [${n.label||n.apiBaseUrl}] \u5931\u8D25 - ${r}`)}return}await this.pullEnginesForProfile(e)}async pullEnginesForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE\u4EE3\u7801 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u63A5\u53E3\u5F15\u64CE [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u68C0\u67E5\u540E\u7AEF\u72B6\u6001..."});let s=await n.get(x.GET_STATUS,void 0,i,e);if(s.Code!==1){let F=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u540E\u7AEF\u72B6\u6001\u5F02\u5E38: ${s.Msg||"Code="+s.Code}${F}`)}o.report({message:"\u83B7\u53D6\u7CFB\u7EDF\u914D\u7F6E..."});let d=await ge.getInstance().getSysConfig(i,r),m=d?.SysShortTitle||"",g=d?.SysTitle||"",l=m||g||d?.CompanyName||e.label||"";l&&(l!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:l,sysShortTitle:m,sysTitle:g}),o.report({message:"\u83B7\u53D6\u63A5\u53E3\u5F15\u64CE\u5217\u8868..."});let u=await n.get(x.GET_ENGINE_LIST,{osClient:r},i,e);if(u.Code!==1){let F=u.Code===1001||u.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u5217\u8868\u5931\u8D25: ${u.Msg||"Code="+u.Code}${F}`)}let{OsClient:p,OsClientType:h,OsClientNetwork:f,List:y,Total:S}=u.Data;if(this.log(`\u83B7\u53D6\u5230 ${S} \u4E2A\u63A5\u53E3\u5F15\u64CE (OsClient: ${p})`),!h||!f)throw new Error(`\u540E\u7AEF\u672A\u8FD4\u56DE\u5B8C\u6574\u7684 OsClientType/OsClientNetwork (OsClient: ${p}, Type: ${h||"\u7A7A"}, Network: ${f||"\u7A7A"})\uFF0C\u65E0\u6CD5\u62C9\u53D6\u4EE3\u7801`);if(h||f){let F={...e,osClientType:h,osClientNetwork:f};await t.addProfile(F)}let C=t.getSyncRootDir(),w=t.buildServerDirName(l,i),R=this.loadMeta(w),E=0,b=0,V=[],U=new Set,A=new Set,P=t.buildOsClientDirName(p,h,f);for(let F of y)try{let k=K(F.Category||"\u672A\u5206\u7C7B"),$=K(F.ApiName||F.ApiEngineKey),j=v.join(C,w,P,Ve,k),W=K(`${$}(${Gt(F.ApiEngineKey)}).js`),ee=v.join(j,W),re=zt(F.ApiV8Code||"");if(!re.trim()){b++,T.existsSync(ee)&&this.backupAndDeleteSyncFile(ee,w,"remote-deleted-api"),delete R.engines[F.ApiEngineKey];continue}U.add(F.ApiEngineKey),te(j),T.writeFileSync(ee,re,"utf-8");let q=new Date(F.UpdateTime);isNaN(q.getTime())||T.utimesSync(ee,q,q),R.engines[F.ApiEngineKey]={id:F.Id,apiName:F.ApiName,category:k,apiAddress:F.ApiAddress,updateTime:F.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),ee)},E++,o.report({message:`${E}/${S} ${F.ApiEngineKey}`,increment:1/S*100})}catch(k){let $=k instanceof Error?k.message:String(k);A.add(F.ApiEngineKey),V.push(`${F.ApiEngineKey}: ${$}`),this.log(`\u63A5\u53E3\u5F15\u64CE\u6587\u4EF6\u5199\u5165\u5931\u8D25\uFF0C\u7EE7\u7EED\u4E0B\u4E00\u9879 [${F.ApiEngineKey}]: ${$}`)}for(let[F,k]of Object.entries(R.engines)){if(U.has(F)||A.has(F))continue;let $=this.getWorkspaceFilePath(k.filePath);$&&this.backupAndDeleteSyncFile($,w,"remote-deleted-api"),delete R.engines[F]}this.saveMeta(R,w);let O=l||e.label||i;this.log(`[${O}] \u62C9\u53D6\u5B8C\u6210: ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${b} \u9879\uFF0C\u5931\u8D25 ${V.length} \u9879`),V.length>0?_.warn(`Microi: [${O}] \u5DF2\u62C9\u53D6 ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE\uFF0C${V.length} \u4E2A\u6587\u4EF6\u5931\u8D25\uFF1B\u5931\u8D25\u660E\u7EC6\u5DF2\u5199\u5165 Microi \u8F93\u51FA\u3002`):_.info(`Microi: [${O}] \u6210\u529F\u62C9\u53D6 ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE${b>0?`\uFF08\u8DF3\u8FC7 ${b} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)})}async pullEvents(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0)return;for(let n of t)try{await this.pullEventsForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6V8\u4E8B\u4EF6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`)}return}await this.pullEventsForProfile(e)}async pullEventsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6V8\u4E8B\u4EF6\u4EE3\u7801 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6V8\u4E8B\u4EF6 [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6V8\u4E8B\u4EF6\u5217\u8868..."});let s=await n.get(x.GET_EVENT_LIST,{osClient:r},i,e);if(s.Code!==1){let P=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6V8\u4E8B\u4EF6\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}${P}`)}let{List:c,Total:d}=s.Data;this.log(`\u83B7\u53D6\u5230 ${d} \u4E2AV8\u4E8B\u4EF6`);let g=await ge.getInstance().getSysConfig(i,r),l=g?.SysShortTitle||"",u=g?.SysTitle||"",p=l||u||g?.CompanyName||e.label||"";p&&(p!==e.label||l!==e.sysShortTitle||u!==e.sysTitle)&&await t.addProfile({...e,label:p,sysShortTitle:l,sysTitle:u});let h=t.getSyncRootDir(),f=t.buildServerDirName(p,i),y=this.loadMeta(f),S=0,C=0,w=0,R=new Set(c.map(P=>`${P.FormEngineKey}__${P.EventType}`)),b=t.getProfiles().find(P=>P.apiBaseUrl===e.apiBaseUrl&&P.osClient===e.osClient)||e;if(!b.osClientType||!b.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE\u4EE5\u83B7\u53D6\u5B8C\u6574\u914D\u7F6E");let V=t.buildOsClientDirName(r,b.osClientType,b.osClientNetwork),U={SubmitBeforeServerV8:"\u540E\u7AEF\u63D0\u4EA4\u524DV8\u4E8B\u4EF6",SubmitAfterServerV8:"\u540E\u7AEF\u63D0\u4EA4\u540EV8\u4E8B\u4EF6",SubmitFormV8:"\u524D\u7AEF\u8868\u5355\u63D0\u4EA4V8\u4E8B\u4EF6",OutFormV8:"\u524D\u7AEF\u8868\u5355\u9000\u51FAV8\u4E8B\u4EF6",ServerDataV8:"\u540E\u7AEF\u6570\u636EV8\u4E8B\u4EF6"};for(let P of c){let O=P.V8Code||"",F=K(P.Description?`${P.Description}\uFF08${P.FormEngineKey}\uFF09`:P.FormEngineKey),k=pn[P.EventType]||P.EventType,$=K(`${k}\uFF08${P.EventType}\uFF09`)+".js",j=v.join(h,f,V,Te,F,ut);te(j);let W=v.join(j,$),ee=U[P.EventType];if(ee){let ce=K(`${ee}\uFF08${P.EventType}\uFF09`)+".js",X=v.join(j,ce);X!==W&&T.existsSync(X)&&!this.isLocalModified(X,P.UpdateTime)&&(T.existsSync(W)?T.unlinkSync(X):T.renameSync(X,W))}let re=`${P.FormEngineKey}__${P.EventType}`;if(y.events[re]={id:P.Id,formEngineKey:P.FormEngineKey,description:P.Description||"",eventType:P.EventType,updateTime:P.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),W)},!O.trim()){T.existsSync(W)&&this.backupAndDeleteSyncFile(W,f,"remote-deleted-form-event"),w++,S++,o.report({message:`${S}/${d}`,increment:d>0?1/d*100:void 0});continue}T.writeFileSync(W,O,"utf-8");let q=new Date(P.UpdateTime);isNaN(q.getTime())||T.utimesSync(W,q,q),C++,S++,o.report({message:`${S}/${d}`,increment:d>0?1/d*100:void 0})}for(let[P,O]of Object.entries(y.events)){if(R.has(P))continue;let F=this.getWorkspaceFilePath(O.filePath);F&&this.backupAndDeleteSyncFile(F,f,"remote-deleted-form-event"),delete y.events[P]}this.saveMeta(y,f);let A=p||e.label||i;this.log(`[${A}] \u62C9\u53D6\u5B8C\u6210: ${C} \u4E2AV8\u4E8B\u4EF6\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${w} \u9879`),_.info(`Microi: [${A}] \u6210\u529F\u62C9\u53D6 ${C} \u4E2AV8\u4E8B\u4EF6\u6587\u4EF6${w>0?`\uFF08\u8DF3\u8FC7 ${w} \u4E2A\u7A7A\u4EE3\u7801\u4E8B\u4EF6\uFF09`:""}`)})}async pullWorkflows(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0)return;for(let n of t)try{await this.pullWorkflowsForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`)}return}await this.pullWorkflowsForProfile(e)}async pullWorkflowsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE\u8282\u70B9 V8 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6\u6D41\u7A0B\u8282\u70B9V8\u5217\u8868..."});let s=await n.get(x.GET_WORKFLOW_V8_EVENT_LIST,{osClient:r},i,e);if(s.Code!==1){let k=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u6D41\u7A0B\u8282\u70B9V8\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}${k}`)}let d=await ge.getInstance().getSysConfig(i,r),m=d?.SysShortTitle||"",g=d?.SysTitle||"",l=m||g||d?.CompanyName||e.label||"";l&&(l!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:l,sysShortTitle:m,sysTitle:g});let p=t.getProfiles().find(k=>k.apiBaseUrl===e.apiBaseUrl&&k.osClient===e.osClient)||e;if(!p.osClientType||!p.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let h=s.Data.OsClient||r,f=t.buildServerDirName(l,i),y=t.buildOsClientDirName(h,p.osClientType,p.osClientNetwork),S=t.getSyncRootDir(),C=this.loadMeta(f);C.workflows||(C.workflows={}),C.workflowNodeEvents||(C.workflowNodeEvents={});let w=s.Data.Flows||[],R=s.Data.Nodes||[],E=s.Data.Lines||[],b=s.Data.List||[],V=new Map(w.map(k=>[String(k.Id||""),k])),U=new Set(w.map(k=>String(k.Id||"")).filter(Boolean)),A=new Set(b.filter(k=>String(k.V8Code||k.Code||"").trim()).map(k=>`${k.FlowDesignId}__${k.NodeId}__${k.EventType}`)),P=0,O=0;for(let k of w){let $=String(k.Id||"");if(!$)continue;let j=String(k.FlowName||$),W=String(k.UpdateTime||me()),ee=v.join(S,f,y,Oe,K(`${j}\uFF08${$}\uFF09`));te(ee);let re=R.filter(X=>String(X.FlowDesignId||"")===$),q=E.filter(X=>String(X.FlowDesignId||"")===$),ce=v.join(ee,"\u6D41\u7A0B\u8BBE\u8BA1\u56FE\uFF08WF_FlowDesign\uFF09.json");T.writeFileSync(ce,JSON.stringify({FlowDesign:k,Nodes:re,Lines:q},null,2),"utf-8"),this.touchSyncedFile(ce,W),C.workflows[$]={flowDesignId:$,flowName:j,updateTime:W,filePath:v.relative(t.getWorkspaceRoot(),ce)}}for(let k of b){let $=String(k.FlowDesignId||""),j=String(k.NodeId||""),W=String(k.EventType||"");if(!$||!j||!W)continue;let ee=V.get($),re=String(k.FlowName||ee?.FlowName||$),q=String(k.NodeName||j),ce=fn[W]||k.EventName||W,X=v.join(S,f,y,Oe,K(`${re}\uFF08${$}\uFF09`),mt,K(`${q}\uFF08${j}\uFF09`));te(X);let N=v.join(X,K(`${ce}\uFF08${W}\uFF09`)+".js"),se=k.V8Code||k.Code||"",Q=String(k.UpdateTime||ee?.UpdateTime||me());if(C.workflowNodeEvents[`${$}__${j}__${W}`]={flowDesignId:$,flowName:re,nodeId:j,nodeName:q,eventType:W,updateTime:Q,filePath:v.relative(t.getWorkspaceRoot(),N)},!se.trim()){T.existsSync(N)&&this.backupAndDeleteSyncFile(N,f,"remote-deleted-workflow-event"),O++,o.report({message:`${P}/${b.length} ${re}/${q}`});continue}T.writeFileSync(N,se,"utf-8"),this.touchSyncedFile(N,Q),P++,o.report({message:`${P}/${b.length} ${re}/${q}`})}for(let[k,$]of Object.entries(C.workflowNodeEvents)){if(A.has(k))continue;let j=this.getWorkspaceFilePath($.filePath);j&&this.backupAndDeleteSyncFile(j,f,"remote-deleted-workflow-event"),delete C.workflowNodeEvents[k]}for(let[k,$]of Object.entries(C.workflows)){if(U.has(k))continue;let j=this.getWorkspaceFilePath($.filePath);j&&this.backupAndDeleteSyncFile(j,f,"remote-deleted-workflow"),delete C.workflows[k]}this.saveMeta(C,f);let F=l||e.label||i;this.log(`[${F}] \u6D41\u7A0B\u5F15\u64CE\u62C9\u53D6\u5B8C\u6210: ${w.length} \u4E2A\u6D41\u7A0B\uFF0C${P} \u4E2A\u8282\u70B9V8\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${O} \u9879`),_.info(`Microi: [${F}] \u6210\u529F\u62C9\u53D6 ${w.length} \u4E2A\u6D41\u7A0B\u3001${P} \u4E2A\u6D41\u7A0B\u8282\u70B9V8\u6587\u4EF6${O>0?`\uFF08\u8DF3\u8FC7 ${O} \u4E2A\u7A7A\u4EE3\u7801\u4E8B\u4EF6\uFF09`:""}`)})}findProfileByServerDir(e){let t=I.getInstance(),n=t.getProfiles();for(let i of n)if(t.buildServerDirName(i.label,i.apiBaseUrl)===e)return i}hasSyncBaseline(e,t){let n=v.resolve(e).toLowerCase(),i=this.loadMeta(t);return[i.engines,i.events,i.fields||{},i.menuButtons||{},i.menuScripts||{},i.workflowNodeEvents||{}].some(o=>Object.values(o).some(s=>{let c=this.getWorkspaceFilePath(s.filePath);return!!c&&v.resolve(c).toLowerCase()===n}))}async runPushPreflight(e,t,n,i){if(!n){let r=`\u65E0\u6CD5\u8BC6\u522B\u6587\u4EF6\u6240\u5C5E\u670D\u52A1\u5668\u914D\u7F6E\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\uFF1A${e}`;return this.log(r),_.error(`Microi: ${r}`),!1}if(!this.hasSyncBaseline(e,t)){let r=`\u6587\u4EF6\u6CA1\u6709\u540C\u6B65\u57FA\u7EBF\uFF0C\u65E0\u6CD5\u786E\u8BA4\u670D\u52A1\u5668\u7AEF\u662F\u5426\u66F4\u65B0\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u3002\u8BF7\u5148\u62C9\u53D6\u5BF9\u5E94\u5F15\u64CE\uFF1A${e}`;return this.log(r),_.error(`Microi: ${r}`),!1}try{let r=await this.checkRemoteDifferences(n,i,e),o=v.resolve(e).toLowerCase(),s=r.find(m=>v.resolve(m.filePath).toLowerCase()===o);if(!s||s.status==="localModified")return!0;let d=`${s.status==="conflict"?"\u672C\u5730\u4E0E\u670D\u52A1\u5668\u5747\u5DF2\u4FEE\u6539":s.status==="remoteDeleted"?"\u670D\u52A1\u5668\u7AEF\u8D44\u6E90\u5DF2\u5220\u9664":"\u670D\u52A1\u5668\u4EE3\u7801\u8F83\u65B0"}\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u4EE5\u907F\u514D\u8986\u76D6\u3002\u8BF7\u5728\u201C\u540C\u6B65\u7ED3\u679C\u201D\u4E2D\u67E5\u770B\u5DEE\u5F02\u5E76\u62C9\u53D6\u6216\u5408\u5E76\uFF1A${s.name}`;return this.log(d),_.error(`Microi: ${d}`),!1}catch(r){let o=r instanceof Error?r.message:String(r);return this.log(`\u63A8\u9001\u524D\u540C\u6B65\u72B6\u6001\u68C0\u6D4B\u5931\u8D25\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\uFF1A${o}`),_.error(`Microi: \u63A8\u9001\u524D\u540C\u6B65\u72B6\u6001\u68C0\u6D4B\u5931\u8D25\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001 - ${o}`),!1}}async pushFile(e,t={}){let i=I.getInstance().getSyncRootDir();if(v.extname(e).toLowerCase()===".js"&&T.existsSync(e)){let g=kn(Ce(T.readFileSync(e,"utf-8")));if(g.length>0){let l=g[0],u=`\u68C0\u6D4B\u5230 AI/\u7EC8\u7AEF\u5DE5\u5177\u8F93\u51FA\u6C61\u67D3\uFF08\u7B2C ${l.line} \u884C: ${l.marker}\uFF09\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u3002\u8BF7\u6062\u590D\u5B8C\u6574\u6E90\u7801\u540E\u518D\u8BD5\uFF1A${e}`;return this.log(u),_.error(`Microi: ${u}`),!1}}let r=Tn(e,i);if(r){let g=this.findProfileByServerDir(r.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,r.serverDir,g,"api")?!1:this.pushEngineFile(e,r,g)}let o=vn(e,i);if(o){let g=this.findProfileByServerDir(o.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,o.serverDir,g,"form")?!1:this.pushEventFile(e,o,g)}let s=En(e,i);if(s){let g=this.findProfileByServerDir(s.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,s.serverDir,g,"form")?!1:this.pushFieldFile(e,s,g)}let c=wn(e,i);if(c){let g=this.findProfileByServerDir(c.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,c.serverDir,g,"module")?!1:this.pushMenuButtonFile(e,c,g)}let d=bn(e,i);if(d){let g=this.findProfileByServerDir(d.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,d.serverDir,g,"module")?!1:this.pushMenuScriptFile(e,d,g)}let m=Dn(e,i);if(m){let g=this.findProfileByServerDir(m.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,m.serverDir,g,"workflow")?!1:this.pushWorkflowNodeFile(e,m,g)}return this.log(`\u65E0\u6CD5\u89E3\u6790\u6587\u4EF6\u8DEF\u5F84: ${e}`),!1}async pushEngineFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001\u63A5\u53E3\u5F15\u64CE: ${t.apiEngineKey}...`);try{let s="",c="";try{let u=await i.post(x.GET_ENGINE_CODE,{OsClient:t.osClient,ApiEngineKey:t.apiEngineKey},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.ApiV8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let d=!o.trim(),m=d?{code:"",version:c,changeHistory:""}:tt({kind:"ApiEngine",key:t.apiEngineKey,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001\u63A5\u53E3\u5F15\u64CE ${t.apiEngineKey}`}),g={OsClient:t.osClient,ApiEngineKey:t.apiEngineKey,ApiV8CodeBase64:Buffer.from(m.code,"utf8").toString("base64")};d||(g.Version=m.version,g.ChangeHistory=m.changeHistory);let l=await i.post(x.UPDATE_ENGINE_CODE,g,void 0,n?.apiBaseUrl,n);if(l.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.apiEngineKey}`);let u=l.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir);if(d?delete p.engines[t.apiEngineKey]:p.engines[t.apiEngineKey]&&(p.engines[t.apiEngineKey].updateTime=u),this.saveMeta(p,t.serverDir),d)T.existsSync(e)&&T.unlinkSync(e);else{T.writeFileSync(e,m.code,"utf-8");let h=new Date(u);isNaN(h.getTime())||T.utimesSync(e,h,h)}return!0}else return this.log(`\u63A8\u9001\u5931\u8D25: ${t.apiEngineKey} - ${l.Msg}`),_.error(`Microi: \u63A8\u9001\u5931\u8D25 - ${l.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u5F02\u5E38: ${t.apiEngineKey} - ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async pushEventFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001V8\u4E8B\u4EF6: ${t.formEngineKey}/${t.eventType}...`);try{let s="",c="";try{let u=await i.post(x.GET_EVENT_CODE,{OsClient:t.osClient,FormEngineKey:t.formEngineKey,EventType:t.eventType},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.V8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let d=!o.trim(),m=d?{code:"",version:c,changeHistory:""}:tt({kind:"V8Event",key:t.formEngineKey,eventType:t.eventType,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001 V8 \u4E8B\u4EF6 ${t.formEngineKey}/${t.eventType}`}),g={OsClient:t.osClient,FormEngineKey:t.formEngineKey,EventType:t.eventType,V8Code:m.code};d||(g.Version=m.version,g.ChangeHistory=m.changeHistory);let l=await i.post(x.UPDATE_EVENT_CODE,g,void 0,n?.apiBaseUrl,n);if(l.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.formEngineKey}/${t.eventType}`);let u=l.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir),h=`${t.formEngineKey}__${t.eventType}`;if(d)delete p.events[h];else{let f=p.events[h];p.events[h]={id:f?.id||"",formEngineKey:t.formEngineKey,description:f?.description||"",eventType:t.eventType,updateTime:u,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}}if(this.saveMeta(p,t.serverDir),d)T.existsSync(e)&&T.unlinkSync(e);else{T.writeFileSync(e,m.code,"utf-8");let f=new Date(u);isNaN(f.getTime())||T.utimesSync(e,f,f)}return!0}else return this.log(`\u63A8\u9001\u5931\u8D25: ${t.formEngineKey}/${t.eventType} - ${l.Msg}`),_.error(`Microi: \u63A8\u9001\u5931\u8D25 - ${l.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u5F02\u5E38: ${t.formEngineKey}/${t.eventType} - ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async createEngine(e){let t=L.getInstance(),n=I.getInstance();this.log(`\u521B\u5EFA\u63A5\u53E3\u5F15\u64CE: ${e.apiEngineKey}...`);try{let i=tt({kind:"ApiEngine",key:e.apiEngineKey,currentCode:"",functionDescription:`\u63A5\u53E3\u5F15\u64CE ${e.apiName} \u7684\u5B8C\u6574\u4E1A\u52A1\u903B\u8F91\u3002`,changeSummary:`\u901A\u8FC7 VS Code \u521B\u5EFA\u63A5\u53E3\u5F15\u64CE ${e.apiEngineKey}`,initial:!0}),r=await t.post(x.CREATE_ENGINE,{OsClient:e.profile.osClient,ApiName:e.apiName,ApiEngineKey:e.apiEngineKey,ApiAddress:e.apiAddress||"",ApiRemark:e.apiRemark||"",Lock:e.lock?1:0,LockKey:e.lockKey||"",AllowAnonymous:e.allowAnonymous?1:0,V8Unlimited:e.v8Unlimited?1:0,IsEnable:e.isEnable!==!1?1:0,ApiRole:e.apiRole||"",Category:e.category||"\u672A\u5206\u7C7B",ApiV8CodeBase64:Buffer.from(i.code,"utf8").toString("base64"),Version:i.version,ChangeHistory:i.changeHistory},void 0,e.profile.apiBaseUrl,e.profile);if(r.Code===1){let o=n.getSyncRootDir(),s=n.buildServerDirName(e.profile.label,e.profile.apiBaseUrl),c=n.buildOsClientDirName(e.profile.osClient,e.profile.osClientType,e.profile.osClientNetwork),d=K(e.category||"\u672A\u5206\u7C7B"),m=K(e.apiName||e.apiEngineKey),g=v.join(o,s,c,Ve,d);te(g);let l=v.join(g,K(`${m}(${Gt(e.apiEngineKey)}).js`));T.writeFileSync(l,i.code,"utf-8");let u=this.loadMeta(s);return u.engines[e.apiEngineKey]={id:"",apiName:e.apiName,category:d,apiAddress:e.apiAddress||"",updateTime:me(),filePath:v.relative(n.getWorkspaceRoot(),l)},this.saveMeta(u,s),this.log(`\u521B\u5EFA\u6210\u529F: ${e.apiEngineKey}`),_.info(`Microi: \u63A5\u53E3\u5F15\u64CE [${e.apiEngineKey}] \u521B\u5EFA\u6210\u529F`),await oe.showTextDocument(ln.file(l)),!0}else return this.log(`\u521B\u5EFA\u5931\u8D25: ${e.apiEngineKey} - ${r.Msg}`),_.error(`Microi: \u521B\u5EFA\u5931\u8D25 - ${r.Msg}`),!1}catch(i){let r=i instanceof Error?i.message:String(i);return this.log(`\u521B\u5EFA\u5F02\u5E38: ${e.apiEngineKey} - ${r}`),_.error(`Microi: \u521B\u5EFA\u5F02\u5E38 - ${r}`),!1}}async pullFields(e){if(!e){let t=I.getInstance().getProfiles();for(let n of t)try{await this.pullFieldsForProfile(n)}catch(i){this.log(`\u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${i instanceof Error?i.message:String(i)}`)}return}await this.pullFieldsForProfile(e)}async pullFieldsForTableFolder(e){let n=I.getInstance().getSyncRootDir(),i=v.relative(n,e).split(v.sep);if(i.length<4||i[2]!==Te){_.warn("Microi: \u8BF7\u5728\u201C\u8868\u5355\u5F15\u64CE\u201D\u4E0B\u7684\u8868\u76EE\u5F55\u6267\u884C\u5B57\u6BB5 V8 \u4E8B\u4EF6\u62C9\u53D6");return}let r=s=>{let c=s.match(/[((]([^))]+)[))]\s*$/);return c?c[1]:s},o=this.findProfileByServerDir(i[0]);if(!o){_.error(`Microi: \u672A\u627E\u5230\u4E0E\u76EE\u5F55 "${i[0]}" \u5339\u914D\u7684\u670D\u52A1\u5668\u8FDE\u63A5`);return}await this.pullFieldsForTable(o,r(i[3]),e,i[0])}async pullFieldsForTable(e,t,n,i){let r=I.getInstance(),o=L.getInstance(),s=this.loadMeta(i);s.fields||(s.fields={}),this.log(`\u62C9\u53D6\u8868\u5B57\u6BB5V8\u4E8B\u4EF6: ${t}...`);let c=await o.get(x.GET_FIELD_LIST,{osClient:e.osClient,tableName:t},e.apiBaseUrl,e);if(c.Code!==1){_.error(`Microi: \u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 - ${c.Msg}`);return}let d=c.Data.List||[],m=["V8Code","KeyupV8Code","V8TmpEngineTable","V8TmpEngineForm"],g=0,l=0;for(let u of d){let p=K(u.Label?`${u.Label}\uFF08${u.Name}\uFF09`:u.Name),h=v.join(n,Je,p);for(let f of m){let y=(u[f]||"").toString(),S=Vt[f]||f,C=K(`${S}\uFF08${f}\uFF09`)+".js",w=v.join(h,C),R=`${t}__${u.Name}__${f}`;if(!y.trim()){l++,T.existsSync(w)&&T.unlinkSync(w),delete s.fields[R];continue}te(h),T.writeFileSync(w,y,"utf-8");let E=new Date(u.UpdateTime);isNaN(E.getTime())||T.utimesSync(w,E,E),s.fields[R]={fieldId:u.Id,tableId:u.TableId,tableName:t,fieldName:u.Name,fieldLabel:u.Label||"",v8Key:f,updateTime:u.UpdateTime,filePath:v.relative(r.getWorkspaceRoot(),w)},g++}}this.saveMeta(s,i),_.info(`Microi: \u5DF2\u62C9\u53D6 ${t} \u7684 ${g} \u4E2A\u5B57\u6BB5V8\u4E8B\u4EF6\u6587\u4EF6${l>0?`\uFF08\u8DF3\u8FC7 ${l} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)}async pullFieldsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6 [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6\u8868\u5217\u8868..."});let s=await n.get(x.GET_DB_SCHEMA,{osClient:r},i,e);if(s.Code!==1)throw new Error(`\u83B7\u53D6\u8868\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}`);let c=s.Data.Tables||[],m=await ge.getInstance().getSysConfig(i,r),g=m?.SysShortTitle||"",l=m?.SysTitle||"",u=g||l||e.label||"",p=t.buildServerDirName(u,i),h=this.loadMeta(p);h.fields||(h.fields={});let y=t.getProfiles().find(A=>A.apiBaseUrl===e.apiBaseUrl&&A.osClient===e.osClient)||e;if(!y.osClientType||!y.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let S=t.buildOsClientDirName(r,y.osClientType,y.osClientNetwork),C=t.getSyncRootDir(),w=["V8Code","KeyupV8Code","V8TmpEngineTable","V8TmpEngineForm"],R=0,E=0,b=0,V=new Set,U=new Set;for(let A of c){b++,o.report({message:`[${b}/${c.length}] ${A.Name}`});let P=await n.get(x.GET_FIELD_LIST,{osClient:r,tableId:A.Id},i,e);if(P.Code!==1){U.add(A.Name.toLowerCase()),this.log(` \u8DF3\u8FC7\u8868 ${A.Name}: ${P.Msg}`);continue}let O=P.Data.List||[],F=K(A.Description?`${A.Description}\uFF08${A.Name}\uFF09`:A.Name);for(let k of O)for(let $ of w){let j=(k[$]||"").toString();if(!j.trim()){E++;continue}let W=K(k.Label?`${k.Label}\uFF08${k.Name}\uFF09`:k.Name),ee=Vt[$]||$,re=K(`${ee}\uFF08${$}\uFF09`)+".js",q=v.join(C,p,S,Te,F,Je,W);te(q);let ce=v.join(q,re);T.writeFileSync(ce,j,"utf-8");let X=new Date(k.UpdateTime);isNaN(X.getTime())||T.utimesSync(ce,X,X);let N=`${A.Name}__${k.Name}__${$}`;V.add(N),h.fields[N]={fieldId:k.Id,tableId:k.TableId,tableName:A.Name,fieldName:k.Name,fieldLabel:k.Label||"",v8Key:$,updateTime:k.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),ce)},R++}}for(let[A,P]of Object.entries(h.fields)){if(V.has(A)||U.has(P.tableName.toLowerCase()))continue;let O=this.getWorkspaceFilePath(P.filePath);O&&this.backupAndDeleteSyncFile(O,p,"remote-deleted-field-event"),delete h.fields[A]}this.saveMeta(h,p),this.log(`\u5B57\u6BB5V8\u4E8B\u4EF6\u62C9\u53D6\u5B8C\u6210: ${R} \u4E2A\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${E} \u9879`),_.info(`Microi: \u6210\u529F\u62C9\u53D6 ${R} \u4E2A\u5B57\u6BB5V8\u4E8B\u4EF6${E>0?`\uFF08\u8DF3\u8FC7 ${E} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)})}async pushFieldFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u5B57\u6BB5V8\u4E8B\u4EF6: ${t.tableName}/${t.fieldName}/${t.v8Key}...`);try{let o=await i.post(x.UPDATE_FIELD,{OsClient:t.osClient,TableName:t.tableName,Name:t.fieldName,[t.v8Key]:r},void 0,n?.apiBaseUrl,n);if(o.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.tableName}/${t.fieldName}/${t.v8Key}`);let s=this.loadMeta(t.serverDir),c=`${t.tableName}__${t.fieldName}__${t.v8Key}`;s.fields||(s.fields={});let d=o.Data?.UpdateTime||me();return r.trim()?s.fields[c]={fieldId:s.fields[c]?.fieldId||"",tableId:s.fields[c]?.tableId||"",tableName:t.tableName,fieldName:t.fieldName,fieldLabel:s.fields[c]?.fieldLabel||"",v8Key:t.v8Key,updateTime:d,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}:delete s.fields[c],this.saveMeta(s,t.serverDir),r.trim()?this.touchSyncedFile(e,d):T.existsSync(e)&&T.unlinkSync(e),!0}return this.log(`\u63A8\u9001\u5931\u8D25: ${o.Msg}`),_.error(`Microi: \u63A8\u9001\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 - ${o.Msg}`),!1}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${s}`),!1}}async pullMenuButtons(e){if(!e){let t=I.getInstance().getProfiles();for(let n of t)try{await this.pullMenuButtonsForProfile(n)}catch(i){this.log(`\u62C9\u53D6\u83DC\u5355\u6309\u94AE\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${i instanceof Error?i.message:String(i)}`)}return}await this.pullMenuButtonsForProfile(e)}async pullMenuButtonsForModuleFolder(e){let n=I.getInstance().getSyncRootDir(),i=v.relative(n,e).split(v.sep);if(i.length<4||i[2]!==ke){_.warn("Microi: \u8BF7\u5728\u201C\u6A21\u5757\u5F15\u64CE\u201D\u4E0B\u7684\u6A21\u5757\u76EE\u5F55\u6267\u884C\u62C9\u53D6");return}let r=this.findProfileByServerDir(i[0]);if(!r){_.error(`Microi: \u672A\u627E\u5230\u4E0E\u76EE\u5F55 "${i[0]}" \u5339\u914D\u7684\u670D\u52A1\u5668\u8FDE\u63A5`);return}let o=this.extractTrailingKey(v.basename(e));await this.pullMenuButtonsForProfile(r,o,i[0],i[1],e)}async pullMenuButtonsForProfile(e,t,n,i,r){let o=I.getInstance(),s=L.getInstance(),c=e.apiBaseUrl,d=e.osClient;this.log(`\u5F00\u59CB\u62C9\u53D6\u6A21\u5757 Join/Where \u4E0E\u6309\u94AE V8 \u4EE3\u7801 [${e.label||c}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u6A21\u5757\u4EE3\u7801 [${e.label||c}]`,cancellable:!1},async m=>{let g=await s.get(x.LIST_MODULES,{osClient:d},c,e);if(g.Code!==1)throw new Error(`\u83B7\u53D6\u6A21\u5757\u5217\u8868\u5931\u8D25: ${g.Msg}`);let l=g.Data.List||[],p=await ge.getInstance().getSysConfig(c,d),h=p?.SysShortTitle||"",f=p?.SysTitle||"",y=h||f||e.label||"",S=n||o.buildServerDirName(y,c),C=this.loadMeta(S);C.menus||(C.menus={}),C.menuButtons||(C.menuButtons={}),C.menuScripts||(C.menuScripts={});let R=o.getProfiles().find(N=>N.apiBaseUrl===e.apiBaseUrl&&N.osClient===e.osClient)||e;if(!R.osClientType||!R.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let E=i||o.buildOsClientDirName(d,R.osClientType,R.osClientNetwork),b=o.getSyncRootDir(),V=v.join(b,S,E,ke),U=Object.keys($e),A=Object.keys(qe),P=0,O=0,F=0,k=0,$=0,j=new Map(l.map(N=>[N.Id,N])),W=new Map,ee=N=>N||"";for(let N of l){let se=ee(N.ParentId);W.has(se)||W.set(se,[]),W.get(se).push(N)}let re=N=>N.sort((se,Q)=>{let le=typeof se.Sort=="number"?se.Sort:0,We=typeof Q.Sort=="number"?Q.Sort:0;return le!==We?le-We:String(se.Name||se.Label||"").localeCompare(String(Q.Name||Q.Label||""))}),q=t?j.get(t)?[j.get(t)]:[]:re(l.filter(N=>!N.ParentId||!j.has(N.ParentId)));if(t&&q.length===0)throw new Error(`\u627E\u4E0D\u5230\u6A21\u5757 Id=${t}`);let ce=t?r||v.join(V,K(`${q[0].Label||q[0].Name||q[0].Id}\uFF08${q[0].Id}\uFF09`)):V;if(this.backupExistingTree(ce,S,t?"module-subtree":"module-engine"),!t)C.menus={},C.menuButtons={},C.menuScripts={};else{let N=new Set,se=Q=>{if(!N.has(Q)){N.add(Q);for(let le of W.get(Q)||[])se(le.Id)}};se(t);for(let Q of N)delete C.menus[Q];for(let[Q,le]of Object.entries(C.menuButtons))N.has(le.moduleId)&&delete C.menuButtons[Q];for(let[Q,le]of Object.entries(C.menuScripts))N.has(le.moduleId)&&delete C.menuScripts[Q]}let X=async(N,se)=>{k++,m.report({message:`[${k}/${l.length}] ${N.Name||N.Label}`});let Q=N.Label||N.Name||N.Id,le=v.join(se,K(`${Q}\uFF08${N.Id}\uFF09`));te(le);let We=re(W.get(N.Id)||[]);if(We.length>0){for(let Z of We)await X(Z,le);return}let Pt=await s.get(x.GET_MODULE,{osClient:d,moduleId:N.Id},c,e);if(Pt.Code!==1){this.log(` \u8DF3\u8FC7\u6A21\u5757 ${N.Name}: ${Pt.Msg}`);return}let _t=Pt.Data,Ee=String(_t.UpdateTime||me()),tn={};for(let Z of A){let lt=String(_t[Z]||""),Nt=qe[Z]||Z,we=v.join(le,K(`${Nt}\uFF08${Z}\uFF09`)+".js");T.writeFileSync(we,lt,"utf-8"),this.touchSyncedFile(we,Ee),C.menuScripts[this.getMenuScriptMetaKey(N.Id,Z)]={moduleId:N.Id,moduleName:Q,scriptField:Z,codeHash:this.sourceHash(lt),updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),we)},F++}for(let Z of U){let lt=$e[Z]||Z,Nt=K(`${lt}\uFF08${Z}\uFF09`),we=v.join(le,Nt);te(we),O++;let dt=_t[Z],Pe=[];if(dt)try{Pe=typeof dt=="string"?JSON.parse(dt):dt,Array.isArray(Pe)||(Pe=[])}catch{this.log(` \u6309\u94AE JSON \u89E3\u6790\u5931\u8D25 ${N.Name}.${Z}`),Pe=[]}let ti=[...Pe].sort((_e,fe)=>String(_e.Id||"").localeCompare(String(fe.Id||"")));tn[Z]=require("crypto").createHash("sha1").update(JSON.stringify(ti)).digest("hex");for(let _e of Pe){let fe=String(_e.Id||""),gt=String(_e.Name||fe||"Unknown");if(!fe)continue;let nn=String(_e.V8Code||""),Mt=v.join(we,K(`${gt}\uFF08${fe}\uFF09`)+".js");C.menuButtons[this.getMenuButtonMetaKey(N.Id,Z,fe,"V8Code")]={moduleId:N.Id,moduleName:Q,btnField:Z,btnId:fe,btnName:gt,v8SubField:"V8Code",updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),Mt)},nn.trim()?(T.writeFileSync(Mt,nn,"utf-8"),this.touchSyncedFile(Mt,Ee),P++):$++;let rn=String(_e.V8CodeShow||"");if(rn.trim()){let Ft=v.join(we,K(`${gt}_\u663E\u9690\u5224\u65AD\uFF08${fe}\uFF09`)+".js");T.writeFileSync(Ft,rn,"utf-8"),this.touchSyncedFile(Ft,Ee),C.menuButtons[this.getMenuButtonMetaKey(N.Id,Z,fe,"V8CodeShow")]={moduleId:N.Id,moduleName:Q,btnField:Z,btnId:fe,btnName:gt,v8SubField:"V8CodeShow",updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),Ft)},P++}else $++}}C.menus[N.Id]={moduleId:N.Id,moduleName:Q,updateTime:Ee,buttonHashes:tn}};te(V);for(let N of q)await X(N,V);this.saveMeta(C,S),this.log(`\u6A21\u5757\u4EE3\u7801\u62C9\u53D6\u5B8C\u6210: ${P} \u4E2A\u6309\u94AEV8\u6587\u4EF6\uFF0C${F} \u4E2A Join/Where \u6587\u4EF6\uFF0C${O} \u4E2A\u6309\u94AE\u76EE\u5F55\uFF0C\u8DF3\u8FC7\u7A7A\u6309\u94AE\u4EE3\u7801 ${$} \u9879`),_.info(`Microi: \u6210\u529F\u62C9\u53D6 ${P} \u4E2A\u6309\u94AEV8\u6587\u4EF6\u548C ${F} \u4E2A Join/Where \u6587\u4EF6${$>0?`\uFF08\u8DF3\u8FC7 ${$} \u4E2A\u7A7A\u6309\u94AE\u4EE3\u7801\uFF09`:""}\uFF0C\u5DF2\u751F\u6210 ${O} \u4E2A\u6309\u94AE\u76EE\u5F55`)})}backupExistingTree(e,t,n){if(!T.existsSync(e))return;let r=I.getInstance().getSyncRootDir();this.ensureSyncGitExcludes(r);let o=v.join(r,".backups",n,this.shortBackupKey(t));te(o);let s=v.join(o,`${Date.now()}-${this.shortBackupKey(v.basename(e))}`);T.renameSync(e,s)}backupAndDeleteSyncFile(e,t,n){if(!T.existsSync(e))return;let i=I.getInstance(),r=i.getSyncRootDir();this.ensureSyncGitExcludes(r);let o=i.getWorkspaceRoot()||r,c=v.relative(o,e).split(v.sep).filter(g=>g&&g!=="..").map(K),d=v.join(r,".backups",n,this.shortBackupKey(t),String(Date.now())),m=v.join(d,...c.length?c:[K(v.basename(e))]);te(v.dirname(m)),T.copyFileSync(e,m),T.unlinkSync(e)}async pushMenuScriptFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u6A21\u5757\u811A\u672C: ${t.moduleId}.${t.scriptField}...`);try{let o=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n);if(o.Code!==1||!o.Data)return _.error(`Microi: \u63A8\u9001\u5931\u8D25 - \u62C9\u53D6\u6A21\u5757\u5931\u8D25 ${o.Msg}`),!1;let s=o.Data,c=String(s[t.scriptField]||""),d=I.getInstance(),m=d.getSyncRootDir();this.ensureSyncGitExcludes(m);let g=v.join(m,".backups","menu-script",this.shortBackupKey(t.serverDir),t.moduleId);te(g),T.writeFileSync(v.join(g,`${t.scriptField}-${Date.now()}.js`),c,"utf-8");let l={OsClient:t.osClient,ModuleId:t.moduleId,[t.scriptField]:r},u=await i.post(x.UPDATE_MODULE,l,void 0,n?.apiBaseUrl,n);if(u.Code!==1)return _.error(`Microi: \u63A8\u9001\u6A21\u5757 ${t.scriptField} \u5931\u8D25 - ${u.Msg}`),!1;let p=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n),h=p.Data;if(p.Code!==1||!h||this.normalizeCode(String(h[t.scriptField]||""))!==this.normalizeCode(r))return _.error(`Microi: ${t.scriptField} \u63A5\u53E3\u8FD4\u56DE\u6210\u529F\uFF0C\u4F46\u8FDC\u7AEF\u56DE\u8BFB\u4E0D\u4E00\u81F4\uFF1B\u5DF2\u4FDD\u7559\u672C\u5730\u4FEE\u6539\u548C\u8FDC\u7AEF\u5907\u4EFD`),!1;let f=String(h.UpdateTime||u.Data?.UpdateTime||me()),y=this.loadMeta(t.serverDir);return y.menuScripts||(y.menuScripts={}),y.menuScripts[this.getMenuScriptMetaKey(t.moduleId,t.scriptField)]={moduleId:t.moduleId,moduleName:String(h.Label||h.Name||s.Label||s.Name||t.moduleId),scriptField:t.scriptField,codeHash:this.sourceHash(r),updateTime:f,filePath:v.relative(d.getWorkspaceRoot(),e)},y.menus||(y.menus={}),y.menus[t.moduleId]={moduleId:t.moduleId,moduleName:String(h.Label||h.Name||s.Label||s.Name||t.moduleId),updateTime:f,buttonHashes:y.menus[t.moduleId]?.buttonHashes||{}},this.saveMeta(y,t.serverDir),this.touchSyncedFile(e,f),this.log(`\u63A8\u9001\u5E76\u56DE\u8BFB\u6210\u529F: ${t.moduleId}.${t.scriptField}`),!0}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u6A21\u5757\u811A\u672C\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u6A21\u5757\u811A\u672C\u5F02\u5E38 - ${s}`),!1}}async pushMenuButtonFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u6309\u94AEV8\u4EE3\u7801: ${t.moduleId}.${t.btnField}.${t.btnId}.${t.v8SubField}...`);try{let o=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n);if(o.Code!==1)return _.error(`Microi: \u63A8\u9001\u5931\u8D25 - \u62C9\u53D6\u6A21\u5757\u5931\u8D25 ${o.Msg}`),!1;let s=o.Data,c=[],d=s[t.btnField];if(d)try{c=typeof d=="string"?JSON.parse(d):d,Array.isArray(c)||(c=[])}catch{return _.error("Microi: \u63A8\u9001\u5931\u8D25 - \u6309\u94AE JSON \u89E3\u6790\u5931\u8D25"),!1}let g=I.getInstance().getSyncRootDir();this.ensureSyncGitExcludes(g);let l=v.join(g,".backups","menu-button-json",this.shortBackupKey(t.serverDir),t.moduleId);te(l);let u=v.join(l,`${t.btnField}-${Date.now()}.json`);T.writeFileSync(u,JSON.stringify(c,null,2),"utf-8");let p=c.find(y=>String(y.Id||"")===t.btnId);if(!p){let y=c.map(S=>Number(S.Sort||0)).filter(S=>!isNaN(S));p={Id:t.btnId,Name:t.btnName||t.btnId,Sort:y.length>0?Math.max(...y)+1:c.length+1,IsVisible:!0,ShowRow:t.btnField==="MoreBtns"},c.push(p)}p[t.v8SubField]=r;let h={OsClient:t.osClient,ModuleId:t.moduleId};h[t.btnField]=JSON.stringify(c);let f=await i.post(x.UPDATE_MODULE,h,void 0,n?.apiBaseUrl,n);if(f.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.moduleId}.${t.btnField}.${t.btnId}.${t.v8SubField}`);let y=f.Data?.UpdateTime||me(),S=this.loadMeta(t.serverDir);S.menuButtons||(S.menuButtons={});let C=this.getMenuButtonMetaKey(t.moduleId,t.btnField,t.btnId,t.v8SubField);return r.trim()?S.menuButtons[C]={moduleId:t.moduleId,moduleName:String(s.Name||s.Label||t.moduleId),btnField:t.btnField,btnId:t.btnId,btnName:String(p.Name||t.btnName||t.btnId),v8SubField:t.v8SubField,updateTime:y,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}:delete S.menuButtons[C],S.menus||(S.menus={}),S.menus[t.moduleId]={moduleId:t.moduleId,moduleName:String(s.Name||s.Label||t.moduleId),updateTime:y,buttonHashes:S.menus[t.moduleId]?.buttonHashes||{}},this.saveMeta(S,t.serverDir),r.trim()?this.touchSyncedFile(e,y):T.existsSync(e)&&T.unlinkSync(e),!0}return _.error(`Microi: \u63A8\u9001\u6309\u94AE\u5931\u8D25 - ${f.Msg}`),!1}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${s}`),!1}}async pushWorkflowNodeFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8: ${t.flowDesignId}/${t.nodeId}/${t.eventType}...`);try{let s="",c="";try{let u=await i.post(x.GET_WORKFLOW_V8_EVENT_CODE,{OsClient:t.osClient,FlowDesignId:t.flowDesignId,NodeId:t.nodeId,EventType:t.eventType},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.V8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let d=!o.trim(),m=d?{code:"",version:c,changeHistory:""}:tt({kind:"Workflow",key:`${t.flowDesignId}/${t.nodeId}`,eventType:t.eventType,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001\u6D41\u7A0B\u8282\u70B9 V8 ${t.flowDesignId}/${t.nodeId}/${t.eventType}`}),g={OsClient:t.osClient,FlowDesignId:t.flowDesignId,NodeId:t.nodeId,EventType:t.eventType};d?g.V8Code="":(g.V8CodeBase64=Buffer.from(m.code,"utf8").toString("base64"),g.Version=m.version,g.ChangeHistory=m.changeHistory);let l=await i.post(x.UPDATE_WORKFLOW_V8_EVENT_CODE,g,void 0,n?.apiBaseUrl,n);if(l.Code===1){let u=l.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir);p.workflowNodeEvents||(p.workflowNodeEvents={});let h=`${t.flowDesignId}__${t.nodeId}__${t.eventType}`;return d?delete p.workflowNodeEvents[h]:p.workflowNodeEvents[h]={flowDesignId:t.flowDesignId,flowName:p.workflowNodeEvents[h]?.flowName||t.flowDesignId,nodeId:t.nodeId,nodeName:p.workflowNodeEvents[h]?.nodeName||t.nodeId,eventType:t.eventType,updateTime:u,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)},this.saveMeta(p,t.serverDir),d?T.existsSync(e)&&T.unlinkSync(e):(T.writeFileSync(e,m.code,"utf-8"),this.touchSyncedFile(e,u)),this.log(`\u63A8\u9001\u6210\u529F: ${t.flowDesignId}/${t.nodeId}/${t.eventType}`),!0}return this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5931\u8D25: ${l.Msg}`),_.error(`Microi: \u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5931\u8D25 - ${l.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5F02\u5E38: ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async pullDbSchema(e){let t=I.getInstance(),n=L.getInstance();if(!e){let i=t.getProfiles();if(i.length===0){_.warn("Microi: \u6CA1\u6709\u5DF2\u8FDE\u63A5\u7684\u670D\u52A1\u5668");return}for(let r of i)try{await this.pullDbSchemaForProfile(r)}catch(o){let s=o instanceof Error?o.message:String(o);this.log(`\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5931\u8D25 [${r.label||r.apiBaseUrl}]: ${s}`)}return}await this.pullDbSchemaForProfile(e)}async pullDbSchemaForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784 [${e.label||i}]...`);let o=await n.get(x.GET_DB_SCHEMA,{osClient:r},i,e);if(o.Code!==1){let b=o.Code===1001||o.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5931\u8D25: ${o.Msg||"Code="+o.Code}${b}`)}let s=t.getSyncRootDir(),d=await ge.getInstance().getSysConfig(i,r),m=d?.SysShortTitle||"",g=d?.SysTitle||"",l=m||g||d?.CompanyName||e.label||"";l&&(l!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:l,sysShortTitle:m,sysTitle:g});let u=t.buildServerDirName(l,i),h=t.getProfiles().find(b=>b.apiBaseUrl===e.apiBaseUrl&&b.osClient===e.osClient)||e,f=t.buildOsClientDirName(r,h.osClientType,h.osClientNetwork),y=v.join(s,u,f);te(y);let S=v.join(y,Le);T.writeFileSync(S,JSON.stringify(o.Data,null,2),"utf-8");let C=v.join(y,De),w=this.formatDbSchemaMarkdown(o.Data,u,f);w&&T.writeFileSync(C,w,"utf-8");let R=o.Data.Tables?.length||0,E=l||e.label||i;this.log(`[${E}] \u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5B8C\u6210: ${R} \u5F20\u8868`),_.info(`Microi: [${E}] \u6210\u529F\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\uFF08${R} \u5F20\u8868\uFF09`)}formatDbSchemaMarkdown(e,t,n){let i=(e.Tables||[]).filter(c=>c.Name);if(!i.length)return"";let r=i.reduce((c,d)=>{let m=d._Fields||d.Fields||[];return c+m.length},0),o=e.Menus?.length||0,s=[];s.push(`# \u6570\u636E\u5E93\u7ED3\u6784 \u2014 ${t}/${n}
41
+ `).trimEnd()}isLocalModified(e,t){try{if(!T.existsSync(e))return!1;let n=T.statSync(e),i=new Date(t);return isNaN(i.getTime())?!1:n.mtime.getTime()>i.getTime()+1e3}catch{return!1}}getLocalModifiedTime(e,t){try{if(!T.existsSync(e))return null;let n=T.statSync(e),i=new Date(t);return isNaN(i.getTime())?null:n.mtime.getTime()>i.getTime()+1e3?me(n.mtime):null}catch{return null}}touchSyncedFile(e,t){let n=new Date(t),i=isNaN(n.getTime())?new Date:n;try{T.utimesSync(e,i,i)}catch{}}ensureSyncGitExcludes(e){try{let t=e||I.getInstance().getSyncRootDir();Be(t),ve(t,[".backups/","**/.backups/",".microi-mcp-tokens.json","**/.microi-mcp-tokens.json"])}catch{}}shortBackupKey(e){return require("crypto").createHash("sha1").update(e||"").digest("hex").slice(0,10)}getMenuButtonMetaKey(e,t,n,i){return`${e}__${t}__${n}__${i}`}getMenuScriptMetaKey(e,t){return`${e}__${t}`}sourceHash(e){return require("crypto").createHash("sha256").update(this.normalizeCode(e||"")).digest("hex")}extractTrailingKey(e){let t=e.match(/[((]([^))]+)[))]\s*$/);return t?t[1]:e}getServerDirs(){try{let e=I.getInstance().getSyncRootDir();return T.existsSync(e)?T.readdirSync(e,{withFileTypes:!0}).filter(t=>t.isDirectory()).filter(t=>!t.name.startsWith(".")).map(t=>t.name):[]}catch{return[]}}getLocalChangeSummary(){let e={engines:0,events:0,fields:0,menuButtons:0,menuScripts:0,workflowNodeEvents:0,total:0};for(let t of this.getLocalChangeItems())t.kind==="engine"?e.engines+=1:t.kind==="event"?e.events+=1:t.kind==="field"?e.fields+=1:t.kind==="menuButton"?e.menuButtons+=1:t.kind==="menuScript"?e.menuScripts+=1:t.kind==="workflow"&&(e.workflowNodeEvents+=1);return e.total=e.engines+e.events+e.fields+e.menuButtons+e.menuScripts+e.workflowNodeEvents,e}getLocalChangeItems(){let e=[],t=(n,i,r,o,s)=>{let c=this.getWorkspaceFilePath(s.filePath);if(!c)return;let l=this.getLocalModifiedTime(c,s.updateTime);l&&e.push({kind:i,key:r,name:o,serverDir:n,filePath:c,updateTime:s.updateTime,modifiedTime:l})};for(let n of this.getServerDirs()){let i=this.loadMeta(n);for(let[r,o]of Object.entries(i.engines))t(n,"engine",r,o.apiName||r,o);for(let[r,o]of Object.entries(i.events))t(n,"event",r,`${o.description||o.formEngineKey}/${o.eventType}`,o);for(let[r,o]of Object.entries(i.fields||{}))t(n,"field",r,`${o.tableName}.${o.fieldName}/${o.v8Key}`,o);for(let[r,o]of Object.entries(i.menuButtons||{}))t(n,"menuButton",r,`${o.moduleName}/${o.btnName}/${o.v8SubField}`,o);for(let[r,o]of Object.entries(i.menuScripts||{}))t(n,"menuScript",r,`${o.moduleName}/${o.scriptField}`,o);for(let[r,o]of Object.entries(i.workflowNodeEvents||{}))t(n,"workflow",r,`${o.flowName}/${o.nodeName}/${o.eventType}`,o)}return e}async checkRemoteDifferences(e,t="all",n){let i=e?[e]:I.getInstance().getProfiles(),r=[];for(let o of i){let s=I.getInstance().buildServerDirName(o.label,o.apiBaseUrl),c=this.loadMeta(s),l=n?this.getTargetSyncKind(c,n):null;if(n&&!l)throw new Error(`\u540C\u6B65\u76EE\u6807\u4E0D\u5728\u672C\u5730\u57FA\u7EBF\u4E2D: ${n}`);(t==="all"||t==="api")&&(!n||l==="engine")&&await this.collectEngineDifferences(o,s,c,r,n),(t==="all"||t==="form")&&(!n||l==="event")&&await this.collectEventDifferences(o,s,c,r,n),(t==="all"||t==="form")&&(!n||l==="field")&&await this.collectFieldDifferences(o,s,c,r,n),(t==="all"||t==="module")&&(!n||l==="menuButton")&&await this.collectMenuButtonDifferences(o,s,c,r,n),(t==="all"||t==="module")&&(!n||l==="menuScript")&&await this.collectMenuScriptDifferences(o,s,c,r,n),(t==="all"||t==="workflow")&&(!n||l==="workflow")&&await this.collectWorkflowDifferences(o,s,c,r,n)}return r}matchesTargetFile(e,t){if(!t)return!0;let n=this.getWorkspaceFilePath(e);return!!n&&v.resolve(n).toLowerCase()===v.resolve(t).toLowerCase()}getTargetSyncKind(e,t){let n=[["engine",e.engines],["event",e.events],["field",e.fields||{}],["menuButton",e.menuButtons||{}],["menuScript",e.menuScripts||{}],["workflow",e.workflowNodeEvents||{}]];for(let[i,r]of n)if(Object.values(r).some(o=>this.matchesTargetFile(o.filePath,t)))return i;return null}classifyDifference(e,t,n,i){return n===i?null:e&&t?"conflict":e?"localModified":"remoteModified"}classifyRemoteDeletion(e,t){return this.isLocalModified(e,t)?"conflict":"remoteDeleted"}createRemoteDeletedItem(e,t,n,i,r,o){return!r||!T.existsSync(r)?null:{kind:e,status:this.classifyRemoteDeletion(r,o),name:t,key:n,serverDir:i,filePath:r,localCode:this.normalizeCode(T.readFileSync(r,"utf-8")),remoteCode:"",localUpdateTime:o,remoteUpdateTime:""}}isRemoteNewer(e,t){let n=new Date(e||"").getTime(),i=new Date(t||"").getTime();return isNaN(n)||isNaN(i)?!1:n>i+1e3}getRemoteOnlyPlaceholderPath(e,t,n,i){let r=I.getInstance(),o=n==="api"?Ve:n==="form"?Te:n==="module"?ke:Oe;return v.join(r.getSyncRootDir(),t,r.buildOsClientDirName(e.osClient,e.osClientType,e.osClientNetwork),o,"\u670D\u52A1\u5668\u65B0\u589E\u5F85\u62C9\u53D6",`${K(i)}.js`)}async collectEngineDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_ENGINE_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u63A5\u53E3\u5F15\u64CE\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map(s.Data.List.map(g=>[g.ApiEngineKey,g])),l=!1;for(let[g,d]of Object.entries(n.engines)){if(!this.matchesTargetFile(d.filePath,r))continue;let u=c.get(g),p=this.getWorkspaceFilePath(d.filePath);if(!p||!T.existsSync(p))continue;if(!u){let w=this.createRemoteDeletedItem("engine",d.apiName||g,g,t,p,d.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.ApiV8Code||""),y=this.isLocalModified(p,d.updateTime),S=this.isRemoteNewer(u.UpdateTime,d.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(d.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),l=!0);continue}let C=this.classifyDifference(y,S,h,f);C&&i.push({kind:"engine",status:C,name:u.ApiName||d.apiName||g,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:d.updateTime,remoteUpdateTime:u.UpdateTime})}if(l&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.engines).map(g=>g.toLowerCase()));for(let g of s.Data.List)!String(g.ApiV8Code||"").trim()||m.has(g.ApiEngineKey.toLowerCase())||i.push({kind:"engine",status:"remoteModified",name:g.ApiName||g.ApiEngineKey,key:g.ApiEngineKey,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"api",g.ApiEngineKey),localCode:"",remoteCode:this.normalizeCode(g.ApiV8Code||""),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}async collectEventDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_EVENT_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u8868\u5355\u4E8B\u4EF6\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map;for(let g of s.Data.List){let d=`${g.FormEngineKey}__${g.EventType}`;c.set(d,g),c.set(d.toLowerCase(),g)}let l=!1;for(let[g,d]of Object.entries(n.events)){if(!this.matchesTargetFile(d.filePath,r))continue;let u=c.get(g)||c.get(g.toLowerCase()),p=this.getWorkspaceFilePath(d.filePath);if(!p||!T.existsSync(p))continue;if(!u){let w=this.createRemoteDeletedItem("event",`${d.description||d.formEngineKey}/${d.eventType}`,g,t,p,d.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.V8Code||""),y=this.isLocalModified(p,d.updateTime),S=this.isRemoteNewer(u.UpdateTime,d.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(d.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),l=!0);continue}let C=this.classifyDifference(y,S,h,f);C&&i.push({kind:"event",status:C,name:`${u.Description||d.formEngineKey}/${d.eventType}`,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:d.updateTime,remoteUpdateTime:u.UpdateTime})}if(l&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.events).map(g=>g.toLowerCase()));for(let g of s.Data.List){let d=`${g.FormEngineKey}__${g.EventType}`;!String(g.V8Code||"").trim()||m.has(d.toLowerCase())||i.push({kind:"event",status:"remoteModified",name:`${g.Description||g.FormEngineKey}/${g.EventType}`,key:d,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"form",d),localCode:"",remoteCode:this.normalizeCode(g.V8Code||""),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}}async collectFieldDifferences(e,t,n,i,r){let o=L.getInstance(),s=new Map;for(let l of Object.entries(n.fields||{})){if(!this.matchesTargetFile(l[1].filePath,r))continue;let m=s.get(l[1].tableId||l[1].tableName)||[];m.push(l),s.set(l[1].tableId||l[1].tableName,m)}let c=!1;await this.runInBatches([...s.values()],r?1:2,async l=>{let m=l[0][1],g=await o.get(x.GET_FIELD_LIST,{osClient:e.osClient,tableId:m.tableId,tableName:m.tableName},e.apiBaseUrl,e);if(g.Code!==1||!Array.isArray(g.Data?.List))throw new Error(`\u83B7\u53D6\u5B57\u6BB5\u540C\u6B65\u72B6\u6001\u5931\u8D25[${m.tableName}]: ${g.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let d=new Map(g.Data.List.map(u=>[String(u.Name||"").toLowerCase(),u]));for(let[u,p]of l){let h=d.get(p.fieldName.toLowerCase()),f=this.getWorkspaceFilePath(p.filePath);if(!f||!T.existsSync(f))continue;if(!h||!String(h[p.v8Key]||"").trim()){let b=this.createRemoteDeletedItem("field",`${p.tableName}.${p.fieldName}/${p.v8Key}`,u,t,f,p.updateTime);b&&i.push(b);continue}let y=this.normalizeCode(T.readFileSync(f,"utf-8")),S=this.normalizeCode(String(h[p.v8Key]||"")),C=String(h.UpdateTime||""),w=this.isLocalModified(f,p.updateTime),R=this.isRemoteNewer(C,p.updateTime);if(y===S){(w||R)&&C&&(p.updateTime=C,this.touchSyncedFile(f,C),c=!0);continue}let E=this.classifyDifference(w,R,y,S);E&&i.push({kind:"field",status:E,name:`${p.tableName}.${p.fieldName}/${p.v8Key}`,key:u,serverDir:t,filePath:f,localCode:y,remoteCode:S,localUpdateTime:p.updateTime,remoteUpdateTime:C})}}),c&&this.saveMeta(n,t)}async collectMenuButtonDifferences(e,t,n,i,r){let o=L.getInstance(),s=new Map;if(!r)for(let d of Object.keys(n.menus||{}))s.set(d,[]);for(let d of Object.entries(n.menuButtons||{})){if(!this.matchesTargetFile(d[1].filePath,r))continue;let u=s.get(d[1].moduleId)||[];u.push(d),s.set(d[1].moduleId,u)}let c=[];if(!r){let d=await o.get(x.LIST_MODULES,{osClient:e.osClient},e.apiBaseUrl,e);if(d.Code!==1||!Array.isArray(d.Data?.List))throw new Error(`\u83B7\u53D6\u6A21\u5757\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${d.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);c=d.Data.List}let l=new Set(c.map(d=>String(d.ParentId||"")).filter(Boolean)),m=new Map(c.map(d=>[d.Id,d]));for(let d of c){if(l.has(d.Id)||n.menus?.[d.Id])continue;let u=d.Label||d.Name||d.Id;i.push({kind:"menuButton",status:"remoteModified",name:`${u}/\u670D\u52A1\u5668\u65B0\u589E\u6A21\u5757`,key:d.Id,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"module",d.Id),localCode:"",remoteCode:JSON.stringify(d,null,2),localUpdateTime:"",remoteUpdateTime:String(d.UpdateTime||"")})}let g=!1;await this.runInBatches([...s.entries()],r?1:2,async([d,u])=>{let p=()=>{for(let[R,E]of u){let b=this.getWorkspaceFilePath(E.filePath);if(!b)continue;let V=this.createRemoteDeletedItem("menuButton",`${E.moduleName}/${E.btnName}/${E.v8SubField}`,R,t,b,E.updateTime);V&&i.push(V)}};if(!r&&!m.has(d)){p();return}let h=await o.get(x.GET_MODULE,{osClient:e.osClient,moduleId:d},e.apiBaseUrl,e);if(h.Code!==1||!h.Data){if(/不存在|not\s*found/i.test(String(h.Msg||""))){p();return}throw new Error(`\u83B7\u53D6\u6A21\u5757\u6309\u94AE\u540C\u6B65\u72B6\u6001\u5931\u8D25[${d}]: ${h.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`)}let f=h.Data,y=String(f.UpdateTime||""),S=new Map;for(let R of Object.keys($e)){let E=[];try{let b=f[R];E=typeof b=="string"?JSON.parse(b):Array.isArray(b)?b:[],Array.isArray(E)||(E=[])}catch{E=[]}S.set(R,new Map(E.map(b=>[String(b.Id||""),b])))}for(let[R,E]of u){let b=S.get(E.btnField)?.get(E.btnId),V=this.getWorkspaceFilePath(E.filePath);if(!V||!T.existsSync(V))continue;if(!b||!String(b[E.v8SubField]||"").trim()){let k=this.createRemoteDeletedItem("menuButton",`${E.moduleName}/${E.btnName}/${E.v8SubField}`,R,t,V,E.updateTime);k&&i.push(k);continue}let U=this.normalizeCode(T.readFileSync(V,"utf-8")),A=this.normalizeCode(String(b[E.v8SubField]||"")),P=this.isLocalModified(V,E.updateTime),O=this.isRemoteNewer(y,E.updateTime);if(U===A){(P||O)&&y&&(E.updateTime=y,this.touchSyncedFile(V,y),g=!0);continue}let F=this.classifyDifference(P,O,U,A);F&&i.push({kind:"menuButton",status:F,name:`${E.moduleName}/${E.btnName}/${E.v8SubField}`,key:R,serverDir:t,filePath:V,localCode:U,remoteCode:A,localUpdateTime:E.updateTime,remoteUpdateTime:y})}if(r)return;let C=new Set(u.map(([R])=>R)),w=n.menus?.[d]?.moduleName||m.get(d)?.Label||m.get(d)?.Name||d;for(let[R,E]of S)for(let[b,V]of E){if(!b)continue;let U=String(V.Name||b);for(let A of["V8Code","V8CodeShow"]){let P=String(V[A]||""),O=this.getMenuButtonMetaKey(d,R,b,A);!P.trim()||C.has(O)||i.push({kind:"menuButton",status:"remoteModified",name:`${w}/${U}/${A}`,key:O,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"module",O),localCode:"",remoteCode:this.normalizeCode(P),localUpdateTime:"",remoteUpdateTime:y})}}}),g&&this.saveMeta(n,t)}async collectMenuScriptDifferences(e,t,n,i,r){let o=L.getInstance(),s=Object.entries(n.menuScripts||{}).filter(([,l])=>this.matchesTargetFile(l.filePath,r)),c=!1;await this.runInBatches(s,r?1:2,async([l,m])=>{let g=this.getWorkspaceFilePath(m.filePath);if(!g||!T.existsSync(g))return;let d=await o.get(x.GET_MODULE,{osClient:e.osClient,moduleId:m.moduleId},e.apiBaseUrl,e);if(d.Code!==1||!d.Data){if(/不存在|not\s*found/i.test(String(d.Msg||""))){let w=this.createRemoteDeletedItem("menuScript",`${m.moduleName}/${m.scriptField}`,l,t,g,m.updateTime);w&&i.push(w);return}throw new Error(`\u83B7\u53D6\u6A21\u5757 Join/Where \u540C\u6B65\u72B6\u6001\u5931\u8D25[${m.moduleId}]: ${d.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`)}let u=d.Data,p=this.normalizeCode(String(u[m.scriptField]||"")),h=this.normalizeCode(T.readFileSync(g,"utf-8")),f=String(u.UpdateTime||""),y=this.isLocalModified(g,m.updateTime),S=this.sourceHash(p)!==m.codeHash;if(h===p){(y||S||f&&f!==m.updateTime)&&(m.codeHash=this.sourceHash(p),m.updateTime=f||m.updateTime,this.touchSyncedFile(g,m.updateTime),c=!0);return}let C=this.classifyDifference(y,S,h,p);C&&i.push({kind:"menuScript",status:C,name:`${m.moduleName}/${m.scriptField}`,key:l,serverDir:t,filePath:g,localCode:h,remoteCode:p,localUpdateTime:m.updateTime,remoteUpdateTime:f})}),c&&this.saveMeta(n,t)}async runInBatches(e,t,n){for(let i=0;i<e.length;i+=t)await Promise.all(e.slice(i,i+t).map(r=>n(r))),i+t<e.length&&await new Promise(r=>setTimeout(r,120))}async collectWorkflowDifferences(e,t,n,i,r){let s=await L.getInstance().get(x.GET_WORKFLOW_V8_EVENT_LIST,{osClient:e.osClient},e.apiBaseUrl,e);if(s.Code!==1||!Array.isArray(s.Data?.List))throw new Error(`\u83B7\u53D6\u6D41\u7A0B\u4E8B\u4EF6\u540C\u6B65\u72B6\u6001\u5931\u8D25: ${s.Msg||"\u670D\u52A1\u5668\u8FD4\u56DE\u6570\u636E\u683C\u5F0F\u4E0D\u6B63\u786E"}`);let c=new Map(s.Data.List.map(g=>[`${g.FlowDesignId}__${g.NodeId}__${g.EventType}`,g])),l=!1;for(let[g,d]of Object.entries(n.workflowNodeEvents||{})){if(!this.matchesTargetFile(d.filePath,r))continue;let u=c.get(g),p=this.getWorkspaceFilePath(d.filePath);if(!p||!T.existsSync(p))continue;if(!u||!String(u.V8Code||u.Code||"").trim()){let w=this.createRemoteDeletedItem("workflow",`${d.flowName}/${d.nodeName}/${d.eventType}`,g,t,p,d.updateTime);w&&i.push(w);continue}let h=this.normalizeCode(T.readFileSync(p,"utf-8")),f=this.normalizeCode(u.V8Code||u.Code||""),y=this.isLocalModified(p,d.updateTime),S=this.isRemoteNewer(u.UpdateTime,d.updateTime);if(h===f){(y||S)&&u.UpdateTime&&(d.updateTime=u.UpdateTime,this.touchSyncedFile(p,u.UpdateTime),l=!0);continue}let C=this.classifyDifference(y,S,h,f);if(C){let w=`${u.FlowName||d.flowName}/${u.NodeName||d.nodeName}/${u.EventType||d.eventType}`;i.push({kind:"workflow",status:C,name:w,key:g,serverDir:t,filePath:p,localCode:h,remoteCode:f,localUpdateTime:d.updateTime,remoteUpdateTime:u.UpdateTime})}}if(l&&this.saveMeta(n,t),r)return;let m=new Set(Object.keys(n.workflowNodeEvents||{}));for(let g of s.Data.List){let d=`${g.FlowDesignId}__${g.NodeId}__${g.EventType}`,u=g.V8Code||g.Code||"";if(!u.trim()||m.has(d))continue;let p=`${g.FlowName||g.FlowDesignId}/${g.NodeName||g.NodeId}/${g.EventType}`;i.push({kind:"workflow",status:"remoteModified",name:p,key:d,serverDir:t,filePath:this.getRemoteOnlyPlaceholderPath(e,t,"workflow",d),localCode:"",remoteCode:this.normalizeCode(u),localUpdateTime:"",remoteUpdateTime:g.UpdateTime})}}migrateFromFlatMeta(e){let t=I.getInstance();try{let n=t.getSyncRootDir(),i=v.join(n,Ae);if(!T.existsSync(i))return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let r=t.getWorkspaceRoot();if(!r)return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};let o=JSON.parse(T.readFileSync(i,"utf-8")),s=o.engines||{},c=o.events||{},l={engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}};for(let[m,g]of Object.entries(s)){let d=g;if(d.filePath){let u=v.join(r,d.filePath);v.relative(n,u).split(v.sep)[0]===e&&(l.engines[m]=d)}}for(let[m,g]of Object.entries(c)){let d=g;if(d.filePath){let u=v.join(r,d.filePath);v.relative(n,u).split(v.sep)[0]===e&&(l.events[m]=d)}}return(Object.keys(l.engines).length>0||Object.keys(l.events).length>0)&&this.saveMeta(l,e),l}catch{return{engines:{},events:{},fields:{},menus:{},menuButtons:{},menuScripts:{},workflows:{},workflowNodeEvents:{}}}}async pullEngines(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0){_.warn("Microi: \u6CA1\u6709\u5DF2\u8FDE\u63A5\u7684\u670D\u52A1\u5668\uFF0C\u8BF7\u5148\u5728\u8BBE\u7F6E\u4E2D\u6DFB\u52A0\u8FDE\u63A5\u5E76\u767B\u5F55");return}for(let n of t)try{await this.pullEnginesForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`),_.error(`Microi: \u62C9\u53D6 [${n.label||n.apiBaseUrl}] \u5931\u8D25 - ${r}`)}return}await this.pullEnginesForProfile(e)}async pullEnginesForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE\u4EE3\u7801 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u63A5\u53E3\u5F15\u64CE [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u68C0\u67E5\u540E\u7AEF\u72B6\u6001..."});let s=await n.get(x.GET_STATUS,void 0,i,e);if(s.Code!==1){let F=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u540E\u7AEF\u72B6\u6001\u5F02\u5E38: ${s.Msg||"Code="+s.Code}${F}`)}o.report({message:"\u83B7\u53D6\u7CFB\u7EDF\u914D\u7F6E..."});let l=await ge.getInstance().getSysConfig(i,r),m=l?.SysShortTitle||"",g=l?.SysTitle||"",d=m||g||l?.CompanyName||e.label||"";d&&(d!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:d,sysShortTitle:m,sysTitle:g}),o.report({message:"\u83B7\u53D6\u63A5\u53E3\u5F15\u64CE\u5217\u8868..."});let u=await n.get(x.GET_ENGINE_LIST,{osClient:r},i,e);if(u.Code!==1){let F=u.Code===1001||u.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u5217\u8868\u5931\u8D25: ${u.Msg||"Code="+u.Code}${F}`)}let{OsClient:p,OsClientType:h,OsClientNetwork:f,List:y,Total:S}=u.Data;if(this.log(`\u83B7\u53D6\u5230 ${S} \u4E2A\u63A5\u53E3\u5F15\u64CE (OsClient: ${p})`),!h||!f)throw new Error(`\u540E\u7AEF\u672A\u8FD4\u56DE\u5B8C\u6574\u7684 OsClientType/OsClientNetwork (OsClient: ${p}, Type: ${h||"\u7A7A"}, Network: ${f||"\u7A7A"})\uFF0C\u65E0\u6CD5\u62C9\u53D6\u4EE3\u7801`);if(h||f){let F={...e,osClientType:h,osClientNetwork:f};await t.addProfile(F)}let C=t.getSyncRootDir(),w=t.buildServerDirName(d,i),R=this.loadMeta(w),E=0,b=0,V=[],U=new Set,A=new Set,P=t.buildOsClientDirName(p,h,f);for(let F of y)try{let k=K(F.Category||"\u672A\u5206\u7C7B"),$=K(F.ApiName||F.ApiEngineKey),j=v.join(C,w,P,Ve,k),W=K(`${$}(${Gt(F.ApiEngineKey)}).js`),ee=v.join(j,W),re=zt(F.ApiV8Code||"");if(!re.trim()){b++,T.existsSync(ee)&&this.backupAndDeleteSyncFile(ee,w,"remote-deleted-api"),delete R.engines[F.ApiEngineKey];continue}U.add(F.ApiEngineKey),te(j),T.writeFileSync(ee,re,"utf-8");let q=new Date(F.UpdateTime);isNaN(q.getTime())||T.utimesSync(ee,q,q),R.engines[F.ApiEngineKey]={id:F.Id,apiName:F.ApiName,category:k,apiAddress:F.ApiAddress,updateTime:F.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),ee)},E++,o.report({message:`${E}/${S} ${F.ApiEngineKey}`,increment:1/S*100})}catch(k){let $=k instanceof Error?k.message:String(k);A.add(F.ApiEngineKey),V.push(`${F.ApiEngineKey}: ${$}`),this.log(`\u63A5\u53E3\u5F15\u64CE\u6587\u4EF6\u5199\u5165\u5931\u8D25\uFF0C\u7EE7\u7EED\u4E0B\u4E00\u9879 [${F.ApiEngineKey}]: ${$}`)}for(let[F,k]of Object.entries(R.engines)){if(U.has(F)||A.has(F))continue;let $=this.getWorkspaceFilePath(k.filePath);$&&this.backupAndDeleteSyncFile($,w,"remote-deleted-api"),delete R.engines[F]}this.saveMeta(R,w);let O=d||e.label||i;this.log(`[${O}] \u62C9\u53D6\u5B8C\u6210: ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${b} \u9879\uFF0C\u5931\u8D25 ${V.length} \u9879`),V.length>0?_.warn(`Microi: [${O}] \u5DF2\u62C9\u53D6 ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE\uFF0C${V.length} \u4E2A\u6587\u4EF6\u5931\u8D25\uFF1B\u5931\u8D25\u660E\u7EC6\u5DF2\u5199\u5165 Microi \u8F93\u51FA\u3002`):_.info(`Microi: [${O}] \u6210\u529F\u62C9\u53D6 ${E} \u4E2A\u63A5\u53E3\u5F15\u64CE${b>0?`\uFF08\u8DF3\u8FC7 ${b} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)})}async pullEvents(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0)return;for(let n of t)try{await this.pullEventsForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6V8\u4E8B\u4EF6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`)}return}await this.pullEventsForProfile(e)}async pullEventsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6V8\u4E8B\u4EF6\u4EE3\u7801 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6V8\u4E8B\u4EF6 [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6V8\u4E8B\u4EF6\u5217\u8868..."});let s=await n.get(x.GET_EVENT_LIST,{osClient:r},i,e);if(s.Code!==1){let P=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6V8\u4E8B\u4EF6\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}${P}`)}let{List:c,Total:l}=s.Data;this.log(`\u83B7\u53D6\u5230 ${l} \u4E2AV8\u4E8B\u4EF6`);let g=await ge.getInstance().getSysConfig(i,r),d=g?.SysShortTitle||"",u=g?.SysTitle||"",p=d||u||g?.CompanyName||e.label||"";p&&(p!==e.label||d!==e.sysShortTitle||u!==e.sysTitle)&&await t.addProfile({...e,label:p,sysShortTitle:d,sysTitle:u});let h=t.getSyncRootDir(),f=t.buildServerDirName(p,i),y=this.loadMeta(f),S=0,C=0,w=0,R=new Set(c.map(P=>`${P.FormEngineKey}__${P.EventType}`)),b=t.getProfiles().find(P=>P.apiBaseUrl===e.apiBaseUrl&&P.osClient===e.osClient)||e;if(!b.osClientType||!b.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE\u4EE5\u83B7\u53D6\u5B8C\u6574\u914D\u7F6E");let V=t.buildOsClientDirName(r,b.osClientType,b.osClientNetwork),U={SubmitBeforeServerV8:"\u540E\u7AEF\u63D0\u4EA4\u524DV8\u4E8B\u4EF6",SubmitAfterServerV8:"\u540E\u7AEF\u63D0\u4EA4\u540EV8\u4E8B\u4EF6",SubmitFormV8:"\u524D\u7AEF\u8868\u5355\u63D0\u4EA4V8\u4E8B\u4EF6",OutFormV8:"\u524D\u7AEF\u8868\u5355\u9000\u51FAV8\u4E8B\u4EF6",ServerDataV8:"\u540E\u7AEF\u6570\u636EV8\u4E8B\u4EF6"};for(let P of c){let O=P.V8Code||"",F=K(P.Description?`${P.Description}\uFF08${P.FormEngineKey}\uFF09`:P.FormEngineKey),k=pn[P.EventType]||P.EventType,$=K(`${k}\uFF08${P.EventType}\uFF09`)+".js",j=v.join(h,f,V,Te,F,ut);te(j);let W=v.join(j,$),ee=U[P.EventType];if(ee){let ce=K(`${ee}\uFF08${P.EventType}\uFF09`)+".js",X=v.join(j,ce);X!==W&&T.existsSync(X)&&!this.isLocalModified(X,P.UpdateTime)&&(T.existsSync(W)?T.unlinkSync(X):T.renameSync(X,W))}let re=`${P.FormEngineKey}__${P.EventType}`;if(y.events[re]={id:P.Id,formEngineKey:P.FormEngineKey,description:P.Description||"",eventType:P.EventType,updateTime:P.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),W)},!O.trim()){T.existsSync(W)&&this.backupAndDeleteSyncFile(W,f,"remote-deleted-form-event"),w++,S++,o.report({message:`${S}/${l}`,increment:l>0?1/l*100:void 0});continue}T.writeFileSync(W,O,"utf-8");let q=new Date(P.UpdateTime);isNaN(q.getTime())||T.utimesSync(W,q,q),C++,S++,o.report({message:`${S}/${l}`,increment:l>0?1/l*100:void 0})}for(let[P,O]of Object.entries(y.events)){if(R.has(P))continue;let F=this.getWorkspaceFilePath(O.filePath);F&&this.backupAndDeleteSyncFile(F,f,"remote-deleted-form-event"),delete y.events[P]}this.saveMeta(y,f);let A=p||e.label||i;this.log(`[${A}] \u62C9\u53D6\u5B8C\u6210: ${C} \u4E2AV8\u4E8B\u4EF6\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${w} \u9879`),_.info(`Microi: [${A}] \u6210\u529F\u62C9\u53D6 ${C} \u4E2AV8\u4E8B\u4EF6\u6587\u4EF6${w>0?`\uFF08\u8DF3\u8FC7 ${w} \u4E2A\u7A7A\u4EE3\u7801\u4E8B\u4EF6\uFF09`:""}`)})}async pullWorkflows(e){if(!e){let t=I.getInstance().getProfiles();if(t.length===0)return;for(let n of t)try{await this.pullWorkflowsForProfile(n)}catch(i){let r=i instanceof Error?i.message:String(i);this.log(`\u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${r}`)}return}await this.pullWorkflowsForProfile(e)}async pullWorkflowsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE\u8282\u70B9 V8 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u6D41\u7A0B\u5F15\u64CE [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6\u6D41\u7A0B\u8282\u70B9V8\u5217\u8868..."});let s=await n.get(x.GET_WORKFLOW_V8_EVENT_LIST,{osClient:r},i,e);if(s.Code!==1){let k=s.Code===1001||s.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u6D41\u7A0B\u8282\u70B9V8\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}${k}`)}let l=await ge.getInstance().getSysConfig(i,r),m=l?.SysShortTitle||"",g=l?.SysTitle||"",d=m||g||l?.CompanyName||e.label||"";d&&(d!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:d,sysShortTitle:m,sysTitle:g});let p=t.getProfiles().find(k=>k.apiBaseUrl===e.apiBaseUrl&&k.osClient===e.osClient)||e;if(!p.osClientType||!p.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let h=s.Data.OsClient||r,f=t.buildServerDirName(d,i),y=t.buildOsClientDirName(h,p.osClientType,p.osClientNetwork),S=t.getSyncRootDir(),C=this.loadMeta(f);C.workflows||(C.workflows={}),C.workflowNodeEvents||(C.workflowNodeEvents={});let w=s.Data.Flows||[],R=s.Data.Nodes||[],E=s.Data.Lines||[],b=s.Data.List||[],V=new Map(w.map(k=>[String(k.Id||""),k])),U=new Set(w.map(k=>String(k.Id||"")).filter(Boolean)),A=new Set(b.filter(k=>String(k.V8Code||k.Code||"").trim()).map(k=>`${k.FlowDesignId}__${k.NodeId}__${k.EventType}`)),P=0,O=0;for(let k of w){let $=String(k.Id||"");if(!$)continue;let j=String(k.FlowName||$),W=String(k.UpdateTime||me()),ee=v.join(S,f,y,Oe,K(`${j}\uFF08${$}\uFF09`));te(ee);let re=R.filter(X=>String(X.FlowDesignId||"")===$),q=E.filter(X=>String(X.FlowDesignId||"")===$),ce=v.join(ee,"\u6D41\u7A0B\u8BBE\u8BA1\u56FE\uFF08WF_FlowDesign\uFF09.json");T.writeFileSync(ce,JSON.stringify({FlowDesign:k,Nodes:re,Lines:q},null,2),"utf-8"),this.touchSyncedFile(ce,W),C.workflows[$]={flowDesignId:$,flowName:j,updateTime:W,filePath:v.relative(t.getWorkspaceRoot(),ce)}}for(let k of b){let $=String(k.FlowDesignId||""),j=String(k.NodeId||""),W=String(k.EventType||"");if(!$||!j||!W)continue;let ee=V.get($),re=String(k.FlowName||ee?.FlowName||$),q=String(k.NodeName||j),ce=fn[W]||k.EventName||W,X=v.join(S,f,y,Oe,K(`${re}\uFF08${$}\uFF09`),mt,K(`${q}\uFF08${j}\uFF09`));te(X);let N=v.join(X,K(`${ce}\uFF08${W}\uFF09`)+".js"),se=k.V8Code||k.Code||"",Q=String(k.UpdateTime||ee?.UpdateTime||me());if(C.workflowNodeEvents[`${$}__${j}__${W}`]={flowDesignId:$,flowName:re,nodeId:j,nodeName:q,eventType:W,updateTime:Q,filePath:v.relative(t.getWorkspaceRoot(),N)},!se.trim()){T.existsSync(N)&&this.backupAndDeleteSyncFile(N,f,"remote-deleted-workflow-event"),O++,o.report({message:`${P}/${b.length} ${re}/${q}`});continue}T.writeFileSync(N,se,"utf-8"),this.touchSyncedFile(N,Q),P++,o.report({message:`${P}/${b.length} ${re}/${q}`})}for(let[k,$]of Object.entries(C.workflowNodeEvents)){if(A.has(k))continue;let j=this.getWorkspaceFilePath($.filePath);j&&this.backupAndDeleteSyncFile(j,f,"remote-deleted-workflow-event"),delete C.workflowNodeEvents[k]}for(let[k,$]of Object.entries(C.workflows)){if(U.has(k))continue;let j=this.getWorkspaceFilePath($.filePath);j&&this.backupAndDeleteSyncFile(j,f,"remote-deleted-workflow"),delete C.workflows[k]}this.saveMeta(C,f);let F=d||e.label||i;this.log(`[${F}] \u6D41\u7A0B\u5F15\u64CE\u62C9\u53D6\u5B8C\u6210: ${w.length} \u4E2A\u6D41\u7A0B\uFF0C${P} \u4E2A\u8282\u70B9V8\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${O} \u9879`),_.info(`Microi: [${F}] \u6210\u529F\u62C9\u53D6 ${w.length} \u4E2A\u6D41\u7A0B\u3001${P} \u4E2A\u6D41\u7A0B\u8282\u70B9V8\u6587\u4EF6${O>0?`\uFF08\u8DF3\u8FC7 ${O} \u4E2A\u7A7A\u4EE3\u7801\u4E8B\u4EF6\uFF09`:""}`)})}findProfileByServerDir(e){let t=I.getInstance(),n=t.getProfiles();for(let i of n)if(t.buildServerDirName(i.label,i.apiBaseUrl)===e)return i}hasSyncBaseline(e,t){let n=v.resolve(e).toLowerCase(),i=this.loadMeta(t);return[i.engines,i.events,i.fields||{},i.menuButtons||{},i.menuScripts||{},i.workflowNodeEvents||{}].some(o=>Object.values(o).some(s=>{let c=this.getWorkspaceFilePath(s.filePath);return!!c&&v.resolve(c).toLowerCase()===n}))}async runPushPreflight(e,t,n,i){if(!n){let r=`\u65E0\u6CD5\u8BC6\u522B\u6587\u4EF6\u6240\u5C5E\u670D\u52A1\u5668\u914D\u7F6E\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\uFF1A${e}`;return this.log(r),_.error(`Microi: ${r}`),!1}if(!this.hasSyncBaseline(e,t)){let r=`\u6587\u4EF6\u6CA1\u6709\u540C\u6B65\u57FA\u7EBF\uFF0C\u65E0\u6CD5\u786E\u8BA4\u670D\u52A1\u5668\u7AEF\u662F\u5426\u66F4\u65B0\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u3002\u8BF7\u5148\u62C9\u53D6\u5BF9\u5E94\u5F15\u64CE\uFF1A${e}`;return this.log(r),_.error(`Microi: ${r}`),!1}try{let r=await this.checkRemoteDifferences(n,i,e),o=v.resolve(e).toLowerCase(),s=r.find(m=>v.resolve(m.filePath).toLowerCase()===o);if(!s||s.status==="localModified")return!0;let l=`${s.status==="conflict"?"\u672C\u5730\u4E0E\u670D\u52A1\u5668\u5747\u5DF2\u4FEE\u6539":s.status==="remoteDeleted"?"\u670D\u52A1\u5668\u7AEF\u8D44\u6E90\u5DF2\u5220\u9664":"\u670D\u52A1\u5668\u4EE3\u7801\u8F83\u65B0"}\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u4EE5\u907F\u514D\u8986\u76D6\u3002\u8BF7\u5728\u201C\u540C\u6B65\u7ED3\u679C\u201D\u4E2D\u67E5\u770B\u5DEE\u5F02\u5E76\u62C9\u53D6\u6216\u5408\u5E76\uFF1A${s.name}`;return this.log(l),_.error(`Microi: ${l}`),!1}catch(r){let o=r instanceof Error?r.message:String(r);return this.log(`\u63A8\u9001\u524D\u540C\u6B65\u72B6\u6001\u68C0\u6D4B\u5931\u8D25\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\uFF1A${o}`),_.error(`Microi: \u63A8\u9001\u524D\u540C\u6B65\u72B6\u6001\u68C0\u6D4B\u5931\u8D25\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001 - ${o}`),!1}}async pushFile(e,t={}){let i=I.getInstance().getSyncRootDir();if(v.extname(e).toLowerCase()===".js"&&T.existsSync(e)){let g=kn(Ce(T.readFileSync(e,"utf-8")));if(g.length>0){let d=g[0],u=`\u68C0\u6D4B\u5230 AI/\u7EC8\u7AEF\u5DE5\u5177\u8F93\u51FA\u6C61\u67D3\uFF08\u7B2C ${d.line} \u884C: ${d.marker}\uFF09\uFF0C\u5DF2\u505C\u6B62\u63A8\u9001\u3002\u8BF7\u6062\u590D\u5B8C\u6574\u6E90\u7801\u540E\u518D\u8BD5\uFF1A${e}`;return this.log(u),_.error(`Microi: ${u}`),!1}}let r=Tn(e,i);if(r){let g=this.findProfileByServerDir(r.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,r.serverDir,g,"api")?!1:this.pushEngineFile(e,r,g)}let o=vn(e,i);if(o){let g=this.findProfileByServerDir(o.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,o.serverDir,g,"form")?!1:this.pushEventFile(e,o,g)}let s=En(e,i);if(s){let g=this.findProfileByServerDir(s.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,s.serverDir,g,"form")?!1:this.pushFieldFile(e,s,g)}let c=wn(e,i);if(c){let g=this.findProfileByServerDir(c.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,c.serverDir,g,"module")?!1:this.pushMenuButtonFile(e,c,g)}let l=bn(e,i);if(l){let g=this.findProfileByServerDir(l.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,l.serverDir,g,"module")?!1:this.pushMenuScriptFile(e,l,g)}let m=Dn(e,i);if(m){let g=this.findProfileByServerDir(m.serverDir);return!t.skipPreflight&&!await this.runPushPreflight(e,m.serverDir,g,"workflow")?!1:this.pushWorkflowNodeFile(e,m,g)}return this.log(`\u65E0\u6CD5\u89E3\u6790\u6587\u4EF6\u8DEF\u5F84: ${e}`),!1}async pushEngineFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001\u63A5\u53E3\u5F15\u64CE: ${t.apiEngineKey}...`);try{let s="",c="";try{let u=await i.post(x.GET_ENGINE_CODE,{OsClient:t.osClient,ApiEngineKey:t.apiEngineKey},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.ApiV8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let l=!o.trim(),m=l?{code:"",version:c,changeHistory:""}:tt({kind:"ApiEngine",key:t.apiEngineKey,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001\u63A5\u53E3\u5F15\u64CE ${t.apiEngineKey}`}),g={OsClient:t.osClient,ApiEngineKey:t.apiEngineKey,ApiV8CodeBase64:Buffer.from(m.code,"utf8").toString("base64")};l||(g.Version=m.version,g.ChangeHistory=m.changeHistory);let d=await i.post(x.UPDATE_ENGINE_CODE,g,void 0,n?.apiBaseUrl,n);if(d.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.apiEngineKey}`);let u=d.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir);if(l?delete p.engines[t.apiEngineKey]:p.engines[t.apiEngineKey]&&(p.engines[t.apiEngineKey].updateTime=u),this.saveMeta(p,t.serverDir),l)T.existsSync(e)&&T.unlinkSync(e);else{T.writeFileSync(e,m.code,"utf-8");let h=new Date(u);isNaN(h.getTime())||T.utimesSync(e,h,h)}return!0}else return this.log(`\u63A8\u9001\u5931\u8D25: ${t.apiEngineKey} - ${d.Msg}`),_.error(`Microi: \u63A8\u9001\u5931\u8D25 - ${d.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u5F02\u5E38: ${t.apiEngineKey} - ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async pushEventFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001V8\u4E8B\u4EF6: ${t.formEngineKey}/${t.eventType}...`);try{let s="",c="";try{let u=await i.post(x.GET_EVENT_CODE,{OsClient:t.osClient,FormEngineKey:t.formEngineKey,EventType:t.eventType},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.V8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let l=!o.trim(),m=l?{code:"",version:c,changeHistory:""}:tt({kind:"V8Event",key:t.formEngineKey,eventType:t.eventType,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001 V8 \u4E8B\u4EF6 ${t.formEngineKey}/${t.eventType}`}),g={OsClient:t.osClient,FormEngineKey:t.formEngineKey,EventType:t.eventType,V8Code:m.code};l||(g.Version=m.version,g.ChangeHistory=m.changeHistory);let d=await i.post(x.UPDATE_EVENT_CODE,g,void 0,n?.apiBaseUrl,n);if(d.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.formEngineKey}/${t.eventType}`);let u=d.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir),h=`${t.formEngineKey}__${t.eventType}`;if(l)delete p.events[h];else{let f=p.events[h];p.events[h]={id:f?.id||"",formEngineKey:t.formEngineKey,description:f?.description||"",eventType:t.eventType,updateTime:u,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}}if(this.saveMeta(p,t.serverDir),l)T.existsSync(e)&&T.unlinkSync(e);else{T.writeFileSync(e,m.code,"utf-8");let f=new Date(u);isNaN(f.getTime())||T.utimesSync(e,f,f)}return!0}else return this.log(`\u63A8\u9001\u5931\u8D25: ${t.formEngineKey}/${t.eventType} - ${d.Msg}`),_.error(`Microi: \u63A8\u9001\u5931\u8D25 - ${d.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u5F02\u5E38: ${t.formEngineKey}/${t.eventType} - ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async createEngine(e){let t=L.getInstance(),n=I.getInstance();this.log(`\u521B\u5EFA\u63A5\u53E3\u5F15\u64CE: ${e.apiEngineKey}...`);try{let i=tt({kind:"ApiEngine",key:e.apiEngineKey,currentCode:"",functionDescription:`\u63A5\u53E3\u5F15\u64CE ${e.apiName} \u7684\u5B8C\u6574\u4E1A\u52A1\u903B\u8F91\u3002`,changeSummary:`\u901A\u8FC7 VS Code \u521B\u5EFA\u63A5\u53E3\u5F15\u64CE ${e.apiEngineKey}`,initial:!0}),r=await t.post(x.CREATE_ENGINE,{OsClient:e.profile.osClient,ApiName:e.apiName,ApiEngineKey:e.apiEngineKey,ApiAddress:e.apiAddress||"",ApiRemark:e.apiRemark||"",Lock:e.lock?1:0,LockKey:e.lockKey||"",AllowAnonymous:e.allowAnonymous?1:0,V8Unlimited:e.v8Unlimited?1:0,IsEnable:e.isEnable!==!1?1:0,ApiRole:e.apiRole||"",Category:e.category||"\u672A\u5206\u7C7B",ApiV8CodeBase64:Buffer.from(i.code,"utf8").toString("base64"),Version:i.version,ChangeHistory:i.changeHistory},void 0,e.profile.apiBaseUrl,e.profile);if(r.Code===1){let o=n.getSyncRootDir(),s=n.buildServerDirName(e.profile.label,e.profile.apiBaseUrl),c=n.buildOsClientDirName(e.profile.osClient,e.profile.osClientType,e.profile.osClientNetwork),l=K(e.category||"\u672A\u5206\u7C7B"),m=K(e.apiName||e.apiEngineKey),g=v.join(o,s,c,Ve,l);te(g);let d=v.join(g,K(`${m}(${Gt(e.apiEngineKey)}).js`));T.writeFileSync(d,i.code,"utf-8");let u=this.loadMeta(s);return u.engines[e.apiEngineKey]={id:"",apiName:e.apiName,category:l,apiAddress:e.apiAddress||"",updateTime:me(),filePath:v.relative(n.getWorkspaceRoot(),d)},this.saveMeta(u,s),this.log(`\u521B\u5EFA\u6210\u529F: ${e.apiEngineKey}`),_.info(`Microi: \u63A5\u53E3\u5F15\u64CE [${e.apiEngineKey}] \u521B\u5EFA\u6210\u529F`),await oe.showTextDocument(ln.file(d)),!0}else return this.log(`\u521B\u5EFA\u5931\u8D25: ${e.apiEngineKey} - ${r.Msg}`),_.error(`Microi: \u521B\u5EFA\u5931\u8D25 - ${r.Msg}`),!1}catch(i){let r=i instanceof Error?i.message:String(i);return this.log(`\u521B\u5EFA\u5F02\u5E38: ${e.apiEngineKey} - ${r}`),_.error(`Microi: \u521B\u5EFA\u5F02\u5E38 - ${r}`),!1}}async pullFields(e){if(!e){let t=I.getInstance().getProfiles();for(let n of t)try{await this.pullFieldsForProfile(n)}catch(i){this.log(`\u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${i instanceof Error?i.message:String(i)}`)}return}await this.pullFieldsForProfile(e)}async pullFieldsForTableFolder(e){let n=I.getInstance().getSyncRootDir(),i=v.relative(n,e).split(v.sep);if(i.length<4||i[2]!==Te){_.warn("Microi: \u8BF7\u5728\u201C\u8868\u5355\u5F15\u64CE\u201D\u4E0B\u7684\u8868\u76EE\u5F55\u6267\u884C\u5B57\u6BB5 V8 \u4E8B\u4EF6\u62C9\u53D6");return}let r=s=>{let c=s.match(/[((]([^))]+)[))]\s*$/);return c?c[1]:s},o=this.findProfileByServerDir(i[0]);if(!o){_.error(`Microi: \u672A\u627E\u5230\u4E0E\u76EE\u5F55 "${i[0]}" \u5339\u914D\u7684\u670D\u52A1\u5668\u8FDE\u63A5`);return}await this.pullFieldsForTable(o,r(i[3]),e,i[0])}async pullFieldsForTable(e,t,n,i){let r=I.getInstance(),o=L.getInstance(),s=this.loadMeta(i);s.fields||(s.fields={}),this.log(`\u62C9\u53D6\u8868\u5B57\u6BB5V8\u4E8B\u4EF6: ${t}...`);let c=await o.get(x.GET_FIELD_LIST,{osClient:e.osClient,tableName:t},e.apiBaseUrl,e);if(c.Code!==1){_.error(`Microi: \u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 - ${c.Msg}`);return}let l=c.Data.List||[],m=["V8Code","KeyupV8Code","V8TmpEngineTable","V8TmpEngineForm"],g=0,d=0;for(let u of l){let p=K(u.Label?`${u.Label}\uFF08${u.Name}\uFF09`:u.Name),h=v.join(n,Je,p);for(let f of m){let y=(u[f]||"").toString(),S=Vt[f]||f,C=K(`${S}\uFF08${f}\uFF09`)+".js",w=v.join(h,C),R=`${t}__${u.Name}__${f}`;if(!y.trim()){d++,T.existsSync(w)&&T.unlinkSync(w),delete s.fields[R];continue}te(h),T.writeFileSync(w,y,"utf-8");let E=new Date(u.UpdateTime);isNaN(E.getTime())||T.utimesSync(w,E,E),s.fields[R]={fieldId:u.Id,tableId:u.TableId,tableName:t,fieldName:u.Name,fieldLabel:u.Label||"",v8Key:f,updateTime:u.UpdateTime,filePath:v.relative(r.getWorkspaceRoot(),w)},g++}}this.saveMeta(s,i),_.info(`Microi: \u5DF2\u62C9\u53D6 ${t} \u7684 ${g} \u4E2A\u5B57\u6BB5V8\u4E8B\u4EF6\u6587\u4EF6${d>0?`\uFF08\u8DF3\u8FC7 ${d} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)}async pullFieldsForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u5168\u91CF\u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6 [${e.label||i}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u5B57\u6BB5V8\u4E8B\u4EF6 [${e.label||i}]`,cancellable:!1},async o=>{o.report({message:"\u83B7\u53D6\u8868\u5217\u8868..."});let s=await n.get(x.GET_DB_SCHEMA,{osClient:r},i,e);if(s.Code!==1)throw new Error(`\u83B7\u53D6\u8868\u5217\u8868\u5931\u8D25: ${s.Msg||"Code="+s.Code}`);let c=s.Data.Tables||[],m=await ge.getInstance().getSysConfig(i,r),g=m?.SysShortTitle||"",d=m?.SysTitle||"",u=g||d||e.label||"",p=t.buildServerDirName(u,i),h=this.loadMeta(p);h.fields||(h.fields={});let y=t.getProfiles().find(A=>A.apiBaseUrl===e.apiBaseUrl&&A.osClient===e.osClient)||e;if(!y.osClientType||!y.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let S=t.buildOsClientDirName(r,y.osClientType,y.osClientNetwork),C=t.getSyncRootDir(),w=["V8Code","KeyupV8Code","V8TmpEngineTable","V8TmpEngineForm"],R=0,E=0,b=0,V=new Set,U=new Set;for(let A of c){b++,o.report({message:`[${b}/${c.length}] ${A.Name}`});let P=await n.get(x.GET_FIELD_LIST,{osClient:r,tableId:A.Id},i,e);if(P.Code!==1){U.add(A.Name.toLowerCase()),this.log(` \u8DF3\u8FC7\u8868 ${A.Name}: ${P.Msg}`);continue}let O=P.Data.List||[],F=K(A.Description?`${A.Description}\uFF08${A.Name}\uFF09`:A.Name);for(let k of O)for(let $ of w){let j=(k[$]||"").toString();if(!j.trim()){E++;continue}let W=K(k.Label?`${k.Label}\uFF08${k.Name}\uFF09`:k.Name),ee=Vt[$]||$,re=K(`${ee}\uFF08${$}\uFF09`)+".js",q=v.join(C,p,S,Te,F,Je,W);te(q);let ce=v.join(q,re);T.writeFileSync(ce,j,"utf-8");let X=new Date(k.UpdateTime);isNaN(X.getTime())||T.utimesSync(ce,X,X);let N=`${A.Name}__${k.Name}__${$}`;V.add(N),h.fields[N]={fieldId:k.Id,tableId:k.TableId,tableName:A.Name,fieldName:k.Name,fieldLabel:k.Label||"",v8Key:$,updateTime:k.UpdateTime,filePath:v.relative(t.getWorkspaceRoot(),ce)},R++}}for(let[A,P]of Object.entries(h.fields)){if(V.has(A)||U.has(P.tableName.toLowerCase()))continue;let O=this.getWorkspaceFilePath(P.filePath);O&&this.backupAndDeleteSyncFile(O,p,"remote-deleted-field-event"),delete h.fields[A]}this.saveMeta(h,p),this.log(`\u5B57\u6BB5V8\u4E8B\u4EF6\u62C9\u53D6\u5B8C\u6210: ${R} \u4E2A\u6587\u4EF6\uFF0C\u8DF3\u8FC7\u7A7A\u4EE3\u7801 ${E} \u9879`),_.info(`Microi: \u6210\u529F\u62C9\u53D6 ${R} \u4E2A\u5B57\u6BB5V8\u4E8B\u4EF6${E>0?`\uFF08\u8DF3\u8FC7 ${E} \u4E2A\u7A7A\u4EE3\u7801\uFF09`:""}`)})}async pushFieldFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u5B57\u6BB5V8\u4E8B\u4EF6: ${t.tableName}/${t.fieldName}/${t.v8Key}...`);try{let o=await i.post(x.UPDATE_FIELD,{OsClient:t.osClient,TableName:t.tableName,Name:t.fieldName,[t.v8Key]:r},void 0,n?.apiBaseUrl,n);if(o.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.tableName}/${t.fieldName}/${t.v8Key}`);let s=this.loadMeta(t.serverDir),c=`${t.tableName}__${t.fieldName}__${t.v8Key}`;s.fields||(s.fields={});let l=o.Data?.UpdateTime||me();return r.trim()?s.fields[c]={fieldId:s.fields[c]?.fieldId||"",tableId:s.fields[c]?.tableId||"",tableName:t.tableName,fieldName:t.fieldName,fieldLabel:s.fields[c]?.fieldLabel||"",v8Key:t.v8Key,updateTime:l,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}:delete s.fields[c],this.saveMeta(s,t.serverDir),r.trim()?this.touchSyncedFile(e,l):T.existsSync(e)&&T.unlinkSync(e),!0}return this.log(`\u63A8\u9001\u5931\u8D25: ${o.Msg}`),_.error(`Microi: \u63A8\u9001\u5B57\u6BB5V8\u4E8B\u4EF6\u5931\u8D25 - ${o.Msg}`),!1}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${s}`),!1}}async pullMenuButtons(e){if(!e){let t=I.getInstance().getProfiles();for(let n of t)try{await this.pullMenuButtonsForProfile(n)}catch(i){this.log(`\u62C9\u53D6\u83DC\u5355\u6309\u94AE\u5931\u8D25 [${n.label||n.apiBaseUrl}]: ${i instanceof Error?i.message:String(i)}`)}return}await this.pullMenuButtonsForProfile(e)}async pullMenuButtonsForModuleFolder(e){let n=I.getInstance().getSyncRootDir(),i=v.relative(n,e).split(v.sep);if(i.length<4||i[2]!==ke){_.warn("Microi: \u8BF7\u5728\u201C\u6A21\u5757\u5F15\u64CE\u201D\u4E0B\u7684\u6A21\u5757\u76EE\u5F55\u6267\u884C\u62C9\u53D6");return}let r=this.findProfileByServerDir(i[0]);if(!r){_.error(`Microi: \u672A\u627E\u5230\u4E0E\u76EE\u5F55 "${i[0]}" \u5339\u914D\u7684\u670D\u52A1\u5668\u8FDE\u63A5`);return}let o=this.extractTrailingKey(v.basename(e));await this.pullMenuButtonsForProfile(r,o,i[0],i[1],e)}async pullMenuButtonsForProfile(e,t,n,i,r){let o=I.getInstance(),s=L.getInstance(),c=e.apiBaseUrl,l=e.osClient;this.log(`\u5F00\u59CB\u62C9\u53D6\u6A21\u5757 Join/Where \u4E0E\u6309\u94AE V8 \u4EE3\u7801 [${e.label||c}]...`),await oe.withProgress({location:Me.Notification,title:`Microi: \u62C9\u53D6\u6A21\u5757\u4EE3\u7801 [${e.label||c}]`,cancellable:!1},async m=>{let g=await s.get(x.LIST_MODULES,{osClient:l},c,e);if(g.Code!==1)throw new Error(`\u83B7\u53D6\u6A21\u5757\u5217\u8868\u5931\u8D25: ${g.Msg}`);let d=g.Data.List||[],p=await ge.getInstance().getSysConfig(c,l),h=p?.SysShortTitle||"",f=p?.SysTitle||"",y=h||f||e.label||"",S=n||o.buildServerDirName(y,c),C=this.loadMeta(S);C.menus||(C.menus={}),C.menuButtons||(C.menuButtons={}),C.menuScripts||(C.menuScripts={});let R=o.getProfiles().find(N=>N.apiBaseUrl===e.apiBaseUrl&&N.osClient===e.osClient)||e;if(!R.osClientType||!R.osClientNetwork)throw new Error("\u7F3A\u5C11 OsClientType/OsClientNetwork\uFF0C\u8BF7\u5148\u62C9\u53D6\u63A5\u53E3\u5F15\u64CE");let E=i||o.buildOsClientDirName(l,R.osClientType,R.osClientNetwork),b=o.getSyncRootDir(),V=v.join(b,S,E,ke),U=Object.keys($e),A=Object.keys(qe),P=0,O=0,F=0,k=0,$=0,j=new Map(d.map(N=>[N.Id,N])),W=new Map,ee=N=>N||"";for(let N of d){let se=ee(N.ParentId);W.has(se)||W.set(se,[]),W.get(se).push(N)}let re=N=>N.sort((se,Q)=>{let le=typeof se.Sort=="number"?se.Sort:0,We=typeof Q.Sort=="number"?Q.Sort:0;return le!==We?le-We:String(se.Name||se.Label||"").localeCompare(String(Q.Name||Q.Label||""))}),q=t?j.get(t)?[j.get(t)]:[]:re(d.filter(N=>!N.ParentId||!j.has(N.ParentId)));if(t&&q.length===0)throw new Error(`\u627E\u4E0D\u5230\u6A21\u5757 Id=${t}`);let ce=t?r||v.join(V,K(`${q[0].Label||q[0].Name||q[0].Id}\uFF08${q[0].Id}\uFF09`)):V;if(this.backupExistingTree(ce,S,t?"module-subtree":"module-engine"),!t)C.menus={},C.menuButtons={},C.menuScripts={};else{let N=new Set,se=Q=>{if(!N.has(Q)){N.add(Q);for(let le of W.get(Q)||[])se(le.Id)}};se(t);for(let Q of N)delete C.menus[Q];for(let[Q,le]of Object.entries(C.menuButtons))N.has(le.moduleId)&&delete C.menuButtons[Q];for(let[Q,le]of Object.entries(C.menuScripts))N.has(le.moduleId)&&delete C.menuScripts[Q]}let X=async(N,se)=>{k++,m.report({message:`[${k}/${d.length}] ${N.Name||N.Label}`});let Q=N.Label||N.Name||N.Id,le=v.join(se,K(`${Q}\uFF08${N.Id}\uFF09`));te(le);let We=re(W.get(N.Id)||[]);if(We.length>0){for(let Z of We)await X(Z,le);return}let Pt=await s.get(x.GET_MODULE,{osClient:l,moduleId:N.Id},c,e);if(Pt.Code!==1){this.log(` \u8DF3\u8FC7\u6A21\u5757 ${N.Name}: ${Pt.Msg}`);return}let _t=Pt.Data,Ee=String(_t.UpdateTime||me()),tn={};for(let Z of A){let lt=String(_t[Z]||""),Nt=qe[Z]||Z,we=v.join(le,K(`${Nt}\uFF08${Z}\uFF09`)+".js");T.writeFileSync(we,lt,"utf-8"),this.touchSyncedFile(we,Ee),C.menuScripts[this.getMenuScriptMetaKey(N.Id,Z)]={moduleId:N.Id,moduleName:Q,scriptField:Z,codeHash:this.sourceHash(lt),updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),we)},F++}for(let Z of U){let lt=$e[Z]||Z,Nt=K(`${lt}\uFF08${Z}\uFF09`),we=v.join(le,Nt);te(we),O++;let dt=_t[Z],Pe=[];if(dt)try{Pe=typeof dt=="string"?JSON.parse(dt):dt,Array.isArray(Pe)||(Pe=[])}catch{this.log(` \u6309\u94AE JSON \u89E3\u6790\u5931\u8D25 ${N.Name}.${Z}`),Pe=[]}let ti=[...Pe].sort((_e,fe)=>String(_e.Id||"").localeCompare(String(fe.Id||"")));tn[Z]=require("crypto").createHash("sha1").update(JSON.stringify(ti)).digest("hex");for(let _e of Pe){let fe=String(_e.Id||""),gt=String(_e.Name||fe||"Unknown");if(!fe)continue;let nn=String(_e.V8Code||""),Mt=v.join(we,K(`${gt}\uFF08${fe}\uFF09`)+".js");C.menuButtons[this.getMenuButtonMetaKey(N.Id,Z,fe,"V8Code")]={moduleId:N.Id,moduleName:Q,btnField:Z,btnId:fe,btnName:gt,v8SubField:"V8Code",updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),Mt)},nn.trim()?(T.writeFileSync(Mt,nn,"utf-8"),this.touchSyncedFile(Mt,Ee),P++):$++;let rn=String(_e.V8CodeShow||"");if(rn.trim()){let Ft=v.join(we,K(`${gt}_\u663E\u9690\u5224\u65AD\uFF08${fe}\uFF09`)+".js");T.writeFileSync(Ft,rn,"utf-8"),this.touchSyncedFile(Ft,Ee),C.menuButtons[this.getMenuButtonMetaKey(N.Id,Z,fe,"V8CodeShow")]={moduleId:N.Id,moduleName:Q,btnField:Z,btnId:fe,btnName:gt,v8SubField:"V8CodeShow",updateTime:Ee,filePath:v.relative(o.getWorkspaceRoot(),Ft)},P++}else $++}}C.menus[N.Id]={moduleId:N.Id,moduleName:Q,updateTime:Ee,buttonHashes:tn}};te(V);for(let N of q)await X(N,V);this.saveMeta(C,S),this.log(`\u6A21\u5757\u4EE3\u7801\u62C9\u53D6\u5B8C\u6210: ${P} \u4E2A\u6309\u94AEV8\u6587\u4EF6\uFF0C${F} \u4E2A Join/Where \u6587\u4EF6\uFF0C${O} \u4E2A\u6309\u94AE\u76EE\u5F55\uFF0C\u8DF3\u8FC7\u7A7A\u6309\u94AE\u4EE3\u7801 ${$} \u9879`),_.info(`Microi: \u6210\u529F\u62C9\u53D6 ${P} \u4E2A\u6309\u94AEV8\u6587\u4EF6\u548C ${F} \u4E2A Join/Where \u6587\u4EF6${$>0?`\uFF08\u8DF3\u8FC7 ${$} \u4E2A\u7A7A\u6309\u94AE\u4EE3\u7801\uFF09`:""}\uFF0C\u5DF2\u751F\u6210 ${O} \u4E2A\u6309\u94AE\u76EE\u5F55`)})}backupExistingTree(e,t,n){if(!T.existsSync(e))return;let r=I.getInstance().getSyncRootDir();this.ensureSyncGitExcludes(r);let o=v.join(r,".backups",n,this.shortBackupKey(t));te(o);let s=v.join(o,`${Date.now()}-${this.shortBackupKey(v.basename(e))}`);T.renameSync(e,s)}backupAndDeleteSyncFile(e,t,n){if(!T.existsSync(e))return;let i=I.getInstance(),r=i.getSyncRootDir();this.ensureSyncGitExcludes(r);let o=i.getWorkspaceRoot()||r,c=v.relative(o,e).split(v.sep).filter(g=>g&&g!=="..").map(K),l=v.join(r,".backups",n,this.shortBackupKey(t),String(Date.now())),m=v.join(l,...c.length?c:[K(v.basename(e))]);te(v.dirname(m)),T.copyFileSync(e,m),T.unlinkSync(e)}async pushMenuScriptFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u6A21\u5757\u811A\u672C: ${t.moduleId}.${t.scriptField}...`);try{let o=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n);if(o.Code!==1||!o.Data)return _.error(`Microi: \u63A8\u9001\u5931\u8D25 - \u62C9\u53D6\u6A21\u5757\u5931\u8D25 ${o.Msg}`),!1;let s=o.Data,c=String(s[t.scriptField]||""),l=I.getInstance(),m=l.getSyncRootDir();this.ensureSyncGitExcludes(m);let g=v.join(m,".backups","menu-script",this.shortBackupKey(t.serverDir),t.moduleId);te(g),T.writeFileSync(v.join(g,`${t.scriptField}-${Date.now()}.js`),c,"utf-8");let d={OsClient:t.osClient,ModuleId:t.moduleId,[t.scriptField]:r},u=await i.post(x.UPDATE_MODULE,d,void 0,n?.apiBaseUrl,n);if(u.Code!==1)return _.error(`Microi: \u63A8\u9001\u6A21\u5757 ${t.scriptField} \u5931\u8D25 - ${u.Msg}`),!1;let p=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n),h=p.Data;if(p.Code!==1||!h||this.normalizeCode(String(h[t.scriptField]||""))!==this.normalizeCode(r))return _.error(`Microi: ${t.scriptField} \u63A5\u53E3\u8FD4\u56DE\u6210\u529F\uFF0C\u4F46\u8FDC\u7AEF\u56DE\u8BFB\u4E0D\u4E00\u81F4\uFF1B\u5DF2\u4FDD\u7559\u672C\u5730\u4FEE\u6539\u548C\u8FDC\u7AEF\u5907\u4EFD`),!1;let f=String(h.UpdateTime||u.Data?.UpdateTime||me()),y=this.loadMeta(t.serverDir);return y.menuScripts||(y.menuScripts={}),y.menuScripts[this.getMenuScriptMetaKey(t.moduleId,t.scriptField)]={moduleId:t.moduleId,moduleName:String(h.Label||h.Name||s.Label||s.Name||t.moduleId),scriptField:t.scriptField,codeHash:this.sourceHash(r),updateTime:f,filePath:v.relative(l.getWorkspaceRoot(),e)},y.menus||(y.menus={}),y.menus[t.moduleId]={moduleId:t.moduleId,moduleName:String(h.Label||h.Name||s.Label||s.Name||t.moduleId),updateTime:f,buttonHashes:y.menus[t.moduleId]?.buttonHashes||{}},this.saveMeta(y,t.serverDir),this.touchSyncedFile(e,f),this.log(`\u63A8\u9001\u5E76\u56DE\u8BFB\u6210\u529F: ${t.moduleId}.${t.scriptField}`),!0}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u6A21\u5757\u811A\u672C\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u6A21\u5757\u811A\u672C\u5F02\u5E38 - ${s}`),!1}}async pushMenuButtonFile(e,t,n){let i=L.getInstance(),r=Ce(T.readFileSync(e,"utf-8"));this.log(`\u63A8\u9001\u6309\u94AEV8\u4EE3\u7801: ${t.moduleId}.${t.btnField}.${t.btnId}.${t.v8SubField}...`);try{let o=await i.get(x.GET_MODULE,{osClient:t.osClient,moduleId:t.moduleId},n?.apiBaseUrl,n);if(o.Code!==1)return _.error(`Microi: \u63A8\u9001\u5931\u8D25 - \u62C9\u53D6\u6A21\u5757\u5931\u8D25 ${o.Msg}`),!1;let s=o.Data,c=[],l=s[t.btnField];if(l)try{c=typeof l=="string"?JSON.parse(l):l,Array.isArray(c)||(c=[])}catch{return _.error("Microi: \u63A8\u9001\u5931\u8D25 - \u6309\u94AE JSON \u89E3\u6790\u5931\u8D25"),!1}let g=I.getInstance().getSyncRootDir();this.ensureSyncGitExcludes(g);let d=v.join(g,".backups","menu-button-json",this.shortBackupKey(t.serverDir),t.moduleId);te(d);let u=v.join(d,`${t.btnField}-${Date.now()}.json`);T.writeFileSync(u,JSON.stringify(c,null,2),"utf-8");let p=c.find(y=>String(y.Id||"")===t.btnId);if(!p){let y=c.map(S=>Number(S.Sort||0)).filter(S=>!isNaN(S));p={Id:t.btnId,Name:t.btnName||t.btnId,Sort:y.length>0?Math.max(...y)+1:c.length+1,IsVisible:!0,ShowRow:t.btnField==="MoreBtns"},c.push(p)}p[t.v8SubField]=r;let h={OsClient:t.osClient,ModuleId:t.moduleId};h[t.btnField]=JSON.stringify(c);let f=await i.post(x.UPDATE_MODULE,h,void 0,n?.apiBaseUrl,n);if(f.Code===1){this.log(`\u63A8\u9001\u6210\u529F: ${t.moduleId}.${t.btnField}.${t.btnId}.${t.v8SubField}`);let y=f.Data?.UpdateTime||me(),S=this.loadMeta(t.serverDir);S.menuButtons||(S.menuButtons={});let C=this.getMenuButtonMetaKey(t.moduleId,t.btnField,t.btnId,t.v8SubField);return r.trim()?S.menuButtons[C]={moduleId:t.moduleId,moduleName:String(s.Name||s.Label||t.moduleId),btnField:t.btnField,btnId:t.btnId,btnName:String(p.Name||t.btnName||t.btnId),v8SubField:t.v8SubField,updateTime:y,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)}:delete S.menuButtons[C],S.menus||(S.menus={}),S.menus[t.moduleId]={moduleId:t.moduleId,moduleName:String(s.Name||s.Label||t.moduleId),updateTime:y,buttonHashes:S.menus[t.moduleId]?.buttonHashes||{}},this.saveMeta(S,t.serverDir),r.trim()?this.touchSyncedFile(e,y):T.existsSync(e)&&T.unlinkSync(e),!0}return _.error(`Microi: \u63A8\u9001\u6309\u94AE\u5931\u8D25 - ${f.Msg}`),!1}catch(o){let s=o instanceof Error?o.message:String(o);return this.log(`\u63A8\u9001\u5F02\u5E38: ${s}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${s}`),!1}}async pushWorkflowNodeFile(e,t,n){let i=L.getInstance(),r=T.readFileSync(e,"utf-8"),o=Ce(r);this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8: ${t.flowDesignId}/${t.nodeId}/${t.eventType}...`);try{let s="",c="";try{let u=await i.post(x.GET_WORKFLOW_V8_EVENT_CODE,{OsClient:t.osClient,FlowDesignId:t.flowDesignId,NodeId:t.nodeId,EventType:t.eventType},void 0,n?.apiBaseUrl,n);u.Code===1&&u.Data&&(s=u.Data.V8Code||u.Data.Code||"",c=u.Data.Version||"")}catch{s="",c=""}let l=!o.trim(),m=l?{code:"",version:c,changeHistory:""}:tt({kind:"Workflow",key:`${t.flowDesignId}/${t.nodeId}`,eventType:t.eventType,currentCode:o,remoteCode:s,remoteVersion:c,changeSummary:`\u901A\u8FC7 VS Code \u63A8\u9001\u6D41\u7A0B\u8282\u70B9 V8 ${t.flowDesignId}/${t.nodeId}/${t.eventType}`}),g={OsClient:t.osClient,FlowDesignId:t.flowDesignId,NodeId:t.nodeId,EventType:t.eventType};l?g.V8Code="":(g.V8CodeBase64=Buffer.from(m.code,"utf8").toString("base64"),g.Version=m.version,g.ChangeHistory=m.changeHistory);let d=await i.post(x.UPDATE_WORKFLOW_V8_EVENT_CODE,g,void 0,n?.apiBaseUrl,n);if(d.Code===1){let u=d.Data?.UpdateTime||me(),p=this.loadMeta(t.serverDir);p.workflowNodeEvents||(p.workflowNodeEvents={});let h=`${t.flowDesignId}__${t.nodeId}__${t.eventType}`;return l?delete p.workflowNodeEvents[h]:p.workflowNodeEvents[h]={flowDesignId:t.flowDesignId,flowName:p.workflowNodeEvents[h]?.flowName||t.flowDesignId,nodeId:t.nodeId,nodeName:p.workflowNodeEvents[h]?.nodeName||t.nodeId,eventType:t.eventType,updateTime:u,filePath:v.relative(I.getInstance().getWorkspaceRoot(),e)},this.saveMeta(p,t.serverDir),l?T.existsSync(e)&&T.unlinkSync(e):(T.writeFileSync(e,m.code,"utf-8"),this.touchSyncedFile(e,u)),this.log(`\u63A8\u9001\u6210\u529F: ${t.flowDesignId}/${t.nodeId}/${t.eventType}`),!0}return this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5931\u8D25: ${d.Msg}`),_.error(`Microi: \u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5931\u8D25 - ${d.Msg}`),!1}catch(s){let c=s instanceof Error?s.message:String(s);return this.log(`\u63A8\u9001\u6D41\u7A0B\u8282\u70B9V8\u5F02\u5E38: ${c}`),_.error(`Microi: \u63A8\u9001\u5F02\u5E38 - ${c}`),!1}}async pullDbSchema(e){let t=I.getInstance(),n=L.getInstance();if(!e){let i=t.getProfiles();if(i.length===0){_.warn("Microi: \u6CA1\u6709\u5DF2\u8FDE\u63A5\u7684\u670D\u52A1\u5668");return}for(let r of i)try{await this.pullDbSchemaForProfile(r)}catch(o){let s=o instanceof Error?o.message:String(o);this.log(`\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5931\u8D25 [${r.label||r.apiBaseUrl}]: ${s}`)}return}await this.pullDbSchemaForProfile(e)}async pullDbSchemaForProfile(e){let t=I.getInstance(),n=L.getInstance(),i=e.apiBaseUrl,r=e.osClient;this.log(`\u5F00\u59CB\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784 [${e.label||i}]...`);let o=await n.get(x.GET_DB_SCHEMA,{osClient:r},i,e);if(o.Code!==1){let b=o.Code===1001||o.Code===1002?"\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55":"";throw new Error(`\u83B7\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5931\u8D25: ${o.Msg||"Code="+o.Code}${b}`)}let s=t.getSyncRootDir(),l=await ge.getInstance().getSysConfig(i,r),m=l?.SysShortTitle||"",g=l?.SysTitle||"",d=m||g||l?.CompanyName||e.label||"";d&&(d!==e.label||m!==e.sysShortTitle||g!==e.sysTitle)&&await t.addProfile({...e,label:d,sysShortTitle:m,sysTitle:g});let u=t.buildServerDirName(d,i),h=t.getProfiles().find(b=>b.apiBaseUrl===e.apiBaseUrl&&b.osClient===e.osClient)||e,f=t.buildOsClientDirName(r,h.osClientType,h.osClientNetwork),y=v.join(s,u,f);te(y);let S=v.join(y,Le);T.writeFileSync(S,JSON.stringify(o.Data,null,2),"utf-8");let C=v.join(y,De),w=this.formatDbSchemaMarkdown(o.Data,u,f);w&&T.writeFileSync(C,w,"utf-8");let R=o.Data.Tables?.length||0,E=d||e.label||i;this.log(`[${E}] \u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\u5B8C\u6210: ${R} \u5F20\u8868`),_.info(`Microi: [${E}] \u6210\u529F\u62C9\u53D6\u6570\u636E\u5E93\u7ED3\u6784\uFF08${R} \u5F20\u8868\uFF09`)}formatDbSchemaMarkdown(e,t,n){let i=(e.Tables||[]).filter(c=>c.Name);if(!i.length)return"";let r=i.reduce((c,l)=>{let m=l._Fields||l.Fields||[];return c+m.length},0),o=e.Menus?.length||0,s=[];s.push(`# \u6570\u636E\u5E93\u7ED3\u6784 \u2014 ${t}/${n}
42
42
  `),s.push("> \u6B64\u6587\u4EF6\u7531 Microi\u543E\u7801 VS Code \u63D2\u4EF6\u81EA\u52A8\u751F\u6210\uFF0C\u4F9B AI \u7F16\u5199 V8.FormEngine / V8.Db \u4EE3\u7801\u65F6\u53C2\u8003\u3002"),s.push(`> \u5171 ${i.length} \u5F20\u8868\uFF0C${r} \u4E2A\u5B57\u6BB5\uFF0C${o} \u4E2A\u83DC\u5355\u3002
43
- `);for(let c of i){let d=c.Description?` \u2014 ${c.Description}`:"";s.push(`## ${c.Name}${d}
43
+ `);for(let c of i){let l=c.Description?` \u2014 ${c.Description}`:"";s.push(`## ${c.Name}${l}
44
44
  `);let m=c._Fields||c.Fields||[];if(!m.length){s.push(`_\u6682\u65E0\u5B57\u6BB5\u4FE1\u606F._
45
- `);continue}s.push("| \u5B57\u6BB5 | \u6807\u7B7E/\u8BF4\u660E | \u7C7B\u578B | \u7EC4\u4EF6 | \u5FC5\u586B | \u5173\u8054 |"),s.push("|------|-----------|------|------|------|------|");for(let g of m){let l=g.Label||g.Description||"",u=g.Type||g.FieldType||"",p=g.Required===!0||g.NotEmpty===1?"\u662F":"",h=g.ChildTableId||g.ChildSysMenuId||"";s.push(`| ${g.Name} | ${l} | ${u} | ${g.Component||""} | ${p} | ${h} |`)}s.push("")}return s.join(`
45
+ `);continue}s.push("| \u5B57\u6BB5 | \u6807\u7B7E/\u8BF4\u660E | \u7C7B\u578B | \u7EC4\u4EF6 | \u5FC5\u586B | \u5173\u8054 |"),s.push("|------|-----------|------|------|------|------|");for(let g of m){let d=g.Label||g.Description||"",u=g.Type||g.FieldType||"",p=g.Required===!0||g.NotEmpty===1?"\u662F":"",h=g.ChildTableId||g.ChildSysMenuId||"";s.push(`| ${g.Name} | ${d} | ${u} | ${g.Component||""} | ${p} | ${h} |`)}s.push("")}return s.join(`
46
46
  `)}dispose(){}};var D=G(require("fs")),M=G(require("path")),Bn=G(require("crypto")),Yt=require("child_process");var ki=`/**
47
47
  * Microi V8\u5F15\u64CE API \u7C7B\u578B\u5B9A\u4E49
48
48
  * \u6B64\u6587\u4EF6\u7531 Microi\u543E\u7801 VS Code \u63D2\u4EF6\u81EA\u52A8\u751F\u6210\uFF0C\u8BF7\u52FF\u624B\u52A8\u4FEE\u6539
@@ -1738,9 +1738,9 @@ console.log('\u8C03\u8BD5\u4FE1\u606F') // \u63
1738
1738
  - \u4E8B\u52A1\u7BA1\u7406\uFF1A\u5E73\u53F0\u4E8B\u52A1\u7981\u6B62\u624B\u52A8 Commit/Rollback\uFF1B\u5E26Code\u5BF9\u8C61\u4EC5Code=1\u63D0\u4EA4\u3001\u65E0Code\u5BF9\u8C61\u56DE\u6EDA\uFF0C\u539F\u59CB\u503C\u65E0\u5F02\u5E38\u65F6\u63D0\u4EA4
1739
1739
  - \`_InvokeType: 'Client'\`\uFF1AFormEngine\u8C03\u7528\u65F6\u89E6\u53D1\u8868\u5355V8\u4E8B\u4EF6\uFF08\u9ED8\u8BA4Server\u6A21\u5F0F\u4E0D\u89E6\u53D1\uFF09
1740
1740
  - \u540E\u7AEF\u53EF\u4FE1V8\u8C03\u7528FormEngine\u4E0D\u8981\u6C42 \`_SysMenuId\`\uFF1B\u6D4F\u89C8\u5668\u4E0D\u80FD\u901A\u8FC7 \`_InvokeType\` \u4F2A\u9020\u4FE1\u4EFB
1741
- `,Li="\n\n## MicroService \u5927\u578B\u4EA7\u7269\u4E0E\u4E0A\u4E0B\u6587\u89C4\u5219\uFF08\u8986\u76D6\u65E7\u517C\u5BB9\u8BF4\u660E\uFF09\n\n- `microi_get_application_context` \u9ED8\u8BA4\u53EA\u8BFB\u5143\u6570\u636E\u3001\u54C8\u5E0C\u3001\u8FD0\u884C\u65F6\u548C\u9875\u9762\uFF1B\u5C11\u91CF\u6B63\u6587\u663E\u5F0F\u5F00\u542F\u5185\u5BB9\u8BFB\u53D6\uFF0C\u5355\u6587\u4EF6\u4F7F\u7528 `microi_get_application_file`\u3002\n- \u771F\u5B9E\u7F16\u8BD1\u76EE\u5F55\u4E00\u5F8B\u9010\u6587\u4EF6\u6D41\u5F0F\u53D1\u5E03\uFF0C\u652F\u6301\u6700\u591A 20,000 \u6587\u4EF6/\u603B\u8BA1 20GB\uFF1B\u51E0\u767E MB\u30011GB \u7EA7\u9879\u76EE\u4E0D\u5F97\u56DE\u9000 Base64\u3002\n- `StorageMode=db` \u7684 256 \u6587\u4EF6/5MB \u4EC5\u7528\u4E8E\u663E\u5F0F\u5C0F\u578B\u5E94\u6025\u6062\u590D\uFF0C\u4E0D\u662F\u6B63\u5E38\u53D1\u5E03\u5BB9\u91CF\u3002\n- \u6D41\u5F0F\u5931\u8D25\u8BFB\u53D6 `uploadedCount/retrySafe` \u5E76\u6309\u540C\u7248\u672C\u5E42\u7B49\u91CD\u8BD5\uFF1B\u7981\u6B62\u56E0\u5927\u6587\u4EF6\u81EA\u52A8\u6539\u8D70 `microi_publish_microservice`\u3002\n- \u5B50\u79DF\u6237\u6240\u6709\u6E90\u7801\u3001\u8D44\u4EA7\u3001\u56DE\u8BFB\u9A8C\u7B7E\u3001\u9875\u9762\u548C\u7F13\u5B58\u5FC5\u987B\u7ED1\u5B9A\u5F53\u524D Token \u7684 OsClient\uFF0C\u4E0D\u5F97\u56DE\u9000\u4E3B\u79DF\u6237\u9ED8\u8BA4\u914D\u7F6E\u3002\n",wt=class a{static getInstance(){return a._instance||(a._instance=new a),a._instance}inject(){let e=I.getInstance();if(!e.getWorkspaceRoot())return;let n;try{n=e.getSyncRootDir()}catch{return}let i=M.join(n,Qe);D.existsSync(i)||D.mkdirSync(i,{recursive:!0});let r=M.join(i,pt);D.writeFileSync(r,ki,"utf-8"),this.injectAiDocs(n),this.ensureJsConfig(n,i)}injectAiDocs(e){try{this.generatePerOsClientSchemaDocs(e);let t=I.getInstance().getWorkspaceRoot();if(!t)return;this.ensureLocalRuntimeFilesIgnored(t,e),this.syncBundledSkills(t);let n=this.collectSkillEntries(t),i=this.buildSkillsReference(n),r=$i+Ln+$n+xn+Ri+Pi+_i+Ni+Mi+Fi+Ai+Li+Oi+Vi+i,o=[{relativePath:`${Ot}/${$t}`,content:nt+r},{relativePath:Lt,content:nt+r},{relativePath:xt,content:nt+r},{relativePath:Bt,content:nt+r}];n.length>0&&o.push({relativePath:`${Ut}/${jt}`,content:this.buildCursorSkillRule(n)}),this.syncGeneratedAiDocs(t,o)}catch{}}ensureLocalRuntimeFilesIgnored(e,t){let n=[".vscode/mcp.json",`.vscode/${Et}`,".cursor/mcp.json",gn,".claude/settings.local.json"],i=M.relative(e,t);if(i&&!i.startsWith("..")&&!M.isAbsolute(i)){let r=i.replace(/\\/g,"/");n.push(`${r}/**/${Le}`,`${r}/**/${De}`,`${r}/**/${Ae}`,`${r}/${ze}`,`${r}/**/${ze}`,`${r}/.backups/`,`${r}/**/.backups/`,`${r}/${Qe}/`)}Be(e),ve(e,n)}getBundledSkillsDir(){return M.join(__dirname,"microi.skills")}syncBundledSkills(e){let t=this.getBundledSkillsDir();if(!D.existsSync(t))return;let n=M.join(e,On),i=M.join(n,Qt),r=this.readSkillManifest(i),o=this.readBundledSkillsMeta(),s=o.skills?.version,c=this.compareMicroiVersions(s,r.bundleVersion)<0,d={version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",bundleVersion:c?r.bundleVersion:s||r.bundleVersion,bundleBuiltAt:c?r.bundleBuiltAt:o.builtAt||r.bundleBuiltAt,fileVersions:{...r.fileVersions||{}},files:{...r.files}},m=[];this.walkSkillSource(t,(l,u)=>{let p=M.join(n,u),h=D.readFileSync(l,"utf-8"),f=this.hashText(h),y=r.files[u],S=o.fileVersions?.[u]||s,C=r.fileVersions?.[u]||r.bundleVersion,w=this.compareMicroiVersions(S,C)<0,R=!1;if(!D.existsSync(p))R=!w;else if(y)try{R=this.hashText(D.readFileSync(p,"utf-8"))===y&&!w}catch{R=!1}if(R){let E=M.dirname(p);D.existsSync(E)||D.mkdirSync(E,{recursive:!0}),D.writeFileSync(p,h,"utf-8"),m.push(u)}if(R)d.files[u]=f,S&&(d.fileVersions[u]=S);else try{if(this.hashText(D.readFileSync(p,"utf-8"))===f){d.files[u]=f;let b=this.pickNewerMicroiVersion(S,r.fileVersions?.[u]);b&&(d.fileVersions[u]=b)}else y?(d.files[u]=y,r.fileVersions?.[u]&&(d.fileVersions[u]=r.fileVersions[u])):(delete d.files[u],delete d.fileVersions[u])}catch{y&&(d.files[u]=y,r.fileVersions?.[u]&&(d.fileVersions[u]=r.fileVersions[u]))}});let g=JSON.stringify(d)!==JSON.stringify(r);(m.length>0||g||!D.existsSync(i))&&(D.existsSync(n)||D.mkdirSync(n,{recursive:!0}),D.writeFileSync(i,JSON.stringify(d,null,2)+`
1742
- `,"utf-8"),ve(e,[`${On}/${Qt}`]))}readSkillManifest(e){if(!D.existsSync(e))return{version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",files:{}};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return{version:typeof t.version=="number"?t.version:1,generatedBy:t.generatedBy||"Microi\u543E\u7801 VSCode Extension",bundleVersion:typeof t.bundleVersion=="string"?t.bundleVersion:void 0,bundleBuiltAt:typeof t.bundleBuiltAt=="string"?t.bundleBuiltAt:void 0,fileVersions:t.fileVersions&&typeof t.fileVersions=="object"?t.fileVersions:{},files:t.files&&typeof t.files=="object"?t.files:{}}}catch{return{version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",files:{}}}}readBundledSkillsMeta(){let e=M.join(__dirname,Di);if(!D.existsSync(e))return{};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return t&&typeof t=="object"?t:{}}catch{return{}}}walkSkillSource(e,t){let n=i=>{for(let r of D.readdirSync(i,{withFileTypes:!0})){if(r.name===".git"||r.name==="node_modules"||r.name===Qt)continue;let o=M.join(i,r.name);if(r.isDirectory())n(o);else if(r.isFile()){let s=M.relative(e,o).replace(/\\/g,"/");t(o,s)}}};n(e)}hashText(e){return Bn.createHash("sha256").update(e,"utf-8").digest("hex")}compareMicroiVersions(e,t){let n=o=>{if(!(!o||!/^\d+(?:\.\d+){2}$/.test(o)))return o.split(".").map(s=>Number(s))},i=n(e),r=n(t);if(!i||!r)return 0;for(let o=0;o<3;o++)if(i[o]!==r[o])return i[o]>r[o]?1:-1;return 0}pickNewerMicroiVersion(e,t){return e?t?this.compareMicroiVersions(e,t)>=0?e:t:e:t}syncGeneratedAiDocs(e,t){let n=t.map(l=>l.relativePath.replace(/\\/g,"/")),i=n.map(l=>this.normalizeRelativePath(l)),r=this.getGitTrackedWorkspaceFiles(e,n);if(r===void 0)return;let o=M.join(e,".vscode",Et),s=this.readAiDocsManifest(o),c=this.readBundledSkillsMeta().skills?.version,d=this.pickNewerMicroiVersion(c,s.bundleVersion),m={version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",bundleVersion:d,fileVersions:{...s.fileVersions||{}},fileHashes:{...s.fileHashes||{}},files:{...s.files}},g=new Set(i);for(let l of Object.keys(m.files))g.has(this.normalizeRelativePath(l))||(delete m.files[l],delete m.fileHashes[l],delete m.fileVersions[l]);for(let l of Object.keys(m.fileHashes))g.has(this.normalizeRelativePath(l))||(delete m.fileHashes[l],delete m.fileVersions[l],delete m.files[l]);for(let l of t){let u=this.normalizeRelativePath(l.relativePath);if(r.has(u)){delete m.files[u],delete m.fileHashes[u],delete m.fileVersions[u];continue}let p=M.join(e,u),h=this.hashText(l.content),f=s.files[u],y=s.fileHashes?.[u]||(/^[a-f0-9]{64}$/i.test(f||"")?f:void 0),S=s.fileVersions?.[u]||s.bundleVersion,C=this.compareMicroiVersions(c,S)<0,w=!D.existsSync(p)&&!C,R="";if(D.existsSync(p))try{let b=D.readFileSync(p,"utf-8");R=this.hashText(b),w=!!y&&R===y&&!C,!y&&b.includes("Generated by Microi\u543E\u7801 VSCode Extension")&&(m.fileHashes[u]=R,S&&(m.fileVersions[u]=S))}catch{w=!1}if(w){let b=M.dirname(p);D.existsSync(b)||D.mkdirSync(b,{recursive:!0}),D.writeFileSync(p,l.content,"utf-8"),R=h,m.fileHashes[u]=h,c&&(m.fileVersions[u]=c)}else if(R===h){m.fileHashes[u]=h;let b=this.pickNewerMicroiVersion(c,S);b&&(m.fileVersions[u]=b)}else y?(m.fileHashes[u]=y,S&&(m.fileVersions[u]=S)):m.fileHashes[u]||delete m.fileVersions[u];let E=m.fileHashes[u];if(E){let b=m.fileVersions[u]||d||"unknown";m.files[u]=`${Ii}${b}:${E}`}else delete m.files[u]}if(JSON.stringify(m)!==JSON.stringify(s)||!D.existsSync(o)){let l=M.dirname(o);D.existsSync(l)||D.mkdirSync(l,{recursive:!0}),D.writeFileSync(o,JSON.stringify(m,null,2)+`
1743
- `,"utf-8")}ve(e,[`.vscode/${Et}`])}readAiDocsManifest(e){if(!D.existsSync(e))return{version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",files:{},fileHashes:{},fileVersions:{}};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return{version:typeof t.version=="number"?t.version:1,generatedBy:t.generatedBy||"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",bundleVersion:typeof t.bundleVersion=="string"?t.bundleVersion:void 0,fileVersions:t.fileVersions&&typeof t.fileVersions=="object"?t.fileVersions:{},fileHashes:t.fileHashes&&typeof t.fileHashes=="object"?t.fileHashes:{},files:t.files&&typeof t.files=="object"?t.files:{}}}catch{return{version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",files:{},fileHashes:{},fileVersions:{}}}}normalizeRelativePath(e){let t=e.replace(/\\/g,"/").replace(/^\.\//,"");return process.platform==="win32"?t.toLowerCase():t}getGitTrackedWorkspaceFiles(e,t){let n=(0,Yt.spawnSync)("git",["-C",e,"rev-parse","--show-toplevel"],{encoding:"utf-8",windowsHide:!0,timeout:3e3});if(n.error)return this.hasGitMetadata(e)?void 0:new Set;if(n.status!==0)return new Set;let i=String(n.stdout||"").trim();if(!i)return;let r=new Map,o=[];for(let d of t){let m=M.relative(i,M.join(e,d));m.startsWith("..")||M.isAbsolute(m)||(o.push(m.replace(/\\/g,"/")),r.set(this.normalizeRelativePath(m),this.normalizeRelativePath(d)))}if(o.length===0)return new Set;let s=(0,Yt.spawnSync)("git",["-C",i,"ls-files","-z","--",...o],{encoding:"utf-8",windowsHide:!0,timeout:3e3,maxBuffer:1024*1024});if(s.error||s.status!==0)return;let c=new Set;for(let d of String(s.stdout||"").split("\0").filter(Boolean)){let m=r.get(this.normalizeRelativePath(d));m&&c.add(m)}return c}hasGitMetadata(e){let t=M.resolve(e);for(;;){if(D.existsSync(M.join(t,".git")))return!0;let n=M.dirname(t);if(n===t)return!1;t=n}}canRemoveGeneratedAiDoc(e,t){if(!D.existsSync(t))return!1;let n=M.relative(e,t).replace(/\\/g,"/"),i=this.normalizeRelativePath(n),r=this.getGitTrackedWorkspaceFiles(e,[n]);if(r===void 0||r.has(i))return!1;let o=this.readAiDocsManifest(M.join(e,".vscode",Et)),s=o.files[i],c=o.fileHashes?.[i]||(/^[a-f0-9]{64}$/i.test(s||"")?s:void 0);if(!c)return!1;try{return this.hashText(D.readFileSync(t,"utf-8"))===c}catch{return!1}}collectSkillEntries(e){let t=M.join(e,"microi.skills");if(!D.existsSync(t))return[];let n=new Map,i=M.join(t,"README.md");if(D.existsSync(i))try{let s=D.readFileSync(i,"utf-8").matchAll(/`([^`]+\/SKILL\.md)`/g),c=0;for(let d of s){let m=d[1].split(/[\\/]/)[0];m&&!n.has(m)&&n.set(m,c++)}}catch{}let r=[];try{for(let o of D.readdirSync(t,{withFileTypes:!0})){if(!o.isDirectory())continue;let s=M.join(t,o.name,"SKILL.md");D.existsSync(s)&&r.push({name:o.name,relativePath:`microi.skills/${o.name}/SKILL.md`,description:this.readSkillDescription(s,o.name)})}}catch{}return r.sort((o,s)=>{let c=n.get(o.name),d=n.get(s.name);return c!==void 0&&d!==void 0?c-d:c!==void 0?-1:d!==void 0?1:o.name.localeCompare(s.name)})}readSkillDescription(e,t){try{let i=D.readFileSync(e,"utf-8").split(/\r?\n/).find(r=>r.startsWith("# "));if(i)return i.replace(/^#\s+/,"").trim()}catch{}return t}buildSkillsReference(e){if(!e.length)return"";let t=e.map(n=>`- \`${n.relativePath}\` \u2014 ${n.description}`).join(`
1741
+ `,Li="\n\n## MicroService \u5927\u578B\u4EA7\u7269\u4E0E\u4E0A\u4E0B\u6587\u89C4\u5219\uFF08\u8986\u76D6\u65E7\u517C\u5BB9\u8BF4\u660E\uFF09\n\n- `microi_get_application_context` \u9ED8\u8BA4\u53EA\u8BFB\u5143\u6570\u636E\u3001\u54C8\u5E0C\u3001\u8FD0\u884C\u65F6\u548C\u9875\u9762\uFF1B\u5C11\u91CF\u6B63\u6587\u663E\u5F0F\u5F00\u542F\u5185\u5BB9\u8BFB\u53D6\uFF0C\u5355\u6587\u4EF6\u4F7F\u7528 `microi_get_application_file`\u3002\n- \u771F\u5B9E\u7F16\u8BD1\u76EE\u5F55\u4E00\u5F8B\u9010\u6587\u4EF6\u6D41\u5F0F\u53D1\u5E03\uFF0C\u652F\u6301\u6700\u591A 20,000 \u6587\u4EF6/\u603B\u8BA1 20GB\uFF1B\u51E0\u767E MB\u30011GB \u7EA7\u9879\u76EE\u4E0D\u5F97\u56DE\u9000 Base64\u3002\n- `StorageMode=db` \u7684 256 \u6587\u4EF6/5MB \u4EC5\u7528\u4E8E\u663E\u5F0F\u5C0F\u578B\u5E94\u6025\u6062\u590D\uFF0C\u4E0D\u662F\u6B63\u5E38\u53D1\u5E03\u5BB9\u91CF\u3002\n- \u6D41\u5F0F\u5931\u8D25\u8BFB\u53D6 `uploadedCount/retrySafe` \u5E76\u6309\u540C\u7248\u672C\u5E42\u7B49\u91CD\u8BD5\uFF1B\u7981\u6B62\u56E0\u5927\u6587\u4EF6\u81EA\u52A8\u6539\u8D70 `microi_publish_microservice`\u3002\n- \u5B50\u79DF\u6237\u6240\u6709\u6E90\u7801\u3001\u8D44\u4EA7\u3001\u56DE\u8BFB\u9A8C\u7B7E\u3001\u9875\u9762\u548C\u7F13\u5B58\u5FC5\u987B\u7ED1\u5B9A\u5F53\u524D Token \u7684 OsClient\uFF0C\u4E0D\u5F97\u56DE\u9000\u4E3B\u79DF\u6237\u9ED8\u8BA4\u914D\u7F6E\u3002\n",wt=class a{static getInstance(){return a._instance||(a._instance=new a),a._instance}inject(){let e=I.getInstance();if(!e.getWorkspaceRoot())return;let n;try{n=e.getSyncRootDir()}catch{return}let i=M.join(n,Qe);D.existsSync(i)||D.mkdirSync(i,{recursive:!0});let r=M.join(i,pt);D.writeFileSync(r,ki,"utf-8"),this.injectAiDocs(n),this.ensureJsConfig(n,i)}injectAiDocs(e){try{this.generatePerOsClientSchemaDocs(e);let t=I.getInstance().getWorkspaceRoot();if(!t)return;this.ensureLocalRuntimeFilesIgnored(t,e),this.syncBundledSkills(t);let n=this.collectSkillEntries(t),i=this.buildSkillsReference(n),r=$i+Ln+$n+xn+Ri+Pi+_i+Ni+Mi+Fi+Ai+Li+Oi+Vi+i,o=[{relativePath:`${Ot}/${$t}`,content:nt+r},{relativePath:Lt,content:nt+r},{relativePath:xt,content:nt+r},{relativePath:Bt,content:nt+r}];n.length>0&&o.push({relativePath:`${Ut}/${jt}`,content:this.buildCursorSkillRule(n)}),this.syncGeneratedAiDocs(t,o)}catch{}}ensureLocalRuntimeFilesIgnored(e,t){let n=[".vscode/mcp.json",`.vscode/${Et}`,".cursor/mcp.json",gn,".claude/settings.local.json"],i=M.relative(e,t);if(i&&!i.startsWith("..")&&!M.isAbsolute(i)){let r=i.replace(/\\/g,"/");n.push(`${r}/**/${Le}`,`${r}/**/${De}`,`${r}/**/${Ae}`,`${r}/${ze}`,`${r}/**/${ze}`,`${r}/.backups/`,`${r}/**/.backups/`,`${r}/${Qe}/`)}Be(e),ve(e,n)}getBundledSkillsDir(){return M.join(__dirname,"microi.skills")}syncBundledSkills(e){let t=this.getBundledSkillsDir();if(!D.existsSync(t))return;let n=M.join(e,On),i=M.join(n,Qt),r=this.readSkillManifest(i),o=this.readBundledSkillsMeta(),s=o.skills?.version,c=this.compareMicroiVersions(s,r.bundleVersion)<0,l={version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",bundleVersion:c?r.bundleVersion:s||r.bundleVersion,bundleBuiltAt:c?r.bundleBuiltAt:o.builtAt||r.bundleBuiltAt,fileVersions:{...r.fileVersions||{}},files:{...r.files}},m=[];this.walkSkillSource(t,(d,u)=>{let p=M.join(n,u),h=D.readFileSync(d,"utf-8"),f=this.hashText(h),y=r.files[u],S=o.fileVersions?.[u]||s,C=r.fileVersions?.[u]||r.bundleVersion,w=this.compareMicroiVersions(S,C)<0,R=!1;if(!D.existsSync(p))R=!w;else if(y)try{R=this.hashText(D.readFileSync(p,"utf-8"))===y&&!w}catch{R=!1}if(R){let E=M.dirname(p);D.existsSync(E)||D.mkdirSync(E,{recursive:!0}),D.writeFileSync(p,h,"utf-8"),m.push(u)}if(R)l.files[u]=f,S&&(l.fileVersions[u]=S);else try{if(this.hashText(D.readFileSync(p,"utf-8"))===f){l.files[u]=f;let b=this.pickNewerMicroiVersion(S,r.fileVersions?.[u]);b&&(l.fileVersions[u]=b)}else y?(l.files[u]=y,r.fileVersions?.[u]&&(l.fileVersions[u]=r.fileVersions[u])):(delete l.files[u],delete l.fileVersions[u])}catch{y&&(l.files[u]=y,r.fileVersions?.[u]&&(l.fileVersions[u]=r.fileVersions[u]))}});let g=JSON.stringify(l)!==JSON.stringify(r);(m.length>0||g||!D.existsSync(i))&&(D.existsSync(n)||D.mkdirSync(n,{recursive:!0}),D.writeFileSync(i,JSON.stringify(l,null,2)+`
1742
+ `,"utf-8"),ve(e,[`${On}/${Qt}`]))}readSkillManifest(e){if(!D.existsSync(e))return{version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",files:{}};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return{version:typeof t.version=="number"?t.version:1,generatedBy:t.generatedBy||"Microi\u543E\u7801 VSCode Extension",bundleVersion:typeof t.bundleVersion=="string"?t.bundleVersion:void 0,bundleBuiltAt:typeof t.bundleBuiltAt=="string"?t.bundleBuiltAt:void 0,fileVersions:t.fileVersions&&typeof t.fileVersions=="object"?t.fileVersions:{},files:t.files&&typeof t.files=="object"?t.files:{}}}catch{return{version:1,generatedBy:"Microi\u543E\u7801 VSCode Extension",files:{}}}}readBundledSkillsMeta(){let e=M.join(__dirname,Di);if(!D.existsSync(e))return{};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return t&&typeof t=="object"?t:{}}catch{return{}}}walkSkillSource(e,t){let n=i=>{for(let r of D.readdirSync(i,{withFileTypes:!0})){if(r.name===".git"||r.name==="node_modules"||r.name===Qt)continue;let o=M.join(i,r.name);if(r.isDirectory())n(o);else if(r.isFile()){let s=M.relative(e,o).replace(/\\/g,"/");t(o,s)}}};n(e)}hashText(e){return Bn.createHash("sha256").update(e,"utf-8").digest("hex")}compareMicroiVersions(e,t){let n=o=>{if(!(!o||!/^\d+(?:\.\d+){2}$/.test(o)))return o.split(".").map(s=>Number(s))},i=n(e),r=n(t);if(!i||!r)return 0;for(let o=0;o<3;o++)if(i[o]!==r[o])return i[o]>r[o]?1:-1;return 0}pickNewerMicroiVersion(e,t){return e?t?this.compareMicroiVersions(e,t)>=0?e:t:e:t}syncGeneratedAiDocs(e,t){let n=t.map(d=>d.relativePath.replace(/\\/g,"/")),i=n.map(d=>this.normalizeRelativePath(d)),r=this.getGitTrackedWorkspaceFiles(e,n);if(r===void 0)return;let o=M.join(e,".vscode",Et),s=this.readAiDocsManifest(o),c=this.readBundledSkillsMeta().skills?.version,l=this.pickNewerMicroiVersion(c,s.bundleVersion),m={version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",bundleVersion:l,fileVersions:{...s.fileVersions||{}},fileHashes:{...s.fileHashes||{}},files:{...s.files}},g=new Set(i);for(let d of Object.keys(m.files))g.has(this.normalizeRelativePath(d))||(delete m.files[d],delete m.fileHashes[d],delete m.fileVersions[d]);for(let d of Object.keys(m.fileHashes))g.has(this.normalizeRelativePath(d))||(delete m.fileHashes[d],delete m.fileVersions[d],delete m.files[d]);for(let d of t){let u=this.normalizeRelativePath(d.relativePath);if(r.has(u)){delete m.files[u],delete m.fileHashes[u],delete m.fileVersions[u];continue}let p=M.join(e,u),h=this.hashText(d.content),f=s.files[u],y=s.fileHashes?.[u]||(/^[a-f0-9]{64}$/i.test(f||"")?f:void 0),S=s.fileVersions?.[u]||s.bundleVersion,C=this.compareMicroiVersions(c,S)<0,w=!D.existsSync(p)&&!C,R="";if(D.existsSync(p))try{let b=D.readFileSync(p,"utf-8");R=this.hashText(b),w=!!y&&R===y&&!C,!y&&b.includes("Generated by Microi\u543E\u7801 VSCode Extension")&&(m.fileHashes[u]=R,S&&(m.fileVersions[u]=S))}catch{w=!1}if(w){let b=M.dirname(p);D.existsSync(b)||D.mkdirSync(b,{recursive:!0}),D.writeFileSync(p,d.content,"utf-8"),R=h,m.fileHashes[u]=h,c&&(m.fileVersions[u]=c)}else if(R===h){m.fileHashes[u]=h;let b=this.pickNewerMicroiVersion(c,S);b&&(m.fileVersions[u]=b)}else y?(m.fileHashes[u]=y,S&&(m.fileVersions[u]=S)):m.fileHashes[u]||delete m.fileVersions[u];let E=m.fileHashes[u];if(E){let b=m.fileVersions[u]||l||"unknown";m.files[u]=`${Ii}${b}:${E}`}else delete m.files[u]}if(JSON.stringify(m)!==JSON.stringify(s)||!D.existsSync(o)){let d=M.dirname(o);D.existsSync(d)||D.mkdirSync(d,{recursive:!0}),D.writeFileSync(o,JSON.stringify(m,null,2)+`
1743
+ `,"utf-8")}ve(e,[`.vscode/${Et}`])}readAiDocsManifest(e){if(!D.existsSync(e))return{version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",files:{},fileHashes:{},fileVersions:{}};try{let t=JSON.parse(D.readFileSync(e,"utf-8"));return{version:typeof t.version=="number"?t.version:1,generatedBy:t.generatedBy||"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",bundleVersion:typeof t.bundleVersion=="string"?t.bundleVersion:void 0,fileVersions:t.fileVersions&&typeof t.fileVersions=="object"?t.fileVersions:{},fileHashes:t.fileHashes&&typeof t.fileHashes=="object"?t.fileHashes:{},files:t.files&&typeof t.files=="object"?t.files:{}}}catch{return{version:2,generatedBy:"Microi\u543E\u7801 AI\u5F00\u53D1\u5DE5\u5177",files:{},fileHashes:{},fileVersions:{}}}}normalizeRelativePath(e){let t=e.replace(/\\/g,"/").replace(/^\.\//,"");return process.platform==="win32"?t.toLowerCase():t}getGitTrackedWorkspaceFiles(e,t){let n=(0,Yt.spawnSync)("git",["-C",e,"rev-parse","--show-toplevel"],{encoding:"utf-8",windowsHide:!0,timeout:3e3});if(n.error)return this.hasGitMetadata(e)?void 0:new Set;if(n.status!==0)return new Set;let i=String(n.stdout||"").trim();if(!i)return;let r=new Map,o=[];for(let l of t){let m=M.relative(i,M.join(e,l));m.startsWith("..")||M.isAbsolute(m)||(o.push(m.replace(/\\/g,"/")),r.set(this.normalizeRelativePath(m),this.normalizeRelativePath(l)))}if(o.length===0)return new Set;let s=(0,Yt.spawnSync)("git",["-C",i,"ls-files","-z","--",...o],{encoding:"utf-8",windowsHide:!0,timeout:3e3,maxBuffer:1024*1024});if(s.error||s.status!==0)return;let c=new Set;for(let l of String(s.stdout||"").split("\0").filter(Boolean)){let m=r.get(this.normalizeRelativePath(l));m&&c.add(m)}return c}hasGitMetadata(e){let t=M.resolve(e);for(;;){if(D.existsSync(M.join(t,".git")))return!0;let n=M.dirname(t);if(n===t)return!1;t=n}}canRemoveGeneratedAiDoc(e,t){if(!D.existsSync(t))return!1;let n=M.relative(e,t).replace(/\\/g,"/"),i=this.normalizeRelativePath(n),r=this.getGitTrackedWorkspaceFiles(e,[n]);if(r===void 0||r.has(i))return!1;let o=this.readAiDocsManifest(M.join(e,".vscode",Et)),s=o.files[i],c=o.fileHashes?.[i]||(/^[a-f0-9]{64}$/i.test(s||"")?s:void 0);if(!c)return!1;try{return this.hashText(D.readFileSync(t,"utf-8"))===c}catch{return!1}}collectSkillEntries(e){let t=M.join(e,"microi.skills");if(!D.existsSync(t))return[];let n=new Map,i=M.join(t,"README.md");if(D.existsSync(i))try{let s=D.readFileSync(i,"utf-8").matchAll(/`([^`]+\/SKILL\.md)`/g),c=0;for(let l of s){let m=l[1].split(/[\\/]/)[0];m&&!n.has(m)&&n.set(m,c++)}}catch{}let r=[];try{for(let o of D.readdirSync(t,{withFileTypes:!0})){if(!o.isDirectory())continue;let s=M.join(t,o.name,"SKILL.md");D.existsSync(s)&&r.push({name:o.name,relativePath:`microi.skills/${o.name}/SKILL.md`,description:this.readSkillDescription(s,o.name)})}}catch{}return r.sort((o,s)=>{let c=n.get(o.name),l=n.get(s.name);return c!==void 0&&l!==void 0?c-l:c!==void 0?-1:l!==void 0?1:o.name.localeCompare(s.name)})}readSkillDescription(e,t){try{let i=D.readFileSync(e,"utf-8").split(/\r?\n/).find(r=>r.startsWith("# "));if(i)return i.replace(/^#\s+/,"").trim()}catch{}return t}buildSkillsReference(e){if(!e.length)return"";let t=e.map(n=>`- \`${n.relativePath}\` \u2014 ${n.description}`).join(`
1744
1744
  `);return`
1745
1745
 
1746
1746
  ---
@@ -1759,23 +1759,23 @@ ${nt}
1759
1759
 
1760
1760
  \u5904\u7406 Microi \u4F4E\u4EE3\u7801\u7CFB\u7EDF\u3001V8 \u5F15\u64CE\u3001PC \u524D\u7AEF\u3001UniApp/H5/\u5C0F\u7A0B\u5E8F\u3001Microi.UI\u3001MCP \u5EFA\u6A21\u3001\u81EA\u52A8\u5316\u6D4B\u8BD5\u6216\u4EA4\u4ED8\u590D\u76D8\u65F6\uFF0C\u4F18\u5148\u53C2\u8003\u4E0B\u5217 skill \u6587\u4EF6\u83B7\u53D6\u6A21\u677F\u3001\u7EA6\u675F\u548C\u9A8C\u6536\u89C4\u8303\u3002\u666E\u901A\u7528\u6237\u5728\u7A7A\u5DE5\u4F5C\u533A\u5B89\u88C5\u63D2\u4EF6\u540E\uFF0C\u53EA\u8981\u901A\u8FC7\u63D2\u4EF6\u6267\u884C\u521D\u59CB\u5316\u6216\u62C9\u53D6\uFF0CAI \u5C31\u5E94\u81EA\u52A8\u8BC6\u522B\u8FD9\u4E9B\u89C4\u5219\uFF0C\u4E0D\u9700\u8981\u518D\u624B\u52A8\u8981\u6C42\u201C\u4E25\u683C\u9075\u5FAA skills\u201D\uFF1A
1761
1761
  ${t}${Ln}${$n}${xn}
1762
- `}generatePerOsClientSchemaDocs(e){let t=[];if(!D.existsSync(e))return t;let n=i=>{try{for(let r of D.readdirSync(i)){if(r.startsWith(".")&&r!==Le)continue;let o=M.join(i,r);if(r===Le)try{let s=JSON.parse(D.readFileSync(o,"utf-8")),c=this.formatDbSchemaFull(s,M.relative(e,i));if(c){let d=M.join(i,De);D.writeFileSync(d,c,"utf-8"),t.push(d)}}catch{}else try{D.statSync(o).isDirectory()&&n(o)}catch{}}}catch{}};return n(e),t}formatDbSchemaFull(e,t){if(!e.Tables||e.Tables.length===0)return"";let n=e.Tables.filter(r=>r.Name);if(n.length===0)return"";let i=[];i.push(`# \u6570\u636E\u5E93\u7ED3\u6784 \u2014 ${t}
1762
+ `}generatePerOsClientSchemaDocs(e){let t=[];if(!D.existsSync(e))return t;let n=i=>{try{for(let r of D.readdirSync(i)){if(r.startsWith(".")&&r!==Le)continue;let o=M.join(i,r);if(r===Le)try{let s=JSON.parse(D.readFileSync(o,"utf-8")),c=this.formatDbSchemaFull(s,M.relative(e,i));if(c){let l=M.join(i,De);D.writeFileSync(l,c,"utf-8"),t.push(l)}}catch{}else try{D.statSync(o).isDirectory()&&n(o)}catch{}}}catch{}};return n(e),t}formatDbSchemaFull(e,t){if(!e.Tables||e.Tables.length===0)return"";let n=e.Tables.filter(r=>r.Name);if(n.length===0)return"";let i=[];i.push(`# \u6570\u636E\u5E93\u7ED3\u6784 \u2014 ${t}
1763
1763
  `),i.push("> \u6B64\u6587\u4EF6\u7531 Microi\u543E\u7801 VS Code \u63D2\u4EF6\u81EA\u52A8\u751F\u6210\uFF0C\u5305\u542B\u8BE5\u5E94\u7528\u7684\u6240\u6709\u6570\u636E\u5E93\u8868\u548C\u5B57\u6BB5\u4FE1\u606F\u3002"),i.push(`> \u5171 ${n.length} \u5F20\u8868\u3002
1764
1764
  `);for(let r of n){let o=r.Description?` \u2014 ${r.Description}`:"";i.push(`## ${r.Name}${o}
1765
- `);let s=r._Fields||r.Fields;if(s&&s.length>0){i.push("| \u5B57\u6BB5 | \u8BF4\u660E | \u7C7B\u578B |"),i.push("|------|------|------|");for(let c of s){let d=c.Description||c.Label||"",m=c.Type||c.FieldType||"";i.push(`| ${c.Name} | ${d} | ${m} |`)}i.push("")}}return i.join(`
1766
- `)}ensureJsConfig(e,t){let n=M.join(e,"jsconfig.json"),i=e,r=e,o;if(D.existsSync(n))try{o=JSON.parse(D.readFileSync(n,"utf-8"))}catch{o={}}else o={};let s=o.compilerOptions||{};s.target=s.target||"ES2020",s.module=s.module||"CommonJS",s.checkJs=!0;let c=M.relative(e,t),d=s.typeRoots||[];d.includes(`./${c}`)||d.push(`./${c}`),s.typeRoots=d,o.compilerOptions=s;let m=o.include||[],g=M.relative(e,i),l=M.relative(e,r),u=`${c}/**/*`;for(let h of[`${g}/**/*`,`${l}/**/*`,u])m.includes(h)||m.push(h);o.include=m;let p=o.exclude||[];p.includes("node_modules")||p.push("node_modules"),o.exclude=p,D.writeFileSync(n,JSON.stringify(o,null,2),"utf-8")}cleanup(){let e=I.getInstance(),t=e.getWorkspaceRoot();if(!t)return;let n=e.getSyncRootDir(),i=M.join(n,Qe),r=M.join(i,pt);D.existsSync(r)&&D.unlinkSync(r);let o=M.join(t,Qe),s=M.join(o,pt);if(D.existsSync(s)&&D.unlinkSync(s),M.resolve(n)!==M.resolve(t)){let c=M.join(t,Ot,$t),d=M.join(t,Lt),m=M.join(t,xt),g=M.join(t,Bt),l=M.join(t,Ut,jt);if(this.canRemoveGeneratedAiDoc(t,c))try{D.unlinkSync(c)}catch{}if(this.canRemoveGeneratedAiDoc(t,d))try{D.unlinkSync(d)}catch{}if(this.canRemoveGeneratedAiDoc(t,m))try{D.unlinkSync(m)}catch{}if(this.canRemoveGeneratedAiDoc(t,g))try{D.unlinkSync(g)}catch{}if(this.canRemoveGeneratedAiDoc(t,l))try{D.unlinkSync(l)}catch{}}this.cleanupSchemaDocs(n)}cleanupSchemaDocs(e){try{for(let t of D.readdirSync(e)){if(t.startsWith(".")&&t!==De)continue;let n=M.join(e,t);if(t===De)try{D.unlinkSync(n)}catch{}else try{D.statSync(n).isDirectory()&&this.cleanupSchemaDocs(n)}catch{}}}catch{}}};function rt(a,e){let t=r=>{if(!(!r||!/^\d+(?:\.\d+){2}$/.test(r)))return r.split(".").map(o=>Number(o))},n=t(a),i=t(e);if(!n||!i)return 0;for(let r=0;r<3;r+=1)if(n[r]!==i[r])return n[r]>i[r]?1:-1;return 0}function it(a){let e=a.env,t=String(e?.MICROI_TOOL_VERSION||"").trim();return/^\d+(?:\.\d+){2}$/.test(t)?t:""}function bt(a){let e=a.env||{},t=a.headers||{},i=(o=>o.trim().replace(/\/+$/,"").toLowerCase())(String(e.MICROI_API_URL||a.url||"")),r=String(e.MICROI_OS_CLIENT||t["X-Microi-OsClient"]||"").trim().toLowerCase();return`${i}|${r}`}function Un(a,e,t){let n={...a},i={},r=new Set,o=[];for(let[c,d]of Object.entries(e)){let m=bt(d),g=it(d),l=Object.entries(n).filter(([p,h])=>{if(!t.isManaged(p,h))return!1;let f=bt(h);return p===c||m!=="|"&&f===m}),u=l.find(([,p])=>rt(it(p),g)>0);if(u){let p=it(u[1]);for(let[h]of l)r.add(h);o.push({name:u[0],version:p});continue}i[c]=d}let s=new Set(Object.values(i).map(bt).filter(c=>c!=="|"));for(let[c,d]of Object.entries(n)){if(!t.isManaged(c,d)||r.has(c))continue;if(Object.prototype.hasOwnProperty.call(i,c)){delete n[c];continue}let m=bt(d);if(s.has(m)){delete n[c];continue}(t.removeManagedNotInNext||t.isStableName&&!t.isStableName(c))&&delete n[c]}return Object.assign(n,i),{servers:n,skippedNewerProviders:o}}var Kn=G(require("crypto")),J=G(require("fs")),Dt=G(require("os")),ne=G(require("path"));var st="";function It(){if(st)return st;try{let a=JSON.parse(J.readFileSync(ne.join(__dirname,"..","package.json"),"utf8"));st=/^\d+(?:\.\d+){2}$/.test(String(a.version||""))?String(a.version):"0.0.0"}catch{st="0.0.0"}return st}function Hn(a){return a.trim().replace(/\/+$/,"")}function Xt(a){return a.normalize("NFKD").replace(/[^\x00-\x7F]/g,"").replace(/[^A-Za-z0-9_]+/g,"_").replace(/_+/g,"_").replace(/^_+|_+$/g,"").toLowerCase().slice(0,48)}function Wn(a){let e="";try{e=Xt(new URL(Hn(a.apiBaseUrl)).host)}catch{e=Xt(a.apiBaseUrl)}return e}function Zt(a){return Xt(a.osClient||a.sysShortTitle||a.sysTitle||a.label||"")||Wn(a)||"default"}function xi(a,e,t){let n=Wn(a),i=Zt(a),r=`microi_${i}`,o=t.has(i)&&n&&n!==i?`${r}_${n}`:r;e.has(o)&&n&&(o=`${r}_${n}`);let s=2;for(;e.has(o);)o=`${r}_${s++}`;return e.add(o),o}function Bi(){let a=`MCP:${Dt.hostname()||"Unknown"}`;return/^[\x20-\x7E]{1,128}$/.test(a)?a:`MCP-${Kn.createHash("sha256").update(a).digest("hex").slice(0,16)}`}function Ui(a,e){let t=e.env;return/^microi(?:_|-|$)/i.test(a)||typeof t?.MICROI_API_URL=="string"}function Gn(a,e){let t=`${a}.${process.pid}.${Date.now()}.tmp`;try{J.writeFileSync(t,e,"utf8"),J.renameSync(t,a)}finally{try{J.existsSync(t)&&J.unlinkSync(t)}catch{}}}function kt(a,e,t,n=!1){J.mkdirSync(ne.dirname(a),{recursive:!0});let i={};if(J.existsSync(a))try{i=ft(J.readFileSync(a,"utf8"))}catch(d){throw new Error(`MCP \u914D\u7F6E\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u4E14\u505C\u6B62\u5199\u5165\uFF1A${a}\uFF08${d instanceof Error?d.message:String(d)}\uFF09`)}let r=i[e]&&typeof i[e]=="object"?i[e]:{},o=Object.fromEntries(Object.entries(t).map(([d,m])=>[d,n?Object.fromEntries(Object.entries(m).filter(([g])=>["command","args","env","url","headers"].includes(g))):m])),s=Un(r,o,{isManaged:Ui,isStableName:d=>/^microi_[a-z0-9_]+$/.test(d),removeManagedNotInNext:!0});i[e]=s.servers;let c=`${JSON.stringify(i,null,2)}
1767
- `;(!J.existsSync(a)||J.readFileSync(a,"utf8")!==c)&&Gn(a,c)}function ot(a){return JSON.stringify(String(a))}function ji(a){return`[${a.map(ot).join(", ")}]`}function Ki(a){return`{ ${Object.entries(a).filter(([,e])=>e!==""&&e!=null).map(([e,t])=>`${ot(e)} = ${ot(t)}`).join(", ")} }`}function Hi(a,e){let t=[],n=[];for(let o of a.split(/\r?\n/))/^\s*\[[^\]]+\]\s*$/.test(o)&&n.length&&(t.push(n),n=[]),n.push(o);n.length&&t.push(n);let i=new Set;return{cleaned:t.filter(o=>{let c=o.find(u=>u.trim())?.match(/^\s*\[mcp_servers\.(?:"([^"]+)"|([A-Za-z0-9_-]+))(?:\.|\])/)||null;if(!c)return!0;let d=(c[1]||c[2]||"").toLowerCase(),m=o.join(`
1768
- `);if(!(/^microi(?:_|-|$)/.test(d)||/\bMICROI_(?:API_URL|TOKEN_FILE|OS_CLIENT)\b/.test(m)))return!0;let l=m.match(/["']?MICROI_TOOL_VERSION["']?\s*=\s*["']([^"']+)["']/)?.[1]||"";return rt(l,e)>0?(i.add(d),!0):!1}).map(o=>o.join(`
1765
+ `);let s=r._Fields||r.Fields;if(s&&s.length>0){i.push("| \u5B57\u6BB5 | \u8BF4\u660E | \u7C7B\u578B |"),i.push("|------|------|------|");for(let c of s){let l=c.Description||c.Label||"",m=c.Type||c.FieldType||"";i.push(`| ${c.Name} | ${l} | ${m} |`)}i.push("")}}return i.join(`
1766
+ `)}ensureJsConfig(e,t){let n=M.join(e,"jsconfig.json"),i=e,r=e,o;if(D.existsSync(n))try{o=JSON.parse(D.readFileSync(n,"utf-8"))}catch{o={}}else o={};let s=o.compilerOptions||{};s.target=s.target||"ES2020",s.module=s.module||"CommonJS",s.checkJs=!0;let c=M.relative(e,t),l=s.typeRoots||[];l.includes(`./${c}`)||l.push(`./${c}`),s.typeRoots=l,o.compilerOptions=s;let m=o.include||[],g=M.relative(e,i),d=M.relative(e,r),u=`${c}/**/*`;for(let h of[`${g}/**/*`,`${d}/**/*`,u])m.includes(h)||m.push(h);o.include=m;let p=o.exclude||[];p.includes("node_modules")||p.push("node_modules"),o.exclude=p,D.writeFileSync(n,JSON.stringify(o,null,2),"utf-8")}cleanup(){let e=I.getInstance(),t=e.getWorkspaceRoot();if(!t)return;let n=e.getSyncRootDir(),i=M.join(n,Qe),r=M.join(i,pt);D.existsSync(r)&&D.unlinkSync(r);let o=M.join(t,Qe),s=M.join(o,pt);if(D.existsSync(s)&&D.unlinkSync(s),M.resolve(n)!==M.resolve(t)){let c=M.join(t,Ot,$t),l=M.join(t,Lt),m=M.join(t,xt),g=M.join(t,Bt),d=M.join(t,Ut,jt);if(this.canRemoveGeneratedAiDoc(t,c))try{D.unlinkSync(c)}catch{}if(this.canRemoveGeneratedAiDoc(t,l))try{D.unlinkSync(l)}catch{}if(this.canRemoveGeneratedAiDoc(t,m))try{D.unlinkSync(m)}catch{}if(this.canRemoveGeneratedAiDoc(t,g))try{D.unlinkSync(g)}catch{}if(this.canRemoveGeneratedAiDoc(t,d))try{D.unlinkSync(d)}catch{}}this.cleanupSchemaDocs(n)}cleanupSchemaDocs(e){try{for(let t of D.readdirSync(e)){if(t.startsWith(".")&&t!==De)continue;let n=M.join(e,t);if(t===De)try{D.unlinkSync(n)}catch{}else try{D.statSync(n).isDirectory()&&this.cleanupSchemaDocs(n)}catch{}}}catch{}}};function rt(a,e){let t=r=>{if(!(!r||!/^\d+(?:\.\d+){2}$/.test(r)))return r.split(".").map(o=>Number(o))},n=t(a),i=t(e);if(!n||!i)return 0;for(let r=0;r<3;r+=1)if(n[r]!==i[r])return n[r]>i[r]?1:-1;return 0}function it(a){let e=a.env,t=String(e?.MICROI_TOOL_VERSION||"").trim();return/^\d+(?:\.\d+){2}$/.test(t)?t:""}function bt(a){let e=a.env||{},t=a.headers||{},i=(o=>o.trim().replace(/\/+$/,"").toLowerCase())(String(e.MICROI_API_URL||a.url||"")),r=String(e.MICROI_OS_CLIENT||t["X-Microi-OsClient"]||"").trim().toLowerCase();return`${i}|${r}`}function Un(a,e,t){let n={...a},i={},r=new Set,o=[];for(let[c,l]of Object.entries(e)){let m=bt(l),g=it(l),d=Object.entries(n).filter(([p,h])=>{if(!t.isManaged(p,h))return!1;let f=bt(h);return p===c||m!=="|"&&f===m}),u=d.find(([,p])=>rt(it(p),g)>0);if(u){let p=it(u[1]);for(let[h]of d)r.add(h);o.push({name:u[0],version:p});continue}i[c]=l}let s=new Set(Object.values(i).map(bt).filter(c=>c!=="|"));for(let[c,l]of Object.entries(n)){if(!t.isManaged(c,l)||r.has(c))continue;if(Object.prototype.hasOwnProperty.call(i,c)){delete n[c];continue}let m=bt(l);if(s.has(m)){delete n[c];continue}(t.removeManagedNotInNext||t.isStableName&&!t.isStableName(c))&&delete n[c]}return Object.assign(n,i),{servers:n,skippedNewerProviders:o}}var Kn=G(require("crypto")),J=G(require("fs")),Dt=G(require("os")),ne=G(require("path"));var st="";function It(){if(st)return st;try{let a=JSON.parse(J.readFileSync(ne.join(__dirname,"..","package.json"),"utf8"));st=/^\d+(?:\.\d+){2}$/.test(String(a.version||""))?String(a.version):"0.0.0"}catch{st="0.0.0"}return st}function Hn(a){return a.trim().replace(/\/+$/,"")}function Xt(a){return a.normalize("NFKD").replace(/[^\x00-\x7F]/g,"").replace(/[^A-Za-z0-9_]+/g,"_").replace(/_+/g,"_").replace(/^_+|_+$/g,"").toLowerCase().slice(0,48)}function Wn(a){let e="";try{e=Xt(new URL(Hn(a.apiBaseUrl)).host)}catch{e=Xt(a.apiBaseUrl)}return e}function Zt(a){return Xt(a.osClient||a.sysShortTitle||a.sysTitle||a.label||"")||Wn(a)||"default"}function xi(a,e,t){let n=Wn(a),i=Zt(a),r=`microi_${i}`,o=t.has(i)&&n&&n!==i?`${r}_${n}`:r;e.has(o)&&n&&(o=`${r}_${n}`);let s=2;for(;e.has(o);)o=`${r}_${s++}`;return e.add(o),o}function Bi(){let a=`MCP:${Dt.hostname()||"Unknown"}`;return/^[\x20-\x7E]{1,128}$/.test(a)?a:`MCP-${Kn.createHash("sha256").update(a).digest("hex").slice(0,16)}`}function Ui(a,e){let t=e.env;return/^microi(?:_|-|$)/i.test(a)||typeof t?.MICROI_API_URL=="string"}function Gn(a,e){let t=`${a}.${process.pid}.${Date.now()}.tmp`;try{J.writeFileSync(t,e,"utf8"),J.renameSync(t,a)}finally{try{J.existsSync(t)&&J.unlinkSync(t)}catch{}}}function kt(a,e,t,n=!1){J.mkdirSync(ne.dirname(a),{recursive:!0});let i={};if(J.existsSync(a))try{i=ft(J.readFileSync(a,"utf8"))}catch(l){throw new Error(`MCP \u914D\u7F6E\u65E0\u6CD5\u89E3\u6790\uFF0C\u5DF2\u4FDD\u7559\u539F\u6587\u4EF6\u4E14\u505C\u6B62\u5199\u5165\uFF1A${a}\uFF08${l instanceof Error?l.message:String(l)}\uFF09`)}let r=i[e]&&typeof i[e]=="object"?i[e]:{},o=Object.fromEntries(Object.entries(t).map(([l,m])=>[l,n?Object.fromEntries(Object.entries(m).filter(([g])=>["command","args","env","url","headers"].includes(g))):m])),s=Un(r,o,{isManaged:Ui,isStableName:l=>/^microi_[a-z0-9_]+$/.test(l),removeManagedNotInNext:!0});i[e]=s.servers;let c=`${JSON.stringify(i,null,2)}
1767
+ `;(!J.existsSync(a)||J.readFileSync(a,"utf8")!==c)&&Gn(a,c)}function ot(a){return JSON.stringify(String(a))}function ji(a){return`[${a.map(ot).join(", ")}]`}function Ki(a){return`{ ${Object.entries(a).filter(([,e])=>e!==""&&e!=null).map(([e,t])=>`${ot(e)} = ${ot(t)}`).join(", ")} }`}function Hi(a,e){let t=[],n=[];for(let o of a.split(/\r?\n/))/^\s*\[[^\]]+\]\s*$/.test(o)&&n.length&&(t.push(n),n=[]),n.push(o);n.length&&t.push(n);let i=new Set;return{cleaned:t.filter(o=>{let c=o.find(u=>u.trim())?.match(/^\s*\[mcp_servers\.(?:"([^"]+)"|([A-Za-z0-9_-]+))(?:\.|\])/)||null;if(!c)return!0;let l=(c[1]||c[2]||"").toLowerCase(),m=o.join(`
1768
+ `);if(!(/^microi(?:_|-|$)/.test(l)||/\bMICROI_(?:API_URL|TOKEN_FILE|OS_CLIENT)\b/.test(m)))return!0;let d=m.match(/["']?MICROI_TOOL_VERSION["']?\s*=\s*["']([^"']+)["']/)?.[1]||"";return rt(d,e)>0?(i.add(l),!0):!1}).map(o=>o.join(`
1769
1769
  `)).join(`
1770
1770
  `).replace(/\n{3,}/g,`
1771
1771
 
1772
- `).trimEnd(),preservedNames:i}}function jn(a,e,t){J.mkdirSync(ne.dirname(a),{recursive:!0});let n=J.existsSync(a)?J.readFileSync(a,"utf8"):"",i=It(),{cleaned:r,preservedNames:o}=Hi(n,i),s=Object.entries(e).filter(([d])=>!o.has(d.toLowerCase())).map(([d,m])=>{let g=[t,...m.args||[]],l={...m.env||{},MICROI_CODEX_MODE:"1"};return delete l.MICROI_TOKEN,[`[mcp_servers.${d}]`,`command = ${ot(m.command)}`,`args = ${ji(g)}`,...m.cwd?[`cwd = ${ot(m.cwd)}`]:[],`env = ${Ki(l)}`,'enabled_tools = ["microi_codex"]','default_tools_approval_mode = "auto"'].join(`
1772
+ `).trimEnd(),preservedNames:i}}function jn(a,e,t){J.mkdirSync(ne.dirname(a),{recursive:!0});let n=J.existsSync(a)?J.readFileSync(a,"utf8"):"",i=It(),{cleaned:r,preservedNames:o}=Hi(n,i),s=Object.entries(e).filter(([l])=>!o.has(l.toLowerCase())).map(([l,m])=>{let g=[t,...m.args||[]],d={...m.env||{},MICROI_CODEX_MODE:"1"};return delete d.MICROI_TOKEN,[`[mcp_servers.${l}]`,`command = ${ot(m.command)}`,`args = ${ji(g)}`,...m.cwd?[`cwd = ${ot(m.cwd)}`]:[],`env = ${Ki(d)}`,'enabled_tools = ["microi_codex"]','default_tools_approval_mode = "auto"'].join(`
1773
1773
  `)}),c=[r,s.join(`
1774
1774
 
1775
1775
  `)].filter(Boolean).join(`
1776
1776
 
1777
1777
  `)+`
1778
- `;(!J.existsSync(a)||n!==c)&&Gn(a,c)}function Wi(a,e){let t=e.label||e.sysShortTitle||e.sysTitle||e.apiBaseUrl||"\u672A\u547D\u540D\u670D\u52A1\u5668";return ne.join(a.getSyncRootDir(),a.buildServerDirName(t,e.apiBaseUrl),a.buildOsClientDirName(e.osClient,e.osClientType,e.osClientNetwork),mn)}function Gi(a,e,t){let n={...a.env||{}},i=String(a.command||""),r=Array.isArray(a.args)?a.args.map(String):[];return process.platform==="win32"&&i&&r.length>0?{command:"cmd.exe",args:["/d","/s","/c","call",t,i,e,r[0]],env:n}:{command:i,args:r,env:n}}async function at(a){let e=I.getInstance(),t=ge.getInstance(),n=L.getInstance(),i=e.getProfiles(),r=It(),o=ne.join(__dirname,"mcp-server.js"),s=ne.join(__dirname,"microi-cli-mcp.js"),c=ne.join(__dirname,"mcp-codex-stdio-adapter.js"),d=ne.join(__dirname,"mcp-trae-windows-launcher.cmd");if(!J.existsSync(o)||!J.existsSync(s)||!J.existsSync(c)||process.platform==="win32"&&!J.existsSync(d))throw new Error("CLI \u5B89\u88C5\u5305\u7F3A\u5C11\u5185\u7F6E MCP Server\uFF0C\u8BF7\u91CD\u65B0\u5B89\u88C5 @microi.net/cli");let m={},g=new Set,l=new Map;for(let f of i)l.set(Zt(f),(l.get(Zt(f))||0)+1);let u=new Set(Array.from(l).filter(([,f])=>f>1).map(([f])=>f));for(let f of i){let y=t.mcpTokenFilePath,S=n.getTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);if(!y||!J.existsSync(y)||!S)continue;let C=xi(f,g,u);m[C]={type:"stdio",command:process.execPath,args:[s],cwd:ne.dirname(__dirname),env:{MICROI_API_URL:Hn(f.apiBaseUrl),MICROI_TOKEN_FILE:y,MICROI_AUTH_RECOVERY_DIR:t.mcpAuthRecoveryDirPath,MICROI_OS_CLIENT:f.osClient||"",MICROI_OS_CLIENT_TYPE:f.osClientType||"",MICROI_OS_CLIENT_NETWORK:f.osClientNetwork||"",MICROI_WORKSPACE_ROOT:a,MICROI_SYNC_ROOT:e.getSyncRootDir(),MICROI_AI_APPLICATIONS_DIR:Wi(e,f),MICROI_LABEL_BASE64:Buffer.from(f.label||"","utf8").toString("base64"),MICROI_MCP_DID:Bi(),MICROI_TOOL_SOURCE:"cli",MICROI_TOOL_VERSION:r}}}await t.writeMcpTokenFile(),Be(a),ve(a,[".vscode/mcp.json",".cursor/mcp.json",".trae/mcp.json",".mcp.json",".codex/config.toml","Microi-V8-Engine/.microi-mcp-tokens.json"]),kt(ne.join(a,".vscode","mcp.json"),"servers",m),kt(ne.join(a,".cursor","mcp.json"),"mcpServers",m);let p=Object.fromEntries(Object.entries(m).map(([f,y])=>[f,Gi(y,c,d)]));kt(ne.join(a,".trae","mcp.json"),"mcpServers",p,!0),kt(ne.join(a,".mcp.json"),"mcpServers",m,!0);let h=process.env.CODEX_HOME||ne.join(Dt.homedir(),".codex");return jn(ne.join(h,"config.toml"),m,c),jn(ne.join(a,".codex","config.toml"),m,c),{count:Object.keys(m).length,names:Object.keys(m)}}var Rt=G(require("fs")),zn=G(require("path"));var en=class{constructor(){this.values=new Map;this.onDidChange=()=>({dispose:()=>{}})}async get(e){return this.values.get(e)}async store(e,t){this.values.set(e,t)}async delete(e){this.values.delete(e)}};async function Jn(a){let e=zn.resolve(a);if(!Rt.existsSync(e)||!Rt.statSync(e).isDirectory())throw new Error(`\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728\u6216\u4E0D\u662F\u76EE\u5F55\uFF1A${e}`);cn(e);let t=I.getInstance(),n=L.getInstance(),i=ge.getInstance(),r=new en;n.setSecretStorage(r),i.setSecretStorage(r);let o=t.getWorkspaceStateFilePath(ze);return i.setMcpTokenFilePath(o),await i.loadMcpTokenFile(),{root:e,config:t,api:n,auth:i}}function ct(a,e){let t=a.getProfiles();if(!t.length)throw new Error("\u5C1A\u672A\u6DFB\u52A0\u670D\u52A1\u5668\u8FDE\u63A5\uFF0C\u8BF7\u5148\u6267\u884C microi profile add");if(!e)return t[0];let n=Number(e);if(Number.isInteger(n)&&n>=1&&n<=t.length)return t[n-1];let i=e.toLowerCase(),r=t.filter(o=>o.osClient.toLowerCase()===i||o.label.toLowerCase()===i||`${o.apiBaseUrl}|${o.osClient}`.toLowerCase()===i);if(r.length!==1)throw new Error(`\u65E0\u6CD5\u552F\u4E00\u5B9A\u4F4D\u670D\u52A1\u5668\u8FDE\u63A5\uFF1A${e}`);return r[0]}function Re(a,e){return!!a.api.getTokenForServer(e.apiBaseUrl,e.osClient,e.osClientType,e.osClientNetwork)}function zi(a){let e=[],t={};for(let n=0;n<a.length;n+=1){let i=a[n];if(!i.startsWith("--")){e.push(i);continue}let[r,o]=i.slice(2).split(/=(.*)/s,2);if(r.startsWith("no-")&&o===void 0){t[r.slice(3)]=!1;continue}if(o!==void 0){t[r]=o;continue}let s=a[n+1];s&&!s.startsWith("--")?(t[r]=s,n+=1):t[r]=!0}return{words:e,options:t}}function ae(a,e){let t=a[e];return typeof t=="string"?t:void 0}function ue(a,e=!1){console.log(e||typeof a!="string"?JSON.stringify(a,null,2):a)}function He(a,e=""){let t=ei.createInterface({input:process.stdin,output:process.stdout});return new Promise(n=>t.question(`${a}${e?` (${e})`:""}: `,i=>{t.close(),n(i.trim()||e)}))}function Ji(a){return!process.stdin.isTTY||!process.stdin.setRawMode?He(a):new Promise((e,t)=>{let n="";process.stdout.write(`${a}: `),process.stdin.setRawMode(!0),process.stdin.resume();let i=()=>{process.stdin.off("data",r),process.stdin.setRawMode(!1),process.stdin.pause()},r=o=>{let s=o.toString("utf8");if(s===""){i(),t(new Error("\u5DF2\u53D6\u6D88"));return}if(s==="\r"||s===`
1778
+ `;(!J.existsSync(a)||n!==c)&&Gn(a,c)}function Wi(a,e){let t=e.label||e.sysShortTitle||e.sysTitle||e.apiBaseUrl||"\u672A\u547D\u540D\u670D\u52A1\u5668";return ne.join(a.getSyncRootDir(),a.buildServerDirName(t,e.apiBaseUrl),a.buildOsClientDirName(e.osClient,e.osClientType,e.osClientNetwork),mn)}function Gi(a,e,t){let n={...a.env||{}},i=String(a.command||""),r=Array.isArray(a.args)?a.args.map(String):[];return process.platform==="win32"&&i&&r.length>0?{command:"cmd.exe",args:["/d","/s","/c","call",t,i,e,r[0]],env:n}:{command:i,args:r,env:n}}async function at(a){let e=I.getInstance(),t=ge.getInstance(),n=L.getInstance(),i=e.getProfiles(),r=It(),o=ne.join(__dirname,"mcp-server.js"),s=ne.join(__dirname,"microi-cli-mcp.js"),c=ne.join(__dirname,"mcp-codex-stdio-adapter.js"),l=ne.join(__dirname,"mcp-trae-windows-launcher.cmd");if(!J.existsSync(o)||!J.existsSync(s)||!J.existsSync(c)||process.platform==="win32"&&!J.existsSync(l))throw new Error("CLI \u5B89\u88C5\u5305\u7F3A\u5C11\u5185\u7F6E MCP Server\uFF0C\u8BF7\u91CD\u65B0\u5B89\u88C5 @microi.net/cli");let m={},g=new Set,d=new Map;for(let f of i)d.set(Zt(f),(d.get(Zt(f))||0)+1);let u=new Set(Array.from(d).filter(([,f])=>f>1).map(([f])=>f));for(let f of i){let y=t.mcpTokenFilePath,S=n.getTokenForServer(f.apiBaseUrl,f.osClient,f.osClientType,f.osClientNetwork);if(!y||!J.existsSync(y)||!S)continue;let C=xi(f,g,u);m[C]={type:"stdio",command:process.execPath,args:[s],cwd:ne.dirname(__dirname),env:{MICROI_API_URL:Hn(f.apiBaseUrl),MICROI_TOKEN_FILE:y,MICROI_AUTH_RECOVERY_DIR:t.mcpAuthRecoveryDirPath,MICROI_OS_CLIENT:f.osClient||"",MICROI_OS_CLIENT_TYPE:f.osClientType||"",MICROI_OS_CLIENT_NETWORK:f.osClientNetwork||"",MICROI_WORKSPACE_ROOT:a,MICROI_SYNC_ROOT:e.getSyncRootDir(),MICROI_AI_APPLICATIONS_DIR:Wi(e,f),MICROI_LABEL_BASE64:Buffer.from(f.label||"","utf8").toString("base64"),MICROI_MCP_DID:Bi(),MICROI_TOOL_SOURCE:"cli",MICROI_TOOL_VERSION:r}}}await t.writeMcpTokenFile(),Be(a),ve(a,[".vscode/mcp.json",".cursor/mcp.json",".trae/mcp.json",".mcp.json",".codex/config.toml","Microi-V8-Engine/.microi-mcp-tokens.json"]),kt(ne.join(a,".vscode","mcp.json"),"servers",m),kt(ne.join(a,".cursor","mcp.json"),"mcpServers",m);let p=Object.fromEntries(Object.entries(m).map(([f,y])=>[f,Gi(y,c,l)]));kt(ne.join(a,".trae","mcp.json"),"mcpServers",p,!0),kt(ne.join(a,".mcp.json"),"mcpServers",m,!0);let h=process.env.CODEX_HOME||ne.join(Dt.homedir(),".codex");return jn(ne.join(h,"config.toml"),m,c),jn(ne.join(a,".codex","config.toml"),m,c),{count:Object.keys(m).length,names:Object.keys(m)}}var Rt=G(require("fs")),zn=G(require("path"));var en=class{constructor(){this.values=new Map;this.onDidChange=()=>({dispose:()=>{}})}async get(e){return this.values.get(e)}async store(e,t){this.values.set(e,t)}async delete(e){this.values.delete(e)}};async function Jn(a){let e=zn.resolve(a);if(!Rt.existsSync(e)||!Rt.statSync(e).isDirectory())throw new Error(`\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728\u6216\u4E0D\u662F\u76EE\u5F55\uFF1A${e}`);cn(e);let t=I.getInstance(),n=L.getInstance(),i=ge.getInstance(),r=new en;n.setSecretStorage(r),i.setSecretStorage(r);let o=t.getWorkspaceStateFilePath(ze);return i.setMcpTokenFilePath(o),await i.loadMcpTokenFile(),{root:e,config:t,api:n,auth:i}}function ct(a,e){let t=a.getProfiles();if(!t.length)throw new Error("\u5C1A\u672A\u6DFB\u52A0\u670D\u52A1\u5668\u8FDE\u63A5\uFF0C\u8BF7\u5148\u6267\u884C microi profile add");if(!e)return t[0];let n=Number(e);if(Number.isInteger(n)&&n>=1&&n<=t.length)return t[n-1];let i=e.toLowerCase(),r=t.filter(o=>o.osClient.toLowerCase()===i||o.label.toLowerCase()===i||`${o.apiBaseUrl}|${o.osClient}`.toLowerCase()===i);if(r.length!==1)throw new Error(`\u65E0\u6CD5\u552F\u4E00\u5B9A\u4F4D\u670D\u52A1\u5668\u8FDE\u63A5\uFF1A${e}`);return r[0]}function Re(a,e){return!!a.api.getTokenForServer(e.apiBaseUrl,e.osClient,e.osClientType,e.osClientNetwork)}function zi(a){let e=[],t={};for(let n=0;n<a.length;n+=1){let i=a[n];if(!i.startsWith("--")){e.push(i);continue}let[r,o]=i.slice(2).split(/=(.*)/s,2);if(r.startsWith("no-")&&o===void 0){t[r.slice(3)]=!1;continue}if(o!==void 0){t[r]=o;continue}let s=a[n+1];s&&!s.startsWith("--")?(t[r]=s,n+=1):t[r]=!0}return{words:e,options:t}}function ae(a,e){let t=a[e];return typeof t=="string"?t:void 0}function ue(a,e=!1){console.log(e||typeof a!="string"?JSON.stringify(a,null,2):a)}function He(a,e=""){let t=ei.createInterface({input:process.stdin,output:process.stdout});return new Promise(n=>t.question(`${a}${e?` (${e})`:""}: `,i=>{t.close(),n(i.trim()||e)}))}function Ji(a){return!process.stdin.isTTY||!process.stdin.setRawMode?He(a):new Promise((e,t)=>{let n="";process.stdout.write(`${a}: `),process.stdin.setRawMode(!0),process.stdin.resume();let i=()=>{process.stdin.off("data",r),process.stdin.setRawMode(!1),process.stdin.pause()},r=o=>{let s=o.toString("utf8");if(s===""){i(),t(new Error("\u5DF2\u53D6\u6D88"));return}if(s==="\r"||s===`
1779
1779
  `){process.stdout.write(`
1780
1780
  `),i(),e(n);return}if(s==="\x7F"||s==="\b"){n&&(n=n.slice(0,-1),process.stdout.write("\b \b"));return}/^[\x20-\x7E\u0080-\uFFFF]+$/.test(s)&&(n+=s,process.stdout.write("*".repeat([...s].length)))};process.stdin.on("data",r)})}function qn(){return`Microi\u543E\u7801 CLI
1781
1781
 
@@ -1791,6 +1791,6 @@ ${t}${Ln}${$n}${xn}
1791
1791
  sync status [--scope ...] \u6BD4\u8F83\u672C\u5730\u4E0E\u8FDC\u7AEF\u5DEE\u5F02
1792
1792
  doctor \u68C0\u67E5\u8FDE\u63A5\u3001Token\u3001AI \u4E0E MCP \u914D\u7F6E
1793
1793
 
1794
- \u901A\u7528\u9009\u9879\uFF1A--workspace <\u76EE\u5F55>\uFF08\u9ED8\u8BA4\u5F53\u524D\u76EE\u5F55\uFF09\u3001--profile <\u5E8F\u53F7/OsClient/\u540D\u79F0>\u3001--json`}async function Qn(a,e){let t=(ae(e,"api")||await He("API \u5730\u5740")).replace(/\/+$/,""),n=ae(e,"os-client")||await He("OsClient");if(!/^https?:\/\//i.test(t))throw new Error("API \u5730\u5740\u5FC5\u987B\u4EE5 http:// \u6216 https:// \u5F00\u5934");if(!n)throw new Error("OsClient \u4E0D\u80FD\u4E3A\u7A7A");let r={label:ae(e,"label")||await He("\u8FDE\u63A5\u540D\u79F0",n),apiBaseUrl:t,osClient:n,osClientType:ae(e,"type")||"",osClientNetwork:ae(e,"network")||""};return await a.config.addProfile(r),r}function qi(a){return a===!0||a===1||String(a||"").trim().toLowerCase()==="true"}async function Yn(a,e,t){let n=ae(t,"account")||await He("\u5E10\u53F7"),i=await Ji("\u5BC6\u7801"),r=await a.auth.getSysConfig(e.apiBaseUrl,e.osClient),o,s,c="";if(qi(r?.EnableCaptcha)){let d=await a.auth.getCaptcha(e.apiBaseUrl,e.osClient);if(!d)throw new Error("\u670D\u52A1\u5668\u8981\u6C42\u9A8C\u8BC1\u7801\uFF0C\u4F46\u9A8C\u8BC1\u7801\u56FE\u7247\u83B7\u53D6\u5931\u8D25");c=he.join(a.config.getSyncRootDir(),".microi-login-captcha.png"),ie.mkdirSync(he.dirname(c),{recursive:!0}),ie.writeFileSync(c,Buffer.from(d.imageBase64.split(",")[1],"base64")),console.log(`\u9A8C\u8BC1\u7801\u56FE\u7247\uFF1A${c}`),o=d.captchaId,s=ae(t,"captcha")||await He("\u9A8C\u8BC1\u7801")}try{let d=await a.auth.login(n,i,{apiBaseUrl:e.apiBaseUrl,osClient:e.osClient,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork,captchaId:o,captchaValue:s});if(!d.ok)throw new Error(d.msg||"\u767B\u5F55\u5931\u8D25");let m=await a.auth.getSysConfig(e.apiBaseUrl,e.osClient,void 0,!0);m&&await a.config.addProfile({...e,label:String(m.SysShortTitle||m.SysTitle||e.label),sysShortTitle:String(m.SysShortTitle||""),sysTitle:String(m.SysTitle||"")})}finally{c&&ie.existsSync(c)&&ie.rmSync(c,{force:!0})}}async function Xn(a,e){wt.getInstance().inject();let t=e?await at(a.root):{count:0,names:[]};return{workspace:a.root,syncRoot:a.config.getSyncRootDir(),mcp:t}}async function Zn(a,e,t){if(!Re(a,e))throw new Error("\u8BE5\u8FDE\u63A5\u6CA1\u6709\u53EF\u7528 Token\uFF0C\u8BF7\u5148\u6267\u884C microi auth login");let n=Ke.getInstance();(t==="all"||t==="api")&&await n.pullEngines(e),(t==="all"||t==="form")&&(await n.pullEvents(e),await n.pullFields(e)),(t==="all"||t==="module")&&await n.pullMenuButtons(e),(t==="all"||t==="workflow")&&await n.pullWorkflows(e),(t==="all"||t==="schema")&&await n.pullDbSchema(e)}async function Qi(){let{words:a,options:e}=zi(process.argv.slice(2));if(!a.length||a[0]==="help"||e.help){console.log(qn());return}let t=e.json===!0,n=await Jn(ae(e,"workspace")||process.cwd()),[i,r,o]=a;if(i==="profile"){if(r==="list"){let s=n.config.getProfiles().map((c,d)=>({index:d+1,...c,loggedIn:Re(n,c)}));ue(s,t);return}if(r==="add"){ue(await Qn(n,e),t);return}if(r==="remove"){let s=ct(n.config,o||ae(e,"profile")),c=n.config.getProfiles().findIndex(d=>d.apiBaseUrl===s.apiBaseUrl&&d.osClient===s.osClient);await n.config.removeProfile(c),await n.auth.writeMcpTokenFile(),await at(n.root),ue({removed:!0,profile:s},t);return}}if(i==="auth"){let s=ct(n.config,ae(e,"profile"));if(r==="login"){await Yn(n,s,e),ue({loggedIn:!0,profile:s.osClient},t);return}if(r==="status"){ue({loggedIn:Re(n,s),profile:s},t);return}if(r==="logout"){await n.api.clearTokenForServer(s.apiBaseUrl,s.osClient,s.osClientType,s.osClientNetwork),await n.auth.writeMcpTokenFile(),await at(n.root),ue({loggedIn:!1,profile:s.osClient},t);return}}if(i==="ai"&&r==="init"){ue(await Xn(n,e.mcp!==!1),t);return}if(i==="mcp"&&r==="init"){ue(await at(n.root),t);return}if(i==="init"){let s=n.config.getProfiles()[0];s||(s=await Qn(n,e)),Re(n,s)||await Yn(n,s,e);let c=await Xn(n,!0);e.pull===!0&&await Zn(n,s,"all"),ue({initialized:!0,pulled:e.pull===!0,details:c},t);return}if(i==="pull"){let s=ct(n.config,ae(e,"profile")),c=ae(e,"scope")||"all";if(!["all","api","form","module","workflow","schema"].includes(c))throw new Error(`\u4E0D\u652F\u6301\u7684\u62C9\u53D6\u8303\u56F4\uFF1A${c}`);await Zn(n,s,c),ue({pulled:!0,scope:c,profile:s.osClient},t);return}if(i==="push"){let s=he.resolve(r||"");if(!ie.existsSync(s))throw new Error(`\u6587\u4EF6\u4E0D\u5B58\u5728\uFF1A${s}`);if(!await Ke.getInstance().pushFile(s))throw new Error("\u63A8\u9001\u5931\u8D25\uFF0C\u8BF7\u67E5\u770B\u4E0A\u65B9 Microi \u65E5\u5FD7");ue({pushed:!0,file:s},t);return}if(i==="sync"&&r==="status"){let s=ct(n.config,ae(e,"profile")),c=ae(e,"scope")||"all";if(!["all","api","form","module","workflow"].includes(c))throw new Error(`\u4E0D\u652F\u6301\u7684\u5DEE\u5F02\u8303\u56F4\uFF1A${c}`);let d=await Ke.getInstance().checkRemoteDifferences(s,c);ue({profile:s.osClient,scope:c,count:d.length,differences:d},t);return}if(i==="doctor"){let s=n.config.getProfiles(),c=It(),d=he.join(n.root,".vscode","mcp.json"),m=[];if(ie.existsSync(d))try{let p=ft(ie.readFileSync(d,"utf-8")),h=p.servers&&typeof p.servers=="object"?p.servers:{};for(let[f,y]of Object.entries(h)){let S=y.env&&typeof y.env=="object"?y.env:{};if(!/^microi(?:_|-|$)/i.test(f)&&typeof S.MICROI_API_URL!="string")continue;let C=it(y),w=rt(C,c);m.push({name:f,source:String(S.MICROI_TOOL_SOURCE||"legacy"),version:C||"legacy",compatibility:w>0?"newer-provider-preserved":w<0?"upgrade-available":"compatible"})}}catch(p){m.push({name:"(config)",source:"unknown",version:"unknown",compatibility:`invalid-json: ${p instanceof Error?p.message:String(p)}`})}let g=he.join(n.root,".vscode",".microi-ai-docs-manifest.json"),l="";if(ie.existsSync(g))try{let p=JSON.parse(ie.readFileSync(g,"utf-8"));l=String(p.bundleVersion||"")}catch{l="invalid-json"}let u={ok:s.length>0&&s.some(p=>Re(n,p)),tool:{source:"cli",version:c},node:process.version,workspace:n.root,syncRoot:n.config.getSyncRootDir(),profiles:s.map(p=>({label:p.label,osClient:p.osClient,apiBaseUrl:p.apiBaseUrl,loggedIn:Re(n,p)})),files:{agents:ie.existsSync(he.join(n.root,"AGENTS.md")),vscodeMcp:ie.existsSync(d),codexMcp:ie.existsSync(he.join(n.root,".codex","config.toml")),tokenFile:ie.existsSync(n.auth.mcpTokenFilePath)},coexistence:{aiBundleVersion:l||"not-initialized",mcpProviders:m}};ue(u,t),u.ok||(process.exitCode=2);return}throw new Error(`\u672A\u77E5\u547D\u4EE4\uFF1A${a.join(" ")}
1794
+ \u901A\u7528\u9009\u9879\uFF1A--workspace <\u76EE\u5F55>\uFF08\u9ED8\u8BA4\u5F53\u524D\u76EE\u5F55\uFF09\u3001--profile <\u5E8F\u53F7/OsClient/\u540D\u79F0>\u3001--json`}async function Qn(a,e){let t=(ae(e,"api")||await He("API \u5730\u5740")).replace(/\/+$/,""),n=ae(e,"os-client")||await He("OsClient");if(!/^https?:\/\//i.test(t))throw new Error("API \u5730\u5740\u5FC5\u987B\u4EE5 http:// \u6216 https:// \u5F00\u5934");if(!n)throw new Error("OsClient \u4E0D\u80FD\u4E3A\u7A7A");let r={label:ae(e,"label")||await He("\u8FDE\u63A5\u540D\u79F0",n),apiBaseUrl:t,osClient:n,osClientType:ae(e,"type")||"",osClientNetwork:ae(e,"network")||""};return await a.config.addProfile(r),r}function qi(a){return a===!0||a===1||String(a||"").trim().toLowerCase()==="true"}async function Yn(a,e,t){let n=ae(t,"account")||await He("\u5E10\u53F7"),i=await Ji("\u5BC6\u7801"),r=await a.auth.getSysConfig(e.apiBaseUrl,e.osClient),o,s,c="";if(qi(r?.EnableCaptcha)){let l=await a.auth.getCaptcha(e.apiBaseUrl,e.osClient);if(!l)throw new Error("\u670D\u52A1\u5668\u8981\u6C42\u9A8C\u8BC1\u7801\uFF0C\u4F46\u9A8C\u8BC1\u7801\u56FE\u7247\u83B7\u53D6\u5931\u8D25");c=he.join(a.config.getSyncRootDir(),".microi-login-captcha.png"),ie.mkdirSync(he.dirname(c),{recursive:!0}),ie.writeFileSync(c,Buffer.from(l.imageBase64.split(",")[1],"base64")),console.log(`\u9A8C\u8BC1\u7801\u56FE\u7247\uFF1A${c}`),o=l.captchaId,s=ae(t,"captcha")||await He("\u9A8C\u8BC1\u7801")}try{let l=await a.auth.login(n,i,{apiBaseUrl:e.apiBaseUrl,osClient:e.osClient,osClientType:e.osClientType,osClientNetwork:e.osClientNetwork,captchaId:o,captchaValue:s});if(!l.ok)throw new Error(l.msg||"\u767B\u5F55\u5931\u8D25");let m=await a.auth.getSysConfig(e.apiBaseUrl,e.osClient,void 0,!0);m&&await a.config.addProfile({...e,label:String(m.SysShortTitle||m.SysTitle||e.label),sysShortTitle:String(m.SysShortTitle||""),sysTitle:String(m.SysTitle||"")})}finally{c&&ie.existsSync(c)&&ie.rmSync(c,{force:!0})}}async function Xn(a,e){wt.getInstance().inject();let t=e?await at(a.root):{count:0,names:[]};return{workspace:a.root,syncRoot:a.config.getSyncRootDir(),mcp:t}}async function Zn(a,e,t){if(!Re(a,e))throw new Error("\u8BE5\u8FDE\u63A5\u6CA1\u6709\u53EF\u7528 Token\uFF0C\u8BF7\u5148\u6267\u884C microi auth login");let n=Ke.getInstance();(t==="all"||t==="api")&&await n.pullEngines(e),(t==="all"||t==="form")&&(await n.pullEvents(e),await n.pullFields(e)),(t==="all"||t==="module")&&await n.pullMenuButtons(e),(t==="all"||t==="workflow")&&await n.pullWorkflows(e),(t==="all"||t==="schema")&&await n.pullDbSchema(e)}async function Qi(){let{words:a,options:e}=zi(process.argv.slice(2));if(!a.length||a[0]==="help"||e.help){console.log(qn());return}let t=e.json===!0,n=await Jn(ae(e,"workspace")||process.cwd()),[i,r,o]=a;if(i==="profile"){if(r==="list"){let s=n.config.getProfiles().map((c,l)=>({index:l+1,...c,loggedIn:Re(n,c)}));ue(s,t);return}if(r==="add"){ue(await Qn(n,e),t);return}if(r==="remove"){let s=ct(n.config,o||ae(e,"profile")),c=n.config.getProfiles().findIndex(l=>l.apiBaseUrl===s.apiBaseUrl&&l.osClient===s.osClient);await n.config.removeProfile(c),await n.auth.writeMcpTokenFile(),await at(n.root),ue({removed:!0,profile:s},t);return}}if(i==="auth"){let s=ct(n.config,ae(e,"profile"));if(r==="login"){await Yn(n,s,e),ue({loggedIn:!0,profile:s.osClient},t);return}if(r==="status"){ue({loggedIn:Re(n,s),profile:s},t);return}if(r==="logout"){await n.api.clearTokenForServer(s.apiBaseUrl,s.osClient,s.osClientType,s.osClientNetwork),await n.auth.writeMcpTokenFile(),await at(n.root),ue({loggedIn:!1,profile:s.osClient},t);return}}if(i==="ai"&&r==="init"){ue(await Xn(n,e.mcp!==!1),t);return}if(i==="mcp"&&r==="init"){ue(await at(n.root),t);return}if(i==="init"){let s=n.config.getProfiles()[0];s||(s=await Qn(n,e)),Re(n,s)||await Yn(n,s,e);let c=await Xn(n,!0);e.pull===!0&&await Zn(n,s,"all"),ue({initialized:!0,pulled:e.pull===!0,details:c},t);return}if(i==="pull"){let s=ct(n.config,ae(e,"profile")),c=ae(e,"scope")||"all";if(!["all","api","form","module","workflow","schema"].includes(c))throw new Error(`\u4E0D\u652F\u6301\u7684\u62C9\u53D6\u8303\u56F4\uFF1A${c}`);await Zn(n,s,c),ue({pulled:!0,scope:c,profile:s.osClient},t);return}if(i==="push"){let s=he.resolve(r||"");if(!ie.existsSync(s))throw new Error(`\u6587\u4EF6\u4E0D\u5B58\u5728\uFF1A${s}`);if(!await Ke.getInstance().pushFile(s))throw new Error("\u63A8\u9001\u5931\u8D25\uFF0C\u8BF7\u67E5\u770B\u4E0A\u65B9 Microi \u65E5\u5FD7");ue({pushed:!0,file:s},t);return}if(i==="sync"&&r==="status"){let s=ct(n.config,ae(e,"profile")),c=ae(e,"scope")||"all";if(!["all","api","form","module","workflow"].includes(c))throw new Error(`\u4E0D\u652F\u6301\u7684\u5DEE\u5F02\u8303\u56F4\uFF1A${c}`);let l=await Ke.getInstance().checkRemoteDifferences(s,c);ue({profile:s.osClient,scope:c,count:l.length,differences:l},t);return}if(i==="doctor"){let s=n.config.getProfiles(),c=It(),l=he.join(n.root,".vscode","mcp.json"),m=[];if(ie.existsSync(l))try{let p=ft(ie.readFileSync(l,"utf-8")),h=p.servers&&typeof p.servers=="object"?p.servers:{};for(let[f,y]of Object.entries(h)){let S=y.env&&typeof y.env=="object"?y.env:{};if(!/^microi(?:_|-|$)/i.test(f)&&typeof S.MICROI_API_URL!="string")continue;let C=it(y),w=rt(C,c);m.push({name:f,source:String(S.MICROI_TOOL_SOURCE||"legacy"),version:C||"legacy",compatibility:w>0?"newer-provider-preserved":w<0?"upgrade-available":"compatible"})}}catch(p){m.push({name:"(config)",source:"unknown",version:"unknown",compatibility:`invalid-json: ${p instanceof Error?p.message:String(p)}`})}let g=he.join(n.root,".vscode",".microi-ai-docs-manifest.json"),d="";if(ie.existsSync(g))try{let p=JSON.parse(ie.readFileSync(g,"utf-8"));d=String(p.bundleVersion||"")}catch{d="invalid-json"}let u={ok:s.length>0&&s.some(p=>Re(n,p)),tool:{source:"cli",version:c},node:process.version,workspace:n.root,syncRoot:n.config.getSyncRootDir(),profiles:s.map(p=>({label:p.label,osClient:p.osClient,apiBaseUrl:p.apiBaseUrl,loggedIn:Re(n,p)})),files:{agents:ie.existsSync(he.join(n.root,"AGENTS.md")),vscodeMcp:ie.existsSync(l),codexMcp:ie.existsSync(he.join(n.root,".codex","config.toml")),tokenFile:ie.existsSync(n.auth.mcpTokenFilePath)},coexistence:{aiBundleVersion:d||"not-initialized",mcpProviders:m}};ue(u,t),u.ok||(process.exitCode=2);return}throw new Error(`\u672A\u77E5\u547D\u4EE4\uFF1A${a.join(" ")}
1795
1795
 
1796
1796
  ${qn()}`)}Qi().catch(a=>{console.error(`Microi CLI: ${a instanceof Error?a.message:String(a)}`),process.exitCode=1});
@@ -1,13 +1,13 @@
1
1
  {
2
- "builtAt": "2026-08-05T14:09:50.477Z",
2
+ "builtAt": "2026-08-05T18:12:16.135Z",
3
3
  "source": "../microi.skills",
4
4
  "extension": {
5
5
  "name": "v8-engine",
6
- "version": "4.6.7",
6
+ "version": "4.6.9",
7
7
  "publisher": "Microi"
8
8
  },
9
9
  "skills": {
10
- "version": "4.6.7",
10
+ "version": "4.6.9",
11
11
  "versionRule": "Microi version uses three numeric parts. Each publish increments the last part; when a part exceeds 9 it carries to the previous part: 1.0.9 -> 1.1.0, 1.9.9 -> 2.0.0.",
12
12
  "managedBy": "Microi.VSCode/bump-version.js"
13
13
  },
@@ -15,10 +15,10 @@
15
15
  "dir": "dist/microi.skills",
16
16
  "files": 105,
17
17
  "skills": 58,
18
- "bytes": 1605303
18
+ "bytes": 1608004
19
19
  },
20
20
  "fileHashes": {
21
- ".microi-skills-version.json": "7bbf166e985d6a885f4d713912e6d6950d3e9d3a619f323c33ddae533c046bdb",
21
+ ".microi-skills-version.json": "293cf1ba47b09bafca90160d341b49eb4a731aaebf33284c6603a612afaf2c09",
22
22
  "README.md": "f88db8f5a0ad3788583b1a0787cb4c485f1027e50a5c21997da41334e2be3b82",
23
23
  "ai-engine/SKILL.md": "371b00ce9860d1516f6eb7eeaed001cbfa852c52e7c0cfccbedc4a71a113e568",
24
24
  "ai-engine/agents/openai.yaml": "40deb07801006a46b9a7f0020d13251955eeadd04c8e591160210479936f8b5b",
@@ -38,7 +38,7 @@
38
38
  "microi-ai-application/SKILL.md": "b267798bd59cedca874ccbefdd6fd3f9be48d383d2aacb151c3fa6e880905e30",
39
39
  "microi-ai-application/agents/openai.yaml": "d3dfc4d0f2fda3391e90e661ca9d8d051cb43824b011d1a88e99db135870454f",
40
40
  "microi-ai-application/references/frontend-baseline.md": "c21a2d38292fd8d445a7538afb45d609881f624f32d39c0fc4bbbb3c2fa64a74",
41
- "microi-client-frontend/SKILL.md": "a5a0a93fa70df02bb696f83bd812cb01f23aa9141303dcb8f93017ac3e8b8f96",
41
+ "microi-client-frontend/SKILL.md": "e634ce51f3e3a52fc1b3638e24cf7e7fa9065d2c16bbdeef0acfdd42851067ed",
42
42
  "microi-datasource-mapping/SKILL.md": "1626bdf242038838028aa1235c5a6262e22680984583c47a8fc4e5fffb24b7df",
43
43
  "microi-db-schema/SKILL.md": "2e4dfd98d7e10bad0e8f68682725e88ebbaa5518bc548f8780685e2cd248defd",
44
44
  "microi-db-schema/agents/openai.yaml": "c725a2be4c904472f9e46dc4b49aa642c9f3a4437c91a28ba7cc27167497ede7",
@@ -58,7 +58,7 @@
58
58
  "microi-form-layout/SKILL.md": "48814c2c138e2c0fb6a11d39cf458df6a1cc28a3156c7540db1fa482a2ce6aec",
59
59
  "microi-frontend-sdk/SKILL.md": "0ff6e2df0dc01a42ca875bb6eeb92a4397c5dd4ecae0f808ccf36f1f549c58f0",
60
60
  "microi-left-right-layout/SKILL.md": "d8c482224846477b6c3068bdf94930cca6d699570f59b09f946601b0a65715f6",
61
- "microi-microservice/SKILL.md": "c173ce95bd0a61e7de1bec95e0b72eff6cf61de53702b02703ef9319b539fd2f",
61
+ "microi-microservice/SKILL.md": "909b0cd048734a21369b1f13ed8291038883aa09f7c451854f27262865e00109",
62
62
  "microi-microservice/references/runtime-delivery.md": "704ed30623d91c971bed359403caa1f848edd07528ecbf211fa3b619ccec117d",
63
63
  "microi-mobile-app-quality/SKILL.md": "810bc23f3cfd4ee47ff3a51917b9aaa46cad8d59d2e3a880ed5f4c41b70eb1d7",
64
64
  "microi-solution-quotation/SKILL.md": "1bd47bd019a62bdc904612a7d8e2501c76df66eed9ef247544dd7fe38eba02e4",
@@ -125,111 +125,111 @@
125
125
  "workspace-conventions/SKILL.md": "a498653fca2c3f1b43241b789a3f07f6aece36d89609999a5177a42705615b0d"
126
126
  },
127
127
  "fileVersions": {
128
- ".microi-skills-version.json": "4.6.7",
129
- "README.md": "4.6.7",
130
- "ai-engine/SKILL.md": "4.6.7",
131
- "ai-engine/agents/openai.yaml": "4.6.7",
132
- "app-store/SKILL.md": "4.6.7",
133
- "app-store/agents/openai.yaml": "4.6.7",
134
- "business-blueprint/SKILL.md": "4.6.7",
135
- "datasource-engine/SKILL.md": "4.6.7",
136
- "datasource-engine/agents/openai.yaml": "4.6.7",
137
- "dos-orm/SKILL.md": "4.6.7",
138
- "dos-orm/references/api-reference.md": "4.6.7",
139
- "job-engine/SKILL.md": "4.6.7",
140
- "job-engine/agents/openai.yaml": "4.6.7",
141
- "message-notification/SKILL.md": "4.6.7",
142
- "message-notification/agents/openai.yaml": "4.6.7",
143
- "message-notification/references/contracts.md": "4.6.7",
144
- "microi-ai-app-auth.js": "4.6.7",
145
- "microi-ai-application/SKILL.md": "4.6.7",
146
- "microi-ai-application/agents/openai.yaml": "4.6.7",
147
- "microi-ai-application/references/frontend-baseline.md": "4.6.7",
148
- "microi-client-frontend/SKILL.md": "4.6.7",
149
- "microi-datasource-mapping/SKILL.md": "4.6.7",
150
- "microi-db-schema/SKILL.md": "4.6.7",
151
- "microi-db-schema/agents/openai.yaml": "4.6.7",
152
- "microi-db-schema/references/core-tables.md": "4.6.7",
153
- "microi-db-schema/references/form-component-options.md": "4.6.7",
154
- "microi-db-schema/references/schema-overview.md": "4.6.7",
155
- "microi-db-schema/references/schema.md": "4.6.7",
156
- "microi-db-schema/references/table-catalog.md": "4.6.7",
157
- "microi-deployment/SKILL.md": "4.6.7",
158
- "microi-deployment/references/deployment-matrix.md": "4.6.7",
159
- "microi-docs-coverage/SKILL.md": "4.6.7",
160
- "microi-docs-coverage/references/capability-map.md": "4.6.7",
161
- "microi-docs-coverage/scripts/audit-doc-skill-coverage.mjs": "4.6.7",
162
- "microi-form-engine/SKILL.md": "4.6.7",
163
- "microi-form-engine/references/component-catalog.md": "4.6.7",
164
- "microi-form-engine/references/data-source-events.md": "4.6.7",
165
- "microi-form-layout/SKILL.md": "4.6.7",
166
- "microi-frontend-sdk/SKILL.md": "4.6.7",
167
- "microi-left-right-layout/SKILL.md": "4.6.7",
168
- "microi-microservice/SKILL.md": "4.6.7",
169
- "microi-microservice/references/runtime-delivery.md": "4.6.7",
170
- "microi-mobile-app-quality/SKILL.md": "4.6.7",
171
- "microi-solution-quotation/SKILL.md": "4.6.7",
172
- "microi-solution-quotation/agents/openai.yaml": "4.6.7",
173
- "microi-solution-quotation/scripts/build_solution_quote.py": "4.6.7",
174
- "microi-system-delivery/SKILL.md": "4.6.7",
175
- "microi-ui/SKILL.md": "4.6.7",
176
- "microi-uniapp-frontend/SKILL.md": "4.6.7",
177
- "microi.v8.js": "4.6.7",
178
- "module-engine/SKILL.md": "4.6.7",
179
- "module-engine/references/module-config.md": "4.6.7",
180
- "ocr-engine/SKILL.md": "4.6.7",
181
- "ocr-engine/agents/openai.yaml": "4.6.7",
182
- "page-engine/SKILL.md": "4.6.7",
183
- "performance-testing/SKILL.md": "4.6.7",
184
- "playwright-e2e/SKILL.md": "4.6.7",
185
- "print-engine/SKILL.md": "4.6.7",
186
- "production-readonly-audit/SKILL.md": "4.6.7",
187
- "report-engine/SKILL.md": "4.6.7",
188
- "report-engine/agents/openai.yaml": "4.6.7",
189
- "search-engine/SKILL.md": "4.6.7",
190
- "search-engine/agents/openai.yaml": "4.6.7",
191
- "spider-engine/SKILL.md": "4.6.7",
192
- "translate-engine/SKILL.md": "4.6.7",
193
- "translate-engine/agents/openai.yaml": "4.6.7",
194
- "ui-design/SKILL.md": "4.6.7",
195
- "ui-design/assets/pattern-showcase/app.js": "4.6.7",
196
- "ui-design/assets/pattern-showcase/index.html": "4.6.7",
197
- "ui-design/assets/pattern-showcase/styles.css": "4.6.7",
198
- "ui-design/assets/templates/MCI-DESIGN.md": "4.6.7",
199
- "ui-design/references/design-pattern-library.md": "4.6.7",
200
- "ui-design/references/mci-design-contract.md": "4.6.7",
201
- "ui-design/references/motion-and-media.md": "4.6.7",
202
- "ui-design/references/product-flow-recipes.md": "4.6.7",
203
- "uniapp-mall-assets/SKILL.md": "4.6.7",
204
- "v8-api-config/SKILL.md": "4.6.7",
205
- "v8-cache-pattern/SKILL.md": "4.6.7",
206
- "v8-crud-api/SKILL.md": "4.6.7",
207
- "v8-debugging/SKILL.md": "4.6.7",
208
- "v8-explorer-tree/SKILL.md": "4.6.7",
209
- "v8-export-import/SKILL.md": "4.6.7",
210
- "v8-file-upload/SKILL.md": "4.6.7",
211
- "v8-formengine-http/SKILL.md": "4.6.7",
212
- "v8-frontend-events/SKILL.md": "4.6.7",
213
- "v8-frontend-events/references/bluetooth-print-api.md": "4.6.7",
214
- "v8-frontend-events/references/bluetooth-print.md": "4.6.7",
215
- "v8-http-integration/SKILL.md": "4.6.7",
216
- "v8-image-processing/SKILL.md": "4.6.7",
217
- "v8-image-processing/agents/openai.yaml": "4.6.7",
218
- "v8-image-processing/references/api-reference.md": "4.6.7",
219
- "v8-menu-buttons/SKILL.md": "4.6.7",
220
- "v8-mongodb/SKILL.md": "4.6.7",
221
- "v8-mq-mqtt/SKILL.md": "4.6.7",
222
- "v8-saas-multi-tenant/SKILL.md": "4.6.7",
223
- "v8-security/SKILL.md": "4.6.7",
224
- "v8-sql-query/SKILL.md": "4.6.7",
225
- "v8-table-event/SKILL.md": "4.6.7",
226
- "v8-template-engine/SKILL.md": "4.6.7",
227
- "v8-utilities/SKILL.md": "4.6.7",
228
- "v8-utilities/references/client-api-index.md": "4.6.7",
229
- "v8-utilities/references/platform-http-routes.md": "4.6.7",
230
- "v8-utilities/references/server-api-index.md": "4.6.7",
231
- "v8-workflow/SKILL.md": "4.6.7",
232
- "workspace-conventions/SKILL.md": "4.6.7"
128
+ ".microi-skills-version.json": "4.6.9",
129
+ "README.md": "4.6.9",
130
+ "ai-engine/SKILL.md": "4.6.9",
131
+ "ai-engine/agents/openai.yaml": "4.6.9",
132
+ "app-store/SKILL.md": "4.6.9",
133
+ "app-store/agents/openai.yaml": "4.6.9",
134
+ "business-blueprint/SKILL.md": "4.6.9",
135
+ "datasource-engine/SKILL.md": "4.6.9",
136
+ "datasource-engine/agents/openai.yaml": "4.6.9",
137
+ "dos-orm/SKILL.md": "4.6.9",
138
+ "dos-orm/references/api-reference.md": "4.6.9",
139
+ "job-engine/SKILL.md": "4.6.9",
140
+ "job-engine/agents/openai.yaml": "4.6.9",
141
+ "message-notification/SKILL.md": "4.6.9",
142
+ "message-notification/agents/openai.yaml": "4.6.9",
143
+ "message-notification/references/contracts.md": "4.6.9",
144
+ "microi-ai-app-auth.js": "4.6.9",
145
+ "microi-ai-application/SKILL.md": "4.6.9",
146
+ "microi-ai-application/agents/openai.yaml": "4.6.9",
147
+ "microi-ai-application/references/frontend-baseline.md": "4.6.9",
148
+ "microi-client-frontend/SKILL.md": "4.6.9",
149
+ "microi-datasource-mapping/SKILL.md": "4.6.9",
150
+ "microi-db-schema/SKILL.md": "4.6.9",
151
+ "microi-db-schema/agents/openai.yaml": "4.6.9",
152
+ "microi-db-schema/references/core-tables.md": "4.6.9",
153
+ "microi-db-schema/references/form-component-options.md": "4.6.9",
154
+ "microi-db-schema/references/schema-overview.md": "4.6.9",
155
+ "microi-db-schema/references/schema.md": "4.6.9",
156
+ "microi-db-schema/references/table-catalog.md": "4.6.9",
157
+ "microi-deployment/SKILL.md": "4.6.9",
158
+ "microi-deployment/references/deployment-matrix.md": "4.6.9",
159
+ "microi-docs-coverage/SKILL.md": "4.6.9",
160
+ "microi-docs-coverage/references/capability-map.md": "4.6.9",
161
+ "microi-docs-coverage/scripts/audit-doc-skill-coverage.mjs": "4.6.9",
162
+ "microi-form-engine/SKILL.md": "4.6.9",
163
+ "microi-form-engine/references/component-catalog.md": "4.6.9",
164
+ "microi-form-engine/references/data-source-events.md": "4.6.9",
165
+ "microi-form-layout/SKILL.md": "4.6.9",
166
+ "microi-frontend-sdk/SKILL.md": "4.6.9",
167
+ "microi-left-right-layout/SKILL.md": "4.6.9",
168
+ "microi-microservice/SKILL.md": "4.6.9",
169
+ "microi-microservice/references/runtime-delivery.md": "4.6.9",
170
+ "microi-mobile-app-quality/SKILL.md": "4.6.9",
171
+ "microi-solution-quotation/SKILL.md": "4.6.9",
172
+ "microi-solution-quotation/agents/openai.yaml": "4.6.9",
173
+ "microi-solution-quotation/scripts/build_solution_quote.py": "4.6.9",
174
+ "microi-system-delivery/SKILL.md": "4.6.9",
175
+ "microi-ui/SKILL.md": "4.6.9",
176
+ "microi-uniapp-frontend/SKILL.md": "4.6.9",
177
+ "microi.v8.js": "4.6.9",
178
+ "module-engine/SKILL.md": "4.6.9",
179
+ "module-engine/references/module-config.md": "4.6.9",
180
+ "ocr-engine/SKILL.md": "4.6.9",
181
+ "ocr-engine/agents/openai.yaml": "4.6.9",
182
+ "page-engine/SKILL.md": "4.6.9",
183
+ "performance-testing/SKILL.md": "4.6.9",
184
+ "playwright-e2e/SKILL.md": "4.6.9",
185
+ "print-engine/SKILL.md": "4.6.9",
186
+ "production-readonly-audit/SKILL.md": "4.6.9",
187
+ "report-engine/SKILL.md": "4.6.9",
188
+ "report-engine/agents/openai.yaml": "4.6.9",
189
+ "search-engine/SKILL.md": "4.6.9",
190
+ "search-engine/agents/openai.yaml": "4.6.9",
191
+ "spider-engine/SKILL.md": "4.6.9",
192
+ "translate-engine/SKILL.md": "4.6.9",
193
+ "translate-engine/agents/openai.yaml": "4.6.9",
194
+ "ui-design/SKILL.md": "4.6.9",
195
+ "ui-design/assets/pattern-showcase/app.js": "4.6.9",
196
+ "ui-design/assets/pattern-showcase/index.html": "4.6.9",
197
+ "ui-design/assets/pattern-showcase/styles.css": "4.6.9",
198
+ "ui-design/assets/templates/MCI-DESIGN.md": "4.6.9",
199
+ "ui-design/references/design-pattern-library.md": "4.6.9",
200
+ "ui-design/references/mci-design-contract.md": "4.6.9",
201
+ "ui-design/references/motion-and-media.md": "4.6.9",
202
+ "ui-design/references/product-flow-recipes.md": "4.6.9",
203
+ "uniapp-mall-assets/SKILL.md": "4.6.9",
204
+ "v8-api-config/SKILL.md": "4.6.9",
205
+ "v8-cache-pattern/SKILL.md": "4.6.9",
206
+ "v8-crud-api/SKILL.md": "4.6.9",
207
+ "v8-debugging/SKILL.md": "4.6.9",
208
+ "v8-explorer-tree/SKILL.md": "4.6.9",
209
+ "v8-export-import/SKILL.md": "4.6.9",
210
+ "v8-file-upload/SKILL.md": "4.6.9",
211
+ "v8-formengine-http/SKILL.md": "4.6.9",
212
+ "v8-frontend-events/SKILL.md": "4.6.9",
213
+ "v8-frontend-events/references/bluetooth-print-api.md": "4.6.9",
214
+ "v8-frontend-events/references/bluetooth-print.md": "4.6.9",
215
+ "v8-http-integration/SKILL.md": "4.6.9",
216
+ "v8-image-processing/SKILL.md": "4.6.9",
217
+ "v8-image-processing/agents/openai.yaml": "4.6.9",
218
+ "v8-image-processing/references/api-reference.md": "4.6.9",
219
+ "v8-menu-buttons/SKILL.md": "4.6.9",
220
+ "v8-mongodb/SKILL.md": "4.6.9",
221
+ "v8-mq-mqtt/SKILL.md": "4.6.9",
222
+ "v8-saas-multi-tenant/SKILL.md": "4.6.9",
223
+ "v8-security/SKILL.md": "4.6.9",
224
+ "v8-sql-query/SKILL.md": "4.6.9",
225
+ "v8-table-event/SKILL.md": "4.6.9",
226
+ "v8-template-engine/SKILL.md": "4.6.9",
227
+ "v8-utilities/SKILL.md": "4.6.9",
228
+ "v8-utilities/references/client-api-index.md": "4.6.9",
229
+ "v8-utilities/references/platform-http-routes.md": "4.6.9",
230
+ "v8-utilities/references/server-api-index.md": "4.6.9",
231
+ "v8-workflow/SKILL.md": "4.6.9",
232
+ "workspace-conventions/SKILL.md": "4.6.9"
233
233
  },
234
234
  "files": [
235
235
  ".microi-skills-version.json",
@@ -1,6 +1,6 @@
1
1
  {
2
- "version": "4.6.7",
2
+ "version": "4.6.9",
3
3
  "versionRule": "Microi version uses three numeric parts. Each publish increments the last part; when a part exceeds 9 it carries to the previous part: 1.0.9 -> 1.1.0, 1.9.9 -> 2.0.0.",
4
4
  "managedBy": "Microi.VSCode/bump-version.js",
5
- "updatedAt": "2026-08-05T14:09:41.443Z"
5
+ "updatedAt": "2026-08-05T18:12:05.984Z"
6
6
  }
@@ -459,9 +459,24 @@ DiyCommon.FormEngine.AddFormData("table_name", { Field: "value" }, function (res
459
459
 
460
460
  `sys_menu.OpenType=MicroService` 时,动态路由必须把 `MicroServiceId`、`MicroServicePageId`、`MicroServiceRoutePath` 和真实入口 `MicroAppUrl` 写入 route meta;浏览器侧菜单路由使用 `/#/micro-app/{MsKey}/{RoutePath}`,不要再生成 `/micro-app-host/{menuId}`,否则地址过长且刷新或直接访问菜单路由容易加载空白页。
461
461
 
462
- 同一个编译后的微服务可以绑定多个后台菜单和内部页面。`MicroAppHost` 的 `<micro-app name>` 必须包含菜单 Id、路由路径或其它实例维度,避免多个菜单共享同一个 appKey 时触发 `app name conflict`。入口 URL 中的 `microRoute/routePath` 只用于解析,最终应通过 `data.microRoute` 传给子应用,入口文件 URL 保持稳定。
463
-
464
- 后台配置必须配套维护 `sys_microiservice_page` 路由子表,并在 `sys_microiservice` 表单上用隐藏子模块 + `TableChild` 显示页面/路由。`sys_menu` 选择微服务时要由前端 V8 事件实时加载页面列表,不能完全依赖 SQL 下拉里的表单变量替换。
462
+ 同一个编译后的微服务可以绑定多个后台菜单和内部页面。`MicroAppHost` 的 `<micro-app name>` 必须包含菜单 Id、路由路径或其它实例维度,避免多个菜单共享同一个 appKey 时触发 `app name conflict`。入口 URL 中的 `microRoute/routePath` 只用于解析,最终应通过 `data.microRoute` 传给子应用,入口文件 URL 保持稳定。
463
+
464
+ 菜单型微服务的宿主操作集中维护在 `views/micro-app/host-bridge.js` `host.vue`。
465
+ `microAppData.hostCapabilities` 必须下发 `microi.host.v1` 协议、`tab` 模式、请求/结果事件名和动作清单;
466
+ 子应用只允许 dispatch `micro-app:host-action`,不能接收父页面函数或直接操作 TagsView/Router。
467
+ 标准动作包括 `closeTab/navigate/replaceTab/back/forward/reloadTab/setTabTitle/showMessage`:
468
+ 关闭当前 Tab 要复用 `useTagsViewStore` 的当前 `fullPath`,拒绝固定/最后一个 Tab;`navigate`
469
+ 保留当前 Tab,`replaceTab` 删除旧 Tab;返回/前进只使用站内 history;右键刷新和 `reloadTab`
470
+ 都重新解析并挂载当前微服务。路由输入必须拒绝外部 URL、协议相对地址、反斜杠、登录、访问密钥和
471
+ 内部 redirect,并在跳转前用当前 Router 解析,404/未注册动态路由失败关闭。宿主结果用
472
+ `micro-app:host-action-result` 尽力回传,但关闭或跳转会卸载子应用,不能承诺结果事件必达。
473
+
474
+ `OpenAppDialog` 不暴露 Tab 模式能力;弹窗成功/取消/失败继续使用
475
+ `app-dialog:success/cancel/error`。修改桥接时至少运行
476
+ `node --test tests/micro-app-host-bridge.spec.mjs tests/micro-app-runtime-contract.spec.mjs`,并同步
477
+ `microi.doc/docs/doc/system-engine/micro-app.md` 与 `microi-microservice` Skill。
478
+
479
+ 后台配置必须配套维护 `sys_microiservice_page` 路由子表,并在 `sys_microiservice` 表单上用隐藏子模块 + `TableChild` 显示页面/路由。`sys_menu` 选择微服务时要由前端 V8 事件实时加载页面列表,不能完全依赖 SQL 下拉里的表单变量替换。
465
480
 
466
481
  `sys_menu.MicroServiceId` 的字段值变更 V8 必须把 `V8.ThisValue` 传给页面列表加载函数,例如 `window.LoadMicroServicePages(V8, false, V8.ThisValue || V8.Form.MicroServiceId)`;不要只读取 `V8.Form.MicroServiceId`,因为字段变更触发瞬间表单模型可能仍是旧值或显示文本。页面列表加载函数必须支持从选中对象、保存 Id、`名称(MsKey)` 文本中解析服务,并在按 `MicroServiceId` 查询为空时按 `MicroServiceKey` 兜底查询。
467
482
 
@@ -92,6 +92,30 @@ AppKey 稳定且只含安全字符。`microi.routes.json` 是页面事实源,
92
92
  Token 只通过宿主上下文传递,不硬编码、不放 URL、不写日志。子应用回传成功/取消/
93
93
  错误事件,宿主负责提示、关闭和刷新。
94
94
 
95
+ 菜单型微服务通过 `window.microApp.getData().hostCapabilities` 发现主框架能力,禁止直接操作
96
+ 父页面 DOM、Pinia 或 Vue Router。能力协议固定为 `microi.host.v1`,请求使用:
97
+
98
+ ```js
99
+ window.microApp.dispatch({
100
+ type: 'micro-app:host-action',
101
+ action: 'closeTab',
102
+ requestId: 'optional-id',
103
+ data: {}
104
+ });
105
+ ```
106
+
107
+ AI 生成菜单微服务时,应优先封装一个 `callMicroiHost(action, data)`,先检查
108
+ `hostCapabilities.actions`,再 dispatch。当前标准动作是:`closeTab`、`navigate`、
109
+ `replaceTab`、`back`、`forward`、`reloadTab`、`setTabTitle`、`showMessage`。
110
+ `navigate/replaceTab` 只传以 `/` 开头的站内 path 或 `{name,params,query,hash}`;禁止传
111
+ 外部 URL、登录页、访问密钥页或内部 redirect。目标仍要存在于当前用户动态路由并经过路由守卫,
112
+ 宿主桥接不授予菜单或数据权限。业务保存成功后才能关闭/跳转,不能把尽力返回的
113
+ `micro-app:host-action-result` 当作业务持久化确认。
114
+
115
+ `closeTab` 与 TagsView 当前页签关闭语义一致,固定页签和最后一个页签拒绝关闭;顶部 Tab
116
+ 右键刷新与 `reloadTab` 都应重载当前微服务。`OpenAppDialog` 页面不使用 Tab 动作,继续发送
117
+ `app-dialog:success/cancel/error` 关闭弹窗并回传结果。
118
+
95
119
  `sys_microiservice_page` 是友好路由的页面事实源,`sys_menu` 只负责导航和角色权限。
96
120
  无需出现在导航中的按钮页/详情页应在页面元数据设置 `InternalOnly=true`,不创建伪隐藏菜单。
97
121
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@microi.net/cli",
3
- "version": "4.6.7",
3
+ "version": "4.6.9",
4
4
  "description": "Microi吾码 AI 开发命令行:服务器连接、登录、AI/MCP 初始化与 V8 资源同步",
5
5
  "license": "MIT",
6
6
  "homepage": "https://microi.net/doc/v8-engine/vs-code-plugin.html",