pi-webapp 0.1.5 → 0.1.7
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 +16 -3
- package/README.zh-CN.md +14 -3
- package/THIRD_PARTY_LICENSE.txt +24 -0
- package/bin/pi-webapp.mjs +93 -5
- package/dist/extension.js +9 -6
- package/package.json +28 -5
- package/web/dist/assets/KaTeX_AMS-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_AMS-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_AMS-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Bold.ttf +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Bold.woff +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Bold.woff2 +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Caligraphic-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Bold.ttf +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Bold.woff +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Bold.woff2 +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Fraktur-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Main-Bold.ttf +0 -0
- package/web/dist/assets/KaTeX_Main-Bold.woff +0 -0
- package/web/dist/assets/KaTeX_Main-Bold.woff2 +0 -0
- package/web/dist/assets/KaTeX_Main-BoldItalic.ttf +0 -0
- package/web/dist/assets/KaTeX_Main-BoldItalic.woff +0 -0
- package/web/dist/assets/KaTeX_Main-BoldItalic.woff2 +0 -0
- package/web/dist/assets/KaTeX_Main-Italic.ttf +0 -0
- package/web/dist/assets/KaTeX_Main-Italic.woff +0 -0
- package/web/dist/assets/KaTeX_Main-Italic.woff2 +0 -0
- package/web/dist/assets/KaTeX_Main-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Main-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Main-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Math-BoldItalic.ttf +0 -0
- package/web/dist/assets/KaTeX_Math-BoldItalic.woff +0 -0
- package/web/dist/assets/KaTeX_Math-BoldItalic.woff2 +0 -0
- package/web/dist/assets/KaTeX_Math-Italic.ttf +0 -0
- package/web/dist/assets/KaTeX_Math-Italic.woff +0 -0
- package/web/dist/assets/KaTeX_Math-Italic.woff2 +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Bold.ttf +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Bold.woff +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Bold.woff2 +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Italic.ttf +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Italic.woff +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Italic.woff2 +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_SansSerif-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Script-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Script-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Script-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Size1-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Size1-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Size1-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Size2-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Size2-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Size2-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Size3-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Size3-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Size4-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Size4-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Size4-Regular.woff2 +0 -0
- package/web/dist/assets/KaTeX_Typewriter-Regular.ttf +0 -0
- package/web/dist/assets/KaTeX_Typewriter-Regular.woff +0 -0
- package/web/dist/assets/KaTeX_Typewriter-Regular.woff2 +0 -0
- package/web/dist/assets/app.js +504 -55
- package/web/dist/assets/asciidoc.js +1 -0
- package/web/dist/assets/bat.js +1 -0
- package/web/dist/assets/bibtex.js +1 -0
- package/web/dist/assets/c.js +1 -0
- package/web/dist/assets/clojure.js +1 -0
- package/web/dist/assets/cmake.js +1 -0
- package/web/dist/assets/cpp.js +1 -0
- package/web/dist/assets/csharp.js +1 -0
- package/web/dist/assets/css.js +1 -0
- package/web/dist/assets/csv.js +1 -0
- package/web/dist/assets/dart.js +1 -0
- package/web/dist/assets/diff.js +1 -0
- package/web/dist/assets/dotenv.js +1 -0
- package/web/dist/assets/elixir.js +1 -0
- package/web/dist/assets/erlang.js +1 -0
- package/web/dist/assets/fish.js +1 -0
- package/web/dist/assets/fsharp.js +1 -0
- package/web/dist/assets/go.js +1 -0
- package/web/dist/assets/graphql.js +1 -0
- package/web/dist/assets/groovy.js +1 -0
- package/web/dist/assets/haskell.js +1 -0
- package/web/dist/assets/hcl.js +1 -0
- package/web/dist/assets/html-derivative.js +1 -0
- package/web/dist/assets/html.js +1 -0
- package/web/dist/assets/http.js +1 -0
- package/web/dist/assets/ini.js +1 -0
- package/web/dist/assets/java.js +1 -0
- package/web/dist/assets/javascript.js +1 -0
- package/web/dist/assets/julia.js +1 -0
- package/web/dist/assets/kotlin.js +1 -0
- package/web/dist/assets/latex.js +1 -0
- package/web/dist/assets/less.js +1 -0
- package/web/dist/assets/log.js +1 -0
- package/web/dist/assets/lua.js +1 -0
- package/web/dist/assets/make.js +1 -0
- package/web/dist/assets/markdown.js +1 -0
- package/web/dist/assets/mdx.js +1 -0
- package/web/dist/assets/nix.js +1 -0
- package/web/dist/assets/perl.js +1 -0
- package/web/dist/assets/php.js +1 -0
- package/web/dist/assets/powershell.js +1 -0
- package/web/dist/assets/proto.js +1 -0
- package/web/dist/assets/python.js +1 -0
- package/web/dist/assets/r.js +1 -0
- package/web/dist/assets/rst.js +1 -0
- package/web/dist/assets/ruby.js +1 -0
- package/web/dist/assets/rust.js +1 -0
- package/web/dist/assets/scala.js +1 -0
- package/web/dist/assets/scss.js +1 -0
- package/web/dist/assets/sql.js +1 -0
- package/web/dist/assets/style.css +1 -1
- package/web/dist/assets/svelte.js +1 -0
- package/web/dist/assets/swift.js +1 -0
- package/web/dist/assets/system-verilog.js +1 -0
- package/web/dist/assets/toml.js +1 -0
- package/web/dist/assets/vb.js +1 -0
- package/web/dist/assets/verilog.js +1 -0
- package/web/dist/assets/vue.js +1 -0
- package/web/dist/assets/xml.js +1 -0
- package/web/dist/assets/yaml.js +1 -0
package/dist/extension.js
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
|
-
import{dirname as
|
|
2
|
-
`,{mode:
|
|
3
|
-
`,{mode:
|
|
4
|
-
`),
|
|
1
|
+
import{delimiter as yi,dirname as vi,join as ee,resolve as we}from"node:path";import{realpathSync as ki,watch as bi}from"node:fs";import{realpath as re}from"node:fs/promises";import{fileURLToPath as Pi}from"node:url";import{DefaultPackageManager as pt,getAgentDir as j,ModelRuntime as Ei,SessionManager as ut,SettingsManager as Si}from"@earendil-works/pi-coding-agent";import{getSupportedThinkingLevels as Ii}from"@earendil-works/pi-ai";import{randomBytes as lr,timingSafeEqual as dr}from"node:crypto";import{readFile as pr,readdir as ur}from"node:fs/promises";import{createServer as fr}from"node:http";import{join as Oe}from"node:path";import{mkdir as ht,opendir as yt,stat as vt}from"node:fs/promises";import{homedir as kt}from"node:os";import{basename as bt,dirname as he,join as ye,posix as Pt,resolve as ve,win32 as Et}from"node:path";function ke(r){return process.platform==="win32"?Et.isAbsolute(r)&&/^(?:[A-Za-z]:[\\/]|[\\/]{2}[^\\/]+[\\/]+[^\\/]+)/.test(r):Pt.isAbsolute(r)}function St(r,e,t){if(r.length===t&&e.name.localeCompare(r[r.length-1].name)>=0)return!0;let n=0,s=r.length;for(;n<s;){let a=n+s>>>1;e.name.localeCompare(r[a].name)<0?s=a:n=a+1}return r.splice(n,0,e),r.length<=t?!1:(r.pop(),!0)}async function be(r){if(r!==void 0&&!ke(r))throw new Error("\u76EE\u5F55\u8DEF\u5F84\u5FC5\u987B\u662F\u7EDD\u5BF9\u8DEF\u5F84");let e=kt(),t=ve(r??e),n=[];for(let o=t;;o=he(o)){let d=he(o);if(n.unshift({name:d===o?o:bt(o),path:o,hidden:!1}),d===o)break}let s=[],a=!1,u=await yt(t);for await(let o of u)!o.isDirectory()&&!o.isSymbolicLink()||St(s,{name:o.name,isDirectory:o.isDirectory(),isSymbolicLink:o.isSymbolicLink()},1001)&&(a=!0);let p=[];for(let o of s){let d=ye(t,o.name);if(!o.isDirectory&&o.isSymbolicLink)try{if(!(await vt(d)).isDirectory())continue}catch{continue}if(p.length===1e3){a=!0;break}p.push({name:o.name,path:d,hidden:o.name.startsWith(".")})}return{path:t,home:e,crumbs:n,entries:p,truncated:a}}async function Pe(r,e){if(!ke(r))throw new Error("\u7236\u76EE\u5F55\u8DEF\u5F84\u5FC5\u987B\u662F\u7EDD\u5BF9\u8DEF\u5F84");if(!e.trim()||e==="."||e===".."||/[/\\]/.test(e))throw new Error("\u6587\u4EF6\u5939\u540D\u79F0\u65E0\u6548");let t=ye(ve(r),e);return await ht(t),t}import{execFile as It}from"node:child_process";import{accessSync as xt,constants as Ct}from"node:fs";import{delimiter as At,join as Mt}from"node:path";var Wt=(r,e,t)=>new Promise((n,s)=>{It(r,[...e],{encoding:"utf8",signal:t,windowsHide:!0},(a,u,p)=>{a?s(Object.assign(new Error(a.message,{cause:a}),{code:a.code,stdout:u,stderr:p})):n({stdout:u,stderr:p})})});function Tt(r){for(let e of(r??"").split(At))if(e)for(let t of["zenity","kdialog"])try{return xt(Mt(e,t),Ct.X_OK),!0}catch{}return!1}function Ee(r=process.platform,e=process.env){return e.SSH_CONNECTION||e.SSH_TTY?"browse":r==="darwin"||r==="linux"&&(e.DISPLAY||e.WAYLAND_DISPLAY)&&Tt(e.PATH)?"native":"browse"}function F(r){if(!(typeof r!="object"||r===null||!("code"in r)))return typeof r.code=="string"||typeof r.code=="number"?r.code:void 0}function Rt(r){return typeof r=="object"&&r!==null&&"stderr"in r&&typeof r.stderr=="string"?r.stderr:""}function ie(r){return r.replace(/[\r\n]+$/,"")||null}async function Se(r,e=process.platform,t=Wt){if(e==="darwin")try{let n=await t("osascript",["-e",'set selectedFolder to choose folder with prompt "Select Workspace Directory"',"-e","POSIX path of selectedFolder"],r);return ie(n.stdout)}catch(n){if(!r.aborted&&F(n)===1&&/(?:User canceled|-128)/i.test(Rt(n)))return null;throw n}if(e==="linux"){try{return ie((await t("zenity",["--file-selection","--directory","--title=Select Workspace Directory"],r)).stdout)}catch(n){if(r.aborted)throw n;if(F(n)===1)return null;if(F(n)!=="ENOENT")throw n}try{return ie((await t("kdialog",["--getexistingdirectory",".","--title","Select Workspace Directory"],r)).stdout)}catch(n){if(r.aborted)throw n;if(F(n)===1)return null;throw n}}throw new Error(`\u5F53\u524D\u7CFB\u7EDF\u4E0D\u652F\u6301\u672C\u5730\u76EE\u5F55\u9009\u62E9\u5668\uFF1A${e}`)}import{createHash as Nt,randomUUID as _t}from"node:crypto";import{mkdir as jt,readFile as Bt,writeFile as Lt}from"node:fs/promises";import{join as Ie}from"node:path";import{getAgentDir as Ot}from"@earendil-works/pi-coding-agent";var H=20*1024*1024,xe=20,Ut=/^(?:con|prn|aux|nul|com[1-9]|lpt[1-9])$/iu;function Vt(r){let e=r.indexOf("."),t=(e<0?r:r.slice(0,e)).replace(/[. ]+$/u,"");return Ut.test(t)}function Dt(r,e){let t=0,n="";for(let s of Buffer.from(r).toString("utf8")){let a=Buffer.byteLength(s);if(t+a>e)break;n+=s,t+=a}return n}function $t(r){if(r===void 0)return"file";let t=r.slice(Math.max(r.lastIndexOf("/"),r.lastIndexOf("\\"))+1).replace(/[\u0000-\u001f\u007f]/g,"").replace(/[<>:"|?*]/g,"_").trim().replace(/[. ]+$/u,"");return Vt(t)&&(t=`_${t}`),t=Dt(t,255).replace(/[. ]+$/u,""),t===""||t==="."||t===".."?"file":t}function Ft(r){return r.length>=8&&r.subarray(0,8).equals(Buffer.from([137,80,78,71,13,10,26,10]))?"image/png":r.length>=3&&r.subarray(0,3).equals(Buffer.from([255,216,255]))?"image/jpeg":r.length>=6&&["GIF87a","GIF89a"].includes(r.toString("ascii",0,6))?"image/gif":r.length>=12&&r.toString("ascii",0,4)==="RIFF"&&r.toString("ascii",8,12)==="WEBP"?"image/webp":null}async function Ce(r,e,t,n){if(n.byteLength===0||n.byteLength>H)throw new Error("\u6587\u4EF6\u4E3A\u7A7A\u6216\u8D85\u8FC7 20 MB");let s=$t(e),a=Nt("sha256").update(n).digest("hex"),u=Ie(Ot(),"pi-web","attachments",a);await jt(u,{recursive:!0});let p=Ie(u,s);try{await Lt(p,n,{flag:"wx",mode:384})}catch(o){if(!(o instanceof Error&&"code"in o&&o.code==="EEXIST"))throw o}return{id:_t(),name:s,bytes:n.byteLength,path:p,mediaType:Ft(n)??t.replace(/^image\//,"application/"),sessionId:r}}async function Ae(r){return{type:"image",data:(await Bt(r.path)).toString("base64"),mimeType:r.mediaType}}import{randomBytes as Ht}from"node:crypto";function Me(r,e,t){return r!=="openai-codex"||e!=="oauth"?t:{...t,prompt:n=>n.type==="select"&&n.options.some(s=>s.id==="browser")&&n.options.some(s=>s.id==="device_code")?Promise.resolve("browser"):t.prompt(n)}}var G=class{flows=new Map;start(e,t,n,s){let a=this.getActive();if(a){if(a.providerId===e&&a.method===t&&s===void 0)return a;throw new Error("\u5176\u4ED6\u63D0\u4F9B\u65B9\u7684\u767B\u5F55\u6B63\u5728\u8FDB\u884C\uFF0C\u8BF7\u5148\u5B8C\u6210\u6216\u53D6\u6D88\u5F53\u524D\u767B\u5F55")}this.flows.clear();let u=Ht(18).toString("base64url"),p={view:{id:u,providerId:e,method:t,status:"running"},controller:new AbortController};return this.flows.set(u,p),n(e,t,{signal:p.controller.signal,notify:o=>{p.view={...p.view,event:o,...o.type==="auth_url"||o.type==="device_code"?{authorization:o}:{}}},prompt:o=>{if(o.type==="secret"&&s!==void 0){let d=s;return s=void 0,Promise.resolve(d)}return new Promise((d,f)=>{let{signal:m,...v}=o;p.answer=d,p.reject=f,p.view={...p.view,status:"waiting",prompt:v},m?.aborted?f(new Error("\u767B\u5F55\u8F93\u5165\u5DF2\u53D6\u6D88")):m?.addEventListener("abort",()=>f(new Error("\u767B\u5F55\u8F93\u5165\u5DF2\u53D6\u6D88")),{once:!0})})}}).then(()=>{p.view.status!=="cancelled"&&(p.view={id:u,providerId:e,method:t,status:"done"})}).catch(()=>{p.view.status!=="cancelled"&&(p.view={id:u,providerId:e,method:t,status:"error",error:"\u767B\u5F55\u5931\u8D25\uFF0C\u8BF7\u68C0\u67E5\u63D0\u4F9B\u65B9\u63D0\u793A\u5E76\u91CD\u8BD5\u3002"})}),{...p.view}}get(e){let t=this.flows.get(e)?.view;return t?{...t}:void 0}getActive(){let e=[...this.flows.values()].find(({view:t})=>t.status==="running"||t.status==="waiting")?.view;return e?{...e}:void 0}respond(e,t){let n=this.flows.get(e);if(!n?.answer||n.view.status!=="waiting"||n.view.prompt?.type==="select"&&!n.view.prompt.options.some(a=>a.id===t))return!1;let s=n.answer;return n.answer=void 0,n.reject=void 0,n.view={...n.view,status:"running",prompt:void 0},s(t),!0}cancel(e){let t=this.flows.get(e);return!t||t.view.status==="done"||t.view.status==="error"?!1:(t.view={...t.view,status:"cancelled",prompt:void 0},t.controller.abort(),t.reject?.(new Error("\u767B\u5F55\u5DF2\u53D6\u6D88")),t.answer=void 0,t.reject=void 0,!0)}close(){for(let e of this.flows.keys())this.cancel(e);this.flows.clear()}};import{randomBytes as Gt}from"node:crypto";import{readFile as Jt,rename as zt,rm as qt,stat as Kt,writeFile as Yt,mkdir as Xt}from"node:fs/promises";import{dirname as Qt}from"node:path";var Zt=["openai-completions","openai-responses","anthropic-messages"];function ne(r){if(!r||typeof r!="object")return!1;let e=r;if(typeof e.id!="string"||!/^[a-z0-9][a-z0-9._-]{0,63}$/.test(e.id)||typeof e.name!="string"||!e.name.trim()||e.name.length>100||typeof e.modelId!="string"||!e.modelId.trim()||e.modelId.length>200||!Zt.includes(e.api)||typeof e.baseUrl!="string"||e.baseUrl.length>2048)return!1;try{let t=new URL(e.baseUrl);return(t.protocol==="https:"||t.protocol==="http:")&&!!t.hostname&&!t.username&&!t.password&&!t.hash}catch{return!1}}async function We(r,e){if(!ne(e))throw new Error("\u81EA\u5B9A\u4E49\u63D0\u4F9B\u65B9\u540D\u79F0\u3001\u5730\u5740\u6216\u6A21\u578B\u65E0\u6548");let t;try{t=await Jt(r,"utf8")}catch(p){if(p.code!=="ENOENT")throw p}let n;if(t===void 0)n={providers:{}};else{try{n=JSON.parse(t)}catch{throw new Error("models.json \u542B\u6CE8\u91CA\u6216\u683C\u5F0F\u9519\u8BEF\uFF0C\u8BF7\u5728\u914D\u7F6E\u6587\u4EF6\u4E2D\u624B\u52A8\u6DFB\u52A0\u63D0\u4F9B\u65B9")}if(!n||typeof n!="object"||!n.providers||typeof n.providers!="object"||Array.isArray(n.providers))throw new Error("models.json \u7ED3\u6784\u65E0\u6548")}if(Object.hasOwn(n.providers,e.id))throw new Error("\u63D0\u4F9B\u65B9\u5DF2\u5B58\u5728");let s={...n,providers:{...n.providers,[e.id]:{name:e.name.trim(),baseUrl:e.baseUrl,api:e.api,models:[{id:e.modelId.trim()}]}}};await Xt(Qt(r),{recursive:!0});let a=t===void 0?384:(await Kt(r)).mode&511,u=`${r}.pi-web-${Gt(6).toString("hex")}.tmp`;try{await Yt(u,`${JSON.stringify(s,null,2)}
|
|
2
|
+
`,{mode:a,flag:"wx"}),await zt(u,r)}finally{await qt(u,{force:!0})}}import{randomBytes as er}from"node:crypto";import{mkdir as tr,readFile as rr,rename as ir,rm as nr,stat as sr,writeFile as or}from"node:fs/promises";import{dirname as ar}from"node:path";function Te(r){if(!r||r.length>2048)return!1;try{let e=new URL(r);return(e.protocol==="https:"||e.protocol==="http:")&&!!e.hostname&&!e.username&&!e.password&&!e.search&&!e.hash}catch{return!1}}function Re(r){if(!r||typeof r!="object")return!1;let e=r;return e.action==="save"?(e.originalId===void 0||typeof e.originalId=="string")&&Ne(e.model):e.action==="base_url"?e.baseUrl===null||typeof e.baseUrl=="string"&&Te(e.baseUrl):e.action==="remove"&&typeof e.id=="string"&&e.id.length>0&&e.id.length<=200}function Ne(r){if(!r||typeof r!="object")return!1;let e=r;if(typeof e.id!="string"||!e.id.trim()||e.id.length>200||e.name!==void 0&&(typeof e.name!="string"||!e.name.trim()||e.name.length>200))return!1;for(let t of[e.contextWindow,e.maxTokens])if(t!==void 0&&(!Number.isSafeInteger(t)||t<=0))return!1;return e.input===void 0||Array.isArray(e.input)&&e.input.length>0&&e.input.every(t=>t==="text"||t==="image")&&new Set(e.input).size===e.input.length}async function _e(r){let e;try{e=await rr(r,"utf8")}catch(n){if(n.code!=="ENOENT")throw n}if(e===void 0)return{config:{providers:{}}};let t;try{t=JSON.parse(e)}catch{throw new Error("models.json \u542B\u6CE8\u91CA\u6216\u683C\u5F0F\u9519\u8BEF\uFF0C\u8BF7\u5728\u914D\u7F6E\u6587\u4EF6\u4E2D\u624B\u52A8\u4FEE\u6539")}if(!t||typeof t!="object"||!t.providers||typeof t.providers!="object"||Array.isArray(t.providers))throw new Error("models.json \u7ED3\u6784\u65E0\u6548");return{config:t,existing:e}}async function cr(r,e,t){await tr(ar(r),{recursive:!0});let n=t===void 0?384:(await sr(r)).mode&511,s=`${r}.pi-web-${er(6).toString("hex")}.tmp`;try{await or(s,`${JSON.stringify(e,null,2)}
|
|
3
|
+
`,{mode:n,flag:"wx"}),await ir(s,r)}finally{await nr(s,{force:!0})}}async function je(r,e,t){if(!t.getProvider(e))throw new Error("\u63D0\u4F9B\u65B9\u4E0D\u5B58\u5728");let{config:n}=await _e(r),s=n.providers[e],a=new Set(s?.models?.map(u=>u.id)??[]);return{providerId:e,baseUrl:s?.baseUrl,models:t.getModels(e).map(u=>({id:u.id,name:u.name,contextWindow:u.contextWindow,maxTokens:u.maxTokens,input:[...u.input],source:a.has(u.id)?"custom":"builtin",overridden:!!s?.modelOverrides?.[u.id]}))}}async function Be(r,e,t,n){if(!n.getProvider(e))throw new Error("\u63D0\u4F9B\u65B9\u4E0D\u5B58\u5728");let{config:s,existing:a}=await _e(r),u={...s.providers[e]??{}},p=[...u.models??[]],o={...u.modelOverrides??{}};if(t.action==="base_url"){if(t.baseUrl!==null&&!Te(t.baseUrl))throw new Error("API \u5730\u5740\u65E0\u6548");t.baseUrl===null?delete u.baseUrl:u.baseUrl=t.baseUrl}else if(t.action==="save"){if(!Ne(t.model))throw new Error("\u6A21\u578B\u53C2\u6570\u65E0\u6548");let d={id:t.model.id.trim(),...t.model.name===void 0?{}:{name:t.model.name},...t.model.contextWindow===void 0?{}:{contextWindow:t.model.contextWindow},...t.model.maxTokens===void 0?{}:{maxTokens:t.model.maxTokens},...t.model.input===void 0?{}:{input:t.model.input}},f=t.originalId,m=f===void 0?-1:p.findIndex(v=>v.id===f);if(f===void 0&&(p.some(v=>v.id===d.id)||n.getModel(e,d.id)))throw new Error("\u6A21\u578B ID \u5DF2\u5B58\u5728");if(m>=0){if(d.id!==f&&(p.some(k=>k.id===d.id)||n.getModel(e,d.id)))throw new Error("\u6A21\u578B ID \u5DF2\u5B58\u5728");let v={...p[m],...d};for(let k of["name","contextWindow","maxTokens","input"])d[k]===void 0&&delete v[k];p[m]=v}else if(f!==void 0&&n.getModel(e,f)){if(d.id!==f)throw new Error("\u5185\u7F6E\u6A21\u578B ID \u4E0D\u53EF\u4FEE\u6539");let{id:v,...k}=d;o[f]={...o[f],...k};for(let w of["name","contextWindow","maxTokens","input"])d[w]===void 0&&delete o[f][w]}else{if(f!==void 0)throw new Error("\u6A21\u578B\u4E0D\u5B58\u5728");p.push(d)}}else{let d=p.findIndex(f=>f.id===t.id);if(d>=0)p.splice(d,1);else if(Object.hasOwn(o,t.id))delete o[t.id];else throw new Error("\u53EA\u80FD\u79FB\u9664\u81EA\u5B9A\u4E49\u6A21\u578B\u6216\u6062\u590D\u5DF2\u4FEE\u6539\u7684\u5185\u7F6E\u6A21\u578B")}p.length?u.models=p:delete u.models,Object.keys(o).length?u.modelOverrides=o:delete u.modelOverrides,Object.keys(u).length?s.providers[e]=u:delete s.providers[e],await cr(r,s,a)}function Le(r){return/^(?:npm:|git:|https?:\/\/|ssh:\/\/|git@)/i.test(r.trim())}var gr={"/":{path:"index.html",type:"text/html; charset=utf-8"},"/assets/app.js":{path:"assets/app.js",type:"text/javascript; charset=utf-8"},"/assets/style.css":{path:"assets/style.css",type:"text/css; charset=utf-8"}};function g(r,e,t){r.writeHead(e,{"Content-Type":"application/json; charset=utf-8","Cache-Control":"no-store"}),r.end(JSON.stringify(t))}function mr(r,e){let t=r.headers.authorization;if(typeof t!="string"||!t.startsWith("Bearer "))return!1;let n=Buffer.from(t.slice(7),"utf8");return n.length===e.length&&dr(n,e)}async function wr(r){let e=0,t=[];for await(let n of r){let s=Buffer.isBuffer(n)?n:Buffer.from(n);if(e+=s.length,e>64*1024)throw new Error("\u8BF7\u6C42\u5185\u5BB9\u8FC7\u5927");t.push(s)}return JSON.parse(Buffer.concat(t).toString("utf8"))}async function hr(r){let e=0,t=[];for await(let n of r){let s=Buffer.isBuffer(n)?n:Buffer.from(n);if(e+=s.length,e>H)throw new Error("\u6587\u4EF6\u8D85\u8FC7 20 MB");t.push(s)}return Buffer.concat(t)}async function yr(r,e=0){await new Promise((n,s)=>{r.once("error",s),r.listen(e,"127.0.0.1",()=>{r.off("error",s),n()})});let t=r.address();if(t===null||typeof t=="string")throw new Error("\u65E0\u6CD5\u786E\u5B9A\u76D1\u542C\u7AEF\u53E3");return t.port}async function Ue(r,e){let t=process.env.PI_WEBAPP_RESTART_TOKEN,n=t&&/^[A-Za-z0-9_-]{32}$/.test(t)?t:lr(24).toString("base64url"),s=Buffer.from(n),a=Ee(),u=new Set,p=new Map,o=new G,d="",f={...gr};for(let w of await ur(Oe(e,"assets")).catch(()=>[])){let l=/^[\w.-]+\.(js|css|woff2?|ttf)$/.exec(w);if(!l)continue;let h={js:"text/javascript; charset=utf-8",css:"text/css; charset=utf-8",woff:"font/woff",woff2:"font/woff2",ttf:"font/ttf"};f[`/assets/${w}`]={path:`assets/${w}`,type:h[l[1]]}}let m=fr(async(w,l)=>{l.setHeader("X-Content-Type-Options","nosniff"),l.setHeader("Referrer-Policy","no-referrer"),l.setHeader("Content-Security-Policy","default-src 'self'; script-src 'self'; style-src 'self'; connect-src 'self'; img-src 'self' data: blob:; object-src 'none'; base-uri 'none'; frame-ancestors 'none'");let h;try{h=new URL(w.url??"/",d).pathname}catch{g(l,400,{error:"\u8BF7\u6C42\u5730\u5740\u65E0\u6548"});return}let M=f[h];if(w.method==="GET"&&M){try{let c=await pr(Oe(e,M.path));l.writeHead(200,{"Content-Type":M.type,"Cache-Control":"no-store"}),l.end(c)}catch{g(l,500,{error:"\u9875\u9762\u6587\u4EF6\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h.startsWith("/plugins/")){try{let c=await r.pluginAsset?.(w.url??h);if(!c){g(l,404,{error:"\u63D2\u4EF6\u8D44\u6E90\u4E0D\u5B58\u5728"});return}l.writeHead(200,{"Content-Type":c.type,"Cache-Control":"no-store"}),l.end(c.bytes)}catch{g(l,404,{error:"\u63D2\u4EF6\u8D44\u6E90\u4E0D\u53EF\u7528"})}return}if(!h.startsWith("/api/")){g(l,404,{error:"\u672A\u627E\u5230"});return}if(!mr(w,s)){g(l,401,{error:"\u8BBF\u95EE\u4EE4\u724C\u65E0\u6548"});return}if(w.method==="GET"&&h==="/api/update/version"){try{g(l,200,{current:await r.selfUpdate?.runningVersion()??null})}catch(c){g(l,503,{error:c instanceof Error?c.message:"\u65E0\u6CD5\u8BFB\u53D6\u7248\u672C"})}return}if(w.method==="GET"&&h==="/api/update"){try{g(l,200,await r.selfUpdate?.check()??{canRestart:!1,reason:"\u5F53\u524D\u6269\u5C55\u4E0D\u652F\u6301\u5728\u7EBF\u5347\u7EA7"})}catch(c){g(l,503,{error:c instanceof Error?c.message:"\u68C0\u67E5\u66F4\u65B0\u5931\u8D25"})}return}if(w.method==="GET"&&h==="/api/image"){let c=new URL(w.url??h,d),y=c.searchParams.get("sessionId")??"",b=c.searchParams.get("messageId")??"",P=Number(c.searchParams.get("index"));if(!y||y!==r.snapshot().sessionId||!b||!Number.isInteger(P)||P<0||P>100){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362\u6216\u56FE\u7247\u5730\u5740\u65E0\u6548"});return}let T=r.image?.(y,b,P);if(!T||!["image/png","image/jpeg","image/webp","image/gif"].includes(T.mimeType)){g(l,404,{error:"\u56FE\u7247\u4E0D\u53EF\u7528"});return}l.writeHead(200,{"Content-Type":T.mimeType,"Cache-Control":"private, no-store"}),l.end(T.data);return}if(w.method==="POST"&&h==="/api/attachment"){if(w.headers.origin!==void 0&&w.headers.origin!==d){g(l,403,{error:"\u6765\u6E90\u4E0D\u5339\u914D"});return}let c=new URL(w.url??h,d),y=c.searchParams.get("sessionId"),b=c.searchParams.get("name");try{if(!y||!b||b.length>1024||y!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362\u6216\u6587\u4EF6\u540D\u65E0\u6548"});return}if(Number(w.headers["content-length"]??0)>H){g(l,413,{error:"\u6587\u4EF6\u8D85\u8FC7 20 MB"});return}let P=await Ce(y,b,w.headers["content-type"]??"application/octet-stream",await hr(w));if(y!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}p.set(P.id,P),g(l,201,{id:P.id,name:P.name,bytes:P.bytes})}catch(P){g(l,400,{error:P instanceof Error?P.message:"\u4E0A\u4F20\u5931\u8D25"})}return}if(w.method==="GET"&&h==="/api/session"){try{g(l,200,r.snapshot())}catch{g(l,503,{error:"\u5F53\u524D\u4F1A\u8BDD\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h==="/api/plugins"){try{g(l,200,await r.plugins?.()??{plugins:[],errors:[]})}catch{g(l,503,{error:"\u63D2\u4EF6\u76EE\u5F55\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h==="/api/providers"){try{g(l,200,await r.providers?.()??[])}catch{g(l,503,{error:"\u6A21\u578B\u63D0\u4F9B\u65B9\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h==="/api/provider/models"){let c=new URL(w.url??h,d).searchParams.get("providerId")??"";try{if(!c||!r.providerModels){g(l,400,{error:"\u63D0\u4F9B\u65B9\u65E0\u6548"});return}g(l,200,await r.providerModels(c))}catch(y){g(l,400,{error:y instanceof Error?y.message:"\u6A21\u578B\u76EE\u5F55\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h==="/api/provider/login/active"){g(l,200,{active:o.getActive()??null});return}if(w.method==="GET"&&h==="/api/provider/login"){let c=new URL(w.url??h,d).searchParams.get("id")??"",y=o.get(c);g(l,y?200:404,y??{error:"\u767B\u5F55\u6D41\u7A0B\u4E0D\u5B58\u5728"});return}if(w.method==="GET"&&(h==="/api/models"||h==="/api/config"||h==="/api/workspaces"||h==="/api/commands")){try{g(l,200,h==="/api/models"?await r.models():h==="/api/config"?await r.config():h==="/api/commands"?r.commands?.()??[]:await r.workspaces())}catch{g(l,503,{error:"Pi \u914D\u7F6E\u4E0D\u53EF\u7528"})}return}if(w.method==="GET"&&h==="/api/directory/capability"){g(l,200,{kind:a});return}if(w.method==="GET"&&h==="/api/events"){let c;try{c=r.snapshot()}catch{g(l,503,{error:"\u5F53\u524D\u4F1A\u8BDD\u4E0D\u53EF\u7528"});return}l.writeHead(200,{"Content-Type":"application/x-ndjson; charset=utf-8","Cache-Control":"no-store",Connection:"keep-alive","X-Accel-Buffering":"no"}),u.add(l),l.write(`${JSON.stringify({type:"snapshot",session:c})}
|
|
4
|
+
`),l.on("close",()=>u.delete(l));return}if(w.method==="POST"&&["/api/plugin-interaction","/api/plugin-action","/api/update","/api/message","/api/attachment/remove","/api/abort","/api/resume","/api/compact","/api/new-session","/api/model","/api/thinking-level","/api/config","/api/provider/login","/api/provider/login/respond","/api/provider/login/cancel","/api/provider/custom","/api/provider/models","/api/provider/logout","/api/workspace/add","/api/workspace/select","/api/workspace/new-session","/api/workspace/remove","/api/session/select","/api/directory/list","/api/directory/create","/api/directory/pick"].includes(h)){if(w.headers.origin!==void 0&&w.headers.origin!==d){g(l,403,{error:"\u6765\u6E90\u4E0D\u5339\u914D"});return}if(!w.headers["content-type"]?.startsWith("application/json")){g(l,415,{error:"\u9700\u8981 JSON \u8BF7\u6C42"});return}try{let c=await wr(w);if(typeof c!="object"||c===null||!("sessionId"in c)||typeof c.sessionId!="string"){g(l,400,{error:"\u7F3A\u5C11\u4F1A\u8BDD\u6807\u8BC6"});return}if(h==="/api/plugin-interaction"){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!("pluginId"in c)||typeof c.pluginId!="string"||c.pluginId.length>200||!("requestId"in c)||typeof c.requestId!="string"||c.requestId.length>200||!r.resolvePluginInteraction||!("value"in c)){g(l,400,{error:"\u63D2\u4EF6\u4EA4\u4E92\u54CD\u5E94\u65E0\u6548"});return}await r.resolvePluginInteraction(c.sessionId,c.pluginId,c.requestId,c.value),g(l,200,{accepted:!0});return}if(h==="/api/plugin-action"){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!("pluginId"in c)||typeof c.pluginId!="string"||c.pluginId.length>200||!("action"in c)||typeof c.action!="string"||c.action.length>100||!r.invokePluginAction){g(l,400,{error:"\u63D2\u4EF6\u52A8\u4F5C\u65E0\u6548"});return}let y=await r.invokePluginAction(c.sessionId,c.pluginId,c.action,"input"in c?c.input:void 0);g(l,200,{value:y});return}if(h==="/api/update"){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!r.snapshot().idle){g(l,409,{error:"\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u540E\u518D\u5347\u7EA7"});return}if(!r.selfUpdate){g(l,409,{error:"\u5F53\u524D\u6269\u5C55\u4E0D\u652F\u6301\u5728\u7EBF\u5347\u7EA7"});return}let y=await r.selfUpdate.prepare();g(l,202,{accepted:!0,version:y.version}),setTimeout(()=>{r.selfUpdate?.requestRestart(y).catch(b=>console.error("pi-webapp restart:",b))},500).unref();return}if(h==="/api/provider/custom"){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!("provider"in c)||!ne(c.provider)||!r.addCustomProvider){g(l,400,{error:"\u81EA\u5B9A\u4E49\u63D0\u4F9B\u65B9\u65E0\u6548"});return}await r.addCustomProvider(c.sessionId,c.provider),g(l,201,{accepted:!0});return}if(h==="/api/provider/models"||h==="/api/provider/logout"){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!("providerId"in c)||typeof c.providerId!="string"){g(l,400,{error:"\u63D0\u4F9B\u65B9\u65E0\u6548"});return}if(h==="/api/provider/models"){if(!("change"in c)||!Re(c.change)||!r.updateProviderModel){g(l,400,{error:"\u6A21\u578B\u53C2\u6570\u65E0\u6548"});return}await r.updateProviderModel(c.sessionId,c.providerId,c.change)}else{if(!r.logoutProvider){g(l,400,{error:"\u65E0\u6CD5\u79FB\u9664\u8BA4\u8BC1"});return}await r.logoutProvider(c.sessionId,c.providerId)}g(l,200,{accepted:!0});return}if(h.startsWith("/api/provider/login")){if(c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(h==="/api/provider/login"){if(!("providerId"in c)||typeof c.providerId!="string"||!("method"in c)||c.method!=="api_key"&&c.method!=="oauth"||!r.loginProvider||!r.providers){g(l,400,{error:"\u767B\u5F55\u65B9\u5F0F\u65E0\u6548"});return}if(!(await r.providers()).some(T=>T.id===c.providerId&&T.methods.includes(c.method))){g(l,400,{error:"\u63D0\u4F9B\u65B9\u4E0D\u652F\u6301\u6B64\u767B\u5F55\u65B9\u5F0F"});return}let b="initialSecret"in c?c.initialSecret:void 0;if(b!==void 0&&(c.method!=="api_key"||typeof b!="string"||!b.trim()||b.length>16384)){g(l,400,{error:"API Key \u65E0\u6548"});return}let P=o.start(c.providerId,c.method,r.loginProvider,b);g(l,202,{id:P.id});return}if(!("id"in c)||typeof c.id!="string"){g(l,400,{error:"\u767B\u5F55\u6D41\u7A0B\u65E0\u6548"});return}if(h==="/api/provider/login/cancel"){g(l,o.cancel(c.id)?202:404,{accepted:!0});return}if(!("value"in c)||typeof c.value!="string"||c.value.length>16384||!o.respond(c.id,c.value)){g(l,400,{error:"\u767B\u5F55\u8F93\u5165\u65E0\u6548"});return}g(l,202,{accepted:!0});return}if(h==="/api/attachment/remove"){if(!("id"in c)||typeof c.id!="string"||c.sessionId!==r.snapshot().sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362\u6216\u9644\u4EF6\u65E0\u6548"});return}p.get(c.id)?.sessionId===c.sessionId&&p.delete(c.id),g(l,202,{accepted:!0});return}if(h==="/api/directory/pick"){if(a!=="native"){g(l,409,{error:"\u672C\u5730\u76EE\u5F55\u9009\u62E9\u5668\u4E0D\u53EF\u7528"});return}let y=new AbortController;l.once("close",()=>y.abort()),g(l,200,{path:await Se(y.signal)});return}if(h==="/api/directory/list"){if("path"in c&&(typeof c.path!="string"||c.path.length>4096)){g(l,400,{error:"\u76EE\u5F55\u8DEF\u5F84\u65E0\u6548"});return}g(l,200,await be("path"in c?c.path:void 0));return}if(h==="/api/directory/create"){if(!("path"in c)||typeof c.path!="string"||c.path.length>4096||!("name"in c)||typeof c.name!="string"||c.name.length>255){g(l,400,{error:"\u6587\u4EF6\u5939\u540D\u79F0\u6216\u8DEF\u5F84\u65E0\u6548"});return}g(l,200,{path:await Pe(c.path,c.name)});return}if(h==="/api/workspace/add"){if(!("path"in c)||typeof c.path!="string"||c.path.length>4096||!("create"in c)||typeof c.create!="boolean"){g(l,400,{error:"\u5DE5\u4F5C\u533A\u8DEF\u5F84\u65E0\u6548"});return}await r.addWorkspace(c.path,c.create),g(l,202,{accepted:!0});return}if(h==="/api/workspace/select"||h==="/api/workspace/remove"||h==="/api/workspace/new-session"){if(!("id"in c)||typeof c.id!="string"){g(l,400,{error:"\u5DE5\u4F5C\u533A\u65E0\u6548"});return}h==="/api/workspace/select"?await r.selectWorkspace(c.id):h==="/api/workspace/new-session"?await r.newSessionInWorkspace(c.id):await r.removeWorkspace(c.id),g(l,202,{accepted:!0});return}if(h==="/api/session/select"){if(!("workspaceId"in c)||typeof c.workspaceId!="string"||!("id"in c)||typeof c.id!="string"||!("path"in c)||typeof c.path!="string"){g(l,400,{error:"\u4F1A\u8BDD\u65E0\u6548"});return}await r.selectSession(c.workspaceId,c.id,c.path),g(l,202,{accepted:!0});return}if(h==="/api/thinking-level"){if(!("level"in c)||typeof c.level!="string"){g(l,400,{error:"\u63A8\u7406\u5F3A\u5EA6\u65E0\u6548"});return}await r.setThinkingLevel(c.sessionId,c.level)}else if(h==="/api/model"){if(!("provider"in c)||typeof c.provider!="string"||!("id"in c)||typeof c.id!="string"){g(l,400,{error:"\u6A21\u578B\u65E0\u6548"});return}await r.setModel(c.sessionId,c.provider,c.id)}else if(h==="/api/config"){let y=c;if(!["packages","extensions","skills"].includes(y.kind)||!["global","project"].includes(y.scope)||!["add","remove"].includes(y.action)||typeof y.value!="string"||!y.value.trim()||y.value.length>2048){g(l,400,{error:"\u914D\u7F6E\u9879\u65E0\u6548"});return}if(y.action==="add"&&y.kind!=="packages"&&Le(y.value)){g(l,400,{error:"npm \u6216 Git \u6765\u6E90\u8BF7\u5728\u300C\u5305\u300D\u4E2D\u6DFB\u52A0\uFF1B\u6269\u5C55\u548C\u6280\u80FD\u53EA\u63A5\u53D7\u6587\u4EF6\u6216\u76EE\u5F55\u8DEF\u5F84"});return}g(l,200,await r.updateConfig(y));return}else if(h==="/api/message"){let y="attachments"in c?c.attachments:[];if(!Array.isArray(y)||y.length>xe||y.some(x=>typeof x!="string")||new Set(y).size!==y.length){g(l,400,{error:"\u9644\u4EF6\u65E0\u6548\u6216\u8FC7\u591A"});return}let b=y.map(x=>p.get(x));if(b.some(x=>!x||x.sessionId!==c.sessionId)){g(l,400,{error:"\u9644\u4EF6\u4E0D\u53EF\u7528"});return}if(!("text"in c)||typeof c.text!="string"||!c.text.trim()&&y.length===0||c.text.length>32e3){g(l,400,{error:"\u6D88\u606F\u65E0\u6548\u6216\u8FC7\u957F"});return}let P=b,T=[c.text.trim(),...P.map(x=>`\u9644\u4EF6 ${JSON.stringify(x.name)}\uFF1A${x.path}`)].filter(Boolean).join(`
|
|
5
5
|
|
|
6
|
-
`),
|
|
7
|
-
`;for(let f of p)f.write(c)},async close(){l.close();for(let g of p)g.end();p.clear(),await new Promise((g,c)=>u.close(f=>f?c(f):g()))}}}import{getSupportedThinkingLevels as Vt}from"@earendil-works/pi-ai";function he(t){let e=[],i=t;for(;;){let r=/(^|\n\n)附件 ("(?:\\.|[^"\\])*"):([^\n]+)$/u.exec(i);if(!r||!/[\\/]pi-web[\\/]attachments[\\/][a-f0-9]{64}[\\/]/u.test(r[3]))break;let n;try{n=JSON.parse(r[2])}catch{break}e.unshift({name:n,image:/\.(?:png|jpe?g|webp|gif)$/iu.test(n)}),i=i.slice(0,r.index)}return{text:i,attachments:e}}function M(t){return typeof t=="string"?[{kind:"text",text:t}]:t.flatMap(e=>e.type==="text"?[{kind:"text",text:e.text}]:e.type==="thinking"?[{kind:"thinking",text:e.thinking}]:e.type==="image"?[{kind:"image",text:"\u56FE\u7247\u9644\u4EF6"}]:e.type==="toolCall"?[{kind:"toolCall",text:JSON.stringify(e.arguments??{}),toolName:e.name,toolCallId:e.id}]:[])}function $(t){if(t.type==="custom_message")return t.display?{id:t.id,role:"notice",timestamp:t.timestamp,blocks:M(t.content)}:null;if(t.type!=="message")return null;let{message:e}=t;return e.role==="user"||e.role==="assistant"?{id:t.id,role:e.role,timestamp:t.timestamp,blocks:M(e.content),...e.role==="assistant"?{...e.stopReason==="error"&&e.errorMessage?{error:e.errorMessage}:{},usage:{input:e.usage.input,output:e.usage.output,cacheRead:e.usage.cacheRead,cacheWrite:e.usage.cacheWrite,...e.usage.reasoning===void 0?{}:{reasoning:e.usage.reasoning},totalTokens:e.usage.totalTokens,cost:e.usage.cost.total},model:`${e.provider}/${e.model}`}:{}}:e.role==="toolResult"?{id:t.id,role:"tool",timestamp:t.timestamp,blocks:M(e.content),isError:e.isError,toolCallId:e.toolCallId,toolName:e.toolName}:null}function F(t,e){let i=t?.trim();if(i)return i;let r=e.find(p=>p.role==="user"),n=he(r?.blocks.find(p=>p.kind==="text")?.text??"").text.replace(/\s+/g," ").trim();return n?n.slice(0,50):"\u5F53\u524D\u4F1A\u8BDD"}function ye(t,e){let i=t.sessionManager.getBranch().flatMap(r=>{let n=$(r);return n?[n]:[]});return{schemaVersion:1,sessionId:t.sessionManager.getSessionId(),cwd:t.cwd,name:F(e,i),model:t.model?`${t.model.provider}/${t.model.id}`:null,thinkingLevel:t.thinkingLevel??null,thinkingLevels:t.model?Vt(t.model):["off"],idle:t.isIdle(),contextUsage:t.getContextUsage()??null,messages:i}}import{randomUUID as H}from"node:crypto";import{mkdir as ve,readFile as _t,realpath as ke,rename as Bt,rm as Ot,stat as be,writeFile as Ut}from"node:fs/promises";import{basename as Pe,dirname as Dt,isAbsolute as Se,join as $t}from"node:path";var R=class{items=[];hiddenPaths=[];mutationChain=Promise.resolve();file;constructor(e){this.file=e}async load(){try{let e=JSON.parse(await _t(this.file,"utf8")),i,r=[];if(Array.isArray(e)?i=e:e&&typeof e=="object"&&"version"in e&&e.version===2&&"items"in e&&"hiddenPaths"in e&&(i=e.items,r=e.hiddenPaths),!Array.isArray(i)||!Array.isArray(r))throw new Error("\u5DE5\u4F5C\u533A\u8BB0\u5F55\u65E0\u6548");this.items=i.filter(n=>typeof n=="object"&&n!==null&&typeof n.id=="string"&&typeof n.path=="string"&&typeof n.title=="string"),this.hiddenPaths=r.filter(n=>typeof n=="string")}catch(e){if(e.code!=="ENOENT")throw e}}list(){return[...this.items]}get(e){return this.items.find(i=>i.id===e)}async add(e,i=!1){if(!Se(e)||e.includes("\0"))throw new Error("\u8BF7\u8F93\u5165\u5B8C\u6574\u7684\u76EE\u5F55\u8DEF\u5F84");i&&await ve(e,{recursive:!0});let r=await ke(e);if(!(await be(r)).isDirectory())throw new Error("\u8DEF\u5F84\u4E0D\u662F\u76EE\u5F55");return this.mutate(async()=>{let n=this.hiddenPaths.filter(a=>a!==r),p=this.items.find(a=>a.path===r);if(p)return n.length!==this.hiddenPaths.length&&(await this.save(this.items,n),this.hiddenPaths=n),p;let o={id:H(),path:r,title:Pe(r)||r},l=[o,...this.items];return await this.save(l,n),this.items=l,this.hiddenPaths=n,o})}async discover(e){let i=(await Promise.all([...new Set(e)].filter(Se).map(async r=>{try{let n=await ke(r);return(await be(n)).isDirectory()?n:null}catch{return null}}))).filter(r=>r!==null);await this.mutate(async()=>{let r=new Set([...this.items.map(o=>o.path),...this.hiddenPaths]),n=[];for(let o of i)r.has(o)||(r.add(o),n.push({id:H(),path:o,title:Pe(o)||o}));if(n.length===0)return;let p=[...this.items,...n];await this.save(p,this.hiddenPaths),this.items=p})}async remove(e){await this.mutate(async()=>{let i=this.get(e);if(!i)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");let r=this.items.filter(p=>p.id!==e),n=[...new Set([...this.hiddenPaths,i.path])];await this.save(r,n),this.items=r,this.hiddenPaths=n})}mutate(e){let i=this.mutationChain.then(e,e);return this.mutationChain=i.then(()=>{},()=>{}),i}async save(e,i){await ve(Dt(this.file),{recursive:!0});let r=`${this.file}.${H()}.tmp`;try{await Ut(r,JSON.stringify({version:2,items:e,hiddenPaths:i},null,2),{mode:384}),await Bt(r,this.file)}catch(n){throw await Ot(r,{force:!0}),n}}};function xe(t){return $t(t,"pi-web","workspaces.json")}import{createAgentSession as Ht,DefaultResourceLoader as Jt,getAgentDir as Gt,SessionManager as V}from"@earendil-works/pi-coding-agent";import{realpath as Ee}from"node:fs/promises";import{realpath as Ie}from"node:fs/promises";import{SessionManager as Ft}from"@earendil-works/pi-coding-agent";async function W(t,e){let i=await Ie(t),r=e??await Ft.listAll(),n=await Promise.all(r.map(async p=>p.cwd!==""&&await Ie(p.cwd).catch(()=>null)===i));return r.filter((p,o)=>n[o])}var _=class{active=null;detach=null;cwd=null;lastStreamAt=0;publish;fallbackModel;constructor(e,i){this.publish=e,this.fallbackModel=i}get session(){return this.active}get path(){return this.cwd}async open(e,i){if(this.active&&!this.active.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u5DE5\u4F5C\u533A");let r=await Ee(e),n;if(i==="new")n=V.create(r);else if(i==="continue"){let a=(await W(r))[0];n=a?V.open(a.path):V.create(r)}else n=V.open(i.sessionFile);if(await Ee(n.getCwd())!==r)throw new Error("\u4F1A\u8BDD\u4E0D\u5C5E\u4E8E\u8BE5\u5DE5\u4F5C\u533A");let p=n.buildSessionProjection().model?void 0:this.active?.model??this.fallbackModel(),o=new Jt({cwd:r,agentDir:Gt(),noExtensions:!0});await o.reload();let{session:l}=await Ht({cwd:r,sessionManager:n,model:p,resourceLoader:o});this.detach?.(),this.active?.dispose(),this.active=l,this.cwd=r,this.detach=l.subscribe(a=>{if(a.type==="message_update"&&a.message.role==="assistant"){let u=Date.now();u-this.lastStreamAt>=60&&(this.lastStreamAt=u,this.publish({type:"stream",message:{id:"stream",role:"assistant",timestamp:new Date(a.message.timestamp).toISOString(),blocks:M(a.message.content)}}))}(a.type==="message_end"||a.type==="agent_start"||a.type==="agent_settled"||a.type==="session_info_changed")&&(a.type==="message_end"&&a.message.role==="assistant"&&this.publish({type:"stream",message:null}),this.publish({type:"snapshot",session:this.snapshot()}))}),this.publish({type:"stream",message:null}),this.publish({type:"snapshot",session:this.snapshot()})}snapshot(){let e=this.active;if(!e||!this.cwd)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u5DE5\u4F5C\u533A\u4F1A\u8BDD");let i=e.sessionManager.getBranch().flatMap(r=>{let n=$(r);return n?[n]:[]});return{schemaVersion:1,sessionId:e.sessionManager.getSessionId(),cwd:this.cwd,name:F(e.sessionManager.getSessionName(),i),model:e.model?`${e.model.provider}/${e.model.id}`:null,thinkingLevel:e.thinkingLevel,thinkingLevels:e.getAvailableThinkingLevels(),idle:e.isIdle,contextUsage:e.getContextUsage()??null,messages:i}}async send(e,i=[]){if(!this.active||!this.active.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let r=this.active,n=!1,p,o,l=new Promise((a,u)=>{p=a,o=u});r.prompt(e,{images:i,preflightResult:a=>{a&&(n=!0,p())}}).then(()=>{n||p()}).catch(a=>{n?this.publish({type:"error",message:a instanceof Error?a.message:"Pi \u8BF7\u6C42\u5931\u8D25"}):o(a)}),await l}async stop(){await this.active?.abort()}async models(){return(await this.active?.modelRuntime.getAvailable()??[]).map(i=>({provider:i.provider,id:i.id,name:i.name}))}async setModel(e,i){if(!this.active||!this.active.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let r=this.active.modelRuntime.getModel(e,i);if(!r)throw new Error("\u6A21\u578B\u4E0D\u53EF\u7528");await this.active.setModel(r),this.publish({type:"snapshot",session:this.snapshot()})}dispose(){this.detach?.(),this.active?.dispose(),this.detach=null,this.active=null,this.cwd=null}};import{basename as J,dirname as Kt}from"node:path";function Ce(t,e){let i=r=>e[r].map(n=>({name:r==="skills"&&J(n.path).toLowerCase()==="skill.md"?J(Kt(n.path)):J(n.path),path:n.path,source:n.metadata.source,scope:n.metadata.scope,enabled:n.enabled}));return{packages:t.map(r=>({name:r.source,path:r.installedPath??"",source:r.source,scope:r.scope,enabled:!!r.installedPath})),extensions:i("extensions"),skills:i("skills")}}import{execFile as zt}from"node:child_process";var Yt=(t,e)=>new Promise((i,r)=>{zt(t,[...e],{windowsHide:!0},n=>{n?r(n):i()})});async function G(t,e=process.platform,i=process.env,r=Yt){if(i.SSH_CONNECTION||i.SSH_TTY||i.SSH_CLIENT||e==="linux"&&!i.DISPLAY&&!i.WAYLAND_DISPLAY)return!1;let n=e==="darwin"?"open":e==="linux"?"xdg-open":e==="win32"?"explorer.exe":null;return n===null?!1:(await r(n,[t]),!0)}var ii=Qt(Xt(Zt(import.meta.url)),"../web/dist"),ri=Symbol.for("pi-web.bridge-state"),s=globalThis[ri]??={bridge:null,current:null,commandContext:null,pi:null,replacementContext:null,replacementSessionId:null,lastStreamAt:0,workspaces:null,workspaceSessions:null,selected:"tui",activeWorkspaceId:null,autoOpened:!1},si=null;function ni(){return si??=qt.create({refreshOnCreate:!1})}var B=new Map;async function A(){let t=await ni(),e=s.selected==="tui"?s.current?.modelRegistry:void 0,i=new Set(e?.getRegisteredProviderIds()??[]);for(let r of B.keys())i.has(r)||(t.unregisterProvider(r),B.delete(r));for(let r of i){let n=e?.getRegisteredNativeProvider(r),p=e?.getRegisteredProviderConfig(r),o=n??p;!o||B.get(r)===o||(n?t.registerNativeProvider(n):p&&t.registerProvider(r,p),B.set(r,o))}return await t.refresh({allowNetwork:!1}),t}function k(){if(s.selected==="sdk")return s.workspaceSessions?.snapshot()??(()=>{throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD")})();if(s.current===null)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");return ye(s.current,s.current.sessionManager.getSessionName())}function S(t){if(k().sessionId!==t)throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362")}async function Te(){let t=s.workspaces?.list()??[],e=k(),i=await O(e.cwd).catch(()=>e.cwd),r=await Ae.listAll(),n=(await Promise.all(t.map(async p=>{let l=(await W(p.path,r).catch(()=>[])).map(a=>({id:a.id,workspaceId:p.id,path:a.path,name:a.name||a.firstMessage?.slice(0,50)||"\u5F53\u524D\u4F1A\u8BDD",modified:a.modified.toISOString()}));return p.path===i&&!l.some(a=>a.id===e.sessionId)&&l.unshift({id:e.sessionId,workspaceId:p.id,path:null,name:e.name,modified:new Date().toISOString()}),l}))).flat();return{items:t,activeId:s.activeWorkspaceId,sessions:n}}async function I(){s.bridge&&s.bridge.publish({type:"workspaces",value:await Te()})}async function z(t,e=!1){let i=s.workspaces?.get(t);if(!i)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");if(await O(i.path),!e&&s.current&&i.path===await O(s.current.cwd)){if(s.selected==="sdk"&&s.workspaceSessions?.session&&!s.workspaceSessions.session.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u5DE5\u4F5C\u533A");s.selected="tui",s.activeWorkspaceId=t,s.bridge?.publish({type:"stream",message:null}),s.bridge?.publish({type:"snapshot",session:k()})}else{if(!s.workspaceSessions)throw new Error("Pi \u5DE5\u4F5C\u533A\u670D\u52A1\u4E0D\u53EF\u7528");await s.workspaceSessions.open(i.path,e?"new":"continue"),s.selected="sdk",s.activeWorkspaceId=t,s.bridge?.publish({type:"snapshot",session:k()})}await I()}function x(t){let e=s.current;if(e===null||e.sessionManager.getSessionId()!==t)throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362");return e}function P(t){s.current=t,s.selected==="tui"&&s.bridge?.publish({type:"snapshot",session:k()})}function We(){if(s.current===null)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");let t=s.selected==="sdk"?s.workspaceSessions?.path:s.current.cwd;if(!t)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u5DE5\u4F5C\u533A");let e=s.selected==="tui"?s.current.isProjectTrusted():s.workspaceSessions?.session?.settingsManager.isProjectTrusted()??!1;return ei.create(t,void 0,{projectTrusted:e})}async function Le(){let t=We(),e=n=>({packages:(n.packages??[]).map(p=>typeof p=="string"?p:p.source),extensions:n.extensions??[],skills:n.skills??[]}),i=new Me({cwd:k().cwd,agentDir:T(),settingsManager:t}),r=Ce(i.listConfiguredPackages(),await i.resolve(async()=>"skip"));return{projectTrusted:t.isProjectTrusted(),global:e(t.getGlobalSettings()),project:e(t.getProjectSettings()),installed:r}}async function oi(t){S(t.sessionId);let e=s.selected==="tui"?x(t.sessionId):null;if(e?!e.isIdle():!s.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let i=We();if(t.scope==="project"&&!i.isProjectTrusted())throw new Error("\u5F53\u524D\u9879\u76EE\u5C1A\u672A\u53D7\u4FE1\u4EFB\uFF0C\u65E0\u6CD5\u4FEE\u6539\u9879\u76EE\u8BBE\u7F6E");let r=t.value.trim(),n=t.scope==="project"?i.getProjectSettings():i.getGlobalSettings();if(t.kind==="packages"){let p=new Me({cwd:k().cwd,agentDir:T(),settingsManager:i});t.action==="add"?await p.installAndPersist(r,{local:t.scope==="project"}):await p.removeAndPersist(r,{local:t.scope==="project"})}else if(t.kind==="extensions"){let p=n.extensions??[],o=t.action==="add"?[...new Set([...p,r])]:p.filter(l=>l!==r);t.scope==="project"?i.setProjectExtensionPaths(o):i.setExtensionPaths(o)}else{let p=n.skills??[],o=t.action==="add"?[...new Set([...p,r])]:p.filter(l=>l!==r);t.scope==="project"?i.setProjectSkillPaths(o):i.setSkillPaths(o)}return await i.flush(),s.selected==="tui"?(s.commandContext&&await s.commandContext.reload(),s.current&&P(s.current)):(await s.workspaceSessions?.session?.resourceLoader.reload(),s.workspaceSessions?.session?.refreshContext()),await Le()}function ai(t,e=G){s.pi=t,t.on("session_start",(r,n)=>{s.replacementSessionId!==n.sessionManager.getSessionId()&&(s.replacementContext=null,s.replacementSessionId=null),P(n),s.selected==="tui"&&s.workspaces&&s.workspaces.add(n.cwd).then(async p=>{s.selected!=="tui"||s.current?.sessionManager.getSessionId()!==n.sessionManager.getSessionId()||(s.activeWorkspaceId=p.id,await I())}).catch(p=>{s.bridge?.publish({type:"error",message:p instanceof Error?p.message:"\u65E0\u6CD5\u6CE8\u518C\u5F53\u524D\u5DE5\u4F5C\u533A"})}),process.env.PI_WEBAPP_AUTO_OPEN==="1"&&n.mode==="tui"&&!s.autoOpened&&(s.autoOpened=!0,i(n).catch(p=>{n.ui.notify(p instanceof Error?p.message:"Web \u542F\u52A8\u5931\u8D25","error")}))}),t.on("agent_start",(r,n)=>P(n)),t.on("agent_end",(r,n)=>P(n)),t.on("agent_settled",(r,n)=>P(n)),t.on("model_select",(r,n)=>P(n)),t.on("thinking_level_select",(r,n)=>P(n)),t.on("message_end",(r,n)=>{s.selected==="tui"&&r.message.role==="assistant"&&s.bridge?.publish({type:"stream",message:null}),P(n),s.selected==="tui"&&I()}),t.on("session_info_changed",(r,n)=>P(n)),t.on("message_update",(r,n)=>{if(s.current=n,s.selected!=="tui"||r.message.role!=="assistant"||s.bridge===null)return;let p=Date.now();p-s.lastStreamAt<60||(s.lastStreamAt=p,s.bridge.publish({type:"stream",message:{id:"stream",role:"assistant",timestamp:new Date(r.message.timestamp).toISOString(),blocks:M(r.message.content)}}))}),t.on("session_shutdown",r=>{if(s.current=null,r.reason==="new"||r.reason==="resume"||r.reason==="fork")return;let n=s.bridge;s.bridge=null,s.commandContext=null,s.replacementContext=null,s.replacementSessionId=null,s.pi=null,s.workspaceSessions?.dispose(),s.workspaceSessions=null,s.selected="tui",s.activeWorkspaceId=null,s.autoOpened=!1,n&&n.close()});let i=async r=>{s.current=r,s.commandContext="newSession"in r?r:null,s.pi=t,s.workspaces===null&&(s.workspaces=new R(xe(T())),await s.workspaces.load());try{await s.workspaces.discover((await Ae.listAll()).map(o=>o.cwd))}catch(o){r.ui.notify(`\u65E0\u6CD5\u8BFB\u53D6\u90E8\u5206 Pi \u5386\u53F2\u5DE5\u4F5C\u533A\uFF1A${o instanceof Error?o.message:String(o)}`,"warning")}let n=await s.workspaces.add(r.cwd);if(s.selected==="tui"&&(s.activeWorkspaceId=n.id),s.bridge&&s.bridge.protocolVersion!==3){let o=s.bridge;s.bridge=null,await o.close()}s.bridge===null&&(s.workspaceSessions=new _(o=>{s.selected==="sdk"&&(s.bridge?.publish(o),o.type==="snapshot"&&o.session.idle&&I())},()=>s.current?.model),s.bridge=await we({snapshot:k,image(o,l,a){S(o);let h=(s.selected==="sdk"?s.workspaceSessions?.session?.sessionManager.getBranch():s.current?.sessionManager.getBranch())?.find(c=>c.id===l);if(h?.type!=="message"||h.message.role!=="user"||!Array.isArray(h.message.content))return null;let g=h.message.content[a];return g?.type!=="image"?null:{data:Buffer.from(g.data,"base64"),mimeType:g.mimeType}},async workspaces(){return Te()},async addWorkspace(o,l){let a=await s.workspaces.add(o,l);try{await z(a.id,!0)}catch(u){throw await I(),u}},async selectWorkspace(o){await z(o)},async newSessionInWorkspace(o){await z(o,!0)},async removeWorkspace(o){if(o===s.activeWorkspaceId)throw new Error("\u8BF7\u5148\u5207\u6362\u5230\u5176\u4ED6\u5DE5\u4F5C\u533A");await s.workspaces.remove(o),await I()},async selectSession(o,l,a){let u=s.workspaces?.get(o);if(!u)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");if(l===s.current?.sessionManager.getSessionId()&&u.path===await O(s.current.cwd)){if(s.selected==="sdk"&&s.workspaceSessions?.session&&!s.workspaceSessions.session.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u4F1A\u8BDD");s.selected="tui",s.activeWorkspaceId=o,s.bridge?.publish({type:"snapshot",session:k()})}else{if(s.selected==="sdk"&&s.workspaceSessions?.session?.sessionManager.getSessionId()===l&&s.workspaceSessions.path===u.path)return;if(!(await W(u.path)).some(g=>g.id===l&&g.path===a))throw new Error("\u4F1A\u8BDD\u4E0D\u5C5E\u4E8E\u8BE5\u5DE5\u4F5C\u533A");await s.workspaceSessions.open(u.path,{sessionFile:a}),s.selected="sdk",s.activeWorkspaceId=o,s.bridge?.publish({type:"snapshot",session:k()})}await I()},async models(){if(s.selected==="sdk")return s.workspaceSessions?.models()??[];let o=s.current;if(!o)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");let l=o.scopedModels?.map(a=>`${a.model.provider}/${a.model.id}`)??[];return o.modelRegistry.getAvailable().filter(a=>l.length===0||l.includes(`${a.provider}/${a.id}`)).map(a=>({provider:a.provider,id:a.id,name:a.name}))},async providers(){let o=await A(),l=new Set((await o.listCredentials()).map(a=>a.providerId));return o.getProviders().map(a=>({id:a.id,name:a.name,configured:o.getProviderAuthStatus(a.id).configured,storedCredential:l.has(a.id),methods:[a.auth.apiKey?.login?"api_key":null,a.auth.oauth?"oauth":null].filter(u=>u!==null)}))},async providerModels(o){let l=await A();return me(K(T(),"models.json"),o,l)},async updateProviderModel(o,l,a){if(S(o),s.selected==="tui"?!x(o).isIdle():!s.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let u=k().model;if(a.action==="remove"&&u===`${l}/${a.id}`)throw new Error("\u8BF7\u5148\u5207\u6362\u5F53\u524D\u4F7F\u7528\u7684\u6A21\u578B");if(a.action==="save"&&a.originalId&&a.originalId!==a.model.id&&u===`${l}/${a.originalId}`)throw new Error("\u8BF7\u5148\u5207\u6362\u5F53\u524D\u4F7F\u7528\u7684\u6A21\u578B");let h=await A();await fe(K(T(),"models.json"),l,a,h),await h.refresh({providers:[l],allowNetwork:!1}),await s.current?.modelRegistry.refresh({providers:[l],allowNetwork:!1}),await s.workspaceSessions?.session?.modelRuntime.refresh({providers:[l],allowNetwork:!1});let g=a.action==="save"?a.model.id:a.action==="base_url"&&u?.startsWith(`${l}/`)?u.slice(l.length+1):null;if(g&&u===`${l}/${g}`)if(s.selected==="sdk")try{await s.workspaceSessions.setModel(l,g)}catch{throw new Error("\u6A21\u578B\u5DF2\u4FDD\u5B58\uFF0C\u8BF7\u91CD\u65B0\u9009\u62E9\u8BE5\u6A21\u578B\u4EE5\u5E94\u7528\u65B0\u53C2\u6570")}else{let c=x(o),f=c.modelRegistry.find(l,g);if(!f||!s.pi||!await s.pi.setModel(f))throw new Error("\u6A21\u578B\u5DF2\u4FDD\u5B58\uFF0C\u8BF7\u91CD\u65B0\u9009\u62E9\u8BE5\u6A21\u578B\u4EE5\u5E94\u7528\u65B0\u53C2\u6570");P(c)}},async logoutProvider(o,l){if(S(o),s.selected==="tui"?!x(o).isIdle():!s.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let a=await A();if(!(await a.listCredentials()).some(u=>u.providerId===l))throw new Error("\u8BE5\u63D0\u4F9B\u65B9\u6CA1\u6709\u5DF2\u4FDD\u5B58\u7684\u8BA4\u8BC1");await a.logout(l),await s.current?.modelRegistry.refresh({providers:[l],allowNetwork:!1}),await s.workspaceSessions?.session?.modelRuntime.refresh({providers:[l],allowNetwork:!1})},async loginProvider(o,l,a){let u=await A();await u.login(o,l,ae(o,l,a)),await u.refresh({providers:[o],allowNetwork:!1}),await s.current?.modelRegistry.refresh({providers:[o],allowNetwork:!1}),await s.workspaceSessions?.session?.modelRuntime.refresh({providers:[o],allowNetwork:!1})},async addCustomProvider(o,l){if(S(o),s.selected==="tui"?!x(o).isIdle():!s.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let a=await A();if(a.getProvider(l.id))throw new Error("\u63D0\u4F9B\u65B9\u5DF2\u5B58\u5728");await de(K(T(),"models.json"),l),await a.refresh({allowNetwork:!1}),await s.current?.modelRegistry.refresh({allowNetwork:!1}),await s.workspaceSessions?.session?.modelRuntime.refresh({allowNetwork:!1})},commands(){return s.selected==="tui"?(s.pi?.getCommands()??[]).filter(o=>o.name!=="web").map(o=>({name:o.name,description:o.description})):[]},async compact(o){if(S(o),s.selected==="sdk"){let a=s.workspaceSessions?.session;if(!a||!a.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");await a.compact(),s.bridge?.publish({type:"snapshot",session:k()});return}let l=x(o);if(!l.isIdle())throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");l.compact()},async setModel(o,l,a){if(S(o),s.selected==="sdk"){await s.workspaceSessions.setModel(l,a);return}let u=x(o);if(!u.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let h=u.modelRegistry.find(l,a);if(!h||!u.modelRegistry.getAvailable().some(g=>g.provider===l&&g.id===a))throw new Error("\u6A21\u578B\u4E0D\u53EF\u7528");if(!s.pi||!await s.pi.setModel(h))throw new Error("\u6A21\u578B\u63D0\u4F9B\u65B9\u672A\u914D\u7F6E\u8BA4\u8BC1");P(u)},async setThinkingLevel(o,l){if(S(o),!["off","minimal","low","medium","high","xhigh"].includes(l))throw new Error("\u63A8\u7406\u5F3A\u5EA6\u65E0\u6548");if(s.selected==="sdk"){let h=s.workspaceSessions?.session;if(!h||!h.isIdle||!h.getAvailableThinkingLevels().includes(l))throw new Error("\u5F53\u524D\u6A21\u578B\u4E0D\u652F\u6301\u6B64\u63A8\u7406\u5F3A\u5EA6");h.setThinkingLevel(l),s.bridge?.publish({type:"snapshot",session:k()});return}let u=x(o);if(!u.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(!u.model||!ti(u.model).includes(l))throw new Error("\u5F53\u524D\u6A21\u578B\u4E0D\u652F\u6301\u6B64\u63A8\u7406\u5F3A\u5EA6");if(!s.pi)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");s.pi.setThinkingLevel(l),P(u)},config:Le,updateConfig:oi,async send(o,l,a=[]){if(S(o),s.selected==="sdk"){await s.workspaceSessions.send(l,a);return}if(!x(o).isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(s.replacementContext!==null&&s.replacementSessionId===o){await s.replacementContext.sendUserMessage(a.length?[{type:"text",text:l},...a]:l,{expandPromptTemplates:!0});return}if(s.pi===null)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");s.pi.sendUserMessage(a.length?[{type:"text",text:l},...a]:l,{expandPromptTemplates:!0})},abort(o){S(o),s.selected==="sdk"?s.workspaceSessions.stop():x(o).abort()},async newSession(o){if(S(o),s.selected==="sdk"){let u=s.workspaces?.get(s.activeWorkspaceId??"");if(!u)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");await s.workspaceSessions.open(u.path,"new"),await I();return}let l=x(o);if(!l.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(s.commandContext===null){await s.workspaceSessions.open(l.cwd,"new"),s.selected="sdk",s.bridge?.publish({type:"snapshot",session:k()}),await I();return}if((await s.commandContext.newSession({withSession:async u=>{s.commandContext=u,s.replacementContext=u,s.replacementSessionId=u.sessionManager.getSessionId(),s.current=u}})).cancelled)throw new Error("\u65B0\u4F1A\u8BDD\u5DF2\u53D6\u6D88");await I()}},ii));let p=await e(s.bridge.url).catch(()=>!1);r.ui.notify(`pi-webapp: ${s.bridge.url}`,p?"info":"warning"),r.ui.setStatus("pi-webapp","Web \u5DF2\u542F\u52A8 \xB7 /web \u91CD\u65B0\u6253\u5F00")};t.registerCommand("web",{description:"Open the current Pi session in a local web interface",handler:async(r,n)=>i(n)})}export{ai as default};
|
|
6
|
+
`),wt=await Promise.all(P.filter(x=>["image/png","image/jpeg","image/webp","image/gif"].includes(x.mediaType)).map(Ae));await r.send(c.sessionId,T,wt);for(let x of y)p.delete(x)}else if(h==="/api/compact"){if(!r.compact)throw new Error("\u5F53\u524D\u4F1A\u8BDD\u4E0D\u652F\u6301\u538B\u7F29");await r.compact(c.sessionId)}else if(h==="/api/resume"){let y=r.snapshot();if(c.sessionId!==y.sessionId){g(l,409,{error:"\u4F1A\u8BDD\u5DF2\u5207\u6362"});return}if(!y.idle){g(l,409,{error:"Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F"});return}if(!y.paused){g(l,409,{error:"\u5F53\u524D\u4F1A\u8BDD\u6CA1\u6709\u6682\u505C\u7684\u4EFB\u52A1"});return}if(y.interactions?.length){g(l,409,{error:"\u8BF7\u5148\u5B8C\u6210\u5F53\u524D\u4EA4\u4E92\u6216\u5BA1\u6279"});return}if(!r.resume)throw new Error("\u5F53\u524D\u670D\u52A1\u4E0D\u652F\u6301\u7EE7\u7EED\uFF0C\u8BF7\u91CD\u8F7D Pi");await r.resume(c.sessionId)}else h==="/api/abort"?await r.abort(c.sessionId):await r.newSession(c.sessionId);g(l,202,{accepted:!0})}catch(c){let y=c instanceof Error?c.message:"\u8BF7\u6C42\u5931\u8D25";g(l,y==="\u4F1A\u8BDD\u5DF2\u5207\u6362"?409:400,{error:y})}return}g(l,404,{error:"\u672A\u627E\u5230"})}),v=Number(process.env.PI_WEBAPP_RESTART_PORT);return d=`http://127.0.0.1:${await yr(m,Number.isInteger(v)&&v>0&&v<65536&&t===n?v:0)}`,{protocolVersion:7,url:`${d}/#${n}`,publish(w){if(w.type==="snapshot")for(let[h,M]of p)M.sessionId!==w.session.sessionId&&p.delete(h);let l=`${JSON.stringify(w)}
|
|
7
|
+
`;for(let h of u)h.write(l)},async close(){o.close();for(let w of u)w.end();u.clear(),await new Promise((w,l)=>m.close(h=>h?l(h):w()))}}}import{getSupportedThinkingLevels as vr}from"@earendil-works/pi-ai";function Ve(r){let e=[],t=r;for(;;){let n=/(^|\n\n)附件 ("(?:\\.|[^"\\])*"):([^\n]+)$/u.exec(t);if(!n||!/[\\/]pi-web[\\/]attachments[\\/][a-f0-9]{64}[\\/]/u.test(n[3]))break;let s;try{s=JSON.parse(n[2])}catch{break}e.unshift({name:s,image:/\.(?:png|jpe?g|webp|gif)$/iu.test(s)}),t=t.slice(0,n.index)}return{text:t,attachments:e}}var O="pi-webapp/paused",se="pi-webapp/resume";function U(r){for(let e=r.length-1;e>=0;e--){let t=r[e];if(t.type==="custom_message"&&t.customType===se)return!1;if(t.type==="custom"&&t.customType===O)return!0;if(t.type==="message"){if(t.message.role==="user")return!1;if(t.message.role==="assistant"){if(t.message.stopReason==="aborted")return!0;if(t.message.stopReason==="stop"||t.message.stopReason==="length"||t.message.stopReason==="error")return!1}}}return!1}function oe(r,e){let t=[],n;for(let s of r){if(s.type==="message"&&(n=s.id),s.type!=="custom")continue;let a=e.find(u=>s.customType.startsWith(`${u}/`));if(a){try{if(JSON.stringify(s.data).length>128*1024)continue}catch{continue}t.push({id:s.id,pluginId:a,kind:s.customType,data:s.data,timestamp:s.timestamp,...n?{afterMessageId:n}:{}})}}return t}function R(r){return typeof r=="string"?[{kind:"text",text:r}]:r.flatMap(e=>e.type==="text"?[{kind:"text",text:e.text}]:e.type==="thinking"?[{kind:"thinking",text:e.thinking}]:e.type==="image"?[{kind:"image",text:"\u56FE\u7247\u9644\u4EF6"}]:e.type==="toolCall"?[{kind:"toolCall",text:JSON.stringify(e.arguments??{}),toolName:e.name,toolCallId:e.id}]:[])}function ae(r){if(r.type==="custom_message")return r.display?{id:r.id,role:"notice",timestamp:r.timestamp,blocks:R(r.content)}:null;if(r.type!=="message")return null;let{message:e}=r;return e.role==="user"||e.role==="assistant"?{id:r.id,role:e.role,timestamp:r.timestamp,blocks:R(e.content),...e.role==="assistant"?{...e.stopReason==="error"&&e.errorMessage?{error:e.errorMessage}:{},usage:{input:e.usage.input,output:e.usage.output,cacheRead:e.usage.cacheRead,cacheWrite:e.usage.cacheWrite,...e.usage.reasoning===void 0?{}:{reasoning:e.usage.reasoning},totalTokens:e.usage.totalTokens,cost:e.usage.cost.total},model:`${e.provider}/${e.model}`}:{}}:e.role==="toolResult"?{id:r.id,role:"tool",timestamp:r.timestamp,blocks:R(e.content),isError:e.isError,toolCallId:e.toolCallId,toolName:e.toolName}:null}function ce(r,e){let t=r?.trim();if(t)return t;let n=e.find(a=>a.role==="user"),s=Ve(n?.blocks.find(a=>a.kind==="text")?.text??"").text.replace(/\s+/g," ").trim();return s?s.slice(0,50):"\u5F53\u524D\u4F1A\u8BDD"}function De(r,e,t=[]){let n=r.sessionManager.getBranch().flatMap(s=>{let a=ae(s);return a?[a]:[]});return{schemaVersion:1,sessionId:r.sessionManager.getSessionId(),cwd:r.cwd,name:ce(e,n),model:r.model?`${r.model.provider}/${r.model.id}`:null,thinkingLevel:r.thinkingLevel??null,thinkingLevels:r.model?vr(r.model):["off"],idle:r.isIdle(),paused:U(r.sessionManager.getBranch()),contextUsage:r.getContextUsage()??null,messages:n,pluginEntries:oe(r.sessionManager.getBranch(),t)}}import{randomUUID as le}from"node:crypto";import{mkdir as $e,readFile as kr,realpath as Fe,rename as br,rm as Pr,stat as He,writeFile as Er}from"node:fs/promises";import{basename as Ge,dirname as Sr,isAbsolute as Je,join as Ir}from"node:path";var J=class{items=[];hiddenPaths=[];mutationChain=Promise.resolve();file;constructor(e){this.file=e}async load(){try{let e=JSON.parse(await kr(this.file,"utf8")),t,n=[];if(Array.isArray(e)?t=e:e&&typeof e=="object"&&"version"in e&&e.version===2&&"items"in e&&"hiddenPaths"in e&&(t=e.items,n=e.hiddenPaths),!Array.isArray(t)||!Array.isArray(n))throw new Error("\u5DE5\u4F5C\u533A\u8BB0\u5F55\u65E0\u6548");this.items=t.filter(s=>typeof s=="object"&&s!==null&&typeof s.id=="string"&&typeof s.path=="string"&&typeof s.title=="string"),this.hiddenPaths=n.filter(s=>typeof s=="string")}catch(e){if(e.code!=="ENOENT")throw e}}list(){return[...this.items]}get(e){return this.items.find(t=>t.id===e)}async add(e,t=!1){if(!Je(e)||e.includes("\0"))throw new Error("\u8BF7\u8F93\u5165\u5B8C\u6574\u7684\u76EE\u5F55\u8DEF\u5F84");t&&await $e(e,{recursive:!0});let n=await Fe(e);if(!(await He(n)).isDirectory())throw new Error("\u8DEF\u5F84\u4E0D\u662F\u76EE\u5F55");return this.mutate(async()=>{let s=this.hiddenPaths.filter(o=>o!==n),a=this.items.find(o=>o.path===n);if(a)return s.length!==this.hiddenPaths.length&&(await this.save(this.items,s),this.hiddenPaths=s),a;let u={id:le(),path:n,title:Ge(n)||n},p=[u,...this.items];return await this.save(p,s),this.items=p,this.hiddenPaths=s,u})}async discover(e){let t=(await Promise.all([...new Set(e)].filter(Je).map(async n=>{try{let s=await Fe(n);return(await He(s)).isDirectory()?s:null}catch{return null}}))).filter(n=>n!==null);await this.mutate(async()=>{let n=new Set([...this.items.map(u=>u.path),...this.hiddenPaths]),s=[];for(let u of t)n.has(u)||(n.add(u),s.push({id:le(),path:u,title:Ge(u)||u}));if(s.length===0)return;let a=[...this.items,...s];await this.save(a,this.hiddenPaths),this.items=a})}async remove(e){await this.mutate(async()=>{let t=this.get(e);if(!t)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");let n=this.items.filter(a=>a.id!==e),s=[...new Set([...this.hiddenPaths,t.path])];await this.save(n,s),this.items=n,this.hiddenPaths=s})}mutate(e){let t=this.mutationChain.then(e,e);return this.mutationChain=t.then(()=>{},()=>{}),t}async save(e,t){await $e(Sr(this.file),{recursive:!0});let n=`${this.file}.${le()}.tmp`;try{await Er(n,JSON.stringify({version:2,items:e,hiddenPaths:t},null,2),{mode:384}),await br(n,this.file)}catch(s){throw await Pr(n,{force:!0}),s}}};function ze(r){return Ir(r,"pi-web","workspaces.json")}import{createAgentSession as ri,createEventBus as ii,DefaultResourceLoader as ni,getAgentDir as si,SessionManager as Y}from"@earendil-works/pi-coding-agent";var xr="pi-webapp:interaction-open:v1",Cr="pi-webapp:interaction-accept:v1",qe="pi-webapp:interaction-settle:v1",Ar="pi-webapp:interaction-cancel:v1";var B=class{bus;accepts;changed;requests=new Map;detach;constructor(e,t,n){this.bus=e,this.accepts=t,this.changed=n,this.detach=[e.on(xr,s=>{!Mr(s)||!t(s)||this.requests.has(s.requestId)||(this.requests.set(s.requestId,s),e.emit(Cr,{requestId:s.requestId}),n())}),e.on(Ar,s=>{let a=s,u=this.requests.get(a?.requestId);u&&u.sessionId===a.sessionId&&u.pluginId===a.pluginId&&(this.requests.delete(a.requestId),n())})]}pending(e){return[...this.requests.values()].filter(t=>t.sessionId===e)}resolve(e,t,n,s){let a=this.requests.get(n);if(!a||a.sessionId!==e||a.pluginId!==t||!this.accepts(a))throw new Error("Interaction expired or session changed");this.requests.delete(n),this.bus.emit(qe,{requestId:n,value:s}),this.changed()}cancelAll(e="Session changed"){for(let t of this.requests.values())this.bus.emit(qe,{requestId:t.requestId,error:e});this.requests.clear(),this.changed()}dispose(){for(let e of this.detach)e();this.cancelAll("Interaction host unloaded")}};function Mr(r){if(!r||typeof r!="object")return!1;let e=r;for(let t of["requestId","sessionId","pluginId","kind"])if(typeof e[t]!="string"||!e[t]||e[t].length>200)return!1;try{return JSON.stringify(e.data).length<=128*1024}catch{return!1}}var Wr=1,Tr="pi-webapp:action:v1",Rr="pi-webapp:action-response:v1",z="pi-webapp:plugin-changed:v1";function Ke(r){if(!r||typeof r!="object")return!1;let e=r;return e.apiVersion===Wr&&typeof e.client=="string"&&/^\.\/dist\/[\w.-]+\.js$/.test(e.client)&&(e.style===void 0||typeof e.style=="string"&&/^\.\/dist\/[\w.-]+\.css$/.test(e.style))}function q(r,e,t=15e3,n){return new Promise((s,a)=>{let u=!1,p=(m,v)=>{u||(u=!0,clearTimeout(d),o(),n?.removeEventListener("abort",f),m?a(m):s(v))},o=r.on(Rr,m=>{let v=m;v?.requestId===e.requestId&&p(v.ok?null:new Error(v.error??"Plugin action failed"),v.value)}),d=setTimeout(()=>p(new Error(`Plugin action timed out: ${e.pluginId}/${e.action}`)),t),f=()=>p(new Error("Plugin action runtime unloaded"));if(n?.addEventListener("abort",f,{once:!0}),n?.aborted)f();else try{r.emit(Tr,e)}catch(m){p(m instanceof Error?m:new Error(String(m)))}})}import{realpath as st}from"node:fs/promises";import{readFile as de,realpath as Ze,stat as et}from"node:fs/promises";import{createHash as Nr}from"node:crypto";import{dirname as Ye,isAbsolute as _r,join as pe,parse as jr,resolve as Br,sep as Lr,delimiter as Or}from"node:path";import{DefaultPackageManager as Ur,getAgentDir as Vr,SettingsManager as Dr}from"@earendil-works/pi-coding-agent";async function Xe(r,e){let t=await de(r),n=e?await de(e):void 0;if(t.length>8*1024*1024||(n?.length??0)>8*1024*1024)throw new Error("Plugin asset exceeds 8 MB");let s=Nr("sha256").update(t).update("\0").update(n??"").digest("hex");return{clientBytes:t,styleBytes:n,revision:s}}function $r(){return(process.env.PI_WEBAPP_PLUGIN_DEV_ROOTS??"").split(Or).filter(Boolean).map(r=>Br(r))}async function Fr(r){let e=Ye(r);for(;e!==jr(e).root;)try{return await et(pe(e,"package.json")),e}catch{e=Ye(e)}return null}async function Qe(r,e){let t=await Ze(pe(r,e));if(!t.startsWith(r+Lr))throw new Error("Asset escapes package root");let n=await et(t);if(!n.isFile()||n.size>8*1024*1024)throw new Error("Plugin asset is not a regular file under 8 MB");return t}var N=class r{plugins;errors;extensionRoots;constructor(e,t,n){this.plugins=e,this.errors=t,this.extensionRoots=n}static async discover(e,t,n=$r()){let s=Dr.create(e,void 0,{projectTrusted:t}),a=new Ur({cwd:e,agentDir:Vr(),settingsManager:s}),u=await a.resolve(async()=>"skip"),p=n.length?await a.resolveExtensionSources(n,{temporary:!0}):{extensions:[]},o=new Set;for(let k of[...u.extensions,...p.extensions]){if(!k.enabled)continue;let w=await Fr(k.path);w&&o.add(w)}for(let k of n)_r(k)&&o.add(k);let d=[],f=[],m=[],v=new Set;for(let k of o)try{let w=await Ze(k),l=JSON.parse(await de(pe(w,"package.json"),"utf8"));if(l.piWebapp===void 0)continue;if(typeof l.name!="string"||!l.name)throw new Error("Missing package name");if(!Ke(l.piWebapp))throw new Error("Unsupported piWebapp manifest or asset path");if(v.has(l.name))throw new Error(`Duplicate plugin id: ${l.name}`);let h=await Qe(w,l.piWebapp.client),M=l.piWebapp.style?await Qe(w,l.piWebapp.style):void 0;v.add(l.name),d.push({id:l.name,root:w,manifest:l.piWebapp,clientPath:h,stylePath:M,...await Xe(h,M)}),m.push(w)}catch(w){f.push(`${k}: ${w instanceof Error?w.message:String(w)}`)}return d.sort((k,w)=>k.id.localeCompare(w.id)),new r(d,f,m)}has(e){return this.plugins.some(t=>t.id===e)}ids(){return this.plugins.map(e=>e.id)}async refreshAssets(){for(let e of this.plugins)Object.assign(e,await Xe(e.clientPath,e.stylePath))}view(){return{plugins:this.plugins.map(e=>({id:e.id,client:`/plugins/${encodeURIComponent(e.id)}/client.js?v=${e.revision}`,...e.stylePath?{style:`/plugins/${encodeURIComponent(e.id)}/client.css?v=${e.revision}`}:{}})),errors:this.errors}}async asset(e){let t=new URL(e,"http://localhost"),n=/^\/plugins\/([^/]+)\/(client\.js|client\.css)$/.exec(t.pathname);if(!n)return null;let s;try{s=decodeURIComponent(n[1])}catch{return null}let a=this.plugins.find(p=>p.id===s);if(!a||t.searchParams.has("v")&&t.searchParams.get("v")!==a.revision)return null;let u=n[2]==="client.js"?a.clientBytes:a.styleBytes;return u?{bytes:u,type:n[2]==="client.js"?"text/javascript; charset=utf-8":"text/css; charset=utf-8"}:null}};import{realpath as tt}from"node:fs/promises";import{SessionManager as Hr}from"@earendil-works/pi-coding-agent";async function V(r,e){let t=await tt(r),n=e??await Hr.listAll(),s=await Promise.all(n.map(async a=>a.cwd!==""&&await tt(a.cwd).catch(()=>null)===t));return n.filter((a,u)=>s[u])}var _=class{tail=Promise.resolve();run(e){let t=this.tail.then(e);return this.tail=t.catch(()=>{}),t}wrap(e){return(...t)=>this.run(()=>e(...t))}},rt=new WeakMap;function it(r,e,t,n=5e3,s=()=>{}){let a=rt.get(r);if(a)return a;let u=(async()=>{let p;try{await Promise.race([r.extensionRunner.emit({type:"session_shutdown",reason:e}),new Promise((o,d)=>{p=setTimeout(()=>d(new Error("Plugin shutdown timed out")),n)})])}catch(o){t(o instanceof Error?o.message:String(o))}finally{clearTimeout(p);try{s()}finally{r.dispose()}}})();return rt.set(r,u),u}function K(r){let t=[...r].reverse().find(n=>n.role==="assistant")?.blocks.filter(n=>n.kind==="text").map(n=>n.text).join(`
|
|
8
|
+
`);return{customType:se,display:!1,details:{action:"resume"},content:"The user clicked Continue for the interrupted turn. Continue the response to the latest user request from the interrupted point. Preserve completed work and do not repeat text already delivered. Check existing task progress when needed."+(t?`
|
|
9
|
+
Already displayed assistant text (reference data):
|
|
10
|
+
${JSON.stringify(t)}`:"")}}import{createHash as Gr}from"node:crypto";import{readFile as Jr,writeFile as zr,unlink as qr}from"node:fs/promises";import{basename as Kr,dirname as Yr,extname as Xr,join as Qr}from"node:path";import{DefaultPackageManager as Zr,getAgentDir as ei,SettingsManager as ti}from"@earendil-works/pi-coding-agent";var D=new Map;async function nt(r,e){let n=await new Zr({cwd:r,agentDir:ei(),settingsManager:ti.create(r)}).resolveExtensionSources([...e],{temporary:!0}),s=[],a=[],u=async()=>{for(let p of s.splice(0)){let o=(D.get(p)??1)-1;o?D.set(p,o):(D.delete(p),await qr(p).catch(()=>{}))}};try{for(let p of n.extensions){if(!p.enabled)continue;let o=Xr(p.path);if(![".js",".mjs"].includes(o)){a.push(p.path);continue}let d=await Jr(p.path),f=Gr("sha256").update(d).digest("hex"),m=Qr(Yr(p.path),`.pi-web-runtime-${Kr(p.path,o)}-${f}${o}`);await zr(m,d,{flag:"wx"}).catch(v=>{if(v.code!=="EEXIST")throw v}),D.set(m,(D.get(m)??0)+1),s.push(m),a.push(m)}return{paths:a,release:u}}catch(p){throw await u(),p}}var X=class{active=null;queue=new _;generation=0;disposed=!1;publish;fallbackModel;isProjectTrusted;constructor(e,t,n=()=>!1){this.publish=e,this.fallbackModel=t,this.isProjectTrusted=n}get session(){return this.active?.session??null}get path(){return this.active?.cwd??null}get catalog(){return this.active?.catalog??null}open(e,t){return this.queue.run(async()=>{this.ensureAvailable();let n=await st(e),s;if(t==="new")s=Y.create(n);else if(t==="continue"){let a=(await V(n))[0];s=a?Y.open(a.path):Y.create(n)}else s=Y.open(t.sessionFile);if(await st(s.getCwd())!==n)throw new Error("\u4F1A\u8BDD\u4E0D\u5C5E\u4E8E\u8BE5\u5DE5\u4F5C\u533A");await this.replace(n,s,t==="new"?"new":"resume")})}reload(){return this.queue.run(async()=>{this.ensureAvailable();let e=this.active;if(!e)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u5DE5\u4F5C\u533A\u4F1A\u8BDD");await this.replace(e.cwd,e.session.sessionManager,"reload")})}ensureAvailable(){if(this.disposed)throw new Error("\u5DE5\u4F5C\u533A\u670D\u52A1\u5DF2\u5173\u95ED");if(this.active&&!this.active.session.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u5DE5\u4F5C\u533A")}diagnostic(e,t,n,s){let a=`plugin=${t} session=${e.session.sessionManager.getSessionId()} generation=${e.generation} stage=${n}: ${s}`;console.error(a),this.disposed||this.publish({type:"error",message:a})}async replace(e,t,n){let s=this.active,a=await N.discover(e,this.isProjectTrusted(e)),u=ii(),p=await nt(e,a.extensionRoots),o=new ni({cwd:e,agentDir:si(),noExtensions:!0,additionalExtensionPaths:p.paths,eventBus:u}),d=null;try{await o.reload();let f=o.getExtensions().errors;if(f.length)throw new Error(f.map(b=>`${b.path}: ${b.error}`).join("; "));let m=t.buildSessionProjection().model?void 0:s?.session.model??this.fallbackModel(),{session:v}=await ri({cwd:e,sessionManager:t,model:m,resourceLoader:o}),k={session:v,cwd:e,catalog:a,bus:u,generation:++this.generation,closing:!1,waitController:new AbortController,interactions:null,detach:()=>{},releasePaths:p.release};d=k;let w=b=>{!this.disposed&&this.active===k&&!k.closing&&this.publish(b)};k.interactions=new B(u,b=>!k.closing&&b.sessionId===v.sessionManager.getSessionId()&&a.has(b.pluginId),()=>w({type:"snapshot",session:this.snapshotOf(k)}));let l=0,h=u.on(z,()=>w({type:"snapshot",session:this.snapshotOf(k)})),M=v.subscribe(b=>{b.type==="message_update"&&b.message.role==="assistant"&&Date.now()-l>=60&&(l=Date.now(),w({type:"stream",message:{id:"stream",role:"assistant",timestamp:new Date(b.message.timestamp).toISOString(),blocks:R(b.message.content)}})),["message_end","agent_start","agent_settled","session_info_changed","entry_appended"].includes(b.type)&&(b.type==="message_end"&&b.message.role==="assistant"&&w({type:"stream",message:null}),w({type:"snapshot",session:this.snapshotOf(k)}))});k.detach=()=>{h(),M()};let c=[],y=!0;if(await v.bindExtensions({mode:"print",shutdownHandler:()=>{},onError:b=>{y&&c.push(b.error),this.diagnostic(k,a.plugins.find(P=>b.extensionPath.startsWith(P.root+"/"))?.id??b.extensionPath,b.event??"runtime",b.error)}}),y=!1,c.length)throw new Error(c.join("; "));if(this.ensureAvailable(),s&&await this.close(s,n),this.disposed)throw new Error("\u5DE5\u4F5C\u533A\u670D\u52A1\u5DF2\u5173\u95ED");this.active=k,d=null,this.publish({type:"stream",message:null}),this.publish({type:"snapshot",session:this.snapshot()})}catch(f){throw d?await this.close(d,"quit"):(u.clear(),await p.release()),f}}async close(e,t){e.closing||(e.closing=!0,e.waitController.abort(),e.interactions.dispose(),await it(e.session,t,n=>this.diagnostic(e,"host","shutdown",n),5e3,()=>{e.detach(),e.bus.clear()}),await e.releasePaths())}snapshotOf(e){let{session:t,cwd:n,catalog:s}=e,a=t.sessionManager.getBranch().flatMap(u=>{let p=ae(u);return p?[p]:[]});return{schemaVersion:1,sessionId:t.sessionManager.getSessionId(),cwd:n,name:ce(t.sessionManager.getSessionName(),a),model:t.model?`${t.model.provider}/${t.model.id}`:null,thinkingLevel:t.thinkingLevel,thinkingLevels:t.getAvailableThinkingLevels(),idle:t.isIdle,paused:U(t.sessionManager.getBranch()),contextUsage:t.getContextUsage()??null,messages:a,interactions:e.interactions.pending(t.sessionManager.getSessionId()),pluginEntries:oe(t.sessionManager.getBranch(),s.ids())}}snapshot(){if(!this.active)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u5DE5\u4F5C\u533A\u4F1A\u8BDD");return this.snapshotOf(this.active)}async invokePluginAction(e){let t=this.active;if(this.disposed||!t||t.closing||e.sessionId!==t.session.sessionManager.getSessionId())throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362");if(!t.catalog.has(e.pluginId))throw new Error("\u63D2\u4EF6\u672A\u542F\u7528");let n=t.session.extensionRunner,s=await q(t.bus,e,15e3,t.waitController.signal);if(this.active!==t||t.closing||n!==t.session.extensionRunner)throw new Error("\u4F1A\u8BDD\u8FD0\u884C\u5B9E\u4F8B\u5DF2\u5207\u6362");return this.publish({type:"snapshot",session:this.snapshot()}),s}resolveInteraction(e,t,n,s){if(this.disposed||!this.active||this.active.closing)throw new Error("Interaction host unavailable");this.active.interactions.resolve(e,t,n,s)}async send(e,t=[]){if(this.disposed||!this.session||!this.session.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let n=this.session,s=!1,a,u,p=new Promise((o,d)=>{a=o,u=d});n.prompt(e,{images:t,preflightResult:o=>{o&&(s=!0,a())}}).then(()=>{s||a()}).catch(o=>{s?this.publish({type:"error",message:o instanceof Error?o.message:"Pi \u8BF7\u6C42\u5931\u8D25"}):u(o)}),await p}async stop(){let e=this.active;!e||e.session.isIdle||(e.session.sessionManager.appendCustomEntry(O),await e.session.abort(),this.active===e&&!e.closing&&this.publish({type:"snapshot",session:this.snapshotOf(e)}))}async resume(){let e=this.active;if(this.disposed||!e||e.closing)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");let t=e.session;if(!t.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(!U(t.sessionManager.getBranch()))throw new Error("\u5F53\u524D\u4F1A\u8BDD\u6CA1\u6709\u6682\u505C\u7684\u4EFB\u52A1");if(!t.model)throw new Error("\u8BF7\u5148\u9009\u62E9\u6A21\u578B");if(!(t.modelRuntime.hasConfiguredAuth(t.model.provider)||await t.modelRuntime.checkAuth(t.model.provider)!==void 0))throw new Error("\u8BF7\u5148\u8FDE\u63A5\u5F53\u524D\u6A21\u578B");if(this.active!==e||e.closing)throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362");if(!t.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(!U(t.sessionManager.getBranch()))throw new Error("\u5F53\u524D\u4F1A\u8BDD\u6CA1\u6709\u6682\u505C\u7684\u4EFB\u52A1");let s=K(this.snapshotOf(e).messages);t.sendCustomMessage(s,{triggerTurn:!0}).catch(a=>{this.active===e&&!e.closing&&this.publish({type:"error",message:a instanceof Error?a.message:"\u7EE7\u7EED\u5931\u8D25"})})}async models(){return(await this.session?.modelRuntime.getAvailable()??[]).map(t=>({provider:t.provider,id:t.id,name:t.name}))}async setModel(e,t){if(this.disposed||!this.session||!this.session.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let n=this.session.modelRuntime.getModel(e,t);if(!n)throw new Error("\u6A21\u578B\u4E0D\u53EF\u7528");await this.session.setModel(n),this.publish({type:"snapshot",session:this.snapshot()})}dispose(){return this.disposed=!0,this.queue.run(async()=>{let e=this.active;this.active=null,e&&await this.close(e,"quit")})}};import{basename as ue,dirname as oi}from"node:path";function ot(r,e){let t=n=>e[n].map(s=>({name:n==="skills"&&ue(s.path).toLowerCase()==="skill.md"?ue(oi(s.path)):ue(s.path),path:s.path,source:s.metadata.source,scope:s.metadata.scope,enabled:s.enabled}));return{packages:r.map(n=>({name:n.source,path:n.installedPath??"",source:n.source,scope:n.scope,enabled:!!n.installedPath})),extensions:t("extensions"),skills:t("skills")}}import{execFile as ai}from"node:child_process";var ci=(r,e)=>new Promise((t,n)=>{ai(r,[...e],{windowsHide:!0},s=>{s?n(s):t()})});async function fe(r,e=process.platform,t=process.env,n=ci){if(t.SSH_CONNECTION||t.SSH_TTY||t.SSH_CLIENT||e==="linux"&&!t.DISPLAY&&!t.WAYLAND_DISPLAY)return!1;let s=e==="darwin"?"open":e==="linux"?"xdg-open":e==="win32"?"explorer.exe":null;return s===null?!1:(await n(s,[r]),!0)}import{execFile as li}from"node:child_process";import{randomUUID as di}from"node:crypto";import{existsSync as at}from"node:fs";import{access as pi,mkdir as ui,readFile as ct,rename as fi,rm as ge,writeFile as lt}from"node:fs/promises";import{join as C}from"node:path";import{promisify as gi}from"node:util";var mi=gi(li),Q=/^(\d+)\.(\d+)\.(\d+)(?:-([0-9A-Za-z.-]+))?$/;function wi(r,e){let t=Q.exec(r),n=Q.exec(e);if(!t||!n)throw new Error("\u7248\u672C\u53F7\u65E0\u6548");for(let s=1;s<=3;s++){let a=Number(t[s])-Number(n[s]);if(a)return a}return!t[4]&&n[4]?1:t[4]&&!n[4]?-1:(t[4]??"").localeCompare(n[4]??"",void 0,{numeric:!0})}async function hi(r){try{let{stdout:e}=await mi("npm",r,{timeout:18e4,maxBuffer:1048576,encoding:"utf8"});return e}catch(e){let t=e;throw new Error(t.stderr?.trim()||t.message)}}var Z=class{agentDir;packageRoot;launcherNonce;runNpm;preparing=!1;restartPending=!1;constructor(e){this.agentDir=e.agentDir,this.packageRoot=e.packageRoot,this.launcherNonce=e.launcherNonce,this.runNpm=e.runNpm??hi}async current(){let e=JSON.parse(await ct(C(this.packageRoot,"package.json"),"utf8"));if(e.name!=="pi-webapp"||typeof e.version!="string"||!Q.test(e.version))throw new Error("\u5F53\u524D pi-webapp \u7248\u672C\u65E0\u6548");return e.version}async runningVersion(){return this.current()}async check(){let e=await this.current(),t=at(C(this.packageRoot,".git")),n={current:e,latest:null,available:!1,canRestart:!!this.launcherNonce&&!t};t?n.reason="\u5F53\u524D\u4ECE\u6E90\u7801\u76EE\u5F55\u8FD0\u884C\u3002\u7F51\u9875\u5347\u7EA7\u4EC5\u652F\u6301 npm \u5B89\u88C5\u7684\u7248\u672C\uFF0C\u4EE5\u514D\u8986\u76D6\u672C\u5730\u4EE3\u7801\u3002":n.canRestart||(n.reason="\u5F53\u524D\u9875\u9762\u7531 Pi \u7EC8\u7AEF\u6253\u5F00\uFF0C\u65E0\u6CD5\u4ECE\u7F51\u9875\u81EA\u52A8\u91CD\u542F Pi\uFF1B\u8BF7\u4F7F\u7528 pi-webapp \u542F\u52A8\u5668\u3002");try{let s=JSON.parse((await this.runNpm(["view","pi-webapp","dist-tags.latest","--json","--prefer-online"])).trim());if(typeof s!="string"||!Q.test(s))throw new Error("npm \u8FD4\u56DE\u7684\u7248\u672C\u53F7\u65E0\u6548");n.latest=s,n.available=wi(s,e)>0}catch(s){throw new Error(`\u68C0\u67E5 npm \u66F4\u65B0\u5931\u8D25\uFF1A${s instanceof Error?s.message:String(s)}`)}return n}async prepare(){if(!this.launcherNonce)throw new Error("\u5F53\u524D\u9875\u9762\u65E0\u6CD5\u81EA\u52A8\u91CD\u542F Pi");if(at(C(this.packageRoot,".git")))throw new Error("\u6E90\u7801\u76EE\u5F55\u4E0D\u80FD\u901A\u8FC7\u7F51\u9875\u5347\u7EA7");if(this.restartPending)throw new Error("\u5347\u7EA7\u5DF2\u5B8C\u6210\uFF0C\u6B63\u5728\u91CD\u542F");if(this.preparing)throw new Error("\u5347\u7EA7\u6B63\u5728\u8FDB\u884C\u4E2D");this.preparing=!0;try{let e=await this.check();if(!e.available||!e.latest)throw new Error("\u5F53\u524D\u5DF2\u662F\u6700\u65B0\u7248\u672C");let t=C(this.agentDir,"pi-web","releases",e.latest);await ge(t,{recursive:!0,force:!0}),await ui(t,{recursive:!0});try{await this.runNpm(["install",`pi-webapp@${e.latest}`,"--prefix",t,"--ignore-scripts","--no-save","--no-audit","--no-fund"]);let n=C(t,"node_modules","pi-webapp"),s=JSON.parse(await ct(C(n,"package.json"),"utf8"));if(s.name!=="pi-webapp"||s.version!==e.latest)throw new Error("\u4E0B\u8F7D\u7684\u5305\u4E0E\u76EE\u6807\u7248\u672C\u4E0D\u7B26");let a=C(n,"bin","pi-webapp.mjs");await Promise.all([a,C(n,"dist","extension.js"),C(n,"web","dist","index.html")].map(o=>pi(o)));let u=C(this.agentDir,"pi-web"),p=C(u,`update.${di()}.tmp`);try{await lt(p,JSON.stringify({version:e.latest,launcher:a}),{mode:384}),await fi(p,C(u,"update.json"))}finally{await ge(p,{force:!0})}return this.restartPending=!0,{version:e.latest,launcher:a}}catch(n){throw await ge(t,{recursive:!0,force:!0}),n}}finally{this.preparing=!1}}async requestRestart(e){if(!this.launcherNonce)throw new Error("\u5F53\u524D\u9875\u9762\u65E0\u6CD5\u81EA\u52A8\u91CD\u542F Pi");try{await lt(C(this.agentDir,"pi-web","launcher.restart"),JSON.stringify({nonce:this.launcherNonce,launcher:e.launcher}),{mode:384})}catch(t){throw this.restartPending=!1,t}}};import{randomUUID as xi}from"node:crypto";var dt=we(vi(Pi(import.meta.url)),"../web/dist"),Ci=Symbol.for(`pi-web.bridge-state:${import.meta.url}`),i=globalThis[Ci]??={bridge:null,current:null,commandContext:null,pi:null,replacementContext:null,replacementSessionId:null,lastStreamAt:0,workspaces:null,workspaceSessions:null,selected:"tui",activeWorkspaceId:null,autoOpened:!1,tuiCatalog:null,stopPluginWatch:null,interactions:null,lifecycle:new _,tuiGeneration:0,stopChanged:null,tuiWaitController:new AbortController};i.lifecycle??=new _;i.tuiGeneration??=0;i.stopChanged??=null;i.tuiWaitController??=new AbortController;function $(){return i.selected==="sdk"?i.workspaceSessions?.catalog??null:i.tuiCatalog}var Ai=null;function Mi(){return Ai??=Ei.create({refreshOnCreate:!1})}var te=new Map;async function L(){let r=await Mi(),e=i.selected==="tui"?i.current?.modelRegistry:void 0,t=new Set(e?.getRegisteredProviderIds()??[]);for(let n of te.keys())t.has(n)||(r.unregisterProvider(n),te.delete(n));for(let n of t){let s=e?.getRegisteredNativeProvider(n),a=e?.getRegisteredProviderConfig(n),u=s??a;!u||te.get(n)===u||(s?r.registerNativeProvider(s):a&&r.registerProvider(n,a),te.set(n,u))}return await r.refresh({allowNetwork:!1}),r}function I(){if(i.selected==="sdk")return i.workspaceSessions?.snapshot()??(()=>{throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD")})();if(i.current===null)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");return{...De(i.current,i.current.sessionManager.getSessionName(),$()?.ids()??[]),interactions:i.interactions?.pending(i.current.sessionManager.getSessionId())??[]}}function E(r){if(I().sessionId!==r)throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362")}async function ft(){let r=i.workspaces?.list()??[],e=I(),t=await re(e.cwd).catch(()=>e.cwd),n=await ut.listAll(),s=(await Promise.all(r.map(async a=>{let p=(await V(a.path,n).catch(()=>[])).map(o=>({id:o.id,workspaceId:a.id,path:o.path,name:o.name||o.firstMessage?.slice(0,50)||"\u5F53\u524D\u4F1A\u8BDD",modified:o.modified.toISOString()}));return a.path===t&&!p.some(o=>o.id===e.sessionId)&&p.unshift({id:e.sessionId,workspaceId:a.id,path:null,name:e.name,modified:new Date().toISOString()}),p}))).flat();return{items:r,activeId:i.activeWorkspaceId,sessions:s}}async function W(){i.bridge&&i.bridge.publish({type:"workspaces",value:await ft()})}async function me(r,e=!1){let t=i.workspaces?.get(r);if(!t)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");if(await re(t.path),!e&&i.current&&t.path===await re(i.current.cwd)){if(i.selected==="sdk"&&i.workspaceSessions?.session&&!i.workspaceSessions.session.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u5DE5\u4F5C\u533A");i.selected="tui",i.activeWorkspaceId=r,i.bridge?.publish({type:"stream",message:null}),i.bridge?.publish({type:"snapshot",session:I()})}else{if(!i.workspaceSessions)throw new Error("Pi \u5DE5\u4F5C\u533A\u670D\u52A1\u4E0D\u53EF\u7528");await i.workspaceSessions.open(t.path,e?"new":"continue"),i.selected="sdk",i.activeWorkspaceId=r,i.bridge?.publish({type:"snapshot",session:I()})}await W()}function A(r){let e=i.current;if(e===null||e.sessionManager.getSessionId()!==r)throw new Error("\u4F1A\u8BDD\u5DF2\u5207\u6362");return e}function S(r){i.current=r,i.selected==="tui"&&i.bridge?.publish({type:"snapshot",session:I()})}function gt(){if(i.current===null)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");let r=i.selected==="sdk"?i.workspaceSessions?.path:i.current.cwd;if(!r)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u5DE5\u4F5C\u533A");let e=i.selected==="tui"?i.current.isProjectTrusted():i.workspaceSessions?.session?.settingsManager.isProjectTrusted()??!1;return Si.create(r,void 0,{projectTrusted:e})}async function mt(){let r=gt(),e=s=>({packages:(s.packages??[]).map(a=>typeof a=="string"?a:a.source),extensions:s.extensions??[],skills:s.skills??[]}),t=new pt({cwd:I().cwd,agentDir:j(),settingsManager:r}),n=ot(t.listConfiguredPackages(),await t.resolve(async()=>"skip"));return{projectTrusted:r.isProjectTrusted(),global:e(r.getGlobalSettings()),project:e(r.getProjectSettings()),installed:n}}async function Wi(r){E(r.sessionId);let e=i.selected==="tui"?A(r.sessionId):null;if(e?!e.isIdle():!i.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let t=gt();if(r.scope==="project"&&!t.isProjectTrusted())throw new Error("\u5F53\u524D\u9879\u76EE\u5C1A\u672A\u53D7\u4FE1\u4EFB\uFF0C\u65E0\u6CD5\u4FEE\u6539\u9879\u76EE\u8BBE\u7F6E");let n=r.value.trim(),s=r.scope==="project"?t.getProjectSettings():t.getGlobalSettings();if(r.kind==="packages"){let a=new pt({cwd:I().cwd,agentDir:j(),settingsManager:t});r.action==="add"?await a.installAndPersist(n,{local:r.scope==="project"}):await a.removeAndPersist(n,{local:r.scope==="project"})}else if(r.kind==="extensions"){let a=s.extensions??[],u=r.action==="add"?[...new Set([...a,n])]:a.filter(p=>p!==n);r.scope==="project"?t.setProjectExtensionPaths(u):t.setExtensionPaths(u)}else{let a=s.skills??[],u=r.action==="add"?[...new Set([...a,n])]:a.filter(p=>p!==n);r.scope==="project"?t.setProjectSkillPaths(u):t.setSkillPaths(u)}return await t.flush(),i.selected==="tui"?(i.commandContext&&await i.commandContext.reload(),i.current&&S(i.current)):(await i.workspaceSessions?.reload(),i.bridge?.publish({type:"plugins_changed"})),await mt()}function Ti(r,e=fe){i.pi=r,i.interactions?.dispose(),i.interactions=new B(r.events,s=>!!i.bridge&&i.selected==="tui"&&s.sessionId===i.current?.sessionManager.getSessionId()&&!!i.tuiCatalog?.has(s.pluginId),()=>{i.current&&i.selected==="tui"&&S(i.current)});let t=()=>{i.stopChanged?.(),i.stopChanged=r.events.on(z,()=>{i.selected==="tui"&&i.current&&S(i.current)})};t(),r.on("session_start",async(s,a)=>{if(i.tuiWaitController.abort(),i.tuiWaitController=new AbortController,i.tuiGeneration++,t(),i.current=a,i.bridge){let u=await N.discover(a.cwd,a.isProjectTrusted?.()??!1);if(i.current!==a)return;i.tuiCatalog=u}i.replacementSessionId!==a.sessionManager.getSessionId()&&(i.replacementContext=null,i.replacementSessionId=null),S(a),i.bridge&&i.bridge.publish({type:"plugins_changed"}),i.selected==="tui"&&i.workspaces&&i.workspaces.add(a.cwd).then(async u=>{i.selected!=="tui"||i.current?.sessionManager.getSessionId()!==a.sessionManager.getSessionId()||(i.activeWorkspaceId=u.id,await W())}).catch(u=>{i.bridge?.publish({type:"error",message:u instanceof Error?u.message:"\u65E0\u6CD5\u6CE8\u518C\u5F53\u524D\u5DE5\u4F5C\u533A"})}),process.env.PI_WEBAPP_AUTO_OPEN==="1"&&a.mode==="tui"&&!i.autoOpened&&(i.autoOpened=!0,n(a).catch(u=>{a.ui.notify(u instanceof Error?u.message:"Web \u542F\u52A8\u5931\u8D25","error")}))}),r.on("agent_start",(s,a)=>S(a)),r.on("agent_end",(s,a)=>S(a)),r.on("agent_settled",(s,a)=>S(a)),r.on("model_select",(s,a)=>S(a)),r.on("thinking_level_select",(s,a)=>S(a)),r.on("message_end",(s,a)=>{i.selected==="tui"&&s.message.role==="assistant"&&i.bridge?.publish({type:"stream",message:null}),S(a),i.selected==="tui"&&W()}),r.on("session_info_changed",(s,a)=>S(a)),r.on("message_update",(s,a)=>{if(i.current=a,i.selected!=="tui"||s.message.role!=="assistant"||i.bridge===null)return;let u=Date.now();u-i.lastStreamAt<60||(i.lastStreamAt=u,i.bridge.publish({type:"stream",message:{id:"stream",role:"assistant",timestamp:new Date(s.message.timestamp).toISOString(),blocks:R(s.message.content)}}))}),r.on("session_shutdown",async s=>{if(i.tuiWaitController.abort(),i.tuiGeneration++,i.stopChanged?.(),i.stopChanged=null,i.interactions?.cancelAll(),i.current=null,s.reason==="new"||s.reason==="resume"||s.reason==="fork"||s.reason==="reload")return;let a=i.bridge;i.bridge=null,i.commandContext=null,i.replacementContext=null,i.replacementSessionId=null,i.pi=null;let u=i.workspaceSessions;i.workspaceSessions=null,await u?.dispose(),i.selected="tui",i.activeWorkspaceId=null,i.autoOpened=!1,i.tuiCatalog=null,i.stopPluginWatch?.(),i.stopPluginWatch=null,a&&await a.close()});let n=async s=>{i.current=s,i.commandContext="newSession"in s?s:null,i.pi=r,i.tuiCatalog=await N.discover(s.cwd,s.isProjectTrusted?.()??!1),i.workspaces===null&&(i.workspaces=new J(ze(j())),await i.workspaces.load());try{await i.workspaces.discover((await ut.listAll()).map(p=>p.cwd))}catch(p){s.ui.notify(`\u65E0\u6CD5\u8BFB\u53D6\u90E8\u5206 Pi \u5386\u53F2\u5DE5\u4F5C\u533A\uFF1A${p instanceof Error?p.message:String(p)}`,"warning")}let a=await i.workspaces.add(s.cwd);if(i.selected==="tui"&&(i.activeWorkspaceId=a.id),i.bridge&&i.bridge.protocolVersion!==7){let p=i.bridge;i.bridge=null,await p.close()}if(i.bridge===null){i.workspaceSessions=new X(o=>{i.selected==="sdk"&&(i.bridge?.publish(o),o.type==="snapshot"&&o.session.idle&&W())},()=>i.current?.model,o=>{try{return!!i.current&&ki(i.current.cwd)===o&&(i.current.isProjectTrusted?.()??!1)}catch{return!1}});let p={selfUpdate:new Z({agentDir:j(),packageRoot:we(dt,"../.."),launcherNonce:process.env.PI_WEBAPP_LAUNCHER_NONCE}),snapshot:I,plugins:async()=>{let o=$();return await o?.refreshAssets(),o?.view()??{plugins:[],errors:[]}},pluginAsset:async o=>$()?.asset(o)??null,async invokePluginAction(o,d,f,m){if(E(o),!$()?.has(d))throw new Error("\u63D2\u4EF6\u672A\u542F\u7528");let v=i.selected,k=i.tuiGeneration,w=i.workspaceSessions?.session,l={requestId:xi(),sessionId:o,pluginId:d,action:f,input:m},h=i.selected==="sdk"?await i.workspaceSessions.invokePluginAction(l):await q(i.pi.events,l,15e3,i.tuiWaitController.signal);if(E(o),v!==i.selected||(v==="tui"?k!==i.tuiGeneration:w!==i.workspaceSessions?.session))throw new Error("\u4F1A\u8BDD\u8FD0\u884C\u5B9E\u4F8B\u5DF2\u5207\u6362");return i.selected==="tui"&&i.current&&S(i.current),h},async resolvePluginInteraction(o,d,f,m){if(E(o),!$()?.has(d))throw new Error("\u63D2\u4EF6\u672A\u542F\u7528");i.selected==="sdk"?i.workspaceSessions.resolveInteraction(o,d,f,m):i.interactions.resolve(o,d,f,m)},image(o,d,f){E(o);let v=(i.selected==="sdk"?i.workspaceSessions?.session?.sessionManager.getBranch():i.current?.sessionManager.getBranch())?.find(w=>w.id===d);if(v?.type!=="message"||v.message.role!=="user"||!Array.isArray(v.message.content))return null;let k=v.message.content[f];return k?.type!=="image"?null:{data:Buffer.from(k.data,"base64"),mimeType:k.mimeType}},async workspaces(){return ft()},async addWorkspace(o,d){let f=await i.workspaces.add(o,d);try{await me(f.id,!0)}catch(m){throw await W(),m}},async selectWorkspace(o){await me(o)},async newSessionInWorkspace(o){await me(o,!0)},async removeWorkspace(o){if(o===i.activeWorkspaceId)throw new Error("\u8BF7\u5148\u5207\u6362\u5230\u5176\u4ED6\u5DE5\u4F5C\u533A");await i.workspaces.remove(o),await W()},async selectSession(o,d,f){let m=i.workspaces?.get(o);if(!m)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");if(d===i.current?.sessionManager.getSessionId()&&m.path===await re(i.current.cwd)){if(i.selected==="sdk"&&i.workspaceSessions?.session&&!i.workspaceSessions.session.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F\u518D\u5207\u6362\u4F1A\u8BDD");i.selected="tui",i.activeWorkspaceId=o,i.bridge?.publish({type:"snapshot",session:I()})}else{if(i.selected==="sdk"&&i.workspaceSessions?.session?.sessionManager.getSessionId()===d&&i.workspaceSessions.path===m.path)return;if(!(await V(m.path)).some(k=>k.id===d&&k.path===f))throw new Error("\u4F1A\u8BDD\u4E0D\u5C5E\u4E8E\u8BE5\u5DE5\u4F5C\u533A");await i.workspaceSessions.open(m.path,{sessionFile:f}),i.selected="sdk",i.activeWorkspaceId=o,i.bridge?.publish({type:"snapshot",session:I()})}await W()},async models(){if(i.selected==="sdk")return i.workspaceSessions?.models()??[];let o=i.current;if(!o)throw new Error("\u6CA1\u6709\u6D3B\u52A8\u4F1A\u8BDD");let d=o.scopedModels?.map(f=>`${f.model.provider}/${f.model.id}`)??[];return o.modelRegistry.getAvailable().filter(f=>d.length===0||d.includes(`${f.provider}/${f.id}`)).map(f=>({provider:f.provider,id:f.id,name:f.name}))},async providers(){let o=await L(),d=new Set((await o.listCredentials()).map(f=>f.providerId));return o.getProviders().map(f=>({id:f.id,name:f.name,configured:o.getProviderAuthStatus(f.id).configured,storedCredential:d.has(f.id),methods:[f.auth.apiKey?.login?"api_key":null,f.auth.oauth?"oauth":null].filter(m=>m!==null)}))},async providerModels(o){let d=await L();return je(ee(j(),"models.json"),o,d)},async updateProviderModel(o,d,f){if(E(o),i.selected==="tui"?!A(o).isIdle():!i.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let m=I().model;if(f.action==="remove"&&m===`${d}/${f.id}`)throw new Error("\u8BF7\u5148\u5207\u6362\u5F53\u524D\u4F7F\u7528\u7684\u6A21\u578B");if(f.action==="save"&&f.originalId&&f.originalId!==f.model.id&&m===`${d}/${f.originalId}`)throw new Error("\u8BF7\u5148\u5207\u6362\u5F53\u524D\u4F7F\u7528\u7684\u6A21\u578B");let v=await L();await Be(ee(j(),"models.json"),d,f,v),await v.refresh({providers:[d],allowNetwork:!1}),await i.current?.modelRegistry.refresh({providers:[d],allowNetwork:!1}),await i.workspaceSessions?.session?.modelRuntime.refresh({providers:[d],allowNetwork:!1});let k=f.action==="save"?f.model.id:f.action==="base_url"&&m?.startsWith(`${d}/`)?m.slice(d.length+1):null;if(k&&m===`${d}/${k}`)if(i.selected==="sdk")try{await i.workspaceSessions.setModel(d,k)}catch{throw new Error("\u6A21\u578B\u5DF2\u4FDD\u5B58\uFF0C\u8BF7\u91CD\u65B0\u9009\u62E9\u8BE5\u6A21\u578B\u4EE5\u5E94\u7528\u65B0\u53C2\u6570")}else{let w=A(o),l=w.modelRegistry.find(d,k);if(!l||!i.pi||!await i.pi.setModel(l))throw new Error("\u6A21\u578B\u5DF2\u4FDD\u5B58\uFF0C\u8BF7\u91CD\u65B0\u9009\u62E9\u8BE5\u6A21\u578B\u4EE5\u5E94\u7528\u65B0\u53C2\u6570");S(w)}},async logoutProvider(o,d){if(E(o),i.selected==="tui"?!A(o).isIdle():!i.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let f=await L();if(!(await f.listCredentials()).some(m=>m.providerId===d))throw new Error("\u8BE5\u63D0\u4F9B\u65B9\u6CA1\u6709\u5DF2\u4FDD\u5B58\u7684\u8BA4\u8BC1");await f.logout(d),await i.current?.modelRegistry.refresh({providers:[d],allowNetwork:!1}),await i.workspaceSessions?.session?.modelRuntime.refresh({providers:[d],allowNetwork:!1})},async loginProvider(o,d,f){let m=await L();await m.login(o,d,Me(o,d,f)),await m.refresh({providers:[o],allowNetwork:!1}),await i.current?.modelRegistry.refresh({providers:[o],allowNetwork:!1}),await i.workspaceSessions?.session?.modelRuntime.refresh({providers:[o],allowNetwork:!1})},async addCustomProvider(o,d){if(E(o),i.selected==="tui"?!A(o).isIdle():!i.workspaceSessions?.session?.isIdle)throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let f=await L();if(f.getProvider(d.id))throw new Error("\u63D0\u4F9B\u65B9\u5DF2\u5B58\u5728");await We(ee(j(),"models.json"),d),await f.refresh({allowNetwork:!1}),await i.current?.modelRegistry.refresh({allowNetwork:!1}),await i.workspaceSessions?.session?.modelRuntime.refresh({allowNetwork:!1})},commands(){return i.selected==="tui"?(i.pi?.getCommands()??[]).filter(o=>o.name!=="web"&&o.name!=="web-dev-reload").map(o=>({name:o.name,description:o.description})):[]},async compact(o){if(E(o),i.selected==="sdk"){let f=i.workspaceSessions?.session;if(!f||!f.isIdle)throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");await f.compact(),i.bridge?.publish({type:"snapshot",session:I()});return}let d=A(o);if(!d.isIdle())throw new Error("\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");d.compact()},async setModel(o,d,f){if(E(o),i.selected==="sdk"){await i.workspaceSessions.setModel(d,f);return}let m=A(o);if(!m.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");let v=m.modelRegistry.find(d,f);if(!v||!m.modelRegistry.getAvailable().some(k=>k.provider===d&&k.id===f))throw new Error("\u6A21\u578B\u4E0D\u53EF\u7528");if(!i.pi||!await i.pi.setModel(v))throw new Error("\u6A21\u578B\u63D0\u4F9B\u65B9\u672A\u914D\u7F6E\u8BA4\u8BC1");S(m)},async setThinkingLevel(o,d){if(E(o),!["off","minimal","low","medium","high","xhigh"].includes(d))throw new Error("\u63A8\u7406\u5F3A\u5EA6\u65E0\u6548");if(i.selected==="sdk"){let v=i.workspaceSessions?.session;if(!v||!v.isIdle||!v.getAvailableThinkingLevels().includes(d))throw new Error("\u5F53\u524D\u6A21\u578B\u4E0D\u652F\u6301\u6B64\u63A8\u7406\u5F3A\u5EA6");v.setThinkingLevel(d),i.bridge?.publish({type:"snapshot",session:I()});return}let m=A(o);if(!m.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(!m.model||!Ii(m.model).includes(d))throw new Error("\u5F53\u524D\u6A21\u578B\u4E0D\u652F\u6301\u6B64\u63A8\u7406\u5F3A\u5EA6");if(!i.pi)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");i.pi.setThinkingLevel(d),S(m)},config:mt,updateConfig:Wi,async send(o,d,f=[]){if(E(o),i.selected==="sdk"){await i.workspaceSessions.send(d,f);return}if(!A(o).isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(i.replacementContext!==null&&i.replacementSessionId===o){await i.replacementContext.sendUserMessage(f.length?[{type:"text",text:d},...f]:d,{expandPromptTemplates:!0});return}if(i.pi===null)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");i.pi.sendUserMessage(f.length?[{type:"text",text:d},...f]:d,{expandPromptTemplates:!0})},async abort(o){if(E(o),i.selected==="sdk")await i.workspaceSessions.stop();else{let d=A(o);if(d.isIdle())return;if(!i.pi)throw new Error("Pi \u4F1A\u8BDD\u4E0D\u53EF\u7528");i.pi.appendEntry(O),d.abort()}},async resume(o){if(E(o),i.selected==="sdk"){await i.workspaceSessions.resume();return}let d=A(o);if(!d.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(!d.model||!i.pi)throw new Error("\u8BF7\u5148\u9009\u62E9\u6A21\u578B");if(!d.modelRegistry.hasConfiguredAuth(d.model))throw new Error("\u8BF7\u5148\u8FDE\u63A5\u5F53\u524D\u6A21\u578B");i.pi.sendMessage(K(I().messages),{triggerTurn:!0})},async newSession(o){if(E(o),i.selected==="sdk"){let m=i.workspaces?.get(i.activeWorkspaceId??"");if(!m)throw new Error("\u5DE5\u4F5C\u533A\u4E0D\u5B58\u5728");await i.workspaceSessions.open(m.path,"new"),await W();return}let d=A(o);if(!d.isIdle())throw new Error("Pi \u6B63\u5728\u8FD0\u884C\uFF0C\u8BF7\u7B49\u5F85\u5F53\u524D\u56DE\u590D\u7ED3\u675F");if(i.commandContext===null){await i.workspaceSessions.open(d.cwd,"new"),i.selected="sdk",i.bridge?.publish({type:"snapshot",session:I()}),await W();return}if((await i.commandContext.newSession({withSession:async m=>{i.commandContext=m,i.replacementContext=m,i.replacementSessionId=m.sessionManager.getSessionId(),i.current=m}})).cancelled)throw new Error("\u65B0\u4F1A\u8BDD\u5DF2\u53D6\u6D88");await W()}};p.addWorkspace=i.lifecycle.wrap(p.addWorkspace),p.selectWorkspace=i.lifecycle.wrap(p.selectWorkspace),p.newSessionInWorkspace=i.lifecycle.wrap(p.newSessionInWorkspace),p.removeWorkspace=i.lifecycle.wrap(p.removeWorkspace),p.selectSession=i.lifecycle.wrap(p.selectSession),p.newSession=i.lifecycle.wrap(p.newSession),p.updateConfig=i.lifecycle.wrap(p.updateConfig),i.bridge=await Ue(p,dt)}if(i.stopPluginWatch===null&&process.env.PI_WEBAPP_PLUGIN_DEV_ROOTS){let p=[],o=null;for(let d of(process.env.PI_WEBAPP_PLUGIN_DEV_ROOTS??"").split(yi).filter(Boolean))try{p.push(bi(ee(we(d),"dist"),(f,m)=>{let v=String(m??"");["client.js","client.css"].includes(v)&&(o&&clearTimeout(o),o=setTimeout(()=>i.bridge?.publish({type:"plugins_changed"}),180))}))}catch(f){i.bridge?.publish({type:"error",message:`\u63D2\u4EF6\u76D1\u542C\u5931\u8D25\uFF1A${d}: ${String(f)}`})}i.stopPluginWatch=()=>{for(let d of p)d.close();o&&clearTimeout(o)}}let u=await e(i.bridge.url).catch(()=>!1);s.ui.notify(`pi-webapp: ${i.bridge.url}`,u?"info":"warning"),s.ui.setStatus("pi-webapp","Web \u5DF2\u542F\u52A8 \xB7 /web \u91CD\u65B0\u6253\u5F00")};r.registerCommand("web",{description:"Open the current Pi session in a local web interface",handler:async(s,a)=>n(a)}),r.registerCommand("web-dev-reload",{description:"Reload local pi-webapp plugins during development",handler:async(s,a)=>{process.env.PI_WEBAPP_PLUGIN_DEV_ROOTS&&(await a.waitForIdle(),await i.lifecycle.run(async()=>{let u=i.workspaceSessions?.session;u&&(await u.waitForIdle(),await i.workspaceSessions.reload()),await a.reload()}))}})}export{Ti as default};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "pi-webapp",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.7",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "A browser interface for Pi with live chat, workspaces, models, and attachments",
|
|
6
6
|
"repository": {
|
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
"pi-webapp": "./bin/pi-webapp.mjs"
|
|
16
16
|
},
|
|
17
17
|
"pi": {
|
|
18
|
-
"image": "https://cdn.jsdelivr.net/npm/pi-webapp@0.1.
|
|
18
|
+
"image": "https://cdn.jsdelivr.net/npm/pi-webapp@0.1.7/assets/cover-webapp.png",
|
|
19
19
|
"extensions": [
|
|
20
20
|
"./dist/extension.js"
|
|
21
21
|
]
|
|
@@ -27,7 +27,8 @@
|
|
|
27
27
|
"web/dist",
|
|
28
28
|
"README.md",
|
|
29
29
|
"README.zh-CN.md",
|
|
30
|
-
"LICENSE"
|
|
30
|
+
"LICENSE",
|
|
31
|
+
"THIRD_PARTY_LICENSE.txt"
|
|
31
32
|
],
|
|
32
33
|
"scripts": {
|
|
33
34
|
"start": "npm run build && node bin/pi-webapp.mjs",
|
|
@@ -37,7 +38,7 @@
|
|
|
37
38
|
"test": "node --experimental-strip-types --test test/*.test.ts",
|
|
38
39
|
"build": "npm run build:web && npm run build:extension",
|
|
39
40
|
"build:web": "vite build",
|
|
40
|
-
"build:extension": "
|
|
41
|
+
"build:extension": "node scripts/build-extension.mjs",
|
|
41
42
|
"prepack": "npm run build",
|
|
42
43
|
"prepublishOnly": "npm run check && npm run build && npm run test"
|
|
43
44
|
},
|
|
@@ -49,12 +50,16 @@
|
|
|
49
50
|
"@earendil-works/pi-coding-agent": "*"
|
|
50
51
|
},
|
|
51
52
|
"devDependencies": {
|
|
53
|
+
"@chengzhiyi/pi-web-protocol": "0.1.0",
|
|
52
54
|
"@earendil-works/pi-ai": "0.87.1",
|
|
53
55
|
"@earendil-works/pi-coding-agent": "0.87.1",
|
|
56
|
+
"@types/katex": "^0.16.7",
|
|
57
|
+
"@types/mdast": "^4.0.4",
|
|
54
58
|
"@types/node": "22.19.19",
|
|
55
59
|
"@types/react": "^18.3.1",
|
|
56
60
|
"@types/react-dom": "^18.3.0",
|
|
57
61
|
"esbuild": "^0.28.2",
|
|
62
|
+
"micromark-util-types": "^2.0.2",
|
|
58
63
|
"typescript": "7.0.2",
|
|
59
64
|
"vite": "^6.4.3"
|
|
60
65
|
},
|
|
@@ -62,12 +67,30 @@
|
|
|
62
67
|
"node": ">=22.19.0"
|
|
63
68
|
},
|
|
64
69
|
"dependencies": {
|
|
70
|
+
"@lexical/history": "0.49.0",
|
|
71
|
+
"@lexical/plain-text": "0.49.0",
|
|
72
|
+
"@shikijs/langs": "^4.3.1",
|
|
65
73
|
"anser": "^2.3.5",
|
|
66
74
|
"clsx": "^2.1.1",
|
|
67
75
|
"cross-spawn": "^7.0.6",
|
|
76
|
+
"katex": "^0.16.47",
|
|
77
|
+
"lexical": "0.49.0",
|
|
78
|
+
"mdast-util-from-markdown": "^2.0.3",
|
|
79
|
+
"mdast-util-gfm": "^3.1.0",
|
|
80
|
+
"mdast-util-math": "^3.0.0",
|
|
81
|
+
"micromark-core-commonmark": "^2.0.3",
|
|
82
|
+
"micromark-extension-gfm": "^3.0.0",
|
|
83
|
+
"micromark-extension-math": "^3.1.0",
|
|
84
|
+
"micromark-factory-space": "^2.0.1",
|
|
85
|
+
"micromark-util-character": "^2.1.1",
|
|
86
|
+
"micromark-util-classify-character": "^2.0.1",
|
|
87
|
+
"micromark-util-sanitize-uri": "^2.0.1",
|
|
88
|
+
"micromark-util-symbol": "^2.0.1",
|
|
68
89
|
"react": "^18.3.1",
|
|
69
90
|
"react-dom": "^18.3.1",
|
|
70
91
|
"react-markdown": "^10.1.0",
|
|
71
|
-
"remark-gfm": "^4.0.1"
|
|
92
|
+
"remark-gfm": "^4.0.1",
|
|
93
|
+
"shiki": "^4.3.1",
|
|
94
|
+
"simple-icons": "^16.31.0"
|
|
72
95
|
}
|
|
73
96
|
}
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|