chainlesschain 0.46.0 → 0.47.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +10 -0
- package/package.json +1 -1
- package/src/assets/web-panel/.build-hash +1 -1
- package/src/assets/web-panel/assets/{Analytics-C1AnPdMx.js → Analytics-DgypYeUB.js} +2 -2
- package/src/assets/web-panel/assets/AppLayout-Bzf3mSZI.js +1 -0
- package/src/assets/web-panel/assets/AppLayout-DQyDwGut.css +1 -0
- package/src/assets/web-panel/assets/{Backup-D31iZX3l.js → Backup-Ba9UybpT.js} +1 -1
- package/src/assets/web-panel/assets/{Chat-DiXJ3TuK.js → Chat-BwXskT21.js} +1 -1
- package/src/assets/web-panel/assets/{Cowork-B8ZDdRm4.js → Cowork-UmOe7qvE.js} +1 -1
- package/src/assets/web-panel/assets/{Cron-DBt1ueXh.js → Cron-JHS-rc-4.js} +2 -2
- package/src/assets/web-panel/assets/{Dashboard-jt6XPIjB.js → Dashboard-B95cMCO7.js} +1 -1
- package/src/assets/web-panel/assets/{Git-hwQ1oZHj.js → Git-CSYO0_zk.js} +2 -2
- package/src/assets/web-panel/assets/{Logs-4D9p6PRM.js → Logs-Hxw_K0km.js} +2 -2
- package/src/assets/web-panel/assets/{McpTools-CyAUjbbs.js → McpTools-DIE75TrB.js} +2 -2
- package/src/assets/web-panel/assets/{Memory-BMqOR7S-.js → Memory-C4KVnLlp.js} +2 -2
- package/src/assets/web-panel/assets/{Notes-Cmas8i4E.js → Notes-DuzrHMAk.js} +2 -2
- package/src/assets/web-panel/assets/{Organization-DnSa58Tl.js → Organization-DTq6uF82.js} +4 -4
- package/src/assets/web-panel/assets/{P2P-BxksIBWs.js → P2P-C0hjlhsR.js} +2 -2
- package/src/assets/web-panel/assets/{Permissions-Bq5Qn2s3.js → Permissions-Ec0NH-xC.js} +4 -4
- package/src/assets/web-panel/assets/{Projects-B7EM0uPg.js → Projects-U8D0asCS.js} +2 -2
- package/src/assets/web-panel/assets/{Providers-DAwgG5KV.js → Providers-BngtTLvJ.js} +2 -2
- package/src/assets/web-panel/assets/{RssFeed-HSZoRXvS.js → RssFeed-B9NbwCKM.js} +3 -3
- package/src/assets/web-panel/assets/{Security-Cz17qBny.js → Security-BL5Rkr1T.js} +3 -3
- package/src/assets/web-panel/assets/{Services-D2EsLq-v.js → Services-D4MJzLld.js} +2 -2
- package/src/assets/web-panel/assets/{Skills-C9v-f3vZ.js → Skills-CQTOMDwF.js} +1 -1
- package/src/assets/web-panel/assets/{Tasks-yMEcU0n7.js → Tasks-DepbJMnL.js} +1 -1
- package/src/assets/web-panel/assets/{Templates-l7SvlKuB.js → Templates-C24PVZPu.js} +1 -1
- package/src/assets/web-panel/assets/{Wallet-BHWhLWn9.js → Wallet-PQoSpN_P.js} +3 -3
- package/src/assets/web-panel/assets/{WebAuthn-kWhFYaUK.js → WebAuthn-BcuyQ4Lr.js} +4 -4
- package/src/assets/web-panel/assets/WorkflowEditor-C-SvXbHW.js +1 -0
- package/src/assets/web-panel/assets/WorkflowEditor-D5bX6woe.css +1 -0
- package/src/assets/web-panel/assets/{antd-D6h4fDFf.js → antd-DEjZPGMj.js} +82 -82
- package/src/assets/web-panel/assets/index-CwvzTTw_.js +2 -0
- package/src/assets/web-panel/assets/{markdown-BZsB-Dsv.js → markdown-CusdXFxb.js} +1 -1
- package/src/assets/web-panel/index.html +2 -2
- package/src/commands/cowork.js +213 -41
- package/src/gateways/ws/action-protocol.js +140 -0
- package/src/gateways/ws/message-dispatcher.js +5 -0
- package/src/gateways/ws/ws-server.js +21 -0
- package/src/lib/cowork-evomap-adapter.js +121 -0
- package/src/lib/cowork-observe-html.js +108 -0
- package/src/lib/cowork-observe.js +160 -0
- package/src/lib/cowork-share.js +114 -10
- package/src/lib/provider-options.js +133 -0
- package/src/lib/skill-loader.js +65 -0
- package/src/lib/sub-agent-context.js +16 -4
- package/src/lib/sub-agent-profiles.js +164 -0
- package/src/lib/todo-manager.js +108 -0
- package/src/lib/turn-context.js +95 -0
- package/src/lib/web-fetch.js +224 -0
- package/src/repl/agent-repl.js +4 -0
- package/src/runtime/agent-core.js +135 -3
- package/src/runtime/coding-agent-contract-shared.cjs +131 -0
- package/src/runtime/coding-agent-policy.cjs +30 -0
- package/src/assets/web-panel/assets/AppLayout-BnvARObz.js +0 -1
- package/src/assets/web-panel/assets/AppLayout-cxfKLu-m.css +0 -1
- package/src/assets/web-panel/assets/index-C1SPm_5l.js +0 -2
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import{u as
|
|
2
|
-
`);for(const v of n){const b=v.trim();if(!b||b.startsWith("─")||b.startsWith("No "))continue;const d=b.split(/\s*[|│]\s*/);d.length>=2&&e.push({key:e.length,id:d[0]||"-",name:d[1]||"-",type:d[2]||"public-key",createdAt:d[3]||"-",lastUsed:d[4]||"-"})}return e}async function pe(){const t=D.value.trim();if(!t){u.warning("请输入凭证名称");return}
|
|
3
|
-
`);for(const v of n){const b=v.trim().match(/^(.+?)\s*[:=:]\s*(.+)$/);if(b){const d=b[1].toLowerCase(),C=b[2].trim();d.includes("provider")?p.value.provider=C:d.includes("client")&&d.includes("id")?p.value.clientId=C:d.includes("redirect")||d.includes("callback")?p.value.redirectUrl=C:(d.includes("status")||d.includes("enabled"))&&(p.value.enabled=/true|enabled|active|已启用/i.test(C))}}}
|
|
1
|
+
import{u as Oe}from"./ws-Dma34ig_.js";import{_ as Ie}from"./_plugin-vue_export-helper-DlAUqK2U.js";import{N as u,q as le,O as Te,a4 as ze,K as ne,a8 as Le,L as oe}from"./antd-DEjZPGMj.js";import{o as $e,a3 as y,a1 as g,k as a,Z as l,f as r,X as s,Y as i,G as c,u as k,W as O,a5 as m,a4 as h,F as j,a7 as se}from"./vendor-CN0Iv_qZ.js";const De={style:{display:"flex","align-items":"center","justify-content":"space-between","margin-bottom":"24px"}},Ne={key:0,style:{"text-align":"center",padding:"60px"}},Pe=["title"],We={key:1,style:{color:"var(--text-primary)"}},Re={key:3,style:{color:"var(--text-secondary)","font-size":"12px"}},je={key:4,style:{color:"var(--text-secondary)","font-size":"12px"}},Ke={key:0,style:{"text-align":"center",padding:"60px"}},Me={style:{color:"#e0e0e0","font-family":"monospace","font-size":"12px"}},qe={style:{color:"var(--text-secondary)","font-size":"12px"}},Be={style:{"margin-top":"16px"}},Ve={key:0,style:{"text-align":"center",padding:"60px"}},Fe={style:{display:"flex","align-items":"center",gap:"16px","margin-bottom":"16px"}},Ee={key:0,style:{"margin-top":"16px"}},Je={style:{"white-space":"pre-wrap","word-break":"break-all",color:"#52c41a","font-size":"11px",background:"var(--bg-base)",padding:"12px","border-radius":"6px",border:"1px solid var(--border-color)"}},Ye={key:0,style:{"margin-top":"16px"}},Ze={style:{background:"var(--bg-base)",padding:"16px","border-radius":"6px",border:"1px solid var(--border-color)"}},Ge={__name:"WebAuthn",setup(Xe){const x=Oe(),I=r("webauthn"),K=r(!1);async function re(){K.value=!0;try{I.value==="webauthn"?await N():I.value==="sso"?await J():I.value==="2fa"&&await ee()}finally{K.value=!1}}function ie(t){t==="sso"&&!V.value&&J(),t==="2fa"&&!Z.value&&ee()}function T(t){try{return JSON.parse(t)}catch{return null}}function ue(t){return t?t.length<=16?t:t.slice(0,8)+"..."+t.slice(-8):"-"}const M=r(!1),q=r(!1),L=r([]),$=r(!1),D=r(""),de=[{title:"ID",key:"id",dataIndex:"id",width:"180px"},{title:"名称",key:"name",dataIndex:"name",width:"160px"},{title:"类型",key:"type",dataIndex:"type",width:"120px"},{title:"创建时间",key:"createdAt",dataIndex:"createdAt",width:"180px"},{title:"最后使用",key:"lastUsed",dataIndex:"lastUsed",width:"180px"},{title:"操作",key:"actions",width:"100px",fixed:"right"}];async function N(){M.value=!0;try{const{output:t}=await x.execute("webauthn list --json",15e3),e=T(t);e&&Array.isArray(e)?L.value=e.map((n,v)=>({key:n.id||v,id:n.id||"-",name:n.name||n.displayName||"-",type:n.type||"public-key",createdAt:n.createdAt||n.created||"-",lastUsed:n.lastUsed||n.lastAuthentication||"-"})):e&&e.credentials?L.value=e.credentials.map((n,v)=>({key:n.id||v,id:n.id||"-",name:n.name||n.displayName||"-",type:n.type||"public-key",createdAt:n.createdAt||n.created||"-",lastUsed:n.lastUsed||n.lastAuthentication||"-"})):L.value=ce(t)}catch(t){u.error("加载 WebAuthn 凭证失败: "+t.message)}finally{M.value=!1}}function ce(t){const e=[],n=t.split(`
|
|
2
|
+
`);for(const v of n){const b=v.trim();if(!b||b.startsWith("─")||b.startsWith("No "))continue;const d=b.split(/\s*[|│]\s*/);d.length>=2&&e.push({key:e.length,id:d[0]||"-",name:d[1]||"-",type:d[2]||"public-key",createdAt:d[3]||"-",lastUsed:d[4]||"-"})}return e}async function pe(){const t=D.value.trim();if(!t){u.warning("请输入凭证名称");return}q.value=!0;try{const e=t.replace(/"/g,'\\"'),{output:n}=await x.execute(`webauthn register --name "${e}" --json`,3e4);n.includes("error")||n.includes("失败")?u.error("注册失败: "+n.slice(0,120)):(u.success("WebAuthn 凭证已注册"),$.value=!1,D.value="",await N())}catch(e){u.error("注册失败: "+e.message)}finally{q.value=!1}}async function fe(t){try{const{output:e}=await x.execute(`webauthn delete "${t.id}"`,15e3);e.includes("error")||e.includes("失败")?u.error("删除失败: "+e.slice(0,120)):(u.success("凭证已删除"),await N())}catch(e){u.error("删除失败: "+e.message)}}const B=r(!1),V=r(!1),F=r(!1),P=r(!1),p=r({provider:"",clientId:"",redirectUrl:"",enabled:!1}),f=r({provider:void 0,clientId:"",clientSecret:"",issuerUrl:""}),E=r([]);async function J(){B.value=!0;try{const{output:t}=await x.execute("sso status --json",15e3),e=T(t);if(e)p.value={provider:e.provider||"",clientId:e.clientId||e.client_id||"",redirectUrl:e.redirectUrl||e.redirect_url||e.callbackUrl||"",enabled:e.enabled||e.active||!1};else{const n=t.split(`
|
|
3
|
+
`);for(const v of n){const b=v.trim().match(/^(.+?)\s*[:=:]\s*(.+)$/);if(b){const d=b[1].toLowerCase(),C=b[2].trim();d.includes("provider")?p.value.provider=C:d.includes("client")&&d.includes("id")?p.value.clientId=C:d.includes("redirect")||d.includes("callback")?p.value.redirectUrl=C:(d.includes("status")||d.includes("enabled"))&&(p.value.enabled=/true|enabled|active|已启用/i.test(C))}}}E.value=[{label:"提供商",value:p.value.provider||"未配置",color:p.value.provider?"#1677ff":"#999"},{label:"状态",value:p.value.enabled?"已启用":"未启用",color:p.value.enabled?"#52c41a":"#faad14"}],V.value=!0}catch{p.value={provider:"",clientId:"",redirectUrl:"",enabled:!1},E.value=[{label:"提供商",value:"未配置",color:"#999"},{label:"状态",value:"未启用",color:"#faad14"}],V.value=!0}finally{B.value=!1}}async function ve(){if(!f.value.provider){u.warning("请选择 SSO 提供商");return}if(!f.value.clientId.trim()){u.warning("请输入 Client ID");return}F.value=!0;try{const t=[`config set sso.provider ${f.value.provider}`,`config set sso.clientId ${f.value.clientId.trim()}`];f.value.clientSecret.trim()&&t.push(`config set sso.clientSecret ${f.value.clientSecret.trim()}`),f.value.issuerUrl.trim()&&t.push(`config set sso.issuerUrl ${f.value.issuerUrl.trim()}`);for(const e of t)await x.execute(e,1e4);u.success("SSO 配置已保存"),P.value=!1,await J()}catch(t){u.error("保存失败: "+t.message)}finally{F.value=!1}}const Y=r(!1),Z=r(!1),w=r(!1),U=r(!1),A=r(""),G=r(!1),S=r([]);async function ee(){Y.value=!0;try{const{output:t}=await x.execute("auth 2fa status --json",15e3),e=T(t);e?w.value=e.enabled||e.active||!1:w.value=/enabled|已启用|active/i.test(t),Z.value=!0}catch{w.value=!1,Z.value=!0}finally{Y.value=!1}}async function ye(){U.value=!0,A.value="";try{const{output:t}=await x.execute("auth 2fa enable --type totp --json",2e4);if(t.includes("error")||t.includes("失败"))u.error("启用失败: "+t.slice(0,120));else{const e=T(t);e&&e.secret?A.value=`TOTP Secret: ${e.secret}
|
|
4
4
|
OTP Auth URL: ${e.otpAuthUrl||e.uri||""}`:A.value=t,w.value=!0,u.success("TOTP 已启用")}}catch(t){u.error("启用失败: "+t.message)}finally{U.value=!1}}async function me(){U.value=!0,A.value="";try{const{output:t}=await x.execute("auth 2fa disable",15e3);t.includes("error")||t.includes("失败")?u.error("禁用失败: "+t.slice(0,120)):(w.value=!1,u.success("双因素认证已禁用"))}catch(t){u.error("禁用失败: "+t.message)}finally{U.value=!1}}async function be(){G.value=!0,S.value=[];try{const{output:t}=await x.execute("auth 2fa recovery-codes --json",15e3),e=T(t);if(e&&Array.isArray(e.codes))S.value=e.codes;else if(e&&Array.isArray(e))S.value=e;else{const n=t.split(`
|
|
5
|
-
`).map(v=>v.trim()).filter(v=>v&&/^[A-Za-z0-9-]{6,}$/.test(v));S.value=n.length>0?n:[t.trim()||"无法生成恢复码"]}S.value.length>0&&S.value[0]!=="无法生成恢复码"&&u.success("恢复码已生成")}catch(t){u.error("生成恢复码失败: "+t.message)}finally{G.value=!1}}return $e(()=>{N()}),(t,e)=>{const n=s("a-button"),v=s("a-space"),b=s("a-spin"),d=s("a-tag"),C=s("a-popconfirm"),ge=s("a-empty"),_e=s("a-table"),X=s("a-input"),z=s("a-form-item"),te=s("a-form"),ae=s("a-modal"),H=s("a-tab-pane"),xe=s("a-statistic"),W=s("a-card"),ke=s("a-col"),we=s("a-row"),R=s("a-descriptions-item"),Se=s("a-descriptions"),Q=s("a-select-option"),he=s("a-select"),Ce=s("a-input-password"),Ue=s("a-alert"),Ae=s("a-tabs");return i(),y("div",null,[g("div",De,[e[11]||(e[11]=g("div",null,[g("h2",{class:"page-title"},"认证管理"),g("p",{class:"page-sub"},"WebAuthn / SSO / 双因素认证")],-1)),a(n,{type:"primary",ghost:"",loading:K.value,onClick:re},{icon:l(()=>[a(k(le))]),default:l(()=>[e[10]||(e[10]=c(" 刷新 ",-1))]),_:1},8,["loading"])]),a(Ae,{activeKey:
|
|
5
|
+
`).map(v=>v.trim()).filter(v=>v&&/^[A-Za-z0-9-]{6,}$/.test(v));S.value=n.length>0?n:[t.trim()||"无法生成恢复码"]}S.value.length>0&&S.value[0]!=="无法生成恢复码"&&u.success("恢复码已生成")}catch(t){u.error("生成恢复码失败: "+t.message)}finally{G.value=!1}}return $e(()=>{N()}),(t,e)=>{const n=s("a-button"),v=s("a-space"),b=s("a-spin"),d=s("a-tag"),C=s("a-popconfirm"),ge=s("a-empty"),_e=s("a-table"),X=s("a-input"),z=s("a-form-item"),te=s("a-form"),ae=s("a-modal"),H=s("a-tab-pane"),xe=s("a-statistic"),W=s("a-card"),ke=s("a-col"),we=s("a-row"),R=s("a-descriptions-item"),Se=s("a-descriptions"),Q=s("a-select-option"),he=s("a-select"),Ce=s("a-input-password"),Ue=s("a-alert"),Ae=s("a-tabs");return i(),y("div",null,[g("div",De,[e[11]||(e[11]=g("div",null,[g("h2",{class:"page-title"},"认证管理"),g("p",{class:"page-sub"},"WebAuthn / SSO / 双因素认证")],-1)),a(n,{type:"primary",ghost:"",loading:K.value,onClick:re},{icon:l(()=>[a(k(le))]),default:l(()=>[e[10]||(e[10]=c(" 刷新 ",-1))]),_:1},8,["loading"])]),a(Ae,{activeKey:I.value,"onUpdate:activeKey":e[9]||(e[9]=o=>I.value=o),type:"card",onChange:ie},{default:l(()=>[a(H,{key:"webauthn"},{tab:l(()=>[a(k(ne)),e[12]||(e[12]=c(" WebAuthn ",-1))]),default:l(()=>[a(v,{style:{"margin-bottom":"16px"}},{default:l(()=>[a(n,{type:"primary",onClick:e[0]||(e[0]=o=>$.value=!0)},{icon:l(()=>[a(k(Te))]),default:l(()=>[e[13]||(e[13]=c(" 注册新凭证 ",-1))]),_:1})]),_:1}),M.value?(i(),y("div",Ne,[a(b,{size:"large"})])):(i(),O(_e,{key:1,columns:de,"data-source":L.value,pagination:{pageSize:20,showTotal:o=>`共 ${o} 条`},size:"small",style:{background:"var(--bg-card)"},"row-class-name":()=>"auth-row"},{bodyCell:l(({column:o,record:_})=>[o.key==="id"?(i(),y("span",{key:0,style:{color:"#e0e0e0","font-family":"monospace","font-size":"12px"},title:_.id},m(ue(_.id)),9,Pe)):h("",!0),o.key==="name"?(i(),y("span",We,m(_.name),1)):h("",!0),o.key==="type"?(i(),O(d,{key:2,color:"blue"},{default:l(()=>[c(m(_.type||"public-key"),1)]),_:2},1024)):h("",!0),o.key==="createdAt"?(i(),y("span",Re,m(_.createdAt||"-"),1)):h("",!0),o.key==="lastUsed"?(i(),y("span",je,m(_.lastUsed||"-"),1)):h("",!0),o.key==="actions"?(i(),O(C,{key:5,title:"确定要删除此凭证吗?","ok-text":"确定","cancel-text":"取消",onConfirm:He=>fe(_)},{default:l(()=>[a(n,{type:"link",danger:"",size:"small"},{icon:l(()=>[a(k(ze))]),default:l(()=>[e[14]||(e[14]=c(" 删除 ",-1))]),_:1})]),_:1},8,["onConfirm"])):h("",!0)]),emptyText:l(()=>[a(ge,{description:"暂无 WebAuthn 凭证,点击「注册新凭证」添加"})]),_:1},8,["data-source","pagination"])),a(ae,{open:$.value,"onUpdate:open":e[2]||(e[2]=o=>$.value=o),title:"注册 WebAuthn 凭证","confirm-loading":q.value,onOk:pe,"ok-text":"注册","cancel-text":"取消"},{default:l(()=>[a(te,{"label-col":{span:6},"wrapper-col":{span:18},style:{"margin-top":"16px"}},{default:l(()=>[a(z,{label:"凭证名称",required:""},{default:l(()=>[a(X,{value:D.value,"onUpdate:value":e[1]||(e[1]=o=>D.value=o),placeholder:"例如:YubiKey-5, TouchID"},null,8,["value"])]),_:1})]),_:1})]),_:1},8,["open","confirm-loading"])]),_:1}),a(H,{key:"sso"},{tab:l(()=>[a(k(Le)),e[15]||(e[15]=c(" SSO 配置 ",-1))]),default:l(()=>[B.value?(i(),y("div",Ke,[a(b,{size:"large"})])):(i(),y(j,{key:1},[a(we,{gutter:[16,16],style:{"margin-bottom":"20px"}},{default:l(()=>[(i(!0),y(j,null,se(E.value,o=>(i(),O(ke,{xs:12,sm:6,key:o.label},{default:l(()=>[a(W,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"},size:"small"},{default:l(()=>[a(xe,{title:o.label,value:o.value,"value-style":{color:o.color,fontSize:"20px"}},null,8,["title","value","value-style"])]),_:2},1024)]),_:2},1024))),128))]),_:1}),a(W,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"},title:"当前 SSO 配置"},{default:l(()=>[a(Se,{column:{xs:1,sm:2},bordered:"",size:"small",style:{background:"var(--bg-card)"}},{default:l(()=>[a(R,{label:"提供商"},{default:l(()=>[a(d,{color:p.value.provider?"blue":"default"},{default:l(()=>[c(m(p.value.provider||"未配置"),1)]),_:1},8,["color"])]),_:1}),a(R,{label:"Client ID"},{default:l(()=>[g("span",Me,m(p.value.clientId||"-"),1)]),_:1}),a(R,{label:"Redirect URL"},{default:l(()=>[g("span",qe,m(p.value.redirectUrl||"-"),1)]),_:1}),a(R,{label:"状态"},{default:l(()=>[a(d,{color:p.value.enabled?"green":"default"},{default:l(()=>[c(m(p.value.enabled?"已启用":"未启用"),1)]),_:1},8,["color"])]),_:1})]),_:1}),g("div",Be,[a(n,{type:"primary",onClick:e[3]||(e[3]=o=>P.value=!0)},{icon:l(()=>[a(k(ne))]),default:l(()=>[e[16]||(e[16]=c(" 配置 SSO ",-1))]),_:1})])]),_:1})],64)),a(ae,{open:P.value,"onUpdate:open":e[8]||(e[8]=o=>P.value=o),title:"配置 SSO","confirm-loading":F.value,onOk:ve,"ok-text":"保存","cancel-text":"取消",width:"520px"},{default:l(()=>[a(te,{"label-col":{span:6},"wrapper-col":{span:18},style:{"margin-top":"16px"}},{default:l(()=>[a(z,{label:"提供商",required:""},{default:l(()=>[a(he,{value:f.value.provider,"onUpdate:value":e[4]||(e[4]=o=>f.value.provider=o),placeholder:"选择 SSO 提供商"},{default:l(()=>[a(Q,{value:"OIDC"},{default:l(()=>[...e[17]||(e[17]=[c("OIDC",-1)])]),_:1}),a(Q,{value:"SAML"},{default:l(()=>[...e[18]||(e[18]=[c("SAML",-1)])]),_:1}),a(Q,{value:"LDAP"},{default:l(()=>[...e[19]||(e[19]=[c("LDAP",-1)])]),_:1})]),_:1},8,["value"])]),_:1}),a(z,{label:"Client ID",required:""},{default:l(()=>[a(X,{value:f.value.clientId,"onUpdate:value":e[5]||(e[5]=o=>f.value.clientId=o),placeholder:"输入 Client ID"},null,8,["value"])]),_:1}),a(z,{label:"Client Secret"},{default:l(()=>[a(Ce,{value:f.value.clientSecret,"onUpdate:value":e[6]||(e[6]=o=>f.value.clientSecret=o),placeholder:"输入 Client Secret"},null,8,["value"])]),_:1}),a(z,{label:"Issuer URL"},{default:l(()=>[a(X,{value:f.value.issuerUrl,"onUpdate:value":e[7]||(e[7]=o=>f.value.issuerUrl=o),placeholder:"https://sso.example.com"},null,8,["value"])]),_:1})]),_:1})]),_:1},8,["open","confirm-loading"])]),_:1}),a(H,{key:"2fa"},{tab:l(()=>[a(k(oe)),e[20]||(e[20]=c(" 双因素认证 ",-1))]),default:l(()=>[Y.value?(i(),y("div",Ve,[a(b,{size:"large"})])):(i(),y(j,{key:1},[a(W,{style:{background:"var(--bg-card)","border-color":"var(--border-color)","margin-bottom":"20px"},title:"TOTP 双因素认证"},{default:l(()=>[g("div",Fe,[e[21]||(e[21]=g("span",{style:{color:"var(--text-primary)","font-size":"14px"}},"状态:",-1)),a(d,{color:w.value?"green":"default",style:{"font-size":"13px"}},{default:l(()=>[c(m(w.value?"已启用":"未启用"),1)]),_:1},8,["color"])]),a(v,null,{default:l(()=>[w.value?(i(),O(C,{key:1,title:"确定要禁用双因素认证吗?这会降低账户安全性。","ok-text":"确定禁用","cancel-text":"取消",onConfirm:me},{default:l(()=>[a(n,{danger:"",loading:U.value},{default:l(()=>[...e[23]||(e[23]=[c(" 禁用 ",-1)])]),_:1},8,["loading"])]),_:1})):(i(),O(n,{key:0,type:"primary",loading:U.value,onClick:ye},{icon:l(()=>[a(k(oe))]),default:l(()=>[e[22]||(e[22]=c(" 启用 TOTP ",-1))]),_:1},8,["loading"]))]),_:1}),A.value?(i(),y("div",Ee,[g("pre",Je,m(A.value),1)])):h("",!0)]),_:1}),a(W,{style:{background:"var(--bg-card)","border-color":"var(--border-color)"},title:"恢复码"},{default:l(()=>[e[25]||(e[25]=g("p",{style:{color:"var(--text-secondary)","margin-bottom":"12px"}}," 恢复码可在丢失 TOTP 设备时用于登录。请妥善保管。 ",-1)),a(n,{loading:G.value,onClick:be},{icon:l(()=>[a(k(le))]),default:l(()=>[e[24]||(e[24]=c(" 生成恢复码 ",-1))]),_:1},8,["loading"]),S.value.length>0?(i(),y("div",Ye,[a(Ue,{type:"warning","show-icon":"",style:{"margin-bottom":"12px"},message:"请立即保存这些恢复码,关闭后将无法再次查看。"}),g("div",Ze,[(i(!0),y(j,null,se(S.value,(o,_)=>(i(),y("div",{key:_,style:{"font-family":"monospace","font-size":"14px",color:"#e0e0e0",padding:"4px 0","letter-spacing":"2px"}},m(_+1)+". "+m(o),1))),128))])])):h("",!0)]),_:1})],64))]),_:1})]),_:1},8,["activeKey"])])}}},lt=Ie(Ge,[["__scopeId","data-v-a4bec262"]]);export{lt as default};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{V as H,f as b,o as K,a3 as v,a1 as _,k as s,Z as l,X as p,Y as c,G as m,u as h,W as L,a2 as P,a5 as y,A as X,F as V,a7 as D,a4 as W,c as Z}from"./vendor-CN0Iv_qZ.js";import{u as Q}from"./ws-Dma34ig_.js";import{_ as ee}from"./_plugin-vue_export-helper-DlAUqK2U.js";import{O as te,q as ae,N as C}from"./antd-DEjZPGMj.js";const se=H("workflow",()=>{const f=Q(),o=b([]),t=b(null),x=b([]),w=b("idle"),R=b(!1),z=b(null);async function E(){R.value=!0,z.value=null;try{await f.waitConnected();const e=await f.sendRaw({type:"workflow-list"});return o.value=Array.isArray(e.workflows)?e.workflows:[],o.value}catch(e){throw z.value=e.message,e}finally{R.value=!1}}async function I(e){await f.waitConnected();const n=await f.sendRaw({type:"workflow-get",id:e});return t.value=n.workflow||null,t.value}async function J(e){await f.waitConnected();const n=await f.sendRaw({type:"workflow-save",workflow:e});if(n.saved){const i=o.value.findIndex(r=>r.id===e.id);i>=0?o.value.splice(i,1,e):o.value.push(e)}return n}async function B(e){await f.waitConnected();const n=await f.sendRaw({type:"workflow-remove",id:e});return n.removed&&(o.value=o.value.filter(i=>i.id!==e)),n}async function q(e,{onEvent:n}={}){await f.waitConnected(),x.value=[],w.value="running";const i=f.onMessage(r=>{!r||typeof r.type!="string"||r.type.startsWith("workflow:")&&(x.value.push(r),n&&n(r),r.type==="workflow:done"&&(w.value=r.status||"completed"))});try{return await f.sendRaw({type:"workflow-run",id:e},12e4)}catch(r){throw w.value="failed",z.value=r.message,r}finally{i()}}function M(e){const n=[];if(!e||typeof e!="object")return{valid:!1,errors:["workflow must be an object"]};if(e.id||n.push("id required"),e.name||n.push("name required"),!Array.isArray(e.steps)||e.steps.length===0)n.push("steps required");else{let g=function(u){O.set(u,j);for(const $ of r.get(u)||[]){if(!r.has($)){n.push(`unknown dependency: ${$}`);continue}const A=O.get($);if(A===j){n.push(`cycle via ${u} -> ${$}`);return}A===N&&g($)}O.set(u,S)};const i=new Set;for(const u of e.steps)u.id||n.push("step.id required"),i.has(u.id)&&n.push(`duplicate step id: ${u.id}`),i.add(u.id);const r=new Map;for(const u of e.steps)r.set(u.id,u.dependsOn||[]);const N=0,j=1,S=2,O=new Map([...r.keys()].map(u=>[u,N]));for(const u of r.keys())O.get(u)===N&&g(u)}return{valid:n.length===0,errors:n}}function d(e){return JSON.stringify(e,null,2)}return{workflows:o,current:t,runEvents:x,runStatus:w,loading:R,error:z,list:E,get:I,save:J,remove:B,run:q,validateLocal:M,exportJson:d}}),ne={style:{display:"flex","align-items":"center","justify-content":"space-between","margin-bottom":"24px"}},le={style:{flex:"1"}},oe={style:{"font-weight":"500"}},re={style:{color:"#888","font-size":"12px"}},ue={style:{color:"#888","font-size":"12px"}},ie={key:0,style:{"margin-top":"12px",color:"#d32f2f"}},de={style:{color:"#1976d2"}},ce={key:0},pe={key:1},fe={key:2,style:{color:"#555"}},ve={__name:"WorkflowEditor",setup(f){const o=se(),t=b(null),x=b(!1),w=Z(()=>t.value?o.validateLocal(t.value):null);K(()=>o.list().catch(()=>{}));function R(){t.value={id:"",name:"",description:"",steps:[{id:"step1",message:"",dependsOn:[]}]}}async function z(d){try{const e=await o.get(d);e&&(t.value=JSON.parse(JSON.stringify(e)),t.value.steps||(t.value.steps=[]))}catch(e){C.error(`加载失败: ${e.message}`)}}function E(){t.value.steps||(t.value.steps=[]),t.value.steps.push({id:`step${t.value.steps.length+1}`,message:"",dependsOn:[]})}function I(d){t.value.steps.splice(d,1)}async function J(){const d=o.validateLocal(t.value);if(!d.valid){C.error(d.errors[0]);return}try{await o.save(t.value),C.success("保存成功")}catch(e){C.error(`保存失败: ${e.message}`)}}async function B(d){try{await o.remove(d),t.value?.id===d&&(t.value=null),C.success("已删除")}catch(e){C.error(`删除失败: ${e.message}`)}}async function q(){x.value=!0;try{await o.run(t.value.id),C.success(`运行完成:${o.runStatus}`)}catch(d){C.error(`运行失败: ${d.message}`)}finally{x.value=!1}}function M(){const d=o.exportJson(t.value),e=new Blob([d],{type:"application/json"}),n=URL.createObjectURL(e),i=document.createElement("a");i.href=n,i.download=`${t.value.id||"workflow"}.json`,i.click(),URL.revokeObjectURL(n)}return(d,e)=>{const n=p("a-button"),i=p("a-space"),r=p("a-empty"),N=p("a-list-item"),j=p("a-list"),S=p("a-card"),O=p("a-col"),g=p("a-input"),u=p("a-form-item"),$=p("a-divider"),A=p("a-select"),F=p("a-input-group"),G=p("a-textarea"),T=p("a-form"),Y=p("a-row");return c(),v("div",null,[_("div",ne,[e[6]||(e[6]=_("div",null,[_("h2",{class:"page-title"},"工作流编辑器"),_("p",{class:"page-sub"},"创建、编辑、运行 Cowork 工作流(N1 — 初版:表单编辑,画布视图规划中)")],-1)),s(i,null,{default:l(()=>[s(n,{onClick:R,type:"primary"},{icon:l(()=>[s(h(te))]),default:l(()=>[e[4]||(e[4]=m(" 新建 ",-1))]),_:1}),s(n,{ghost:"",loading:h(o).loading,onClick:e[0]||(e[0]=a=>h(o).list())},{icon:l(()=>[s(h(ae))]),default:l(()=>[e[5]||(e[5]=m(" 刷新 ",-1))]),_:1},8,["loading"])]),_:1})]),s(Y,{gutter:16},{default:l(()=>[s(O,{span:8},{default:l(()=>[s(S,{title:"工作流列表",size:"small"},{default:l(()=>[h(o).workflows.length?(c(),L(j,{key:1,"data-source":h(o).workflows,size:"small"},{renderItem:l(({item:a})=>[s(N,{class:P({active:t.value?.id===a.id}),style:{cursor:"pointer"},onClick:U=>z(a.id)},{default:l(()=>[_("div",le,[_("div",oe,y(a.name||a.id),1),_("div",re,y((a.steps||[]).length)+" 步骤 ",1)]),s(n,{size:"small",danger:"",type:"text",onClick:X(U=>B(a.id),["stop"])},{default:l(()=>[...e[7]||(e[7]=[m("删除",-1)])]),_:1},8,["onClick"])]),_:2},1032,["class","onClick"])]),_:1},8,["data-source"])):(c(),L(r,{key:0,description:"暂无工作流"}))]),_:1})]),_:1}),s(O,{span:16},{default:l(()=>[t.value?(c(),L(S,{key:0,size:"small"},{title:l(()=>[m(" 编辑: "+y(t.value.name||t.value.id),1)]),extra:l(()=>[s(i,null,{default:l(()=>[s(n,{size:"small",onClick:M},{default:l(()=>[...e[8]||(e[8]=[m("导出 JSON",-1)])]),_:1}),s(n,{size:"small",loading:x.value,onClick:q,disabled:!t.value.id},{default:l(()=>[...e[9]||(e[9]=[m(" 运行 ",-1)])]),_:1},8,["loading","disabled"]),s(n,{size:"small",type:"primary",onClick:J},{default:l(()=>[...e[10]||(e[10]=[m("保存",-1)])]),_:1})]),_:1})]),default:l(()=>[s(T,{layout:"vertical",model:t.value},{default:l(()=>[s(u,{label:"ID (唯一标识)"},{default:l(()=>[s(g,{value:t.value.id,"onUpdate:value":e[1]||(e[1]=a=>t.value.id=a),placeholder:"my-workflow"},null,8,["value"])]),_:1}),s(u,{label:"名称"},{default:l(()=>[s(g,{value:t.value.name,"onUpdate:value":e[2]||(e[2]=a=>t.value.name=a),placeholder:"我的工作流"},null,8,["value"])]),_:1}),s(u,{label:"描述"},{default:l(()=>[s(g,{value:t.value.description,"onUpdate:value":e[3]||(e[3]=a=>t.value.description=a),placeholder:"(可选)"},null,8,["value"])]),_:1}),s($,null,{default:l(()=>[...e[11]||(e[11]=[m("步骤",-1)])]),_:1}),(c(!0),v(V,null,D(t.value.steps,(a,U)=>(c(),v("div",{key:U,class:"step-card"},[s(i,{style:{width:"100%","margin-bottom":"8px"},direction:"vertical"},{default:l(()=>[s(F,{compact:""},{default:l(()=>[s(g,{value:a.id,"onUpdate:value":k=>a.id=k,placeholder:"step-id",style:{width:"30%"}},null,8,["value","onUpdate:value"]),s(A,{value:a.dependsOn,"onUpdate:value":k=>a.dependsOn=k,mode:"tags",placeholder:"dependsOn",style:{width:"70%"}},null,8,["value","onUpdate:value"])]),_:2},1024),s(G,{value:a.message,"onUpdate:value":k=>a.message=k,rows:2,placeholder:"任务 prompt(支持 \\${step.<id>.summary} 占位)"},null,8,["value","onUpdate:value"]),s(g,{value:a.when,"onUpdate:value":k=>a.when=k,placeholder:"when 条件(可选,如 step.s1.status === 'completed')"},null,8,["value","onUpdate:value"]),s(i,null,{default:l(()=>[s(n,{size:"small",danger:"",onClick:k=>I(U)},{default:l(()=>[...e[12]||(e[12]=[m("删除",-1)])]),_:1},8,["onClick"]),_("span",ue," step "+y(U+1)+" / "+y(t.value.steps.length),1)]),_:2},1024)]),_:2},1024)]))),128)),s(n,{block:"",onClick:E},{default:l(()=>[...e[13]||(e[13]=[m("+ 添加步骤",-1)])]),_:1})]),_:1},8,["model"]),w.value&&!w.value.valid?(c(),v("div",ie,[(c(!0),v(V,null,D(w.value.errors,a=>(c(),v("div",{key:a},"• "+y(a),1))),128))])):W("",!0)]),_:1})):(c(),L(S,{key:1,size:"small"},{default:l(()=>[s(r,{description:"从左侧选择工作流或新建一个"})]),_:1})),h(o).runEvents.length?(c(),L(S,{key:2,size:"small",title:"运行日志",style:{"margin-top":"12px"}},{default:l(()=>[(c(!0),v(V,null,D(h(o).runEvents,(a,U)=>(c(),v("div",{key:U,style:{"font-family":"monospace","font-size":"12px","margin-bottom":"4px"}},[_("span",de,y(a.type),1),a.stepId?(c(),v("span",ce," ["+y(a.stepId)+"]",1)):W("",!0),a.status?(c(),v("span",pe," → "+y(a.status),1)):W("",!0),a.summary?(c(),v("span",fe," — "+y(a.summary),1)):W("",!0)]))),128))]),_:1})):W("",!0)]),_:1})]),_:1})])}}},ge=ee(ve,[["__scopeId","data-v-0d6dcf38"]]);export{ge as default};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
.step-card[data-v-0d6dcf38]{background:#fafafa;border:1px solid #eee;border-radius:4px;padding:12px;margin-bottom:12px}.active[data-v-0d6dcf38]{background:#e3f2fd}.page-title[data-v-0d6dcf38]{margin:0;font-size:20px}.page-sub[data-v-0d6dcf38]{margin:4px 0 0;color:#888;font-size:13px}
|