@storvia/sdk 0.8.2 → 0.8.3

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/dist/index.cjs.js CHANGED
@@ -1,4 +1,4 @@
1
- "use strict";var re=Object.defineProperty;var xe=Object.getOwnPropertyDescriptor;var _e=Object.getOwnPropertyNames;var Oe=Object.prototype.hasOwnProperty;var Ae=(i,e)=>{for(var t in e)re(i,t,{get:e[t],enumerable:!0})},Me=(i,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of _e(e))!Oe.call(i,r)&&r!==t&&re(i,r,{get:()=>e[r],enumerable:!(n=xe(e,r))||n.enumerable});return i};var De=i=>Me(re({},"__esModule",{value:!0}),i);var je={};Ae(je,{PROTOCOL_VERSION:()=>M,StorviaBus:()=>O,StorviaError:()=>p,StorviaSDK:()=>Y,createStorviaSDK:()=>Pe,envelope:()=>C,extractFieldValue:()=>ke,isProtocolEnvelope:()=>W,isRichFieldValue:()=>le,setToastEnabled:()=>Ie,showToast:()=>se});module.exports=De(je);var p=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var M=1;function W(i){if(!i||typeof i!="object")return!1;let e=i;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function C(i,e,t){return{protocol:1,type:i,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var O=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!W(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(o){console.error(`[StorviaBus] handler '${t.type}' threw:`,o)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:C(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(o){console.error("[StorviaBus] customSend failed:",o,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(o){console.error("[StorviaBus] postMessage failed:",o,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let o=e.id??Ne(),s=C(e.type,e.payload,{id:o}),c=setTimeout(()=>{this.pendingAcks.delete(o),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(o,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Ne(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var oe=null;function fe(i){oe=i}var ee="storvia-sdk-toast-style",te="storvia-sdk-toast-stack",we=`
1
+ "use strict";var re=Object.defineProperty;var xe=Object.getOwnPropertyDescriptor;var _e=Object.getOwnPropertyNames;var Oe=Object.prototype.hasOwnProperty;var Me=(i,e)=>{for(var t in e)re(i,t,{get:e[t],enumerable:!0})},Ae=(i,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of _e(e))!Oe.call(i,r)&&r!==t&&re(i,r,{get:()=>e[r],enumerable:!(n=xe(e,r))||n.enumerable});return i};var De=i=>Ae(re({},"__esModule",{value:!0}),i);var je={};Me(je,{PROTOCOL_VERSION:()=>A,StorviaBus:()=>O,StorviaError:()=>u,StorviaSDK:()=>Y,createStorviaSDK:()=>Pe,envelope:()=>R,extractFieldValue:()=>ke,isProtocolEnvelope:()=>W,isRichFieldValue:()=>le,setToastEnabled:()=>Ie,showToast:()=>se});module.exports=De(je);var u=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var A=1;function W(i){if(!i||typeof i!="object")return!1;let e=i;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function R(i,e,t){return{protocol:1,type:i,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var O=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!W(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(o){console.error(`[StorviaBus] handler '${t.type}' threw:`,o)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:R(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(o){console.error("[StorviaBus] customSend failed:",o,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(o){console.error("[StorviaBus] postMessage failed:",o,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let o=e.id??Ne(),s=R(e.type,e.payload,{id:o}),c=setTimeout(()=>{this.pendingAcks.delete(o),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(o,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Ne(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var oe=null;function fe(i){oe=i}var ee="storvia-sdk-toast-style",te="storvia-sdk-toast-stack",ye=`
2
2
  #${te} {
3
3
  position: fixed;
4
4
  top: max(20px, env(safe-area-inset-top, 0px) + 20px);
@@ -219,10 +219,10 @@
219
219
  .storvia-sheet-msg { font-size: 13px; margin-bottom: 22px; }
220
220
  .storvia-sheet-btn { height: 40px; font-size: 13px; }
221
221
  }
222
- `,Ue={success:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>',error:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>',warning:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><path d="M10.29 3.86 1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"/><line x1="12" y1="9" x2="12" y2="13"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',info:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="16" x2="12" y2="12"/><line x1="12" y1="8" x2="12.01" y2="8"/></svg>'},ie={UNAUTHORIZED:"\u767B\u5F55\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55",INSUFFICIENT_CREDITS:"\u82B1\u56ED\u5E01\u4E0D\u8DB3\uFF0C\u8BF7\u5145\u503C\u540E\u518D\u7EE7\u7EED\u6E38\u620F",VIOLATION_WORD_DETECTED:"\u5185\u5BB9\u542B\u6709\u8FDD\u7981\u8BCD\uFF0C\u8BF7\u4FEE\u6539\u540E\u91CD\u8BD5",CONTENT_FILTERED:"\u5185\u5BB9\u88AB\u5B89\u5168\u7B56\u7565\u62E6\u622A\uFF0C\u8BF7\u8C03\u6574\u540E\u91CD\u8BD5",MODEL_REFUSAL:"\u6A21\u578B\u62D2\u7EDD\u54CD\u5E94\uFF0C\u6362\u4E2A\u8BF4\u6CD5\u8BD5\u8BD5",STREAM_INTERRUPTED:"\u56DE\u590D\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",RATE_LIMITED:"\u64CD\u4F5C\u8FC7\u4E8E\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5",MODEL_NOT_FOUND:"\u6240\u9009\u6A21\u578B\u4E0D\u53EF\u7528\uFF0C\u8BF7\u5207\u6362\u5176\u4ED6\u6A21\u578B",GAME_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u6E38\u620F",INVALID_REQUEST:"\u8BF7\u6C42\u65E0\u6548\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",INTERNAL_ERROR:"\u670D\u52A1\u51FA\u4E86\u70B9\u5C0F\u95EE\u9898\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",NOT_INITIALIZED:"SDK \u5C1A\u672A\u521D\u59CB\u5316",NOT_SUPPORTED_IN_PREVIEW:"\u5F53\u524D\u63A5\u53E3\u5728\u9884\u89C8\u6A21\u5F0F\u4E0B\u4E0D\u53EF\u7528",NETWORK_ERROR:"\u7F51\u7EDC\u5F02\u5E38\uFF0C\u8BF7\u68C0\u67E5\u8FDE\u63A5",REQUEST_TIMEOUT:"\u8BF7\u6C42\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",MODEL_LOADING_TIMEOUT:"\u6A21\u578B\u54CD\u5E94\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",STREAM_INACTIVITY:"\u8FDE\u63A5\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",DAISY_CARD_REQUIRED:"\u56DE\u6EAF\u6D88\u606F\u9700\u8981\u6709\u6548\u7684\u96CF\u83CA\u5361\u8BA2\u9605",MESSAGE_NOT_FOUND:"\u6D88\u606F\u4E0D\u5B58\u5728\u6216\u65E0\u6743\u64CD\u4F5C",MESSAGE_TOO_OLD:"\u4EC5\u53EF\u56DE\u6EAF 30 \u5929\u5185\u7684\u6D88\u606F",NO_MESSAGES_TO_DELETE:"\u8BE5\u6D88\u606F\u4E4B\u540E\u6CA1\u6709\u53EF\u56DE\u6EAF\u7684\u6D88\u606F",GENERATION_TIMEOUT:"\u751F\u6210\u8D85\u65F6\uFF0C\u8BF7\u91CD\u8BD5",REPETITION_LOOP:"\u56DE\u590D\u51FA\u73B0\u91CD\u590D\uFF0C\u8BF7\u91CD\u8BD5\u6216\u6362\u4E2A\u8BF4\u6CD5",SAVE_FAILED:"\u6D88\u606F\u4FDD\u5B58\u5931\u8D25\uFF0C\u672C\u6B21\u4E0D\u6263\u8D39\uFF0C\u8BF7\u91CD\u8BD5",FINALIZE_FAILED:"\u56DE\u590D\u5904\u7406\u5931\u8D25\uFF0C\u8BF7\u91CD\u8BD5",CONVERSATION_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u4F1A\u8BDD",EMPTY_MESSAGE:"\u6D88\u606F\u5185\u5BB9\u4E0D\u80FD\u4E3A\u7A7A",CONTINUE_MODEL_NOT_AVAILABLE:"\u7EED\u5199\u6A21\u578B\u5F53\u524D\u4E0D\u53EF\u7528",CONTINUE_PROMPT_MISSING:"\u7EED\u5199\u914D\u7F6E\u7F3A\u5931"},ye=!0;function Ie(i){ye=i}function $e(){if(typeof document>"u")return null;let i=document.getElementById(te);if(!i){if(!document.getElementById(ee)){let e=document.createElement("style");e.id=ee,e.textContent=we,document.head.appendChild(e)}i=document.createElement("div"),i.id=te,document.body.appendChild(i)}return i}function se(i,e="info",t=3500,n){if(!ye)return;let r=$e();if(!r)return;let o=t<=0,s=document.createElement("div");s.className=`storvia-toast ${e}`,s.innerHTML=`
222
+ `,Ue={success:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>',error:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>',warning:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><path d="M10.29 3.86 1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"/><line x1="12" y1="9" x2="12" y2="13"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',info:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="16" x2="12" y2="12"/><line x1="12" y1="8" x2="12.01" y2="8"/></svg>'},ie={UNAUTHORIZED:"\u767B\u5F55\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55",INSUFFICIENT_CREDITS:"\u82B1\u56ED\u5E01\u4E0D\u8DB3\uFF0C\u8BF7\u5145\u503C\u540E\u518D\u7EE7\u7EED\u6E38\u620F",VIOLATION_WORD_DETECTED:"\u5185\u5BB9\u542B\u6709\u8FDD\u7981\u8BCD\uFF0C\u8BF7\u4FEE\u6539\u540E\u91CD\u8BD5",CONTENT_FILTERED:"\u5185\u5BB9\u88AB\u5B89\u5168\u7B56\u7565\u62E6\u622A\uFF0C\u8BF7\u8C03\u6574\u540E\u91CD\u8BD5",MODEL_REFUSAL:"\u6A21\u578B\u62D2\u7EDD\u54CD\u5E94\uFF0C\u6362\u4E2A\u8BF4\u6CD5\u8BD5\u8BD5",STREAM_INTERRUPTED:"\u56DE\u590D\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",RATE_LIMITED:"\u64CD\u4F5C\u8FC7\u4E8E\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5",MODEL_NOT_FOUND:"\u6240\u9009\u6A21\u578B\u4E0D\u53EF\u7528\uFF0C\u8BF7\u5207\u6362\u5176\u4ED6\u6A21\u578B",GAME_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u6E38\u620F",INVALID_REQUEST:"\u8BF7\u6C42\u65E0\u6548\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",INTERNAL_ERROR:"\u670D\u52A1\u51FA\u4E86\u70B9\u5C0F\u95EE\u9898\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",NOT_INITIALIZED:"SDK \u5C1A\u672A\u521D\u59CB\u5316",NOT_SUPPORTED_IN_PREVIEW:"\u5F53\u524D\u63A5\u53E3\u5728\u9884\u89C8\u6A21\u5F0F\u4E0B\u4E0D\u53EF\u7528",NETWORK_ERROR:"\u7F51\u7EDC\u5F02\u5E38\uFF0C\u8BF7\u68C0\u67E5\u8FDE\u63A5",REQUEST_TIMEOUT:"\u8BF7\u6C42\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",MODEL_LOADING_TIMEOUT:"\u6A21\u578B\u54CD\u5E94\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",STREAM_INACTIVITY:"\u8FDE\u63A5\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",DAISY_CARD_REQUIRED:"\u56DE\u6EAF\u6D88\u606F\u9700\u8981\u6709\u6548\u7684\u96CF\u83CA\u5361\u8BA2\u9605",MESSAGE_NOT_FOUND:"\u6D88\u606F\u4E0D\u5B58\u5728\u6216\u65E0\u6743\u64CD\u4F5C",MESSAGE_TOO_OLD:"\u4EC5\u53EF\u56DE\u6EAF 30 \u5929\u5185\u7684\u6D88\u606F",NO_MESSAGES_TO_DELETE:"\u8BE5\u6D88\u606F\u4E4B\u540E\u6CA1\u6709\u53EF\u56DE\u6EAF\u7684\u6D88\u606F",GENERATION_TIMEOUT:"\u751F\u6210\u8D85\u65F6\uFF0C\u8BF7\u91CD\u8BD5",REPETITION_LOOP:"\u56DE\u590D\u51FA\u73B0\u91CD\u590D\uFF0C\u8BF7\u91CD\u8BD5\u6216\u6362\u4E2A\u8BF4\u6CD5",SAVE_FAILED:"\u6D88\u606F\u4FDD\u5B58\u5931\u8D25\uFF0C\u672C\u6B21\u4E0D\u6263\u8D39\uFF0C\u8BF7\u91CD\u8BD5",FINALIZE_FAILED:"\u56DE\u590D\u5904\u7406\u5931\u8D25\uFF0C\u8BF7\u91CD\u8BD5",CONVERSATION_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u4F1A\u8BDD",EMPTY_MESSAGE:"\u6D88\u606F\u5185\u5BB9\u4E0D\u80FD\u4E3A\u7A7A",CONTINUE_MODEL_NOT_AVAILABLE:"\u7EED\u5199\u6A21\u578B\u5F53\u524D\u4E0D\u53EF\u7528",CONTINUE_PROMPT_MISSING:"\u7EED\u5199\u914D\u7F6E\u7F3A\u5931"},we=!0;function Ie(i){we=i}function $e(){if(typeof document>"u")return null;let i=document.getElementById(te);if(!i){if(!document.getElementById(ee)){let e=document.createElement("style");e.id=ee,e.textContent=ye,document.head.appendChild(e)}i=document.createElement("div"),i.id=te,document.body.appendChild(i)}return i}function se(i,e="info",t=3500,n){if(!we)return;let r=$e();if(!r)return;let o=t<=0,s=document.createElement("div");s.className=`storvia-toast ${e}`,s.innerHTML=`
223
223
  <span class="storvia-toast-icon">${Ue[e]}</span>
224
224
  <span class="storvia-toast-msg"></span>
225
- `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=i);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(h){console.error("[Storvia toast] action error:",h)}d()}),s.appendChild(a)}if(o){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),o||setTimeout(d,t)}function b(i,e){if(i==="INSUFFICIENT_CREDITS"){ve({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||ie.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(i==="DAISY_CARD_REQUIRED"){ve({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||ie.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=ie[i]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";se(t,i==="RATE_LIMITED"?"warning":"error")}var X=null;function ve(i){if(typeof document>"u"||X)return;if(!document.getElementById(ee)){let s=document.createElement("style");s.id=ee,s.textContent=we,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
225
+ `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=i);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(l){console.error("[Storvia toast] action error:",l)}d()}),s.appendChild(a)}if(o){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),o||setTimeout(d,t)}function k(i,e){if(i==="INSUFFICIENT_CREDITS"){ve({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||ie.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(i==="DAISY_CARD_REQUIRED"){ve({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||ie.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=ie[i]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";se(t,i==="RATE_LIMITED"?"warning":"error")}var X=null;function ve(i){if(typeof document>"u"||X)return;if(!document.getElementById(ee)){let s=document.createElement("style");s.id=ee,s.textContent=ye,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
226
226
  <div class="storvia-sheet" role="dialog" aria-modal="true" aria-labelledby="storvia-sheet-title">
227
227
  <div class="storvia-sheet-icon">
228
228
  <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>
@@ -234,6 +234,6 @@
234
234
  <button type="button" class="storvia-sheet-btn storvia-sheet-btn-primary" data-role="navigate"></button>
235
235
  </div>
236
236
  </div>
237
- `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=i.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=i.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=i.primaryLabel);let o=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),X===e&&(X=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",o),e.addEventListener("click",s=>{s.target===e&&o()}),r?.addEventListener("click",()=>{if(oe)try{oe(C("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");o()}),document.body.appendChild(e),X=e,requestAnimationFrame(()=>e.classList.add("show"))}var y=class y{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof p||b("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new p("REQUEST_TIMEOUT","Request timed out");return b("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),y.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:o,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:h}=e,l="%c[Storvia SDK]",m="color: #6366f1; font-weight: bold",v=a!==void 0?` (${a}ms)`:"",u=o!==void 0?` [${o}]`:"",P=h?` [model: ${h}]`:"";d?(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2717`,m,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2713`,m,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,h])=>n.searchParams.set(a,h));let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),o=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,parsedData:l,durationMs:Date.now()-r}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,error:h,durationMs:Date.now()-r}),h===a&&this.maybeShowNetworkToast(a),h}}async post(e,t,n){let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),o=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,parsedData:l,durationMs:Date.now()-r,modelName:n?.modelName}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,error:h,durationMs:Date.now()-r,modelName:n?.modelName}),h===a&&this.maybeShowNetworkToast(a),h}}async patch(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:o,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:o.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,o,s,c,d,a,h){let l=Date.now(),m=o?.modelName?` [model: ${o.modelName}]`:"",v=[],u=f=>{this.debug&&v.push({t:Date.now()-l,event:f})},P=new AbortController,R=null,I=null,k=null,T=null,x=()=>{R!==null&&(clearTimeout(R),R=null),I!==null&&(clearTimeout(I),I=null),k!==null&&(clearTimeout(k),k=null)},Q=f=>{T=f,x(),P.abort()};R=setTimeout(()=>Q("REQUEST_TIMEOUT"),y.REQUEST_TIMEOUT);let E;try{E=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:P.signal})}catch(f){if(x(),T){let w=new p(T,"Request timed out");throw b(T),this.log({method:"STREAM",path:e,body:t,error:w,durationMs:Date.now()-l,modelName:o?.modelName}),w}throw this.maybeShowNetworkToast(f),f}if(R!==null&&(clearTimeout(R),R=null),!E.ok){x();let f=await E.text().catch(()=>""),w={};try{w=JSON.parse(f)}catch{}let S=w.code||"INTERNAL_ERROR",g=new p(S,w.message||`HTTP ${E.status}`);throw b(S,w.message),this.log({method:"STREAM",path:e,body:t,status:E.status,rawResponse:f,error:g,durationMs:Date.now()-l,modelName:o?.modelName}),g}let he=E.body?.getReader();if(!he)throw x(),new p("INTERNAL_ERROR","No response body for stream");I=setTimeout(()=>Q("MODEL_LOADING_TIMEOUT"),y.MODEL_LOADING_TIMEOUT);let ue=new TextDecoder,H="",_="",pe=!1,ne,Z,A="",J=!1,me=f=>{if(J)return;let w=f.endsWith("\r")?f.slice(0,-1):f;if(w.startsWith("id: ")){Z=w.slice(4);return}if(!w.startsWith("data: "))return;let S=w.slice(6);if(S==="[DONE]"){u("[DONE]"),J=!0;return}try{let g=JSON.parse(S);u(g),g.type==="done"&&g.id?H=g.id:g.type==="state"?(s&&s(g.delta,g.full??null),d&&Array.isArray(g.createdNames)&&g.createdNames.length&&d(g.createdNames)):g.type==="thinking"?c&&(g.status==="start"||g.status==="end")&&c(g.status):g.content&&(pe?(k!==null&&clearTimeout(k),k=setTimeout(()=>Q("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)):(pe=!0,I!==null&&(clearTimeout(I),I=null),k=setTimeout(()=>Q("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)),_+=g.content,n(g.content))}catch{u({raw:S})}Z!==void 0&&(ne=Z,Z=void 0)},ge=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",H),console.log(`SSE events (${v.length}):`,v),console.groupEnd()),r(H)};try{for(;;){let{done:f,value:w}=await he.read();if(f)break;A+=ue.decode(w,{stream:!0});let S=A.split(`
238
- `);A=S.pop()??"";for(let g of S)me(g);if(J){ge();return}}if(A+=ue.decode(),A&&me(A),J){ge();return}}catch(f){if(x(),T){let w=new p(T,T==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw b(T),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2717 ${T}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Timeout:",w),console.groupEnd()),w}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0});return}throw f}if(x(),H){r(H);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0})}async resumeLoop(e,t,n,r){let o=t;for(let c=1;c<=y.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(y.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(l=>setTimeout(l,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:o},h;try{h=await this.pumpGetStream(e.conversationId,e.topic,o,a,n)}catch{continue}if(o=a.lastId??o,h==="done"){n.onDone(a.messageId);return}if(h==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new p("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw b("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},o;try{o=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(o==="done"){n.onDone(r.messageId);return}if(o==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,o){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),y.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new p("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let l=a.body?.getReader();return l?await this.pumpReader(l,r,o):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,o,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},y.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,h=l=>{if(a)return;let m=l.endsWith("\r")?l.slice(0,-1):l;if(m.startsWith("id: ")){o=m.slice(4);return}if(!m.startsWith("data: "))return;let v=m.slice(6);if(v==="[DONE]"){a=!0;return}try{let u=JSON.parse(v);u.type==="done"&&u.id?t.messageId=u.id:u.type==="state"?(n.onState?.(u.delta,u.full??null),Array.isArray(u.createdNames)&&u.createdNames.length&&n.onCreatedCharacters?.(u.createdNames)):u.type==="thinking"?(u.status==="start"||u.status==="end")&&n.onThinking?.(u.status):u.content&&n.onChunk(u.content)}catch{}o!==void 0&&(t.lastId=o,o=void 0)};try{for(;;){let{done:l,value:m}=await e.read();if(l)break;c(),d+=r.decode(m,{stream:!0});let v=d.split(`
239
- `);d=v.pop()??"";for(let u of v)h(u);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&h(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},o={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||o[e.status]||"INTERNAL_ERROR",c=new p(s,r.message||`HTTP ${e.status}`);throw b(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};y.REQUEST_TIMEOUT=6e4,y.MODEL_LOADING_TIMEOUT=18e4,y.STREAM_INACTIVITY_TIMEOUT=6e4,y.RECONNECT_MAX_ATTEMPTS=10,y.RECONNECT_BACKOFF_CAP=15e3;var K=y;var D=class{constructor(e,t,n,r,o=!1,s,c){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=o;this.previewConfig=s,this.getModelName=c}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:q(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[]};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",o=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,h)=>{o=a,s=h,e.onState&&e.onState(o,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return o&&(d.delta=o,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function q(i){if(i)return(e,t)=>i(e,t)}var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},N=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(Ce)),this.state=new ae(e,t,n,o)}setInitial(e,t){this.mem=e?e.map(Ce):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(Re):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?Re(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function Ce(i){return{name:i.name,description:i.description,avatar:i.avatar,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.gender?{gender:i.gender}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}function Re(i){return{name:i.name,avatar:i.avatar,description:i.description,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.gender?{gender:i.gender}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(o=>({...o})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(o=>o.from===e&&o.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Te(i){let e={count:i.count};return i.desc!==void 0&&(e.desc=i.desc),i.icon_url!==void 0&&(e.iconUrl=i.icon_url),e}function de(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i)){let r={};for(let[o,s]of Object.entries(n))r[o]=Te(s);e[t]=r}return e}function Le(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i))e[t]=Te(n);return e}var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=de(r))}setInitial(e){this.mem=e?de(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,o]of Object.entries(this.mem))n[r]={...o};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return Le(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return de(t)}async add(e){let{group:t,name:n,count:r=1,desc:o,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};o!==void 0&&(d.desc=o),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:o,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),o!==void 0&&(a.desc=o),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:o}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=o||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:o})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let o=this.mem[e];if(o&&Object.keys(o).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var L=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ce=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},F=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ce(e,t,n,o)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function G(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,o,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};o&&(this.mem=Ee(o)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Ee(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,o]of Object.entries(e))typeof o=="object"&&o!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...o}:this.mem[r]=o,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Ee(i){let e={};for(let[t,n]of Object.entries(i))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Se(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var j=class{constructor(e,t,n,r=!1,o){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};o&&(this.mem={...o})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Se(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Se(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var z=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var B=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var be="/functions/v1/world-engine/v1",Fe="https://api.storvia.ai";function Ge(){return window.__STORVIA__||{}}function Ve(i,e=3e4){let t=Ge();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let o=setTimeout(()=>{s(),c(),r(new p("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=i.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,debug:a.payload.debug})}),c=i.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(o),s(),c();let h=window;h.__STORVIA__=a,n(a)}i.send(C("ready",{}))})}var Y=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new O({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?l=>l.source===null||l.source===window:l=>l.source===window.parent,customSend:t?l=>e.callHandler("storviaBus",l):void 0}),fe(l=>this.bus.send(l));let n=await Ve(this.bus),r=n.apiBase;if(!r)throw new p("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${be}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new p("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new p("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new K(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[l,m]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=l,this.modelId=(n.selectedModelId&&l.some(I=>I.id===n.selectedModelId)?n.selectedModelId:"")||l[0]?.id||"";let v=()=>this.gameId,u=()=>this.conversationId,P=()=>this.modelId,R=()=>this.models.find(I=>I.id===this.modelId)?.name;this.chat=new D(this.http,v,u,P,!0,this.previewConfig,R),this.characters=new N(this.http,u,!0,m?.characters,m?.characterStates),this.relationships=new U(this.http,u,!0,m?.relationships),this.inventory=new $(this.http,u,!0,m?.inventory),this.world=new L(this.http,u,!0,m?.world),this.player=new F(this.http,u,!0,m?.player,m?.playerState),this.custom=new V(this.http,u,v,!0,m?.custom,m?.custom_inject),this.save=new j(this.http,u,v,!0,m?.save_data),this.state=new z(this.http,u,!0),this.memory=new B(this.http,u,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[o,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=o.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(l=>l.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"";let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,h=()=>this.models.find(l=>l.id===this.modelId)?.name;this.chat=new D(this.http,c,d,a,!1,void 0,h),this.characters=new N(this.http,d),this.relationships=new U(this.http,d),this.inventory=new $(this.http,d),this.world=new L(this.http,d),this.player=new F(this.http,d),this.custom=new V(this.http,d,c),this.save=new j(this.http,d,c),this.state=new z(this.http,d),this.memory=new B(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new p("UNAUTHORIZED","User not authenticated"):t.status===404?new p("GAME_NOT_FOUND","Game not found or not published"):new p("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${Fe}${be}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new K(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let o=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new D(this.http,o,s,c,!0,void 0,d),this.characters=new N(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new U(this.http,s,!0,n?.relationships),this.inventory=new $(this.http,s,!0,n?.inventory),this.world=new L(this.http,s,!0,n?.world),this.player=new F(this.http,s,!0,n?.player,n?.playerState),this.custom=new V(this.http,s,o,!0,n?.custom),this.save=new j(this.http,s,o,!0,n?.save_data),this.memory=new B(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(o=>({id:o.id,name:o.name,url:o.url,assetType:o.asset_type,category:o.category}))}};async function Pe(i){let e=new Y;return i?.dev?await e.initDev(i.dev):await e.init(),e}function le(i){return typeof i=="object"&&i!==null&&"value"in i&&"type"in i&&(i.type==="number"||i.type==="text")}function ke(i){return le(i)?i.value:i}0&&(module.exports={PROTOCOL_VERSION,StorviaBus,StorviaError,StorviaSDK,createStorviaSDK,envelope,extractFieldValue,isProtocolEnvelope,isRichFieldValue,setToastEnabled,showToast});
237
+ `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=i.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=i.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=i.primaryLabel);let o=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),X===e&&(X=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",o),e.addEventListener("click",s=>{s.target===e&&o()}),r?.addEventListener("click",()=>{if(oe)try{oe(R("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");o()}),document.body.appendChild(e),X=e,requestAnimationFrame(()=>e.classList.add("show"))}var I=class I{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof u||k("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new u("REQUEST_TIMEOUT","Request timed out");return k("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),I.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:o,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:l}=e,p="%c[Storvia SDK]",h="color: #6366f1; font-weight: bold",g=a!==void 0?` (${a}ms)`:"",m=o!==void 0?` [${o}]`:"",w=l?` [model: ${l}]`:"";d?(console.groupCollapsed(`${p} %c${t} ${n}${m}${w}${g} %c\u2717`,h,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${p} %c${t} ${n}${m}${w}${g} %c\u2713`,h,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,l])=>n.searchParams.set(a,l));let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),o=a.status;let{raw:l,data:p}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,parsedData:p,durationMs:Date.now()-r}),p}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,error:l,durationMs:Date.now()-r}),l===a&&this.maybeShowNetworkToast(a),l}}async post(e,t,n){let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),o=a.status;let{raw:l,data:p}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,parsedData:p,durationMs:Date.now()-r,modelName:n?.modelName}),p}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,error:l,durationMs:Date.now()-r,modelName:n?.modelName}),l===a&&this.maybeShowNetworkToast(a),l}}async patch(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:o,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:o.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,o,s,c,d,a,l){let p=Date.now(),h=o?.modelName?` [model: ${o.modelName}]`:"",g=[],m=f=>{this.debug&&g.push({t:Date.now()-p,event:f})},w=new AbortController,T=null,S=null,E=null,C=null,x=()=>{T!==null&&(clearTimeout(T),T=null),S!==null&&(clearTimeout(S),S=null),E!==null&&(clearTimeout(E),E=null)},Q=f=>{C=f,x(),w.abort()};T=setTimeout(()=>Q("REQUEST_TIMEOUT"),I.REQUEST_TIMEOUT);let b;try{b=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:w.signal})}catch(f){if(x(),C){let y=new u(C,"Request timed out");throw k(C),this.log({method:"STREAM",path:e,body:t,error:y,durationMs:Date.now()-p,modelName:o?.modelName}),y}throw this.maybeShowNetworkToast(f),f}if(T!==null&&(clearTimeout(T),T=null),!b.ok){x();let f=await b.text().catch(()=>""),y={};try{y=JSON.parse(f)}catch{}let P=y.code||"INTERNAL_ERROR",v=new u(P,y.message||`HTTP ${b.status}`);throw k(P,y.message),this.log({method:"STREAM",path:e,body:t,status:b.status,rawResponse:f,error:v,durationMs:Date.now()-p,modelName:o?.modelName}),v}let he=b.body?.getReader();if(!he)throw x(),new u("INTERNAL_ERROR","No response body for stream");S=setTimeout(()=>Q("MODEL_LOADING_TIMEOUT"),I.MODEL_LOADING_TIMEOUT);let ue=new TextDecoder,H="",_="",pe=!1,ne,Z,M="",J=!1,me=f=>{if(J)return;let y=f.endsWith("\r")?f.slice(0,-1):f;if(y.startsWith("id: ")){Z=y.slice(4);return}if(!y.startsWith("data: "))return;let P=y.slice(6);if(P==="[DONE]"){m("[DONE]"),J=!0;return}try{let v=JSON.parse(P);m(v),v.type==="done"&&v.id?H=v.id:v.type==="state"?(s&&s(v.delta,v.full??null),d&&Array.isArray(v.createdNames)&&v.createdNames.length&&d(v.createdNames)):v.type==="thinking"?c&&(v.status==="start"||v.status==="end")&&c(v.status):v.content&&(pe?(E!==null&&clearTimeout(E),E=setTimeout(()=>Q("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)):(pe=!0,S!==null&&(clearTimeout(S),S=null),E=setTimeout(()=>Q("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)),_+=v.content,n(v.content))}catch{m({raw:P})}Z!==void 0&&(ne=Z,Z=void 0)},ge=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",H),console.log(`SSE events (${g.length}):`,g),console.groupEnd()),r(H)};try{for(;;){let{done:f,value:y}=await he.read();if(f)break;M+=ue.decode(y,{stream:!0});let P=M.split(`
238
+ `);M=P.pop()??"";for(let v of P)me(v);if(J){ge();return}}if(M+=ue.decode(),M&&me(M),J){ge();return}}catch(f){if(x(),C){let y=new u(C,C==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw k(C),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2717 ${C}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Timeout:",y),console.groupEnd()),y}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0});return}throw f}if(x(),H){r(H);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0})}async resumeLoop(e,t,n,r){let o=t;for(let c=1;c<=I.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(I.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(p=>setTimeout(p,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:o},l;try{l=await this.pumpGetStream(e.conversationId,e.topic,o,a,n)}catch{continue}if(o=a.lastId??o,l==="done"){n.onDone(a.messageId);return}if(l==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new u("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw k("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},o;try{o=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(o==="done"){n.onDone(r.messageId);return}if(o==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,o){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),I.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new u("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let p=a.body?.getReader();return p?await this.pumpReader(p,r,o):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,o,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},I.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,l=p=>{if(a)return;let h=p.endsWith("\r")?p.slice(0,-1):p;if(h.startsWith("id: ")){o=h.slice(4);return}if(!h.startsWith("data: "))return;let g=h.slice(6);if(g==="[DONE]"){a=!0;return}try{let m=JSON.parse(g);m.type==="done"&&m.id?t.messageId=m.id:m.type==="state"?(n.onState?.(m.delta,m.full??null),Array.isArray(m.createdNames)&&m.createdNames.length&&n.onCreatedCharacters?.(m.createdNames)):m.type==="thinking"?(m.status==="start"||m.status==="end")&&n.onThinking?.(m.status):m.content&&n.onChunk(m.content)}catch{}o!==void 0&&(t.lastId=o,o=void 0)};try{for(;;){let{done:p,value:h}=await e.read();if(p)break;c(),d+=r.decode(h,{stream:!0});let g=d.split(`
239
+ `);d=g.pop()??"";for(let m of g)l(m);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&l(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},o={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||o[e.status]||"INTERNAL_ERROR",c=new u(s,r.message||`HTTP ${e.status}`);throw k(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};I.REQUEST_TIMEOUT=6e4,I.MODEL_LOADING_TIMEOUT=18e4,I.STREAM_INACTIVITY_TIMEOUT=6e4,I.RECONNECT_MAX_ATTEMPTS=10,I.RECONNECT_BACKOFF_CAP=15e3;var K=I;var D=class{constructor(e,t,n,r,o=!1,s,c,d){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=o;this.previewConfig=s,this.getModelName=c,this.getStoryMode=d}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:q(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[],story_mode:this.getStoryMode?.()};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",o=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,l)=>{o=a,s=l,e.onState&&e.onState(o,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return o&&(d.delta=o,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function q(i){if(i)return(e,t)=>i(e,t)}var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},N=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(Ce)),this.state=new ae(e,t,n,o)}setInitial(e,t){this.mem=e?e.map(Ce):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(Re):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?Re(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function Ce(i){return{name:i.name,description:i.description,avatar:i.avatar,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.gender?{gender:i.gender}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}function Re(i){return{name:i.name,avatar:i.avatar,description:i.description,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.gender?{gender:i.gender}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(o=>({...o})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(o=>o.from===e&&o.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Te(i){let e={count:i.count};return i.desc!==void 0&&(e.desc=i.desc),i.icon_url!==void 0&&(e.iconUrl=i.icon_url),e}function de(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i)){let r={};for(let[o,s]of Object.entries(n))r[o]=Te(s);e[t]=r}return e}function Le(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i))e[t]=Te(n);return e}var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=de(r))}setInitial(e){this.mem=e?de(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,o]of Object.entries(this.mem))n[r]={...o};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return Le(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return de(t)}async add(e){let{group:t,name:n,count:r=1,desc:o,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};o!==void 0&&(d.desc=o),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:o,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),o!==void 0&&(a.desc=o),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:o}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=o||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:o})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let o=this.mem[e];if(o&&Object.keys(o).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var L=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ce=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},F=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ce(e,t,n,o)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function G(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,o,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};o&&(this.mem=Se(o)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Se(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,o]of Object.entries(e))typeof o=="object"&&o!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...o}:this.mem[r]=o,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Se(i){let e={};for(let[t,n]of Object.entries(i))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Ee(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var j=class{constructor(e,t,n,r=!1,o){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};o&&(this.mem={...o})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Ee(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Ee(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var z=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var B=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var be="/functions/v1/world-engine/v1",Fe="https://api.storvia.ai";function Ge(){return window.__STORVIA__||{}}function Ve(i,e=3e4){let t=Ge();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let o=setTimeout(()=>{s(),c(),r(new u("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=i.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,storyMode:a.payload.storyMode,debug:a.payload.debug})}),c=i.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(o),s(),c();let l=window;l.__STORVIA__=a,n(a)}i.send(R("ready",{}))})}var Y=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.storyMode=!1;this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new O({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?h=>h.source===null||h.source===window:h=>h.source===window.parent,customSend:t?h=>e.callHandler("storviaBus",h):void 0}),fe(h=>this.bus.send(h));let n=await Ve(this.bus),r=n.apiBase;if(!r)throw new u("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${be}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new u("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new u("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new K(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[h,g]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=h,this.modelId=(n.selectedModelId&&h.some(C=>C.id===n.selectedModelId)?n.selectedModelId:"")||h[0]?.id||"",this.storyMode=n.storyMode===!0;let m=()=>this.gameId,w=()=>this.conversationId,T=()=>this.modelId,S=()=>this.models.find(C=>C.id===this.modelId)?.name,E=()=>this.storyMode;this.chat=new D(this.http,m,w,T,!0,this.previewConfig,S,E),this.characters=new N(this.http,w,!0,g?.characters,g?.characterStates),this.relationships=new U(this.http,w,!0,g?.relationships),this.inventory=new $(this.http,w,!0,g?.inventory),this.world=new L(this.http,w,!0,g?.world),this.player=new F(this.http,w,!0,g?.player,g?.playerState),this.custom=new V(this.http,w,m,!0,g?.custom,g?.custom_inject),this.save=new j(this.http,w,m,!0,g?.save_data),this.state=new z(this.http,w,!0),this.memory=new B(this.http,w,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[o,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=o.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(h=>h.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"",this.storyMode=n.storyMode===!0;let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,l=()=>this.models.find(h=>h.id===this.modelId)?.name,p=()=>this.storyMode;this.chat=new D(this.http,c,d,a,!1,void 0,l,p),this.characters=new N(this.http,d),this.relationships=new U(this.http,d),this.inventory=new $(this.http,d),this.world=new L(this.http,d),this.player=new F(this.http,d),this.custom=new V(this.http,d,c),this.save=new j(this.http,d,c),this.state=new z(this.http,d),this.memory=new B(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new u("UNAUTHORIZED","User not authenticated"):t.status===404?new u("GAME_NOT_FOUND","Game not found or not published"):new u("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${Fe}${be}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new K(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let o=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new D(this.http,o,s,c,!0,void 0,d),this.characters=new N(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new U(this.http,s,!0,n?.relationships),this.inventory=new $(this.http,s,!0,n?.inventory),this.world=new L(this.http,s,!0,n?.world),this.player=new F(this.http,s,!0,n?.player,n?.playerState),this.custom=new V(this.http,s,o,!0,n?.custom),this.save=new j(this.http,s,o,!0,n?.save_data),this.memory=new B(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(o=>({id:o.id,name:o.name,url:o.url,assetType:o.asset_type,category:o.category}))}};async function Pe(i){let e=new Y;return i?.dev?await e.initDev(i.dev):await e.init(),e}function le(i){return typeof i=="object"&&i!==null&&"value"in i&&"type"in i&&(i.type==="number"||i.type==="text")}function ke(i){return le(i)?i.value:i}0&&(module.exports={PROTOCOL_VERSION,StorviaBus,StorviaError,StorviaSDK,createStorviaSDK,envelope,extractFieldValue,isProtocolEnvelope,isRichFieldValue,setToastEnabled,showToast});
package/dist/index.d.mts CHANGED
@@ -458,7 +458,8 @@ declare class ChatModule {
458
458
  private isPreview;
459
459
  private previewConfig?;
460
460
  private getModelName?;
461
- constructor(http: HttpClient, getGameId: () => string, getConversationId: () => string, getModelId: () => string, isPreview?: boolean, previewConfig?: Record<string, unknown>, getModelName?: () => string | undefined);
461
+ private getStoryMode?;
462
+ constructor(http: HttpClient, getGameId: () => string, getConversationId: () => string, getModelId: () => string, isPreview?: boolean, previewConfig?: Record<string, unknown>, getModelName?: () => string | undefined, getStoryMode?: () => boolean);
462
463
  /** 构造 http 层的元信息(用于 debug 日志标题显示) */
463
464
  private reqMeta;
464
465
  /** 更新预览配置(由父页面 postMessage 触发) */
@@ -765,6 +766,8 @@ declare class StorviaSDK {
765
766
  private conversationId;
766
767
  private modelId;
767
768
  private models;
769
+ /** 剧情模式开关;由宿主经 init / 'set-story-mode' 下发,每次生成请求自动带上 */
770
+ private storyMode;
768
771
  private accessToken;
769
772
  private initialized;
770
773
  private isPreview;
@@ -859,6 +862,13 @@ interface InitPayload {
859
862
  * 在 SDK 注册监听前到达而丢失的竞态。运行时切换仍走 envelope 'set-model'。
860
863
  */
861
864
  selectedModelId?: string;
865
+ /**
866
+ * 宿主(主站/App)当前的「剧情模式」开关状态。跟 selectedModelId 完全同一套机制:
867
+ * 随 init 一起下发初始值,避免竞态;运行时切换走 envelope 'set-story-mode'。
868
+ * SDK 把它存成内部状态,每次生成请求自动带上 story_mode,游戏作者零适配。
869
+ * 纯文风选择,不是信任边界——服务端仍用 isUnrestricted 兜底内容分级。
870
+ */
871
+ storyMode?: boolean;
862
872
  debug?: boolean;
863
873
  }
864
874
  interface PreviewConfig {
@@ -882,6 +892,8 @@ interface PreviewInitPayload {
882
892
  provider?: string;
883
893
  }>;
884
894
  selectedModelId?: string;
895
+ /** 预览模式下宿主(创作台)当前的剧情模式开关初始值;运行时切换走 'set-story-mode' */
896
+ storyMode?: boolean;
885
897
  debug?: boolean;
886
898
  }
887
899
  interface TokenUpdatePayload {
@@ -893,6 +905,9 @@ interface ConfigUpdatePayload {
893
905
  interface SetModelPayload {
894
906
  modelId: string;
895
907
  }
908
+ interface SetStoryModePayload {
909
+ storyMode: boolean;
910
+ }
896
911
  interface OrientationPayload {
897
912
  mode: 'landscape' | 'portrait';
898
913
  }
@@ -916,7 +931,7 @@ interface AckPayload {
916
931
  ok: boolean;
917
932
  error?: string;
918
933
  }
919
- type DownstreamMsg = ProtocolEnvelope<'init', InitPayload> | ProtocolEnvelope<'preview-init', PreviewInitPayload> | ProtocolEnvelope<'token-update', TokenUpdatePayload> | ProtocolEnvelope<'config-update', ConfigUpdatePayload> | ProtocolEnvelope<'set-model', SetModelPayload> | ProtocolEnvelope<'orientation', OrientationPayload> | ProtocolEnvelope<'ack', AckPayload>;
934
+ type DownstreamMsg = ProtocolEnvelope<'init', InitPayload> | ProtocolEnvelope<'preview-init', PreviewInitPayload> | ProtocolEnvelope<'token-update', TokenUpdatePayload> | ProtocolEnvelope<'config-update', ConfigUpdatePayload> | ProtocolEnvelope<'set-model', SetModelPayload> | ProtocolEnvelope<'set-story-mode', SetStoryModePayload> | ProtocolEnvelope<'orientation', OrientationPayload> | ProtocolEnvelope<'ack', AckPayload>;
920
935
  type UpstreamMsg = ProtocolEnvelope<'ready', ReadyPayload> | ProtocolEnvelope<'exit', Record<string, never>> | ProtocolEnvelope<'request-orientation', OrientationPayload> | ProtocolEnvelope<'error', SdkErrorPayload> | ProtocolEnvelope<'navigate', NavigatePayload> | ProtocolEnvelope<'model-change', SetModelPayload> | ProtocolEnvelope<'ack', AckPayload>;
921
936
  declare function isProtocolEnvelope(data: unknown): data is ProtocolEnvelope<string, unknown>;
922
937
  declare function envelope<T extends string, P>(type: T, payload: P, opts?: {
package/dist/index.esm.js CHANGED
@@ -1,4 +1,4 @@
1
- var p=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var H=1;function Z(o){if(!o||typeof o!="object")return!1;let e=o;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function S(o,e,t){return{protocol:1,type:o,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var A=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!Z(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(i){console.error(`[StorviaBus] handler '${t.type}' threw:`,i)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:S(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(i){console.error("[StorviaBus] customSend failed:",i,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(i){console.error("[StorviaBus] postMessage failed:",i,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let i=e.id??Se(),s=S(e.type,e.payload,{id:i}),c=setTimeout(()=>{this.pendingAcks.delete(i),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(i,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Se(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var ie=null;function me(o){ie=o}var X="storvia-sdk-toast-style",ee="storvia-sdk-toast-stack",ge=`
1
+ var m=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var H=1;function Z(o){if(!o||typeof o!="object")return!1;let e=o;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function P(o,e,t){return{protocol:1,type:o,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var M=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!Z(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(i){console.error(`[StorviaBus] handler '${t.type}' threw:`,i)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:P(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(i){console.error("[StorviaBus] customSend failed:",i,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(i){console.error("[StorviaBus] postMessage failed:",i,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let i=e.id??Ee(),s=P(e.type,e.payload,{id:i}),c=setTimeout(()=>{this.pendingAcks.delete(i),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(i,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Ee(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var ie=null;function me(o){ie=o}var X="storvia-sdk-toast-style",ee="storvia-sdk-toast-stack",ge=`
2
2
  #${ee} {
3
3
  position: fixed;
4
4
  top: max(20px, env(safe-area-inset-top, 0px) + 20px);
@@ -222,7 +222,7 @@ var p=class extends Error{constructor(e,t){super(t),this.name="StorviaError",thi
222
222
  `,be={success:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>',error:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>',warning:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><path d="M10.29 3.86 1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"/><line x1="12" y1="9" x2="12" y2="13"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',info:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="16" x2="12" y2="12"/><line x1="12" y1="8" x2="12.01" y2="8"/></svg>'},re={UNAUTHORIZED:"\u767B\u5F55\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55",INSUFFICIENT_CREDITS:"\u82B1\u56ED\u5E01\u4E0D\u8DB3\uFF0C\u8BF7\u5145\u503C\u540E\u518D\u7EE7\u7EED\u6E38\u620F",VIOLATION_WORD_DETECTED:"\u5185\u5BB9\u542B\u6709\u8FDD\u7981\u8BCD\uFF0C\u8BF7\u4FEE\u6539\u540E\u91CD\u8BD5",CONTENT_FILTERED:"\u5185\u5BB9\u88AB\u5B89\u5168\u7B56\u7565\u62E6\u622A\uFF0C\u8BF7\u8C03\u6574\u540E\u91CD\u8BD5",MODEL_REFUSAL:"\u6A21\u578B\u62D2\u7EDD\u54CD\u5E94\uFF0C\u6362\u4E2A\u8BF4\u6CD5\u8BD5\u8BD5",STREAM_INTERRUPTED:"\u56DE\u590D\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",RATE_LIMITED:"\u64CD\u4F5C\u8FC7\u4E8E\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5",MODEL_NOT_FOUND:"\u6240\u9009\u6A21\u578B\u4E0D\u53EF\u7528\uFF0C\u8BF7\u5207\u6362\u5176\u4ED6\u6A21\u578B",GAME_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u6E38\u620F",INVALID_REQUEST:"\u8BF7\u6C42\u65E0\u6548\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",INTERNAL_ERROR:"\u670D\u52A1\u51FA\u4E86\u70B9\u5C0F\u95EE\u9898\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",NOT_INITIALIZED:"SDK \u5C1A\u672A\u521D\u59CB\u5316",NOT_SUPPORTED_IN_PREVIEW:"\u5F53\u524D\u63A5\u53E3\u5728\u9884\u89C8\u6A21\u5F0F\u4E0B\u4E0D\u53EF\u7528",NETWORK_ERROR:"\u7F51\u7EDC\u5F02\u5E38\uFF0C\u8BF7\u68C0\u67E5\u8FDE\u63A5",REQUEST_TIMEOUT:"\u8BF7\u6C42\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",MODEL_LOADING_TIMEOUT:"\u6A21\u578B\u54CD\u5E94\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",STREAM_INACTIVITY:"\u8FDE\u63A5\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",DAISY_CARD_REQUIRED:"\u56DE\u6EAF\u6D88\u606F\u9700\u8981\u6709\u6548\u7684\u96CF\u83CA\u5361\u8BA2\u9605",MESSAGE_NOT_FOUND:"\u6D88\u606F\u4E0D\u5B58\u5728\u6216\u65E0\u6743\u64CD\u4F5C",MESSAGE_TOO_OLD:"\u4EC5\u53EF\u56DE\u6EAF 30 \u5929\u5185\u7684\u6D88\u606F",NO_MESSAGES_TO_DELETE:"\u8BE5\u6D88\u606F\u4E4B\u540E\u6CA1\u6709\u53EF\u56DE\u6EAF\u7684\u6D88\u606F",GENERATION_TIMEOUT:"\u751F\u6210\u8D85\u65F6\uFF0C\u8BF7\u91CD\u8BD5",REPETITION_LOOP:"\u56DE\u590D\u51FA\u73B0\u91CD\u590D\uFF0C\u8BF7\u91CD\u8BD5\u6216\u6362\u4E2A\u8BF4\u6CD5",SAVE_FAILED:"\u6D88\u606F\u4FDD\u5B58\u5931\u8D25\uFF0C\u672C\u6B21\u4E0D\u6263\u8D39\uFF0C\u8BF7\u91CD\u8BD5",FINALIZE_FAILED:"\u56DE\u590D\u5904\u7406\u5931\u8D25\uFF0C\u8BF7\u91CD\u8BD5",CONVERSATION_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u4F1A\u8BDD",EMPTY_MESSAGE:"\u6D88\u606F\u5185\u5BB9\u4E0D\u80FD\u4E3A\u7A7A",CONTINUE_MODEL_NOT_AVAILABLE:"\u7EED\u5199\u6A21\u578B\u5F53\u524D\u4E0D\u53EF\u7528",CONTINUE_PROMPT_MISSING:"\u7EED\u5199\u914D\u7F6E\u7F3A\u5931"},ve=!0;function Pe(o){ve=o}function ke(){if(typeof document>"u")return null;let o=document.getElementById(ee);if(!o){if(!document.getElementById(X)){let e=document.createElement("style");e.id=X,e.textContent=ge,document.head.appendChild(e)}o=document.createElement("div"),o.id=ee,document.body.appendChild(o)}return o}function fe(o,e="info",t=3500,n){if(!ve)return;let r=ke();if(!r)return;let i=t<=0,s=document.createElement("div");s.className=`storvia-toast ${e}`,s.innerHTML=`
223
223
  <span class="storvia-toast-icon">${be[e]}</span>
224
224
  <span class="storvia-toast-msg"></span>
225
- `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=o);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(h){console.error("[Storvia toast] action error:",h)}d()}),s.appendChild(a)}if(i){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),i||setTimeout(d,t)}function b(o,e){if(o==="INSUFFICIENT_CREDITS"){pe({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||re.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(o==="DAISY_CARD_REQUIRED"){pe({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||re.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=re[o]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";fe(t,o==="RATE_LIMITED"?"warning":"error")}var J=null;function pe(o){if(typeof document>"u"||J)return;if(!document.getElementById(X)){let s=document.createElement("style");s.id=X,s.textContent=ge,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
225
+ `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=o);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(l){console.error("[Storvia toast] action error:",l)}d()}),s.appendChild(a)}if(i){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),i||setTimeout(d,t)}function k(o,e){if(o==="INSUFFICIENT_CREDITS"){pe({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||re.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(o==="DAISY_CARD_REQUIRED"){pe({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||re.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=re[o]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";fe(t,o==="RATE_LIMITED"?"warning":"error")}var J=null;function pe(o){if(typeof document>"u"||J)return;if(!document.getElementById(X)){let s=document.createElement("style");s.id=X,s.textContent=ge,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
226
226
  <div class="storvia-sheet" role="dialog" aria-modal="true" aria-labelledby="storvia-sheet-title">
227
227
  <div class="storvia-sheet-icon">
228
228
  <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>
@@ -234,6 +234,6 @@ var p=class extends Error{constructor(e,t){super(t),this.name="StorviaError",thi
234
234
  <button type="button" class="storvia-sheet-btn storvia-sheet-btn-primary" data-role="navigate"></button>
235
235
  </div>
236
236
  </div>
237
- `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=o.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=o.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=o.primaryLabel);let i=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),J===e&&(J=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",i),e.addEventListener("click",s=>{s.target===e&&i()}),r?.addEventListener("click",()=>{if(ie)try{ie(S("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");i()}),document.body.appendChild(e),J=e,requestAnimationFrame(()=>e.classList.add("show"))}var y=class y{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof p||b("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new p("REQUEST_TIMEOUT","Request timed out");return b("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),y.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:i,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:h}=e,l="%c[Storvia SDK]",m="color: #6366f1; font-weight: bold",v=a!==void 0?` (${a}ms)`:"",u=i!==void 0?` [${i}]`:"",P=h?` [model: ${h}]`:"";d?(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2717`,m,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2713`,m,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,h])=>n.searchParams.set(a,h));let r=Date.now(),i,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),i=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"GET",path:e,body:t,status:i,rawResponse:s,parsedData:l,durationMs:Date.now()-r}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:i,rawResponse:s,error:h,durationMs:Date.now()-r}),h===a&&this.maybeShowNetworkToast(a),h}}async post(e,t,n){let r=Date.now(),i,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),i=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"POST",path:e,body:t,status:i,rawResponse:s,parsedData:l,durationMs:Date.now()-r,modelName:n?.modelName}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:i,rawResponse:s,error:h,durationMs:Date.now()-r,modelName:n?.modelName}),h===a&&this.maybeShowNetworkToast(a),h}}async patch(e,t){let n=Date.now(),r,i,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return i=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:i,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:i,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,i,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return i=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:i,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:i,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:i,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:i.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,i,s,c,d,a,h){let l=Date.now(),m=i?.modelName?` [model: ${i.modelName}]`:"",v=[],u=f=>{this.debug&&v.push({t:Date.now()-l,event:f})},P=new AbortController,C=null,I=null,k=null,R=null,x=()=>{C!==null&&(clearTimeout(C),C=null),I!==null&&(clearTimeout(I),I=null),k!==null&&(clearTimeout(k),k=null)},z=f=>{R=f,x(),P.abort()};C=setTimeout(()=>z("REQUEST_TIMEOUT"),y.REQUEST_TIMEOUT);let T;try{T=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:P.signal})}catch(f){if(x(),R){let w=new p(R,"Request timed out");throw b(R),this.log({method:"STREAM",path:e,body:t,error:w,durationMs:Date.now()-l,modelName:i?.modelName}),w}throw this.maybeShowNetworkToast(f),f}if(C!==null&&(clearTimeout(C),C=null),!T.ok){x();let f=await T.text().catch(()=>""),w={};try{w=JSON.parse(f)}catch{}let E=w.code||"INTERNAL_ERROR",g=new p(E,w.message||`HTTP ${T.status}`);throw b(E,w.message),this.log({method:"STREAM",path:e,body:t,status:T.status,rawResponse:f,error:g,durationMs:Date.now()-l,modelName:i?.modelName}),g}let de=T.body?.getReader();if(!de)throw x(),new p("INTERNAL_ERROR","No response body for stream");I=setTimeout(()=>z("MODEL_LOADING_TIMEOUT"),y.MODEL_LOADING_TIMEOUT);let ce=new TextDecoder,B="",_="",le=!1,ne,Y,O="",Q=!1,he=f=>{if(Q)return;let w=f.endsWith("\r")?f.slice(0,-1):f;if(w.startsWith("id: ")){Y=w.slice(4);return}if(!w.startsWith("data: "))return;let E=w.slice(6);if(E==="[DONE]"){u("[DONE]"),Q=!0;return}try{let g=JSON.parse(E);u(g),g.type==="done"&&g.id?B=g.id:g.type==="state"?(s&&s(g.delta,g.full??null),d&&Array.isArray(g.createdNames)&&g.createdNames.length&&d(g.createdNames)):g.type==="thinking"?c&&(g.status==="start"||g.status==="end")&&c(g.status):g.content&&(le?(k!==null&&clearTimeout(k),k=setTimeout(()=>z("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)):(le=!0,I!==null&&(clearTimeout(I),I=null),k=setTimeout(()=>z("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)),_+=g.content,n(g.content))}catch{u({raw:E})}Y!==void 0&&(ne=Y,Y=void 0)},ue=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${T.status}]${m} (${Date.now()-l}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",B),console.log(`SSE events (${v.length}):`,v),console.groupEnd()),r(B)};try{for(;;){let{done:f,value:w}=await de.read();if(f)break;O+=ce.decode(w,{stream:!0});let E=O.split(`
238
- `);O=E.pop()??"";for(let g of E)he(g);if(Q){ue();return}}if(O+=ce.decode(),O&&he(O),Q){ue();return}}catch(f){if(x(),R){let w=new p(R,R==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw b(R),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${T.status}]${m} (${Date.now()-l}ms) %c\u2717 ${R}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Timeout:",w),console.groupEnd()),w}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${T.status}]${m} (${Date.now()-l}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0});return}throw f}if(x(),B){r(B);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0})}async resumeLoop(e,t,n,r){let i=t;for(let c=1;c<=y.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(y.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(l=>setTimeout(l,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:i},h;try{h=await this.pumpGetStream(e.conversationId,e.topic,i,a,n)}catch{continue}if(i=a.lastId??i,h==="done"){n.onDone(a.messageId);return}if(h==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new p("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw b("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},i;try{i=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(i==="done"){n.onDone(r.messageId);return}if(i==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,i){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),y.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new p("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let l=a.body?.getReader();return l?await this.pumpReader(l,r,i):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,i,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},y.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,h=l=>{if(a)return;let m=l.endsWith("\r")?l.slice(0,-1):l;if(m.startsWith("id: ")){i=m.slice(4);return}if(!m.startsWith("data: "))return;let v=m.slice(6);if(v==="[DONE]"){a=!0;return}try{let u=JSON.parse(v);u.type==="done"&&u.id?t.messageId=u.id:u.type==="state"?(n.onState?.(u.delta,u.full??null),Array.isArray(u.createdNames)&&u.createdNames.length&&n.onCreatedCharacters?.(u.createdNames)):u.type==="thinking"?(u.status==="start"||u.status==="end")&&n.onThinking?.(u.status):u.content&&n.onChunk(u.content)}catch{}i!==void 0&&(t.lastId=i,i=void 0)};try{for(;;){let{done:l,value:m}=await e.read();if(l)break;c(),d+=r.decode(m,{stream:!0});let v=d.split(`
239
- `);d=v.pop()??"";for(let u of v)h(u);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&h(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},i={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||i[e.status]||"INTERNAL_ERROR",c=new p(s,r.message||`HTTP ${e.status}`);throw b(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};y.REQUEST_TIMEOUT=6e4,y.MODEL_LOADING_TIMEOUT=18e4,y.STREAM_INACTIVITY_TIMEOUT=6e4,y.RECONNECT_MAX_ATTEMPTS=10,y.RECONNECT_BACKOFF_CAP=15e3;var W=y;var M=class{constructor(e,t,n,r,i=!1,s,c){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=i;this.previewConfig=s,this.getModelName=c}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:K(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[]};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",i=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,h)=>{i=a,s=h,e.onState&&e.onState(i,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return i&&(d.delta=i,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function K(o){if(o)return(e,t)=>o(e,t)}var oe=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},D=class{constructor(e,t,n=!1,r,i){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(we)),this.state=new oe(e,t,n,i)}setInitial(e,t){this.mem=e?e.map(we):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(ye):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?ye(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function we(o){return{name:o.name,description:o.description,avatar:o.avatar,...o.introduction!==void 0?{introduction:o.introduction}:{},...o.visibleAtStart!==void 0?{visibleAtStart:o.visibleAtStart}:{},...o.gender?{gender:o.gender}:{},...o.userDescription!==void 0?{userDescription:o.userDescription}:{},...o.isPreset!==void 0?{isPreset:o.isPreset}:{}}}function ye(o){return{name:o.name,avatar:o.avatar,description:o.description,...o.introduction!==void 0?{introduction:o.introduction}:{},...o.visibleAtStart!==void 0?{visibleAtStart:o.visibleAtStart}:{},...o.userDescription!==void 0?{userDescription:o.userDescription}:{},...o.gender?{gender:o.gender}:{},...o.isPreset!==void 0?{isPreset:o.isPreset}:{}}}var N=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(i=>({...i})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(i=>i.from===e&&i.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Ie(o){let e={count:o.count};return o.desc!==void 0&&(e.desc=o.desc),o.icon_url!==void 0&&(e.iconUrl=o.icon_url),e}function se(o){let e={};if(!o)return e;for(let[t,n]of Object.entries(o)){let r={};for(let[i,s]of Object.entries(n))r[i]=Ie(s);e[t]=r}return e}function xe(o){let e={};if(!o)return e;for(let[t,n]of Object.entries(o))e[t]=Ie(n);return e}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=se(r))}setInitial(e){this.mem=e?se(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,i]of Object.entries(this.mem))n[r]={...i};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return xe(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return se(t)}async add(e){let{group:t,name:n,count:r=1,desc:i,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};i!==void 0&&(d.desc=i),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};i!==void 0&&(c.desc=i),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:i,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),i!==void 0&&(a.desc=i),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),i!==void 0&&(c.desc=i),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:i}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=i||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:i})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let i=this.mem[e];if(i&&Object.keys(i).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},L=class{constructor(e,t,n=!1,r,i){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ae(e,t,n,i)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function F(o,e){if(!e)return o;let t=o.includes("?")?"&":"?";return`${o}${t}game_id=${encodeURIComponent(e)}`}var G=class{constructor(e,t,n,r=!1,i,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};i&&(this.mem=Ce(i)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Ce(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(F(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,i]of Object.entries(e))typeof i=="object"&&i!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...i}:this.mem[r]=i,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(F(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(F(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Ce(o){let e={};for(let[t,n]of Object.entries(o))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Re(o,e){if(!e)return o;let t=o.includes("?")?"&":"?";return`${o}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,i){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};i&&(this.mem={...i})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Re(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Re(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var q=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var j=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var Te="/functions/v1/world-engine/v1",_e="https://api.storvia.ai";function Oe(){return window.__STORVIA__||{}}function Ae(o,e=3e4){let t=Oe();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let i=setTimeout(()=>{s(),c(),r(new p("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=o.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,debug:a.payload.debug})}),c=o.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(i),s(),c();let h=window;h.__STORVIA__=a,n(a)}o.send(S("ready",{}))})}var te=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new A({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?l=>l.source===null||l.source===window:l=>l.source===window.parent,customSend:t?l=>e.callHandler("storviaBus",l):void 0}),me(l=>this.bus.send(l));let n=await Ae(this.bus),r=n.apiBase;if(!r)throw new p("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${Te}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new p("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new p("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new W(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[l,m]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=l,this.modelId=(n.selectedModelId&&l.some(I=>I.id===n.selectedModelId)?n.selectedModelId:"")||l[0]?.id||"";let v=()=>this.gameId,u=()=>this.conversationId,P=()=>this.modelId,C=()=>this.models.find(I=>I.id===this.modelId)?.name;this.chat=new M(this.http,v,u,P,!0,this.previewConfig,C),this.characters=new D(this.http,u,!0,m?.characters,m?.characterStates),this.relationships=new N(this.http,u,!0,m?.relationships),this.inventory=new U(this.http,u,!0,m?.inventory),this.world=new $(this.http,u,!0,m?.world),this.player=new L(this.http,u,!0,m?.player,m?.playerState),this.custom=new G(this.http,u,v,!0,m?.custom,m?.custom_inject),this.save=new V(this.http,u,v,!0,m?.save_data),this.state=new q(this.http,u,!0),this.memory=new j(this.http,u,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[i,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=i.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(l=>l.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"";let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,h=()=>this.models.find(l=>l.id===this.modelId)?.name;this.chat=new M(this.http,c,d,a,!1,void 0,h),this.characters=new D(this.http,d),this.relationships=new N(this.http,d),this.inventory=new U(this.http,d),this.world=new $(this.http,d),this.player=new L(this.http,d),this.custom=new G(this.http,d,c),this.save=new V(this.http,d,c),this.state=new q(this.http,d),this.memory=new j(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new p("UNAUTHORIZED","User not authenticated"):t.status===404?new p("GAME_NOT_FOUND","Game not found or not published"):new p("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${_e}${Te}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new W(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let i=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new M(this.http,i,s,c,!0,void 0,d),this.characters=new D(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new N(this.http,s,!0,n?.relationships),this.inventory=new U(this.http,s,!0,n?.inventory),this.world=new $(this.http,s,!0,n?.world),this.player=new L(this.http,s,!0,n?.player,n?.playerState),this.custom=new G(this.http,s,i,!0,n?.custom),this.save=new V(this.http,s,i,!0,n?.save_data),this.memory=new j(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(i=>({id:i.id,name:i.name,url:i.url,assetType:i.asset_type,category:i.category}))}};async function Me(o){let e=new te;return o?.dev?await e.initDev(o.dev):await e.init(),e}function Ee(o){return typeof o=="object"&&o!==null&&"value"in o&&"type"in o&&(o.type==="number"||o.type==="text")}function De(o){return Ee(o)?o.value:o}export{H as PROTOCOL_VERSION,A as StorviaBus,p as StorviaError,te as StorviaSDK,Me as createStorviaSDK,S as envelope,De as extractFieldValue,Z as isProtocolEnvelope,Ee as isRichFieldValue,Pe as setToastEnabled,fe as showToast};
237
+ `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=o.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=o.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=o.primaryLabel);let i=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),J===e&&(J=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",i),e.addEventListener("click",s=>{s.target===e&&i()}),r?.addEventListener("click",()=>{if(ie)try{ie(P("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");i()}),document.body.appendChild(e),J=e,requestAnimationFrame(()=>e.classList.add("show"))}var I=class I{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof m||k("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new m("REQUEST_TIMEOUT","Request timed out");return k("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),I.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:i,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:l}=e,u="%c[Storvia SDK]",h="color: #6366f1; font-weight: bold",g=a!==void 0?` (${a}ms)`:"",p=i!==void 0?` [${i}]`:"",w=l?` [model: ${l}]`:"";d?(console.groupCollapsed(`${u} %c${t} ${n}${p}${w}${g} %c\u2717`,h,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${u} %c${t} ${n}${p}${w}${g} %c\u2713`,h,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,l])=>n.searchParams.set(a,l));let r=Date.now(),i,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),i=a.status;let{raw:l,data:u}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"GET",path:e,body:t,status:i,rawResponse:s,parsedData:u,durationMs:Date.now()-r}),u}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:i,rawResponse:s,error:l,durationMs:Date.now()-r}),l===a&&this.maybeShowNetworkToast(a),l}}async post(e,t,n){let r=Date.now(),i,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),i=a.status;let{raw:l,data:u}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"POST",path:e,body:t,status:i,rawResponse:s,parsedData:u,durationMs:Date.now()-r,modelName:n?.modelName}),u}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:i,rawResponse:s,error:l,durationMs:Date.now()-r,modelName:n?.modelName}),l===a&&this.maybeShowNetworkToast(a),l}}async patch(e,t){let n=Date.now(),r,i,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return i=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:i,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:i,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,i,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return i=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:i,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:i,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:i,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:i.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,i,s,c,d,a,l){let u=Date.now(),h=i?.modelName?` [model: ${i.modelName}]`:"",g=[],p=f=>{this.debug&&g.push({t:Date.now()-u,event:f})},w=new AbortController,R=null,T=null,S=null,C=null,x=()=>{R!==null&&(clearTimeout(R),R=null),T!==null&&(clearTimeout(T),T=null),S!==null&&(clearTimeout(S),S=null)},z=f=>{C=f,x(),w.abort()};R=setTimeout(()=>z("REQUEST_TIMEOUT"),I.REQUEST_TIMEOUT);let E;try{E=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:w.signal})}catch(f){if(x(),C){let y=new m(C,"Request timed out");throw k(C),this.log({method:"STREAM",path:e,body:t,error:y,durationMs:Date.now()-u,modelName:i?.modelName}),y}throw this.maybeShowNetworkToast(f),f}if(R!==null&&(clearTimeout(R),R=null),!E.ok){x();let f=await E.text().catch(()=>""),y={};try{y=JSON.parse(f)}catch{}let b=y.code||"INTERNAL_ERROR",v=new m(b,y.message||`HTTP ${E.status}`);throw k(b,y.message),this.log({method:"STREAM",path:e,body:t,status:E.status,rawResponse:f,error:v,durationMs:Date.now()-u,modelName:i?.modelName}),v}let de=E.body?.getReader();if(!de)throw x(),new m("INTERNAL_ERROR","No response body for stream");T=setTimeout(()=>z("MODEL_LOADING_TIMEOUT"),I.MODEL_LOADING_TIMEOUT);let ce=new TextDecoder,B="",_="",le=!1,ne,Y,O="",Q=!1,he=f=>{if(Q)return;let y=f.endsWith("\r")?f.slice(0,-1):f;if(y.startsWith("id: ")){Y=y.slice(4);return}if(!y.startsWith("data: "))return;let b=y.slice(6);if(b==="[DONE]"){p("[DONE]"),Q=!0;return}try{let v=JSON.parse(b);p(v),v.type==="done"&&v.id?B=v.id:v.type==="state"?(s&&s(v.delta,v.full??null),d&&Array.isArray(v.createdNames)&&v.createdNames.length&&d(v.createdNames)):v.type==="thinking"?c&&(v.status==="start"||v.status==="end")&&c(v.status):v.content&&(le?(S!==null&&clearTimeout(S),S=setTimeout(()=>z("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)):(le=!0,T!==null&&(clearTimeout(T),T=null),S=setTimeout(()=>z("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)),_+=v.content,n(v.content))}catch{p({raw:b})}Y!==void 0&&(ne=Y,Y=void 0)},ue=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${h} (${Date.now()-u}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",B),console.log(`SSE events (${g.length}):`,g),console.groupEnd()),r(B)};try{for(;;){let{done:f,value:y}=await de.read();if(f)break;O+=ce.decode(y,{stream:!0});let b=O.split(`
238
+ `);O=b.pop()??"";for(let v of b)he(v);if(Q){ue();return}}if(O+=ce.decode(),O&&he(O),Q){ue();return}}catch(f){if(x(),C){let y=new m(C,C==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw k(C),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${h} (${Date.now()-u}ms) %c\u2717 ${C}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Timeout:",y),console.groupEnd()),y}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${h} (${Date.now()-u}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0});return}throw f}if(x(),B){r(B);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0})}async resumeLoop(e,t,n,r){let i=t;for(let c=1;c<=I.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(I.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(u=>setTimeout(u,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:i},l;try{l=await this.pumpGetStream(e.conversationId,e.topic,i,a,n)}catch{continue}if(i=a.lastId??i,l==="done"){n.onDone(a.messageId);return}if(l==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new m("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw k("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},i;try{i=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(i==="done"){n.onDone(r.messageId);return}if(i==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,i){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),I.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new m("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let u=a.body?.getReader();return u?await this.pumpReader(u,r,i):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,i,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},I.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,l=u=>{if(a)return;let h=u.endsWith("\r")?u.slice(0,-1):u;if(h.startsWith("id: ")){i=h.slice(4);return}if(!h.startsWith("data: "))return;let g=h.slice(6);if(g==="[DONE]"){a=!0;return}try{let p=JSON.parse(g);p.type==="done"&&p.id?t.messageId=p.id:p.type==="state"?(n.onState?.(p.delta,p.full??null),Array.isArray(p.createdNames)&&p.createdNames.length&&n.onCreatedCharacters?.(p.createdNames)):p.type==="thinking"?(p.status==="start"||p.status==="end")&&n.onThinking?.(p.status):p.content&&n.onChunk(p.content)}catch{}i!==void 0&&(t.lastId=i,i=void 0)};try{for(;;){let{done:u,value:h}=await e.read();if(u)break;c(),d+=r.decode(h,{stream:!0});let g=d.split(`
239
+ `);d=g.pop()??"";for(let p of g)l(p);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&l(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},i={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||i[e.status]||"INTERNAL_ERROR",c=new m(s,r.message||`HTTP ${e.status}`);throw k(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};I.REQUEST_TIMEOUT=6e4,I.MODEL_LOADING_TIMEOUT=18e4,I.STREAM_INACTIVITY_TIMEOUT=6e4,I.RECONNECT_MAX_ATTEMPTS=10,I.RECONNECT_BACKOFF_CAP=15e3;var W=I;var A=class{constructor(e,t,n,r,i=!1,s,c,d){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=i;this.previewConfig=s,this.getModelName=c,this.getStoryMode=d}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new m("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new m("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new m("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new m("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:K(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[],story_mode:this.getStoryMode?.()};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),K(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",i=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,l)=>{i=a,s=l,e.onState&&e.onState(i,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return i&&(d.delta=i,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function K(o){if(o)return(e,t)=>o(e,t)}var oe=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},D=class{constructor(e,t,n=!1,r,i){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(ye)),this.state=new oe(e,t,n,i)}setInitial(e,t){this.mem=e?e.map(ye):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(we):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?we(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function ye(o){return{name:o.name,description:o.description,avatar:o.avatar,...o.introduction!==void 0?{introduction:o.introduction}:{},...o.visibleAtStart!==void 0?{visibleAtStart:o.visibleAtStart}:{},...o.gender?{gender:o.gender}:{},...o.userDescription!==void 0?{userDescription:o.userDescription}:{},...o.isPreset!==void 0?{isPreset:o.isPreset}:{}}}function we(o){return{name:o.name,avatar:o.avatar,description:o.description,...o.introduction!==void 0?{introduction:o.introduction}:{},...o.visibleAtStart!==void 0?{visibleAtStart:o.visibleAtStart}:{},...o.userDescription!==void 0?{userDescription:o.userDescription}:{},...o.gender?{gender:o.gender}:{},...o.isPreset!==void 0?{isPreset:o.isPreset}:{}}}var N=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(i=>({...i})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(i=>i.from===e&&i.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Ie(o){let e={count:o.count};return o.desc!==void 0&&(e.desc=o.desc),o.icon_url!==void 0&&(e.iconUrl=o.icon_url),e}function se(o){let e={};if(!o)return e;for(let[t,n]of Object.entries(o)){let r={};for(let[i,s]of Object.entries(n))r[i]=Ie(s);e[t]=r}return e}function xe(o){let e={};if(!o)return e;for(let[t,n]of Object.entries(o))e[t]=Ie(n);return e}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=se(r))}setInitial(e){this.mem=e?se(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,i]of Object.entries(this.mem))n[r]={...i};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return xe(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return se(t)}async add(e){let{group:t,name:n,count:r=1,desc:i,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};i!==void 0&&(d.desc=i),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};i!==void 0&&(c.desc=i),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:i,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),i!==void 0&&(a.desc=i),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),i!==void 0&&(c.desc=i),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:i}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=i||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:i})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let i=this.mem[e];if(i&&Object.keys(i).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},L=class{constructor(e,t,n=!1,r,i){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ae(e,t,n,i)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function F(o,e){if(!e)return o;let t=o.includes("?")?"&":"?";return`${o}${t}game_id=${encodeURIComponent(e)}`}var G=class{constructor(e,t,n,r=!1,i,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};i&&(this.mem=Ce(i)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Ce(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(F(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,i]of Object.entries(e))typeof i=="object"&&i!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...i}:this.mem[r]=i,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(F(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(F(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(F(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Ce(o){let e={};for(let[t,n]of Object.entries(o))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Re(o,e){if(!e)return o;let t=o.includes("?")?"&":"?";return`${o}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,i){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};i&&(this.mem={...i})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Re(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Re(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var q=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new m("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var j=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var Te="/functions/v1/world-engine/v1",_e="https://api.storvia.ai";function Oe(){return window.__STORVIA__||{}}function Me(o,e=3e4){let t=Oe();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let i=setTimeout(()=>{s(),c(),r(new m("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=o.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,storyMode:a.payload.storyMode,debug:a.payload.debug})}),c=o.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(i),s(),c();let l=window;l.__STORVIA__=a,n(a)}o.send(P("ready",{}))})}var te=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.storyMode=!1;this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new M({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?h=>h.source===null||h.source===window:h=>h.source===window.parent,customSend:t?h=>e.callHandler("storviaBus",h):void 0}),me(h=>this.bus.send(h));let n=await Me(this.bus),r=n.apiBase;if(!r)throw new m("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${Te}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new m("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new m("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new W(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[h,g]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=h,this.modelId=(n.selectedModelId&&h.some(C=>C.id===n.selectedModelId)?n.selectedModelId:"")||h[0]?.id||"",this.storyMode=n.storyMode===!0;let p=()=>this.gameId,w=()=>this.conversationId,R=()=>this.modelId,T=()=>this.models.find(C=>C.id===this.modelId)?.name,S=()=>this.storyMode;this.chat=new A(this.http,p,w,R,!0,this.previewConfig,T,S),this.characters=new D(this.http,w,!0,g?.characters,g?.characterStates),this.relationships=new N(this.http,w,!0,g?.relationships),this.inventory=new U(this.http,w,!0,g?.inventory),this.world=new $(this.http,w,!0,g?.world),this.player=new L(this.http,w,!0,g?.player,g?.playerState),this.custom=new G(this.http,w,p,!0,g?.custom,g?.custom_inject),this.save=new V(this.http,w,p,!0,g?.save_data),this.state=new q(this.http,w,!0),this.memory=new j(this.http,w,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[i,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=i.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(h=>h.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"",this.storyMode=n.storyMode===!0;let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,l=()=>this.models.find(h=>h.id===this.modelId)?.name,u=()=>this.storyMode;this.chat=new A(this.http,c,d,a,!1,void 0,l,u),this.characters=new D(this.http,d),this.relationships=new N(this.http,d),this.inventory=new U(this.http,d),this.world=new $(this.http,d),this.player=new L(this.http,d),this.custom=new G(this.http,d,c),this.save=new V(this.http,d,c),this.state=new q(this.http,d),this.memory=new j(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new m("UNAUTHORIZED","User not authenticated"):t.status===404?new m("GAME_NOT_FOUND","Game not found or not published"):new m("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${_e}${Te}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new W(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let i=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new A(this.http,i,s,c,!0,void 0,d),this.characters=new D(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new N(this.http,s,!0,n?.relationships),this.inventory=new U(this.http,s,!0,n?.inventory),this.world=new $(this.http,s,!0,n?.world),this.player=new L(this.http,s,!0,n?.player,n?.playerState),this.custom=new G(this.http,s,i,!0,n?.custom),this.save=new V(this.http,s,i,!0,n?.save_data),this.memory=new j(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(i=>({id:i.id,name:i.name,url:i.url,assetType:i.asset_type,category:i.category}))}};async function Ae(o){let e=new te;return o?.dev?await e.initDev(o.dev):await e.init(),e}function Se(o){return typeof o=="object"&&o!==null&&"value"in o&&"type"in o&&(o.type==="number"||o.type==="text")}function De(o){return Se(o)?o.value:o}export{H as PROTOCOL_VERSION,M as StorviaBus,m as StorviaError,te as StorviaSDK,Ae as createStorviaSDK,P as envelope,De as extractFieldValue,Z as isProtocolEnvelope,Se as isRichFieldValue,Pe as setToastEnabled,fe as showToast};
package/dist/index.umd.js CHANGED
@@ -1,4 +1,4 @@
1
- "use strict";var StorviaSDK=(()=>{var re=Object.defineProperty;var xe=Object.getOwnPropertyDescriptor;var _e=Object.getOwnPropertyNames;var Oe=Object.prototype.hasOwnProperty;var Ae=(i,e)=>{for(var t in e)re(i,t,{get:e[t],enumerable:!0})},Me=(i,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of _e(e))!Oe.call(i,r)&&r!==t&&re(i,r,{get:()=>e[r],enumerable:!(n=xe(e,r))||n.enumerable});return i};var De=i=>Me(re({},"__esModule",{value:!0}),i);var je={};Ae(je,{PROTOCOL_VERSION:()=>M,StorviaBus:()=>O,StorviaError:()=>p,StorviaSDK:()=>Y,createStorviaSDK:()=>Pe,envelope:()=>C,extractFieldValue:()=>ke,isProtocolEnvelope:()=>W,isRichFieldValue:()=>le,setToastEnabled:()=>Ie,showToast:()=>se});var p=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var M=1;function W(i){if(!i||typeof i!="object")return!1;let e=i;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function C(i,e,t){return{protocol:1,type:i,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var O=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!W(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(o){console.error(`[StorviaBus] handler '${t.type}' threw:`,o)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:C(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(o){console.error("[StorviaBus] customSend failed:",o,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(o){console.error("[StorviaBus] postMessage failed:",o,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let o=e.id??Ne(),s=C(e.type,e.payload,{id:o}),c=setTimeout(()=>{this.pendingAcks.delete(o),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(o,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Ne(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var oe=null;function fe(i){oe=i}var ee="storvia-sdk-toast-style",te="storvia-sdk-toast-stack",we=`
1
+ "use strict";var StorviaSDK=(()=>{var re=Object.defineProperty;var xe=Object.getOwnPropertyDescriptor;var _e=Object.getOwnPropertyNames;var Oe=Object.prototype.hasOwnProperty;var Me=(i,e)=>{for(var t in e)re(i,t,{get:e[t],enumerable:!0})},Ae=(i,e,t,n)=>{if(e&&typeof e=="object"||typeof e=="function")for(let r of _e(e))!Oe.call(i,r)&&r!==t&&re(i,r,{get:()=>e[r],enumerable:!(n=xe(e,r))||n.enumerable});return i};var De=i=>Ae(re({},"__esModule",{value:!0}),i);var je={};Me(je,{PROTOCOL_VERSION:()=>A,StorviaBus:()=>O,StorviaError:()=>u,StorviaSDK:()=>Y,createStorviaSDK:()=>Pe,envelope:()=>R,extractFieldValue:()=>ke,isProtocolEnvelope:()=>W,isRichFieldValue:()=>le,setToastEnabled:()=>Ie,showToast:()=>se});var u=class extends Error{constructor(e,t){super(t),this.name="StorviaError",this.code=e}};var A=1;function W(i){if(!i||typeof i!="object")return!1;let e=i;return typeof e.protocol=="number"&&typeof e.type=="string"&&"payload"in e}function R(i,e,t){return{protocol:1,type:i,payload:e,...t?.id?{id:t.id}:{},...t?.ackId?{ackId:t.ackId}:{}}}var O=class{constructor(e){this.handlers=new Map;this.pendingAcks=new Map;this.listener=null;this.incoming=e.incoming,this.getOutgoing=e.outgoing,this.verifySource=e.verifySource??(()=>!0),this.validate=e.validate,this.debug=!!e.debug,this.getTransferables=e.transfer??(()=>{}),this.customSend=e.customSend,this.attach()}attach(){this.listener=e=>{if((this.incoming instanceof Window||this.incoming===window)&&!this.verifySource(e))return;let t=e.data;if(!W(t))return;if(t.protocol!==1){this.debug&&console.warn("[StorviaBus] protocol mismatch",{expected:1,got:t.protocol,type:t.type});return}if(this.validate&&!this.validate(t)){this.debug&&console.warn("[StorviaBus] validation failed",t);return}if(t.ackId){let r=this.pendingAcks.get(t.ackId);if(r){this.pendingAcks.delete(t.ackId),r(t);return}}let n=this.handlers.get(t.type);if(!n||n.size===0){this.debug&&console.debug("[StorviaBus] no handler for",t.type);return}n.forEach(r=>{try{r(t)}catch(o){console.error(`[StorviaBus] handler '${t.type}' threw:`,o)}})},this.incoming.addEventListener("message",this.listener),this.incoming instanceof MessagePort&&this.incoming.start()}on(e,t){let n=this.handlers.get(e);n||(n=new Set,this.handlers.set(e,n));let r=t;return n.add(r),()=>n.delete(r)}send(e){let t=e.protocol?e:R(e.type,e.payload,{id:e.id,ackId:e.ackId});if(this.customSend){try{this.customSend(t)}catch(o){console.error("[StorviaBus] customSend failed:",o,{type:e.type})}return}let n=this.getOutgoing();if(!n){this.debug&&console.warn("[StorviaBus] outgoing target unavailable, drop:",e.type);return}let r=this.getTransferables(t);try{n instanceof MessagePort?n.postMessage(t,r??[]):n.postMessage(t,"*",r??[])}catch(o){console.error("[StorviaBus] postMessage failed:",o,{type:e.type})}}request(e,t=1e4){return new Promise((n,r)=>{let o=e.id??Ne(),s=R(e.type,e.payload,{id:o}),c=setTimeout(()=>{this.pendingAcks.delete(o),r(new Error(`[StorviaBus] request '${e.type}' timed out after ${t}ms`))},t);this.pendingAcks.set(o,d=>{clearTimeout(c),n(d)}),this.send(s)})}destroy(){if(this.listener&&(this.incoming.removeEventListener("message",this.listener),this.listener=null),this.incoming instanceof MessagePort)try{this.incoming.close()}catch{}this.handlers.clear(),this.pendingAcks.clear()}};function Ne(){return`bus-${Date.now()}-${Math.random().toString(36).slice(2,8)}`}var oe=null;function fe(i){oe=i}var ee="storvia-sdk-toast-style",te="storvia-sdk-toast-stack",ye=`
2
2
  #${te} {
3
3
  position: fixed;
4
4
  top: max(20px, env(safe-area-inset-top, 0px) + 20px);
@@ -219,10 +219,10 @@
219
219
  .storvia-sheet-msg { font-size: 13px; margin-bottom: 22px; }
220
220
  .storvia-sheet-btn { height: 40px; font-size: 13px; }
221
221
  }
222
- `,Ue={success:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>',error:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>',warning:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><path d="M10.29 3.86 1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"/><line x1="12" y1="9" x2="12" y2="13"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',info:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="16" x2="12" y2="12"/><line x1="12" y1="8" x2="12.01" y2="8"/></svg>'},ie={UNAUTHORIZED:"\u767B\u5F55\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55",INSUFFICIENT_CREDITS:"\u82B1\u56ED\u5E01\u4E0D\u8DB3\uFF0C\u8BF7\u5145\u503C\u540E\u518D\u7EE7\u7EED\u6E38\u620F",VIOLATION_WORD_DETECTED:"\u5185\u5BB9\u542B\u6709\u8FDD\u7981\u8BCD\uFF0C\u8BF7\u4FEE\u6539\u540E\u91CD\u8BD5",CONTENT_FILTERED:"\u5185\u5BB9\u88AB\u5B89\u5168\u7B56\u7565\u62E6\u622A\uFF0C\u8BF7\u8C03\u6574\u540E\u91CD\u8BD5",MODEL_REFUSAL:"\u6A21\u578B\u62D2\u7EDD\u54CD\u5E94\uFF0C\u6362\u4E2A\u8BF4\u6CD5\u8BD5\u8BD5",STREAM_INTERRUPTED:"\u56DE\u590D\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",RATE_LIMITED:"\u64CD\u4F5C\u8FC7\u4E8E\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5",MODEL_NOT_FOUND:"\u6240\u9009\u6A21\u578B\u4E0D\u53EF\u7528\uFF0C\u8BF7\u5207\u6362\u5176\u4ED6\u6A21\u578B",GAME_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u6E38\u620F",INVALID_REQUEST:"\u8BF7\u6C42\u65E0\u6548\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",INTERNAL_ERROR:"\u670D\u52A1\u51FA\u4E86\u70B9\u5C0F\u95EE\u9898\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",NOT_INITIALIZED:"SDK \u5C1A\u672A\u521D\u59CB\u5316",NOT_SUPPORTED_IN_PREVIEW:"\u5F53\u524D\u63A5\u53E3\u5728\u9884\u89C8\u6A21\u5F0F\u4E0B\u4E0D\u53EF\u7528",NETWORK_ERROR:"\u7F51\u7EDC\u5F02\u5E38\uFF0C\u8BF7\u68C0\u67E5\u8FDE\u63A5",REQUEST_TIMEOUT:"\u8BF7\u6C42\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",MODEL_LOADING_TIMEOUT:"\u6A21\u578B\u54CD\u5E94\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",STREAM_INACTIVITY:"\u8FDE\u63A5\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",DAISY_CARD_REQUIRED:"\u56DE\u6EAF\u6D88\u606F\u9700\u8981\u6709\u6548\u7684\u96CF\u83CA\u5361\u8BA2\u9605",MESSAGE_NOT_FOUND:"\u6D88\u606F\u4E0D\u5B58\u5728\u6216\u65E0\u6743\u64CD\u4F5C",MESSAGE_TOO_OLD:"\u4EC5\u53EF\u56DE\u6EAF 30 \u5929\u5185\u7684\u6D88\u606F",NO_MESSAGES_TO_DELETE:"\u8BE5\u6D88\u606F\u4E4B\u540E\u6CA1\u6709\u53EF\u56DE\u6EAF\u7684\u6D88\u606F",GENERATION_TIMEOUT:"\u751F\u6210\u8D85\u65F6\uFF0C\u8BF7\u91CD\u8BD5",REPETITION_LOOP:"\u56DE\u590D\u51FA\u73B0\u91CD\u590D\uFF0C\u8BF7\u91CD\u8BD5\u6216\u6362\u4E2A\u8BF4\u6CD5",SAVE_FAILED:"\u6D88\u606F\u4FDD\u5B58\u5931\u8D25\uFF0C\u672C\u6B21\u4E0D\u6263\u8D39\uFF0C\u8BF7\u91CD\u8BD5",FINALIZE_FAILED:"\u56DE\u590D\u5904\u7406\u5931\u8D25\uFF0C\u8BF7\u91CD\u8BD5",CONVERSATION_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u4F1A\u8BDD",EMPTY_MESSAGE:"\u6D88\u606F\u5185\u5BB9\u4E0D\u80FD\u4E3A\u7A7A",CONTINUE_MODEL_NOT_AVAILABLE:"\u7EED\u5199\u6A21\u578B\u5F53\u524D\u4E0D\u53EF\u7528",CONTINUE_PROMPT_MISSING:"\u7EED\u5199\u914D\u7F6E\u7F3A\u5931"},ye=!0;function Ie(i){ye=i}function $e(){if(typeof document>"u")return null;let i=document.getElementById(te);if(!i){if(!document.getElementById(ee)){let e=document.createElement("style");e.id=ee,e.textContent=we,document.head.appendChild(e)}i=document.createElement("div"),i.id=te,document.body.appendChild(i)}return i}function se(i,e="info",t=3500,n){if(!ye)return;let r=$e();if(!r)return;let o=t<=0,s=document.createElement("div");s.className=`storvia-toast ${e}`,s.innerHTML=`
222
+ `,Ue={success:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><polyline points="20 6 9 17 4 12"/></svg>',error:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>',warning:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><path d="M10.29 3.86 1.82 18a2 2 0 0 0 1.71 3h16.94a2 2 0 0 0 1.71-3L13.71 3.86a2 2 0 0 0-3.42 0z"/><line x1="12" y1="9" x2="12" y2="13"/><line x1="12" y1="17" x2="12.01" y2="17"/></svg>',info:'<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="16" x2="12" y2="12"/><line x1="12" y1="8" x2="12.01" y2="8"/></svg>'},ie={UNAUTHORIZED:"\u767B\u5F55\u5DF2\u5931\u6548\uFF0C\u8BF7\u91CD\u65B0\u767B\u5F55",INSUFFICIENT_CREDITS:"\u82B1\u56ED\u5E01\u4E0D\u8DB3\uFF0C\u8BF7\u5145\u503C\u540E\u518D\u7EE7\u7EED\u6E38\u620F",VIOLATION_WORD_DETECTED:"\u5185\u5BB9\u542B\u6709\u8FDD\u7981\u8BCD\uFF0C\u8BF7\u4FEE\u6539\u540E\u91CD\u8BD5",CONTENT_FILTERED:"\u5185\u5BB9\u88AB\u5B89\u5168\u7B56\u7565\u62E6\u622A\uFF0C\u8BF7\u8C03\u6574\u540E\u91CD\u8BD5",MODEL_REFUSAL:"\u6A21\u578B\u62D2\u7EDD\u54CD\u5E94\uFF0C\u6362\u4E2A\u8BF4\u6CD5\u8BD5\u8BD5",STREAM_INTERRUPTED:"\u56DE\u590D\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",RATE_LIMITED:"\u64CD\u4F5C\u8FC7\u4E8E\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5",MODEL_NOT_FOUND:"\u6240\u9009\u6A21\u578B\u4E0D\u53EF\u7528\uFF0C\u8BF7\u5207\u6362\u5176\u4ED6\u6A21\u578B",GAME_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u6E38\u620F",INVALID_REQUEST:"\u8BF7\u6C42\u65E0\u6548\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",INTERNAL_ERROR:"\u670D\u52A1\u51FA\u4E86\u70B9\u5C0F\u95EE\u9898\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",NOT_INITIALIZED:"SDK \u5C1A\u672A\u521D\u59CB\u5316",NOT_SUPPORTED_IN_PREVIEW:"\u5F53\u524D\u63A5\u53E3\u5728\u9884\u89C8\u6A21\u5F0F\u4E0B\u4E0D\u53EF\u7528",NETWORK_ERROR:"\u7F51\u7EDC\u5F02\u5E38\uFF0C\u8BF7\u68C0\u67E5\u8FDE\u63A5",REQUEST_TIMEOUT:"\u8BF7\u6C42\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",MODEL_LOADING_TIMEOUT:"\u6A21\u578B\u54CD\u5E94\u8D85\u65F6\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5",STREAM_INACTIVITY:"\u8FDE\u63A5\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u91CD\u8BD5",DAISY_CARD_REQUIRED:"\u56DE\u6EAF\u6D88\u606F\u9700\u8981\u6709\u6548\u7684\u96CF\u83CA\u5361\u8BA2\u9605",MESSAGE_NOT_FOUND:"\u6D88\u606F\u4E0D\u5B58\u5728\u6216\u65E0\u6743\u64CD\u4F5C",MESSAGE_TOO_OLD:"\u4EC5\u53EF\u56DE\u6EAF 30 \u5929\u5185\u7684\u6D88\u606F",NO_MESSAGES_TO_DELETE:"\u8BE5\u6D88\u606F\u4E4B\u540E\u6CA1\u6709\u53EF\u56DE\u6EAF\u7684\u6D88\u606F",GENERATION_TIMEOUT:"\u751F\u6210\u8D85\u65F6\uFF0C\u8BF7\u91CD\u8BD5",REPETITION_LOOP:"\u56DE\u590D\u51FA\u73B0\u91CD\u590D\uFF0C\u8BF7\u91CD\u8BD5\u6216\u6362\u4E2A\u8BF4\u6CD5",SAVE_FAILED:"\u6D88\u606F\u4FDD\u5B58\u5931\u8D25\uFF0C\u672C\u6B21\u4E0D\u6263\u8D39\uFF0C\u8BF7\u91CD\u8BD5",FINALIZE_FAILED:"\u56DE\u590D\u5904\u7406\u5931\u8D25\uFF0C\u8BF7\u91CD\u8BD5",CONVERSATION_NOT_FOUND:"\u672A\u627E\u5230\u5BF9\u5E94\u4F1A\u8BDD",EMPTY_MESSAGE:"\u6D88\u606F\u5185\u5BB9\u4E0D\u80FD\u4E3A\u7A7A",CONTINUE_MODEL_NOT_AVAILABLE:"\u7EED\u5199\u6A21\u578B\u5F53\u524D\u4E0D\u53EF\u7528",CONTINUE_PROMPT_MISSING:"\u7EED\u5199\u914D\u7F6E\u7F3A\u5931"},we=!0;function Ie(i){we=i}function $e(){if(typeof document>"u")return null;let i=document.getElementById(te);if(!i){if(!document.getElementById(ee)){let e=document.createElement("style");e.id=ee,e.textContent=ye,document.head.appendChild(e)}i=document.createElement("div"),i.id=te,document.body.appendChild(i)}return i}function se(i,e="info",t=3500,n){if(!we)return;let r=$e();if(!r)return;let o=t<=0,s=document.createElement("div");s.className=`storvia-toast ${e}`,s.innerHTML=`
223
223
  <span class="storvia-toast-icon">${Ue[e]}</span>
224
224
  <span class="storvia-toast-msg"></span>
225
- `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=i);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(h){console.error("[Storvia toast] action error:",h)}d()}),s.appendChild(a)}if(o){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),o||setTimeout(d,t)}function b(i,e){if(i==="INSUFFICIENT_CREDITS"){ve({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||ie.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(i==="DAISY_CARD_REQUIRED"){ve({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||ie.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=ie[i]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";se(t,i==="RATE_LIMITED"?"warning":"error")}var X=null;function ve(i){if(typeof document>"u"||X)return;if(!document.getElementById(ee)){let s=document.createElement("style");s.id=ee,s.textContent=we,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
225
+ `;let c=s.querySelector(".storvia-toast-msg");c&&(c.textContent=i);let d=()=>{s.isConnected&&(s.classList.add("leaving"),s.classList.remove("show"),setTimeout(()=>s.remove(),320))};if(n){let a=document.createElement("button");a.type="button",a.className="storvia-toast-action",a.textContent=n.label,a.addEventListener("click",()=>{try{n.onClick()}catch(l){console.error("[Storvia toast] action error:",l)}d()}),s.appendChild(a)}if(o){let a=document.createElement("button");a.type="button",a.className="storvia-toast-close",a.setAttribute("aria-label","\u5173\u95ED"),a.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2.5" stroke-linecap="round" stroke-linejoin="round"><line x1="18" y1="6" x2="6" y2="18"/><line x1="6" y1="6" x2="18" y2="18"/></svg>',a.addEventListener("click",d),s.appendChild(a)}r.appendChild(s),requestAnimationFrame(()=>s.classList.add("show")),o||setTimeout(d,t)}function k(i,e){if(i==="INSUFFICIENT_CREDITS"){ve({title:"\u82B1\u56ED\u5E01\u4E0D\u8DB3",msg:e||ie.INSUFFICIENT_CREDITS,primaryLabel:"\u53BB\u5145\u503C"});return}if(i==="DAISY_CARD_REQUIRED"){ve({title:"\u9700\u8981\u96CF\u83CA\u5361",msg:e||ie.DAISY_CARD_REQUIRED,primaryLabel:"\u53BB\u5F00\u901A"});return}let t=ie[i]||e||"\u64CD\u4F5C\u5931\u8D25\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5";se(t,i==="RATE_LIMITED"?"warning":"error")}var X=null;function ve(i){if(typeof document>"u"||X)return;if(!document.getElementById(ee)){let s=document.createElement("style");s.id=ee,s.textContent=ye,document.head.appendChild(s)}let e=document.createElement("div");e.className="storvia-sheet-backdrop",e.innerHTML=`
226
226
  <div class="storvia-sheet" role="dialog" aria-modal="true" aria-labelledby="storvia-sheet-title">
227
227
  <div class="storvia-sheet-icon">
228
228
  <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><circle cx="12" cy="12" r="10"/><line x1="12" y1="8" x2="12" y2="12"/><line x1="12" y1="16" x2="12.01" y2="16"/></svg>
@@ -234,7 +234,7 @@
234
234
  <button type="button" class="storvia-sheet-btn storvia-sheet-btn-primary" data-role="navigate"></button>
235
235
  </div>
236
236
  </div>
237
- `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=i.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=i.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=i.primaryLabel);let o=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),X===e&&(X=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",o),e.addEventListener("click",s=>{s.target===e&&o()}),r?.addEventListener("click",()=>{if(oe)try{oe(C("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");o()}),document.body.appendChild(e),X=e,requestAnimationFrame(()=>e.classList.add("show"))}var y=class y{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof p||b("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new p("REQUEST_TIMEOUT","Request timed out");return b("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),y.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:o,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:h}=e,l="%c[Storvia SDK]",m="color: #6366f1; font-weight: bold",v=a!==void 0?` (${a}ms)`:"",u=o!==void 0?` [${o}]`:"",P=h?` [model: ${h}]`:"";d?(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2717`,m,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${l} %c${t} ${n}${u}${P}${v} %c\u2713`,m,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,h])=>n.searchParams.set(a,h));let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),o=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,parsedData:l,durationMs:Date.now()-r}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,error:h,durationMs:Date.now()-r}),h===a&&this.maybeShowNetworkToast(a),h}}async post(e,t,n){let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),o=a.status;let{raw:h,data:l}=await this.handleResponseWithRaw(a);return s=h,this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,parsedData:l,durationMs:Date.now()-r,modelName:n?.modelName}),l}catch(a){d();let h=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,error:h,durationMs:Date.now()-r,modelName:n?.modelName}),h===a&&this.maybeShowNetworkToast(a),h}}async patch(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:h}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,parsedData:h,durationMs:Date.now()-n}),h}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:o,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:o.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,o,s,c,d,a,h){let l=Date.now(),m=o?.modelName?` [model: ${o.modelName}]`:"",v=[],u=f=>{this.debug&&v.push({t:Date.now()-l,event:f})},P=new AbortController,R=null,I=null,k=null,T=null,x=()=>{R!==null&&(clearTimeout(R),R=null),I!==null&&(clearTimeout(I),I=null),k!==null&&(clearTimeout(k),k=null)},Q=f=>{T=f,x(),P.abort()};R=setTimeout(()=>Q("REQUEST_TIMEOUT"),y.REQUEST_TIMEOUT);let E;try{E=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:P.signal})}catch(f){if(x(),T){let w=new p(T,"Request timed out");throw b(T),this.log({method:"STREAM",path:e,body:t,error:w,durationMs:Date.now()-l,modelName:o?.modelName}),w}throw this.maybeShowNetworkToast(f),f}if(R!==null&&(clearTimeout(R),R=null),!E.ok){x();let f=await E.text().catch(()=>""),w={};try{w=JSON.parse(f)}catch{}let S=w.code||"INTERNAL_ERROR",g=new p(S,w.message||`HTTP ${E.status}`);throw b(S,w.message),this.log({method:"STREAM",path:e,body:t,status:E.status,rawResponse:f,error:g,durationMs:Date.now()-l,modelName:o?.modelName}),g}let he=E.body?.getReader();if(!he)throw x(),new p("INTERNAL_ERROR","No response body for stream");I=setTimeout(()=>Q("MODEL_LOADING_TIMEOUT"),y.MODEL_LOADING_TIMEOUT);let ue=new TextDecoder,H="",_="",pe=!1,ne,Z,A="",J=!1,me=f=>{if(J)return;let w=f.endsWith("\r")?f.slice(0,-1):f;if(w.startsWith("id: ")){Z=w.slice(4);return}if(!w.startsWith("data: "))return;let S=w.slice(6);if(S==="[DONE]"){u("[DONE]"),J=!0;return}try{let g=JSON.parse(S);u(g),g.type==="done"&&g.id?H=g.id:g.type==="state"?(s&&s(g.delta,g.full??null),d&&Array.isArray(g.createdNames)&&g.createdNames.length&&d(g.createdNames)):g.type==="thinking"?c&&(g.status==="start"||g.status==="end")&&c(g.status):g.content&&(pe?(k!==null&&clearTimeout(k),k=setTimeout(()=>Q("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)):(pe=!0,I!==null&&(clearTimeout(I),I=null),k=setTimeout(()=>Q("STREAM_INACTIVITY"),y.STREAM_INACTIVITY_TIMEOUT)),_+=g.content,n(g.content))}catch{u({raw:S})}Z!==void 0&&(ne=Z,Z=void 0)},ge=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",H),console.log(`SSE events (${v.length}):`,v),console.groupEnd()),r(H)};try{for(;;){let{done:f,value:w}=await he.read();if(f)break;A+=ue.decode(w,{stream:!0});let S=A.split(`
238
- `);A=S.pop()??"";for(let g of S)me(g);if(J){ge();return}}if(A+=ue.decode(),A&&me(A),J){ge();return}}catch(f){if(x(),T){let w=new p(T,T==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw b(T),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2717 ${T}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Timeout:",w),console.groupEnd()),w}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${E.status}]${m} (${Date.now()-l}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${v.length}):`,v),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0});return}throw f}if(x(),H){r(H);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:h},{finalize:!0})}async resumeLoop(e,t,n,r){let o=t;for(let c=1;c<=y.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(y.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(l=>setTimeout(l,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:o},h;try{h=await this.pumpGetStream(e.conversationId,e.topic,o,a,n)}catch{continue}if(o=a.lastId??o,h==="done"){n.onDone(a.messageId);return}if(h==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new p("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw b("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},o;try{o=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(o==="done"){n.onDone(r.messageId);return}if(o==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,o){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),y.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new p("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let l=a.body?.getReader();return l?await this.pumpReader(l,r,o):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,o,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},y.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,h=l=>{if(a)return;let m=l.endsWith("\r")?l.slice(0,-1):l;if(m.startsWith("id: ")){o=m.slice(4);return}if(!m.startsWith("data: "))return;let v=m.slice(6);if(v==="[DONE]"){a=!0;return}try{let u=JSON.parse(v);u.type==="done"&&u.id?t.messageId=u.id:u.type==="state"?(n.onState?.(u.delta,u.full??null),Array.isArray(u.createdNames)&&u.createdNames.length&&n.onCreatedCharacters?.(u.createdNames)):u.type==="thinking"?(u.status==="start"||u.status==="end")&&n.onThinking?.(u.status):u.content&&n.onChunk(u.content)}catch{}o!==void 0&&(t.lastId=o,o=void 0)};try{for(;;){let{done:l,value:m}=await e.read();if(l)break;c(),d+=r.decode(m,{stream:!0});let v=d.split(`
239
- `);d=v.pop()??"";for(let u of v)h(u);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&h(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},o={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||o[e.status]||"INTERNAL_ERROR",c=new p(s,r.message||`HTTP ${e.status}`);throw b(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};y.REQUEST_TIMEOUT=6e4,y.MODEL_LOADING_TIMEOUT=18e4,y.STREAM_INACTIVITY_TIMEOUT=6e4,y.RECONNECT_MAX_ATTEMPTS=10,y.RECONNECT_BACKOFF_CAP=15e3;var K=y;var D=class{constructor(e,t,n,r,o=!1,s,c){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=o;this.previewConfig=s,this.getModelName=c}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:q(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[]};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",o=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,h)=>{o=a,s=h,e.onState&&e.onState(o,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return o&&(d.delta=o,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function q(i){if(i)return(e,t)=>i(e,t)}var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},N=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(Ce)),this.state=new ae(e,t,n,o)}setInitial(e,t){this.mem=e?e.map(Ce):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(Re):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?Re(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function Ce(i){return{name:i.name,description:i.description,avatar:i.avatar,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.gender?{gender:i.gender}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}function Re(i){return{name:i.name,avatar:i.avatar,description:i.description,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.gender?{gender:i.gender}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(o=>({...o})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(o=>o.from===e&&o.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Te(i){let e={count:i.count};return i.desc!==void 0&&(e.desc=i.desc),i.icon_url!==void 0&&(e.iconUrl=i.icon_url),e}function de(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i)){let r={};for(let[o,s]of Object.entries(n))r[o]=Te(s);e[t]=r}return e}function Le(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i))e[t]=Te(n);return e}var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=de(r))}setInitial(e){this.mem=e?de(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,o]of Object.entries(this.mem))n[r]={...o};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return Le(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return de(t)}async add(e){let{group:t,name:n,count:r=1,desc:o,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};o!==void 0&&(d.desc=o),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:o,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),o!==void 0&&(a.desc=o),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:o}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=o||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:o})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let o=this.mem[e];if(o&&Object.keys(o).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var L=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ce=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},F=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ce(e,t,n,o)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function G(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,o,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};o&&(this.mem=Ee(o)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Ee(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,o]of Object.entries(e))typeof o=="object"&&o!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...o}:this.mem[r]=o,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Ee(i){let e={};for(let[t,n]of Object.entries(i))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Se(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var j=class{constructor(e,t,n,r=!1,o){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};o&&(this.mem={...o})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Se(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Se(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var z=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new p("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var B=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var be="/functions/v1/world-engine/v1",Fe="https://api.storvia.ai";function Ge(){return window.__STORVIA__||{}}function Ve(i,e=3e4){let t=Ge();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let o=setTimeout(()=>{s(),c(),r(new p("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=i.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,debug:a.payload.debug})}),c=i.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(o),s(),c();let h=window;h.__STORVIA__=a,n(a)}i.send(C("ready",{}))})}var Y=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new O({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?l=>l.source===null||l.source===window:l=>l.source===window.parent,customSend:t?l=>e.callHandler("storviaBus",l):void 0}),fe(l=>this.bus.send(l));let n=await Ve(this.bus),r=n.apiBase;if(!r)throw new p("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${be}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new p("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new p("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new K(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[l,m]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=l,this.modelId=(n.selectedModelId&&l.some(I=>I.id===n.selectedModelId)?n.selectedModelId:"")||l[0]?.id||"";let v=()=>this.gameId,u=()=>this.conversationId,P=()=>this.modelId,R=()=>this.models.find(I=>I.id===this.modelId)?.name;this.chat=new D(this.http,v,u,P,!0,this.previewConfig,R),this.characters=new N(this.http,u,!0,m?.characters,m?.characterStates),this.relationships=new U(this.http,u,!0,m?.relationships),this.inventory=new $(this.http,u,!0,m?.inventory),this.world=new L(this.http,u,!0,m?.world),this.player=new F(this.http,u,!0,m?.player,m?.playerState),this.custom=new V(this.http,u,v,!0,m?.custom,m?.custom_inject),this.save=new j(this.http,u,v,!0,m?.save_data),this.state=new z(this.http,u,!0),this.memory=new B(this.http,u,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[o,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=o.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(l=>l.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"";let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,h=()=>this.models.find(l=>l.id===this.modelId)?.name;this.chat=new D(this.http,c,d,a,!1,void 0,h),this.characters=new N(this.http,d),this.relationships=new U(this.http,d),this.inventory=new $(this.http,d),this.world=new L(this.http,d),this.player=new F(this.http,d),this.custom=new V(this.http,d,c),this.save=new j(this.http,d,c),this.state=new z(this.http,d),this.memory=new B(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new p("UNAUTHORIZED","User not authenticated"):t.status===404?new p("GAME_NOT_FOUND","Game not found or not published"):new p("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${Fe}${be}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new K(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let o=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new D(this.http,o,s,c,!0,void 0,d),this.characters=new N(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new U(this.http,s,!0,n?.relationships),this.inventory=new $(this.http,s,!0,n?.inventory),this.world=new L(this.http,s,!0,n?.world),this.player=new F(this.http,s,!0,n?.player,n?.playerState),this.custom=new V(this.http,s,o,!0,n?.custom),this.save=new j(this.http,s,o,!0,n?.save_data),this.memory=new B(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(o=>({id:o.id,name:o.name,url:o.url,assetType:o.asset_type,category:o.category}))}};async function Pe(i){let e=new Y;return i?.dev?await e.initDev(i.dev):await e.init(),e}function le(i){return typeof i=="object"&&i!==null&&"value"in i&&"type"in i&&(i.type==="number"||i.type==="text")}function ke(i){return le(i)?i.value:i}return De(je);})();
237
+ `;let t=e.querySelector(".storvia-sheet-title");t&&(t.textContent=i.title);let n=e.querySelector(".storvia-sheet-msg");n&&(n.textContent=i.msg);let r=e.querySelector('[data-role="navigate"]');r&&(r.textContent=i.primaryLabel);let o=()=>{e.isConnected&&(e.classList.add("leaving"),e.classList.remove("show"),setTimeout(()=>{e.remove(),X===e&&(X=null)},240))};e.querySelector('[data-role="cancel"]')?.addEventListener("click",o),e.addEventListener("click",s=>{s.target===e&&o()}),r?.addEventListener("click",()=>{if(oe)try{oe(R("navigate",{target:"wallet"})),console.log("[Storvia] navigate \u2192 wallet\uFF1A\u5DF2\u901A\u8FC7 bus \u901A\u77E5\u5BBF\u4E3B\u8DF3\u8F6C\u94B1\u5305\u9875")}catch(s){console.error("[Storvia] navigate \u2192 wallet \u901A\u8FC7 bus \u53D1\u9001\u5931\u8D25:",s)}else console.warn("[Storvia] navigate \u2192 wallet\uFF1A\u5F53\u524D\u672A\u68C0\u6D4B\u5230\u5BBF\u4E3B\uFF08dev \u6A21\u5F0F\uFF09\uFF0C\u6309\u94AE\u5DF2\u70B9\u4F46\u65E0\u4EBA\u63A5\u6536\u3002\u751F\u4EA7\u73AF\u5883\u4F1A\u81EA\u52A8\u8DF3\u5230\u4E3B\u7AD9 /wallet \u6216 App \u94B1\u5305\u9875\u3002");o()}),document.body.appendChild(e),X=e,requestAnimationFrame(()=>e.classList.add("show"))}var I=class I{constructor(e,t,n=!1,r=""){this.baseUrl=e,this.token=t,this.debug=n,this.devApiKey=r}setToken(e){this.token=e}setDebug(e){this.debug=e}maybeShowNetworkToast(e){e instanceof u||k("NETWORK_ERROR")}wrapAbortError(e){if(e instanceof DOMException&&e.name==="AbortError"){let t=new u("REQUEST_TIMEOUT","Request timed out");return k("REQUEST_TIMEOUT"),t}return e}createTimeoutController(){let e=new AbortController,t=setTimeout(()=>e.abort(),I.REQUEST_TIMEOUT);return{controller:e,clear:()=>clearTimeout(t)}}buildHeaders(){let e={"Content-Type":"application/json"};return this.token&&(e.Authorization=`Bearer ${this.token}`),this.devApiKey&&(e["x-api-key"]=this.devApiKey),e}log(e){if(!this.debug)return;let{method:t,path:n,body:r,status:o,rawResponse:s,parsedData:c,error:d,durationMs:a,modelName:l}=e,p="%c[Storvia SDK]",h="color: #6366f1; font-weight: bold",g=a!==void 0?` (${a}ms)`:"",m=o!==void 0?` [${o}]`:"",w=l?` [model: ${l}]`:"";d?(console.groupCollapsed(`${p} %c${t} ${n}${m}${w}${g} %c\u2717`,h,"color: #e0e0e0","color: #ef4444"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),console.error("Error:",d),console.groupEnd()):(console.groupCollapsed(`${p} %c${t} ${n}${m}${w}${g} %c\u2713`,h,"color: #e0e0e0","color: #22c55e"),r!==void 0&&console.log("Request:",r),s!==void 0&&console.log("Response (raw):",s),c!==void 0&&c!==s&&console.log("Response (data):",c),console.groupEnd())}async get(e,t){let n=new URL(`${this.baseUrl}${e}`);t&&Object.entries(t).forEach(([a,l])=>n.searchParams.set(a,l));let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(n.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal});d(),o=a.status;let{raw:l,data:p}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,parsedData:p,durationMs:Date.now()-r}),p}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"GET",path:e,body:t,status:o,rawResponse:s,error:l,durationMs:Date.now()-r}),l===a&&this.maybeShowNetworkToast(a),l}}async post(e,t,n){let r=Date.now(),o,s,{controller:c,clear:d}=this.createTimeoutController();try{let a=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:c.signal});d(),o=a.status;let{raw:l,data:p}=await this.handleResponseWithRaw(a);return s=l,this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,parsedData:p,durationMs:Date.now()-r,modelName:n?.modelName}),p}catch(a){d();let l=this.wrapAbortError(a);throw this.log({method:"POST",path:e,body:t,status:o,rawResponse:s,error:l,durationMs:Date.now()-r,modelName:n?.modelName}),l===a&&this.maybeShowNetworkToast(a),l}}async patch(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PATCH",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PATCH",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async put(e,t){let n=Date.now(),r,o,{controller:s,clear:c}=this.createTimeoutController();try{let d=await fetch(`${this.baseUrl}${e}`,{method:"PUT",headers:this.buildHeaders(),body:t?JSON.stringify(t):void 0,signal:s.signal});c(),r=d.status;let{raw:a,data:l}=await this.handleResponseWithRaw(d);return o=a,this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,parsedData:l,durationMs:Date.now()-n}),l}catch(d){c();let a=this.wrapAbortError(d);throw this.log({method:"PUT",path:e,body:t,status:r,rawResponse:o,error:a,durationMs:Date.now()-n}),a===d&&this.maybeShowNetworkToast(d),a}}async delete(e){let t=Date.now(),n,r,{controller:o,clear:s}=this.createTimeoutController();try{let c=await fetch(`${this.baseUrl}${e}`,{method:"DELETE",headers:this.buildHeaders(),signal:o.signal});s(),n=c.status;let{raw:d,data:a}=await this.handleResponseWithRaw(c);return r=d,this.log({method:"DELETE",path:e,status:n,rawResponse:r,parsedData:a,durationMs:Date.now()-t}),a}catch(c){s();let d=this.wrapAbortError(c);throw this.log({method:"DELETE",path:e,status:n,rawResponse:r,error:d,durationMs:Date.now()-t}),d===c&&this.maybeShowNetworkToast(c),d}}async stream(e,t,n,r,o,s,c,d,a,l){let p=Date.now(),h=o?.modelName?` [model: ${o.modelName}]`:"",g=[],m=f=>{this.debug&&g.push({t:Date.now()-p,event:f})},w=new AbortController,T=null,S=null,E=null,C=null,x=()=>{T!==null&&(clearTimeout(T),T=null),S!==null&&(clearTimeout(S),S=null),E!==null&&(clearTimeout(E),E=null)},Q=f=>{C=f,x(),w.abort()};T=setTimeout(()=>Q("REQUEST_TIMEOUT"),I.REQUEST_TIMEOUT);let b;try{b=await fetch(`${this.baseUrl}${e}`,{method:"POST",headers:this.buildHeaders(),body:JSON.stringify(t),signal:w.signal})}catch(f){if(x(),C){let y=new u(C,"Request timed out");throw k(C),this.log({method:"STREAM",path:e,body:t,error:y,durationMs:Date.now()-p,modelName:o?.modelName}),y}throw this.maybeShowNetworkToast(f),f}if(T!==null&&(clearTimeout(T),T=null),!b.ok){x();let f=await b.text().catch(()=>""),y={};try{y=JSON.parse(f)}catch{}let P=y.code||"INTERNAL_ERROR",v=new u(P,y.message||`HTTP ${b.status}`);throw k(P,y.message),this.log({method:"STREAM",path:e,body:t,status:b.status,rawResponse:f,error:v,durationMs:Date.now()-p,modelName:o?.modelName}),v}let he=b.body?.getReader();if(!he)throw x(),new u("INTERNAL_ERROR","No response body for stream");S=setTimeout(()=>Q("MODEL_LOADING_TIMEOUT"),I.MODEL_LOADING_TIMEOUT);let ue=new TextDecoder,H="",_="",pe=!1,ne,Z,M="",J=!1,me=f=>{if(J)return;let y=f.endsWith("\r")?f.slice(0,-1):f;if(y.startsWith("id: ")){Z=y.slice(4);return}if(!y.startsWith("data: "))return;let P=y.slice(6);if(P==="[DONE]"){m("[DONE]"),J=!0;return}try{let v=JSON.parse(P);m(v),v.type==="done"&&v.id?H=v.id:v.type==="state"?(s&&s(v.delta,v.full??null),d&&Array.isArray(v.createdNames)&&v.createdNames.length&&d(v.createdNames)):v.type==="thinking"?c&&(v.status==="start"||v.status==="end")&&c(v.status):v.content&&(pe?(E!==null&&clearTimeout(E),E=setTimeout(()=>Q("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)):(pe=!0,S!==null&&(clearTimeout(S),S=null),E=setTimeout(()=>Q("STREAM_INACTIVITY"),I.STREAM_INACTIVITY_TIMEOUT)),_+=v.content,n(v.content))}catch{m({raw:P})}Z!==void 0&&(ne=Z,Z=void 0)},ge=()=>{x(),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2713`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #22c55e"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log("Message ID:",H),console.log(`SSE events (${g.length}):`,g),console.groupEnd()),r(H)};try{for(;;){let{done:f,value:y}=await he.read();if(f)break;M+=ue.decode(y,{stream:!0});let P=M.split(`
238
+ `);M=P.pop()??"";for(let v of P)me(v);if(J){ge();return}}if(M+=ue.decode(),M&&me(M),J){ge();return}}catch(f){if(x(),C){let y=new u(C,C==="MODEL_LOADING_TIMEOUT"?"Model loading timed out":"Stream inactivity timed out");throw k(C),this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2717 ${C}`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Timeout:",y),console.groupEnd()),y}if(this.debug&&(console.groupCollapsed(`%c[Storvia SDK] %cSTREAM ${e} [${b.status}]${h} (${Date.now()-p}ms) %c\u2717`,"color: #6366f1; font-weight: bold","color: #e0e0e0","color: #ef4444"),console.log("Request:",t),console.log(`Accumulated content (${_.length} chars):`,_),console.log(`SSE events (${g.length}):`,g),console.error("Stream error:",f),console.groupEnd()),a){await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0});return}throw f}if(x(),H){r(H);return}a&&await this.resumeLoop(a,ne,{onChunk:n,onDone:r,onState:s,onThinking:c,onCreatedCharacters:d,onReconnect:l},{finalize:!0})}async resumeLoop(e,t,n,r){let o=t;for(let c=1;c<=I.RECONNECT_MAX_ATTEMPTS;c++){let d=Math.min(I.RECONNECT_BACKOFF_CAP,1e3*2**(c-1));await new Promise(p=>setTimeout(p,d)),n.onReconnect?.({attempt:c});let a={messageId:"",lastId:o},l;try{l=await this.pumpGetStream(e.conversationId,e.topic,o,a,n)}catch{continue}if(o=a.lastId??o,l==="done"){n.onDone(a.messageId);return}if(l==="inactive"){(a.messageId||r?.finalize)&&n.onDone(a.messageId);return}}let s=new u("STREAM_INTERRUPTED","Stream reconnection failed after maximum attempts");throw k("STREAM_INTERRUPTED"),s}async resumeStream(e,t,n){let r={messageId:""},o;try{o=await this.pumpGetStream(e,t,void 0,r,n)}catch{await this.resumeLoop({conversationId:e,topic:t},r.lastId,n);return}if(o==="done"){n.onDone(r.messageId);return}if(o==="inactive"){r.messageId&&n.onDone(r.messageId);return}await this.resumeLoop({conversationId:e,topic:t},r.lastId,n)}async pumpGetStream(e,t,n,r,o){let s=new URL(`${this.baseUrl}/conversations/${encodeURIComponent(e)}/stream`);n&&s.searchParams.set("from",n),t&&s.searchParams.set("topic",t);let c=new AbortController,d=setTimeout(()=>c.abort(),I.REQUEST_TIMEOUT),a;try{a=await fetch(s.toString(),{method:"GET",headers:this.buildHeaders(),signal:c.signal})}finally{clearTimeout(d)}if(!a.ok)throw new u("STREAM_INTERRUPTED",`Resume HTTP ${a.status}`);if(!(a.headers.get("content-type")||"").includes("text/event-stream"))return"inactive";let p=a.body?.getReader();return p?await this.pumpReader(p,r,o):"inactive"}async pumpReader(e,t,n){let r=new TextDecoder,o,s=null,c=()=>{s&&clearTimeout(s),s=setTimeout(()=>{e.cancel().catch(()=>{})},I.STREAM_INACTIVITY_TIMEOUT)};c();let d="",a=!1,l=p=>{if(a)return;let h=p.endsWith("\r")?p.slice(0,-1):p;if(h.startsWith("id: ")){o=h.slice(4);return}if(!h.startsWith("data: "))return;let g=h.slice(6);if(g==="[DONE]"){a=!0;return}try{let m=JSON.parse(g);m.type==="done"&&m.id?t.messageId=m.id:m.type==="state"?(n.onState?.(m.delta,m.full??null),Array.isArray(m.createdNames)&&m.createdNames.length&&n.onCreatedCharacters?.(m.createdNames)):m.type==="thinking"?(m.status==="start"||m.status==="end")&&n.onThinking?.(m.status):m.content&&n.onChunk(m.content)}catch{}o!==void 0&&(t.lastId=o,o=void 0)};try{for(;;){let{done:p,value:h}=await e.read();if(p)break;c(),d+=r.decode(h,{stream:!0});let g=d.split(`
239
+ `);d=g.pop()??"";for(let m of g)l(m);if(a)return s&&clearTimeout(s),"done"}if(d+=r.decode(),d&&l(d),a)return s&&clearTimeout(s),"done"}catch{}finally{s&&clearTimeout(s)}return"eof"}async handleResponseWithRaw(e){let t=await e.text(),n;try{n=t?JSON.parse(t):null}catch{n=t}if(!e.ok){let r=n&&typeof n=="object"?n:{},o={401:"UNAUTHORIZED",402:"INSUFFICIENT_CREDITS",429:"RATE_LIMITED"},s=r.code||o[e.status]||"INTERNAL_ERROR",c=new u(s,r.message||`HTTP ${e.status}`);throw k(s,r.message),c}return n&&typeof n=="object"&&"data"in n?{raw:n,data:n.data}:{raw:n,data:n}}};I.REQUEST_TIMEOUT=6e4,I.MODEL_LOADING_TIMEOUT=18e4,I.STREAM_INACTIVITY_TIMEOUT=6e4,I.RECONNECT_MAX_ATTEMPTS=10,I.RECONNECT_BACKOFF_CAP=15e3;var K=I;var D=class{constructor(e,t,n,r,o=!1,s,c,d){this.http=e;this.getGameId=t;this.getConversationId=n;this.getModelId=r;this.isPreview=o;this.previewConfig=s,this.getModelName=c,this.getStoryMode=d}reqMeta(){let e=this.getModelName?.();return e?{modelName:e}:void 0}updatePreviewConfig(e){this.previewConfig=e}async send(e){if(this.isPreview)return this.sendPreview(e);let t={game_id:this.getGameId(),conversation_id:this.getConversationId(),model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/chat",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/chat",t,this.reqMeta())}async save(e){return this.isPreview?{id:`preview-${Date.now()}`}:this.http.post("/messages/save",{conversation_id:this.getConversationId(),role:e.role,content:e.content,topic:e.topic})}async generate(e){if(this.isPreview)return this.sendPreview({message:"",topic:e.topic,sceneKey:e.sceneKey,stream:e.stream,onChunk:e.onChunk,onDone:e.onDone,onState:e.onState,onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters});let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/generate",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/generate",t,this.reqMeta())}async retry(e={}){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.retry() is not available in preview mode. Publish the game and test on the Storvia platform.");let t={conversation_id:this.getConversationId(),model_id:this.getModelId(),topic:e.topic,scene_key:e.sceneKey,extract:e.extract,stream:e.stream??!1,story_mode:this.getStoryMode?.()};if(e.stream){await this.http.stream("/retry",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters,{conversationId:this.getConversationId(),topic:e.topic},e.onReconnecting);return}return this.http.post("/retry",t,this.reqMeta())}async messages(e){if(this.isPreview)return{data:[],hasMore:!1,nextCursor:null};let t={conversation_id:this.getConversationId(),order:e.order,limit:String(e.limit??20)};e.topic&&(t.topic=e.topic),e.cursor&&(t.cursor_uuid=e.cursor.uuid,t.cursor_created_at=e.cursor.createdAt);let n=await this.http.get("/messages",t);return{data:n.messages.map(r=>({uuid:r.uuid,role:r.role,content:r.content,topic:r.topic,status:r.status,model:r.model,createdAt:r.created_at})),hasMore:n.has_more,nextCursor:n.next_cursor?{uuid:n.next_cursor.cursor_uuid,createdAt:n.next_cursor.cursor_created_at}:null}}async edit(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.edit() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.patch(`/messages/${encodeURIComponent(e.uuid)}`,{content:e.content});return{uuid:t.uuid,role:t.role,content:t.content,updatedAt:t.updated_at}}async delete(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.delete() is not available in preview mode. Publish the game and test on the Storvia platform.");return{uuid:(await this.http.delete(`/messages/${encodeURIComponent(e.uuid)}`)).uuid}}async rollback(e){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.chat.rollback() is not available in preview mode. Publish the game and test on the Storvia platform.");let t=await this.http.post(`/messages/${encodeURIComponent(e.uuid)}/rollback`,{});return{deletedCount:t.deleted_count,deletedUuids:t.deleted_uuids,restoredGameState:t.restored_game_state}}async resume(e={}){this.isPreview||await this.http.resumeStream(this.getConversationId(),e.topic,{onChunk:e.onChunk??(()=>{}),onDone:e.onDone??(()=>{}),onState:q(e.onState),onThinking:e.onThinking,onCreatedCharacters:e.onCreatedCharacters,onReconnect:e.onReconnecting})}async sendPreview(e){let t={model_id:this.getModelId(),message:e.message,topic:e.topic,scene_key:e.sceneKey,history_messages:[],story_mode:this.getStoryMode?.()};this.previewConfig?t.prompt_config=this.previewConfig:t.game_id=this.getGameId();let n=this.previewConfig;if(n?.reply_length&&(t.reply_length=n.reply_length),n?.reply_language&&(t.reply_language=n.reply_language),e.stream){await this.http.stream("/preview",t,e.onChunk??(()=>{}),e.onDone??(()=>{}),this.reqMeta(),q(e.onState),e.onThinking,e.onCreatedCharacters);return}let r="",o=null,s=null,c=[];await this.http.stream("/preview",t,a=>{r+=a},()=>{},this.reqMeta(),(a,l)=>{o=a,s=l,e.onState&&e.onState(o,s)},void 0,a=>{c=a,e.onCreatedCharacters&&e.onCreatedCharacters(a)});let d={id:"",content:r};return o&&(d.delta=o,s&&(d.full=s)),c.length&&(d.createdNames=c),d}};function q(i){if(i)return(e,t)=>i(e,t)}var ae=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e,t){if(this.isPreview){let r=this.mem[e]||{};return t?{...r[t]||{}}:{...r}}let n=t?{group:t}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,n)}async update(e,t,n){if(this.isPreview){let r=this.mem[e]||(this.mem[e]={});r[t]={...r[t]||{},...n};return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{group:t,values:n})}},N=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(Ce)),this.state=new ae(e,t,n,o)}setInitial(e,t){this.mem=e?e.map(Ce):[],this.state.setInitial(t)}async list(){return this.isPreview?this.mem.map(Re):this.http.get(`/conversations/${this.getConversationId()}/characters`)}async get(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return t?Re(t):{name:e}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async add(e){if(this.isPreview){this.mem.push({...e,isPreset:!1});return}await this.http.post(`/conversations/${this.getConversationId()}/characters`,e)}async update(e,t){if(this.isPreview){let n=this.mem.find(r=>r.name===e);n&&Object.assign(n,t);return}await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`,t)}async remove(e){if(this.isPreview){this.mem=this.mem.filter(t=>t.name!==e);return}await this.http.delete(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}`)}async detail(e){if(this.isPreview){let t=this.mem.find(n=>n.name===e);return{name:e,avatar:t?.avatar,description:t?.description,...t?.introduction!==void 0?{introduction:t.introduction}:{},...t?.visibleAtStart!==void 0?{visibleAtStart:t.visibleAtStart}:{},userDescription:t?.userDescription,...t?.gender?{gender:t.gender}:{},...t?.isPreset!==void 0?{isPreset:t.isPreset}:{},state:await this.state.get(e)}}return this.http.get(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/detail`)}async setPriority(e,t){let n=Math.max(0,Math.min(100,Math.round(t)));this.isPreview||await this.http.patch(`/conversations/${this.getConversationId()}/characters/${encodeURIComponent(e)}/state`,{priority:n})}};function Ce(i){return{name:i.name,description:i.description,avatar:i.avatar,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.gender?{gender:i.gender}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}function Re(i){return{name:i.name,avatar:i.avatar,description:i.description,...i.introduction!==void 0?{introduction:i.introduction}:{},...i.visibleAtStart!==void 0?{visibleAtStart:i.visibleAtStart}:{},...i.userDescription!==void 0?{userDescription:i.userDescription}:{},...i.gender?{gender:i.gender}:{},...i.isPreset!==void 0?{isPreset:i.isPreset}:{}}}var U=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=[];r&&(this.mem=r.map(o=>({...o})))}setInitial(e){this.mem=e?e.map(t=>({...t})):[]}async list(){return this.isPreview?[...this.mem]:this.http.get(`/conversations/${this.getConversationId()}/relationships`)}async get(e,t){if(this.isPreview){let n=this.mem.find(r=>r.from===e&&r.to===t);if(n)return{...n};throw new Error("Relationship not found")}return this.http.get(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}async add(e){if(this.isPreview){this.mem.push({...e});return}await this.http.post(`/conversations/${this.getConversationId()}/relationships`,e)}async update(e,t,n){if(this.isPreview){let r=this.mem.find(o=>o.from===e&&o.to===t);r?Object.assign(r,n):this.mem.push({from:e,to:t,...n});return}await this.http.patch(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,n)}async remove(e,t){if(this.isPreview){this.mem=this.mem.filter(n=>!(n.from===e&&n.to===t));return}await this.http.delete(`/conversations/${this.getConversationId()}/relationships/${encodeURIComponent(e)}/${encodeURIComponent(t)}`)}};function Te(i){let e={count:i.count};return i.desc!==void 0&&(e.desc=i.desc),i.icon_url!==void 0&&(e.iconUrl=i.icon_url),e}function de(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i)){let r={};for(let[o,s]of Object.entries(n))r[o]=Te(s);e[t]=r}return e}function Le(i){let e={};if(!i)return e;for(let[t,n]of Object.entries(i))e[t]=Te(n);return e}var $=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem=de(r))}setInitial(e){this.mem=e?de(e):{}}async list(e){if(this.isPreview){if(e!==void 0)return{...this.mem[e]||{}};let n={};for(let[r,o]of Object.entries(this.mem))n[r]={...o};return n}if(e!==void 0){let n=await this.http.get(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(e)}`);return Le(n)}let t=await this.http.get(`/conversations/${this.getConversationId()}/inventory`);return de(t)}async add(e){let{group:t,name:n,count:r=1,desc:o,iconUrl:s}=e;if(this.isPreview){if(!this.mem[t])throw new Error(`Group "${t}" does not exist`);if(n in this.mem[t])throw new Error(`Item "${n}" already exists in group "${t}"`);let d={count:r};o!==void 0&&(d.desc=o),s!==void 0&&(d.iconUrl=s),this.mem[t][n]=d;return}let c={group:t,name:n,count:r};o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.post(`/conversations/${this.getConversationId()}/inventory`,c)}async update(e){let{group:t,name:n,count:r,desc:o,iconUrl:s}=e;if(this.isPreview){let d=this.mem[t];if(!d||!(n in d))throw new Error(`Item "${t}/${n}" not found`);let a=d[n];r!==void 0&&(a.count=r),o!==void 0&&(a.desc=o),s!==void 0&&(a.iconUrl=s);return}let c={};r!==void 0&&(c.count=r),o!==void 0&&(c.desc=o),s!==void 0&&(c.icon_url=s),await this.http.patch(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`,c)}async remove(e){let{group:t,name:n}=e;if(this.isPreview){this.mem[t]&&delete this.mem[t][n];return}await this.http.delete(`/conversations/${this.getConversationId()}/inventory/${encodeURIComponent(t)}/${encodeURIComponent(n)}`)}async move(e){let{fromGroup:t,toGroup:n,name:r,newName:o}=e;if(this.isPreview){let s=this.mem[t];if(!s||!(r in s))throw new Error(`Source item "${t}/${r}" not found`);if(!this.mem[n])throw new Error(`Target group "${n}" does not exist`);let c=o||r;if(t===n&&c===r)return;if(c in this.mem[n])throw new Error(`Item "${c}" already exists in target group`);this.mem[n][c]=s[r],delete s[r];return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/move`,{fromGroup:t,toGroup:n,name:r,newName:o})}async ensureGroup(e){if(this.isPreview){this.mem[e]||(this.mem[e]={});return}await this.http.post(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}`,{})}async removeGroup(e,t){let n=t?.cascade??!1;if(this.isPreview){let o=this.mem[e];if(o&&Object.keys(o).length>0&&!n)throw new Error(`Group "${e}" is not empty, pass cascade: true to force delete`);delete this.mem[e];return}let r=n?"?cascade=true":"";await this.http.delete(`/conversations/${this.getConversationId()}/inventory/groups/${encodeURIComponent(e)}${r}`)}};var L=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:this.http.get(`/conversations/${this.getConversationId()}/world`)}async update(e){if(this.isPreview){Object.assign(this.mem,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/world`,e)}};var ce=class{constructor(e,t,n=!1,r){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem={};r&&(this.mem={...r})}setInitial(e){this.mem=e?{...e}:{}}async get(e){if(this.isPreview)return e?{...this.mem[e]||{}}:{...this.mem};let t=e?{group:e}:void 0;return this.http.get(`/conversations/${this.getConversationId()}/player/state`,t)}async update(e,t){if(this.isPreview){this.mem[e]={...this.mem[e]||{},...t};return}await this.http.patch(`/conversations/${this.getConversationId()}/player/state`,{group:e,values:t})}},F=class{constructor(e,t,n=!1,r,o){this.http=e;this.getConversationId=t;this.isPreview=n;this.memPersona={name:""};r&&(this.memPersona={...r}),this.state=new ce(e,t,n,o)}setInitial(e,t){this.memPersona=e?{...e}:{name:""},this.state.setInitial(t)}async get(){return this.isPreview?{...this.memPersona}:this.http.get(`/conversations/${this.getConversationId()}/player`)}async update(e){if(this.isPreview){Object.assign(this.memPersona,e);return}await this.http.patch(`/conversations/${this.getConversationId()}/player`,e)}};function G(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var V=class{constructor(e,t,n,r=!1,o,s){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};this.memInject={};o&&(this.mem=Se(o)),s&&(this.memInject={...s})}setInitial(e,t){this.mem=e?Se(e):{},this.memInject=t?{...t}:{}}async get(e){if(this.isPreview)return e!==void 0?this.mem[e]:{...this.mem};let t=await this.http.get(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()));return e!==void 0?t[e]:t}async set(e,t){if(this.isPreview){for(let[r,o]of Object.entries(e))typeof o=="object"&&o!==null&&typeof this.mem[r]=="object"&&this.mem[r]!==null?this.mem[r]={...this.mem[r],...o}:this.mem[r]=o,t?.inject!==void 0&&(this.memInject[r]=t.inject);return}let n=t?.inject!==void 0?{data:e,inject:t.inject}:e;await this.http.patch(G(`/conversations/${this.getConversationId()}/custom`,this.getGameId()),n)}async setInject(e,t){if(this.isPreview){this.memInject[e]=t;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/inject/${encodeURIComponent(e)}`,this.getGameId()),{inject:t})}getInject(){return{...this.memInject}}async delete(e){if(this.isPreview){delete this.mem[e],delete this.memInject[e];return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}`,this.getGameId()))}async setGroupField(e,t,n){if(this.isPreview){(!this.mem[e]||typeof this.mem[e]!="object")&&(this.mem[e]={}),this.mem[e][t]=n;return}await this.http.patch(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()),{value:n})}async deleteGroupField(e,t){if(this.isPreview){if(typeof this.mem[e]=="object"&&this.mem[e]!==null){let n=this.mem[e];delete n[t]}return}await this.http.delete(G(`/conversations/${this.getConversationId()}/custom/${encodeURIComponent(e)}/${encodeURIComponent(t)}`,this.getGameId()))}};function Se(i){let e={};for(let[t,n]of Object.entries(i))typeof n=="object"&&n!==null&&!Array.isArray(n)?e[t]={...n}:e[t]=n;return e}function Ee(i,e){if(!e)return i;let t=i.includes("?")?"&":"?";return`${i}${t}game_id=${encodeURIComponent(e)}`}var j=class{constructor(e,t,n,r=!1,o){this.http=e;this.getConversationId=t;this.getGameId=n;this.isPreview=r;this.mem={};o&&(this.mem={...o})}setInitial(e){this.mem=e?{...e}:{}}async get(){return this.isPreview?{...this.mem}:await this.http.get(Ee(`/conversations/${this.getConversationId()}/save`,this.getGameId()))}async set(e){if(this.isPreview){this.mem={...e};return}await this.http.put(Ee(`/conversations/${this.getConversationId()}/save`,this.getGameId()),e)}};var z=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n}async get(){if(this.isPreview)throw new u("NOT_SUPPORTED_IN_PREVIEW","storvia.state.get() is not available in preview mode. Publish the game and test on the Storvia platform. (Use per-module get() like storvia.world.get() if you need to inspect state during preview.)");return this.http.get(`/conversations/${this.getConversationId()}/state`)}};var B=class{constructor(e,t,n=!1){this.http=e;this.getConversationId=t;this.isPreview=n;this.mem=null}async get(){return this.isPreview?this.mem?{...this.mem}:null:(await this.http.get(`/conversations/${this.getConversationId()}/summary`)).ai_summary}async update(e){let t=(e??"").trim();if(this.isPreview){let r={content:t,updated_at:new Date().toISOString()};return this.mem=r,{...r}}return(await this.http.patch(`/conversations/${this.getConversationId()}/summary`,{content:t})).ai_summary}};var be="/functions/v1/world-engine/v1",Fe="https://api.storvia.ai";function Ge(){return window.__STORVIA__||{}}function Ve(i,e=3e4){let t=Ge();return t.apiBase?Promise.resolve(t):new Promise((n,r)=>{let o=setTimeout(()=>{s(),c(),r(new u("NOT_INITIALIZED","Timed out waiting for __STORVIA__ config from parent frame."))},e),s=i.on("init",a=>{a.payload?.apiBase&&d({apiBase:a.payload.apiBase,gameId:a.payload.gameId,conversationId:a.payload.conversationId,accessToken:a.payload.accessToken,selectedModelId:a.payload.selectedModelId,storyMode:a.payload.storyMode,debug:a.payload.debug})}),c=i.on("preview-init",a=>{a.payload?.apiBase&&d(a.payload)});function d(a){clearTimeout(o),s(),c();let l=window;l.__STORVIA__=a,n(a)}i.send(R("ready",{}))})}var Y=class{constructor(){this.baseUrl="";this.gameId="";this.conversationId="";this.modelId="";this.models=[];this.storyMode=!1;this.accessToken="";this.initialized=!1;this.isPreview=!1;this.previewConfig=void 0}async init(){if(this.initialized)return;let e=window.flutter_inappwebview,t=typeof e?.callHandler=="function";this.bus=new O({incoming:window,outgoing:()=>t?null:window.parent,verifySource:t?h=>h.source===null||h.source===window:h=>h.source===window.parent,customSend:t?h=>e.callHandler("storviaBus",h):void 0}),fe(h=>this.bus.send(h));let n=await Ve(this.bus),r=n.apiBase;if(!r)throw new u("NOT_INITIALIZED","window.__STORVIA__.apiBase is not set. The platform must inject it before SDK init.");if(this.baseUrl=`${r}${be}`,this.isPreview=!!n.preview,this.previewConfig=n.previewConfig,!n.gameId)throw new u("GAME_NOT_FOUND","window.__STORVIA__.gameId is not set. The platform must inject it before SDK init.");if(this.gameId=n.gameId,!n.accessToken)throw new u("UNAUTHORIZED","window.__STORVIA__.accessToken is not set. The platform must inject the user token before SDK init.");if(this.accessToken=n.accessToken,this.http=new K(this.baseUrl,this.accessToken,!!n.debug),this.isPreview){this.conversationId="00000000-0000-0000-0000-000000000000";let[h,g]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=h,this.modelId=(n.selectedModelId&&h.some(C=>C.id===n.selectedModelId)?n.selectedModelId:"")||h[0]?.id||"",this.storyMode=n.storyMode===!0;let m=()=>this.gameId,w=()=>this.conversationId,T=()=>this.modelId,S=()=>this.models.find(C=>C.id===this.modelId)?.name,E=()=>this.storyMode;this.chat=new D(this.http,m,w,T,!0,this.previewConfig,S,E),this.characters=new N(this.http,w,!0,g?.characters,g?.characterStates),this.relationships=new U(this.http,w,!0,g?.relationships),this.inventory=new $(this.http,w,!0,g?.inventory),this.world=new L(this.http,w,!0,g?.world),this.player=new F(this.http,w,!0,g?.player,g?.playerState),this.custom=new V(this.http,w,m,!0,g?.custom,g?.custom_inject),this.save=new j(this.http,w,m,!0,g?.save_data),this.state=new z(this.http,w,!0),this.memory=new B(this.http,w,!0),this.initialized=!0,this.listenForPreviewMessages(),this.listenForTokenUpdate();return}this.conversationId=n.conversationId??"";let[o,s]=await Promise.all([this.authenticate(),this.fetchModels()]);this.conversationId=o.conversationId,this.models=s,this.modelId=(n.selectedModelId&&s.some(h=>h.id===n.selectedModelId)?n.selectedModelId:"")||s[0]?.id||"",this.storyMode=n.storyMode===!0;let c=()=>this.gameId,d=()=>this.conversationId,a=()=>this.modelId,l=()=>this.models.find(h=>h.id===this.modelId)?.name,p=()=>this.storyMode;this.chat=new D(this.http,c,d,a,!1,void 0,l,p),this.characters=new N(this.http,d),this.relationships=new U(this.http,d),this.inventory=new $(this.http,d),this.world=new L(this.http,d),this.player=new F(this.http,d),this.custom=new V(this.http,d,c),this.save=new j(this.http,d,c),this.state=new z(this.http,d),this.memory=new B(this.http,d),this.listenForTokenUpdate(),this.listenForModelChange(),this.initialized=!0}listenForModelChange(){this.bus.on("set-model",e=>{let t=e.payload?.modelId||"";t&&(this.modelId=t)}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0})}listenForTokenUpdate(){this.bus.on("token-update",e=>{let t=e.payload?.accessToken;typeof t!="string"||!t||(this.accessToken=t,this.http?.setToken(t))})}listenForPreviewMessages(){this.bus.on("set-model",e=>{this.modelId=e.payload.modelId||""}),this.bus.on("set-story-mode",e=>{this.storyMode=e.payload?.storyMode===!0}),this.bus.on("config-update",e=>{this.previewConfig=e.payload.previewConfig,this.chat&&this.chat.updatePreviewConfig(this.previewConfig),this.refreshPreviewSnapshot().catch(t=>{console.warn("[Storvia SDK] refreshPreviewSnapshot failed:",t)})})}async fetchPreviewSnapshot(){try{let e={game_id:this.gameId};return this.previewConfig&&("game_config"in this.previewConfig&&(e.game_config=this.previewConfig.game_config),"game_state"in this.previewConfig&&(e.game_state_override=this.previewConfig.game_state)),await this.http.post("/preview/initial-snapshot",e)}catch(e){return console.warn("[Storvia SDK] fetchPreviewSnapshot failed:",e),null}}async refreshPreviewSnapshot(){let e=await this.fetchPreviewSnapshot();e&&(this.characters?.setInitial(e.characters,e.characterStates),this.player?.setInitial(e.player,e.playerState),this.inventory?.setInitial(e.inventory),this.relationships?.setInitial(e.relationships),this.world?.setInitial(e.world),this.custom?.setInitial(e.custom,e.custom_inject),this.save?.setInitial(e.save_data))}async fetchModels(){try{return await this.http.get("/models")}catch{}return[]}async authenticate(){let e={game_id:this.gameId};this.conversationId&&(e.conversation_id=this.conversationId);let t=await fetch(`${this.baseUrl}/auth`,{method:"POST",headers:{"Content-Type":"application/json",Authorization:`Bearer ${this.accessToken}`},body:JSON.stringify(e)});if(!t.ok)throw t.status===401?new u("UNAUTHORIZED","User not authenticated"):t.status===404?new u("GAME_NOT_FOUND","Game not found or not published"):new u("INTERNAL_ERROR",`Auth failed: HTTP ${t.status}`);let n=await t.json();return n.data??n}async initDev(e){if(this.initialized)return;this.baseUrl=`${Fe}${be}`,this.gameId=e.gameId,this.isPreview=!0,this.http=new K(this.baseUrl,"",!1,e.apiKey);let[t,n]=await Promise.all([this.fetchModels(),this.fetchPreviewSnapshot()]);this.models=t;let r=e.model?t.find(a=>a.name===e.model)?.id??"":"";this.modelId=r||t[0]?.id||"",this.conversationId="00000000-0000-0000-0000-000000000000";let o=()=>this.gameId,s=()=>this.conversationId,c=()=>this.modelId,d=()=>this.models.find(a=>a.id===this.modelId)?.name;this.chat=new D(this.http,o,s,c,!0,void 0,d),this.characters=new N(this.http,s,!0,n?.characters,n?.characterStates),this.relationships=new U(this.http,s,!0,n?.relationships),this.inventory=new $(this.http,s,!0,n?.inventory),this.world=new L(this.http,s,!0,n?.world),this.player=new F(this.http,s,!0,n?.player,n?.playerState),this.custom=new V(this.http,s,o,!0,n?.custom),this.save=new j(this.http,s,o,!0,n?.save_data),this.memory=new B(this.http,s,!0),this.initialized=!0}async getAssets(e,t){let n={asset_type:e};return t&&(n.category=t),(await this.http.get("/assets",n)).map(o=>({id:o.id,name:o.name,url:o.url,assetType:o.asset_type,category:o.category}))}};async function Pe(i){let e=new Y;return i?.dev?await e.initDev(i.dev):await e.init(),e}function le(i){return typeof i=="object"&&i!==null&&"value"in i&&"type"in i&&(i.type==="number"||i.type==="text")}function ke(i){return le(i)?i.value:i}return De(je);})();
240
240
  if(typeof window!=="undefined"){window.createStorviaSDK=StorviaSDK.createStorviaSDK;}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@storvia/sdk",
3
- "version": "0.8.2",
3
+ "version": "0.8.3",
4
4
  "description": "Storvia World SDK - Build interactive text games on the Storvia platform",
5
5
  "main": "dist/index.cjs.js",
6
6
  "module": "dist/index.esm.js",