@oracle-agent/oracle 0.35.44 → 0.35.45
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/agent-sessions.mjs +24 -24
- package/dist/assets/skills/oracle-desk-product/SKILL.md +1 -1
- package/dist/bin/desk-server.mjs +26 -26
- package/dist/bin/oracle-data-mcp.mjs +14 -14
- package/dist/bin/oracle-gateway.mjs +47 -47
- package/dist/bin/oracle-investigate.mjs +4 -4
- package/dist/bin/oracle-launch-radar-shadow.mjs +5 -5
- package/dist/bin/oracle-mev-arb-shadow.mjs +5 -5
- package/dist/bin/oracle-mev-shadow.mjs +5 -5
- package/dist/bin/oracle-public-server.mjs +5 -5
- package/dist/bin/oracle-route.mjs +23 -23
- package/dist/bin/oracle-scan.mjs +6 -6
- package/dist/bin/oracle.mjs +1 -0
- package/dist/cli/commands/account.mjs +39 -0
- package/dist/cli/commands/agent-session.mjs +23 -23
- package/dist/cli/commands/airdrop.mjs +7 -7
- package/dist/cli/commands/chat.mjs +198 -198
- package/dist/cli/commands/data.mjs +29 -29
- package/dist/cli/commands/doctor.mjs +7 -7
- package/dist/cli/commands/eval.mjs +123 -123
- package/dist/cli/commands/farm.mjs +16 -16
- package/dist/cli/commands/follow.mjs +36 -36
- package/dist/cli/commands/mint.mjs +10 -10
- package/dist/cli/commands/model.mjs +205 -205
- package/dist/cli/commands/quickstart.mjs +6 -6
- package/dist/cli/commands/receipt.mjs +11 -11
- package/dist/cli/commands/resolve.mjs +9 -9
- package/dist/cli/commands/session-vault.mjs +5 -5
- package/dist/cli/commands/sign.mjs +12 -12
- package/dist/cli/commands/signer.mjs +25 -25
- package/dist/cli/commands/snipe.mjs +7 -7
- package/dist/cli/commands/strategy.mjs +5 -5
- package/dist/cli/commands/swap.mjs +14 -14
- package/dist/cli/commands/venues.mjs +2 -2
- package/dist/data/desk-data.mjs +24 -24
- package/dist/data/names.mjs +3 -3
- package/dist/data/providers/farming.mjs +2 -2
- package/dist/data/providers/lp-destination-discovery.mjs +4 -4
- package/dist/index.mjs +44 -44
- package/dist/investigator/index.mjs +2 -2
- package/dist/launch-radar/index.mjs +5 -5
- package/dist/local-signer/anvil-attestation-worker.mjs +1 -1
- package/dist/local-signer/index.mjs +7 -3
- package/dist/local-signer/runtime.mjs +22 -22
- package/dist/nft/universal-mint-router.mjs +4 -4
- package/dist/notifications/index.mjs +7 -7
- package/dist/router/index.mjs +3 -3
- package/dist/router/prepare-bridge.mjs +2 -2
- package/dist/router/prepare-route.mjs +3 -3
- package/dist/scanner/index.mjs +4 -4
- package/dist/strategy/index.mjs +3 -3
- package/dist/tui/standalone-client.mjs +85 -85
- package/package.json +1 -1
- package/public/oracle-splash/docs/browser-and-web/index.html +2 -2
- package/public/oracle-splash/docs/connectors/index.html +2 -2
- package/public/oracle-splash/docs/getting-started/index.html +2 -2
- package/public/oracle-splash/docs/index.html +3 -3
- package/public/oracle-splash/docs/reference/index.html +2 -2
- package/public/oracle-splash/docs/security/index.html +2 -2
- package/public/oracle-splash/docs/using-oracle/index.html +2 -2
- package/public/oracle-splash/download/index.html +3 -3
- package/public/oracle-splash/downloads/index.html +1 -1
- package/public/oracle-splash/index.html +6 -6
- package/server.json +2 -2
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
var Fn=Object.defineProperty;var V=(e,t,r)=>()=>{if(r)throw r[0];try{return e&&(t=e(e=0)),t}catch(n){throw r=[n],n}};var Cn=(e,t)=>{for(var r in t)Fn(e,r,{get:t[r],enumerable:!0})};import{AsyncLocalStorage as Un}from"node:async_hooks";function Qe(e){let t=qn.getStore();if(!t||t.closed||!Dn.includes(e))return null;if(t.spans.length>=Bn)return t.droppedSpans++,null;let r={stage:e,startMs:t.now()-t.start,durationMs:null,outcome:"pending",status:null};return t.spans.push(r),(n,o=null)=>{t.closed||r.durationMs!==null||(r.durationMs=Math.max(0,t.now()-t.start-r.startMs),r.outcome=n==="succeeded"?"succeeded":"failed",r.status=Number.isInteger(o)&&o>=100&&o<=599?o:null)}}var qn,Dn,Bn,ar=V(()=>{qn=new Un,Dn=["http","retry","shared"],Bn=512});import Ee from"node:net";import zn from"node:dns";function et(e){let t=String(e).toLowerCase().split("%")[0];if((t.match(/::/g)||[]).length>1)return null;let r=u=>{if(!u)return[];let c=u.split(":"),d=c.at(-1);if(d?.includes(".")){let m=d.split(".").map(Number);if(m.length!==4||m.some(p=>!Number.isInteger(p)||p<0||p>255))return null;c.splice(c.length-1,1,(m[0]<<8|m[1]).toString(16),(m[2]<<8|m[3]).toString(16))}return c.some(m=>!/^[0-9a-f]{1,4}$/.test(m))?null:c.map(m=>Number.parseInt(m,16))},[n,o]=t.split("::"),i=r(n),s=r(o);if(!i||!s)return null;let a=t.includes("::"),l=8-i.length-s.length;if(!a&&l!==0||a&&l<1)return null;let f=[...i,...Array(Math.max(0,l)).fill(0),...s];return f.length!==8?null:Uint8Array.from(f.flatMap(u=>[u>>8,u&255]))}function ht(e,t,r){let n=Math.floor(r/8),o=r%8;for(let s=0;s<n;s+=1)if(e[s]!==t[s])return!1;if(!o)return!0;let i=255<<8-o;return(e[n]&i)===(t[n]&i)}function yt(e){if(Ee.isIPv4(e)){let t=e.split(".").map(Number);return!(t[0]===0||t[0]===10||t[0]===127||t[0]>=224||t[0]===100&&t[1]>=64&&t[1]<=127||t[0]===169&&t[1]===254||t[0]===172&&t[1]>=16&&t[1]<=31||t[0]===192&&(t[1]===0||t[1]===2||t[1]===168)||t[0]===192&&t[1]===88&&t[2]===99||t[0]===198&&(t[1]===18||t[1]===19||t[1]===51)||t[0]===203&&t[1]===0&&t[2]===113)}if(Ee.isIPv6(e)){let t=et(e);if(!t)return!1;let r=et("::ffff:0:0");return ht(t,r,96)?yt([...t.slice(12)].join(".")):ht(t,et("2000::"),3)?![["2001::",23],["2001:db8::",32],["2001:10::",28],["2001:2::",48],["2002::",16],["3fff::",20]].some(([o,i])=>ht(t,et(o),i)):!1}return!1}function Jn(e){let t;try{t=new URL(String(e))}catch{return{ok:!1,error:`not a valid URL: ${String(e).slice(0,120)}`}}if(t.protocol!=="http:"&&t.protocol!=="https:")return{ok:!1,error:`refused protocol ${t.protocol} (only http/https)`};let r=t.hostname.toLowerCase().replace(/^\[|\]$/g,"").replace(/\.+$/,"");if(Vn.has(r)||r.endsWith(".localhost")||r.endsWith(".internal"))return{ok:!1,error:`refused internal host ${r}`};let n=Ee.isIP(r);return n!==0&&!yt(r)?{ok:!1,error:`refused private address ${r}`}:{ok:!0,url:t,host:r,isLiteralIp:n!==0}}async function wt(e,{lookupFn:t=zn.promises.lookup}={}){let r=Jn(e);if(!r.ok)return r;if(r.isLiteralIp)return{ok:!0,url:r.url,addresses:[{address:r.host,family:Ee.isIPv6(r.host)?6:4}]};let n;try{n=await t(r.host,{all:!0,verbatim:!0})}catch{return{ok:!1,error:`refused: ${r.host} did not resolve`}}return!Array.isArray(n)||n.length===0||n.some(o=>!yt(o.address))?{ok:!1,error:`refused: ${r.host} resolves to a non-public address`}:{ok:!0,url:r.url,addresses:n}}async function gt({requireUndici:e=!1,importUndici:t=()=>import("undici")}={}){let r,n;try{let c=await t();r=c.Agent,n=c.fetch}catch(c){if(e)throw new Error(`egress-guard: untrustedUrl pinning requires the undici package, which failed to load: ${c?.message||c}`);return null}if(typeof r!="function"||typeof n!="function"){if(e)throw new Error("egress-guard: untrustedUrl pinning requires undici's Agent and fetch exports, which were not found on the imported module");return null}let o=c=>String(c).toLowerCase().replace(/^\[|\]$/g,"").replace(/\.+$/,""),i=new Map,s=c=>(Array.isArray(c)?c:[c]).map(d=>typeof d=="string"?{address:d}:d).filter(d=>d&&d.address).map(d=>({address:d.address,family:d.family||(Ee.isIPv6(d.address)?6:4)})),a=(c,d,m)=>{i.set(o(c),s(typeof d=="string"?[{address:d,family:m}]:d))},l=c=>{let d=o(c);if(Ee.isIP(d))return[{address:d,family:Ee.isIPv6(d)?6:4}];let m=i.get(d);if(!m||!m.length)throw new Error(`refused: unpinned host ${c} during pinned fetch`);return m},f=new r({connect:{lookup(c,d,m){let p;try{p=l(c)}catch(w){return m(w)}return d?.all?m(null,p):m(null,p[0].address,p[0].family)}}}),u=Gn((c,d={})=>n(c,{...d,dispatcher:f}),a);return{dispatcher:f,fetch:u,pin:a,resolve:l,async close(){try{await f.destroy()}catch{}}}}function Gn(e,t){if(typeof e!="function")throw new Error("markPinCapableFetch: fetchImpl must be a function");if(typeof t!="function")throw new Error("markPinCapableFetch: pin must be a function");return e[bt]=Object.freeze({pin:t}),e}function Et(e){return typeof e=="function"&&typeof e[bt]?.pin=="function"}function cr(e,t,r){if(!Et(e))throw new Error("pinFetchToAddresses: fetchImpl is not pin-capable");e[bt].pin(t,r)}var Vn,bt,lr=V(()=>{Vn=new Set(["localhost","metadata.google.internal","metadata.goog"]);bt=Symbol.for("oracle.egressGuard.pinCapableFetch")});import{createHash as Kn}from"node:crypto";import{types as de}from"node:util";function J(e){return me(`HTTP JSON body refused: ${e}`)}function no(e){return["isArgumentsObject","isArrayBuffer","isAnyArrayBuffer","isArrayBufferView","isBoxedPrimitive","isDataView","isDate","isExternal","isGeneratorObject","isKeyObject","isCryptoKey","isMap","isMapIterator","isModuleNamespaceObject","isNativeError","isPromise","isRegExp","isSet","isSetIterator","isTypedArray","isWeakMap","isWeakSet"].some(t=>typeof de[t]=="function"&&de[t](e))}function oo(e){let t=[],r=0,n=0,o=0,i=0,s=new WeakSet,a=u=>{if(r+=Buffer.byteLength(u,"utf8"),r>fe.bytes)throw J("serialized byte limit exceeded");t.push(u)},l=u=>{if(Buffer.byteLength(u,"utf8")>fe.bytes)throw J("serialized byte limit exceeded");return JSON.stringify(u)},f=(u,c)=>{if(n+=1,n>fe.nodes)throw J("node limit exceeded");if(c>fe.depth)throw J("depth limit exceeded");if(u===null){a("null");return}if(typeof u=="string"){a(l(u));return}if(typeof u=="boolean"){a(u?"true":"false");return}if(typeof u=="number"){if(!Number.isFinite(u))throw J("non-finite number");a(Object.is(u,-0)?"0":String(u));return}if(typeof u!="object")throw J("unsupported non-JSON value");if(de.isProxy(u))throw J("proxy value");if(no(u))throw J("unsupported exotic object");if(s.has(u))throw J("cyclic value");s.add(u);try{if(Object.getOwnPropertySymbols(u).length>0)throw J("symbol-keyed fields are unsupported");if(Array.isArray(u)){let p=Object.getPrototypeOf(u),w=0;for(;p!==null;){if(de.isProxy(p))throw J("proxy array prototype");if(w+=1,w>fe.depth)throw J("array prototype depth limit exceeded");p=Object.getPrototypeOf(p)}if(u.length>fe.arrayLength)throw J("array length limit exceeded");for(let S=0;S<u.length;S+=1){let j=Object.getOwnPropertyDescriptor(u,String(S));if(!j||!Object.hasOwn(j,"value")||j.enumerable!==!0)throw J("array entries must be dense enumerable own data")}let g=0;for(let S in u){if(i+=1,i>fe.fields)throw J("enumeration limit exceeded");if(Object.hasOwn(u,S)&&(g+=1,g>u.length))throw J("named array fields are unsupported")}if(g!==u.length)throw J("array entries must be dense enumerable own data");a("[");for(let S=0;S<u.length;S+=1)S&&a(","),f(Object.getOwnPropertyDescriptor(u,String(S)).value,c+1);a("]");return}let d=Object.getPrototypeOf(u);if(d!==Object.prototype&&d!==null)throw J("non-plain object");let m=[];for(let p in u){if(i+=1,i>fe.fields)throw J("enumeration limit exceeded");if(!Object.hasOwn(u,p))continue;if(o+=1,o>fe.fields)throw J("field limit exceeded");let w=Object.getOwnPropertyDescriptor(u,p);if(!w||!Object.hasOwn(w,"value")||w.enumerable!==!0)throw J("object fields must be enumerable own data");m.push([p,w.value])}a("{");for(let p=0;p<m.length;p+=1)p&&a(","),a(l(m[p][0])),a(":"),f(m[p][1],c+1);a("}")}finally{s.delete(u)}};return f(e,0),t.join("")}function so(e){let t=Object.create(null);if(e==null)return t;if(typeof e!="object"&&typeof e!="function")throw new TypeError("HTTP headers must be an object");if(de.isProxy(e))throw new TypeError("HTTP headers must not be a proxy");if(Object.getOwnPropertySymbols(e).length>0)throw new TypeError("HTTP headers must not contain symbol fields");let r=new Set;for(let n of Object.keys(e)){if(!/^[!#$%&'*+.^_`|~0-9A-Za-z-]+$/u.test(n))throw new TypeError("HTTP header names must be valid tokens");let o=n.toLowerCase();if(r.has(o))throw new TypeError("HTTP headers contain a duplicate canonical name");r.add(o);let i=Object.getOwnPropertyDescriptor(e,n);if(!i||!Object.hasOwn(i,"value"))throw new TypeError("HTTP headers must contain own data properties");let s=i.value;if(s==null||["object","function","symbol"].includes(typeof s))throw new TypeError("HTTP header values must be scalar");t[n]=String(s)}return t}function io(){return Object.assign(Object.create(null),{Accept:"application/json"})}function ao(e,t){if(!e)throw new Error(`HTTP redirect from ${t} missing Location`);let r=new URL(String(e),String(t));if(r.protocol!=="http:"&&r.protocol!=="https:")throw new Error(`HTTP redirect from ${t} used unsupported protocol ${r.protocol}`);return r.toString()}function co(e,t){return new URL(String(e)).origin===new URL(String(t)).origin}function tt(e){if((typeof e!="object"||e===null)&&typeof e!="function")return`${typeof e}:${String(e)}`;let t=mr.get(e);return t||(t=hr,hr+=1,mr.set(e,t)),`reference:${t}`}function yr(e){if(!e||typeof e!="object"||Array.isArray(e)||!Object.hasOwn(e,"jsonrpc")||!Object.hasOwn(e,"method")||e.jsonrpc!=="2.0")return!1;let t=typeof e.method=="string"?e.method:"";return t?lo.has(t)||/^get[A-Z0-9_]/u.test(t)||/^is[A-Z0-9_]/u.test(t)||/^eth_get[A-Z0-9_]/u.test(t):!1}function wr(e,t){if(e==="GET"&&t==null)return!0;if(e!=="POST"||t==null)return!1;let r=t;if(typeof t=="string")try{r=JSON.parse(t)}catch{return!1}if(Array.isArray(r))return r.length>0&&r.every(yr);if(!r||typeof r!="object")return!1;if(Object.hasOwn(r,"jsonrpc")||Object.hasOwn(r,"method"))return yr(r);let n=Object.hasOwn(r,"type")?r.type:null;return typeof n=="string"&&uo.has(n)&&(!Object.hasOwn(r,"action")||r.action==null)&&(!Object.hasOwn(r,"signature")||r.signature==null)&&(!Object.hasOwn(r,"nonce")||r.nonce==null)}function fo(e,t,r,n={},o=null){let i=Kn("sha256"),s=(l,f)=>{let u=String(f);i.update(String(Buffer.byteLength(l,"utf8"))).update(":").update(l),i.update("=").update(String(Buffer.byteLength(u,"utf8"))).update(":").update(u).update(`
|
|
2
|
-
`)};s("method",e),s("url",t),Object.keys(r||{}).map((l,f)=>({name:l.toLowerCase(),order:f,value:String(r[l])})).sort((l,f)=>l.name.localeCompare(f.name)||l.order-f.order).forEach((l,f)=>{s(`header-name-${f}`,l.name),s(`header-value-${f}`,l.value)}),s("body",o??"-");for(let l of["untrustedUrl","maxResponseBytes","sameOriginRedirectsOnly","redirectPolicy","maxRedirects","timeoutMs","retries","fetchImpl","realFetch","lookupFn","importUndici","validateResponse"])s(`context-${l}`,n[l]??"-");return i.digest("hex")}function po(e,t){let r=Number(t);return Number.isFinite(r)&&r>0?Math.min(r*1e3,fr):Math.min(250*2**e,fr)+Math.floor(Math.random()*100)}function me(e,t={}){let r=new Error(e);return r.retryable=!1,Object.assign(r,t),r}function St(e,t,r){return me(`HTTP response from ${e} exceeded maxResponseBytes ${r} (${t})`,{oversize:!0})}function xe(e){try{let t=e?.body?.cancel?.();t&&typeof t.then=="function"&&t.catch(()=>{})}catch{}}function ho(e){return e?e.byteLength??e.length??0:0}async function yo(e,t,{url:r,truncate:n=!1,onOversize:o}={}){if(t==null)return await e.text();let i=Number(e.headers?.get?.("content-length"));if(Number.isFinite(i)&&i>t&&(xe(e),!n))throw St(r,`content-length ${i}`,t);let s=e.body?.getReader?.();if(!s){let c=await e.text(),d=Buffer.byteLength(c,"utf8");if(d>t){if(!n)throw St(r,`body ${d} bytes`,t);return Buffer.from(c,"utf8").subarray(0,t).toString("utf8")}return c}let a=[],l=0,f=!1;try{for(;;){let{value:c,done:d}=await s.read();if(d)break;if(c&&(a.push(Buffer.from(c)),l+=ho(c),l>t)){f=!0;break}}}finally{if(f)try{await s.cancel()}catch{}try{s.releaseLock?.()}catch{}}if(f&&(typeof o=="function"&&o(),!n))throw St(r,`streamed ${l} bytes`,t);let u=Buffer.concat(a);return(f?u.subarray(0,t):u).toString("utf8")}function wo(e){if(!e)return null;try{return JSON.parse(e)}catch{return null}}async function go(e,{fetchImpl:t,method:r,headers:n,body:o,timeoutMs:i,lookupFn:s,realFetch:a,untrustedUrl:l=!1,maxResponseBytes:f=null,sameOriginRedirectsOnly:u=!1,importUndici:c,validateResponse:d,signal:m,redirectPolicy:p="follow",maxRedirects:w=rt}){let g=null,S=t,j=s?{lookupFn:s}:{};if(l&&!a&&!Et(S))throw me(`HTTP refused ${e}: untrustedUrl requires a pin-capable fetchImpl (see markPinCapableFetch in egress-guard.mjs) or no fetchImpl override so Oracle can pin the connection itself`);let T=new AbortController,x=setTimeout(()=>T.abort(),i),M=m?pr?pr([m,T.signal]):m:T.signal,$=async(h,{status:R=null}={})=>{let U=await wt(h,j);if(!U.ok)throw me(R==null?`HTTP refused ${h}: ${U.error}`:`HTTP redirect to ${h} ${U.error}`,R==null?{}:{status:R});let K=new URL(h).hostname;if(a){if(g&&(await g.close(),g=null),!g)try{g=await gt({requireUndici:!0,...c?{importUndici:c}:{}})}catch(k){throw me(R==null?`HTTP refused ${h}: ${k?.message||k}`:`HTTP redirect to ${h} refused: ${k?.message||k}`,R==null?{}:{status:R})}g.pin(K,U.addresses),S=g.fetch}else cr(S,K,U.addresses);return U};try{let h=String(e),R=Object.assign(Object.create(null),n||{});l&&await $(h);for(let U=0;U<=w;U+=1){let K=Object.assign(Object.create(null),{method:r,headers:R,body:o,signal:M,redirect:"manual",dispatcher:void 0}),k=await S(h,K);if((p==="error"||w===0)&&k.status>=300&&k.status<400)throw xe(k),me(`HTTP ${k.status} ${r} redirect refused`,{status:k.status,redirectRefused:!0});if(ro.has(k.status)){let v=u===!0&&r==="POST"&&[307,308].includes(k.status)&&wr(r,o);if(r!=="GET"&&r!=="HEAD"&&!v){xe(k);let P=new Error(`HTTP ${k.status} ${r} ${h} redirected non-idempotent request`);throw P.status=k.status,P}if(U===w)throw xe(k),me(`HTTP ${k.status} ${r} redirect budget exhausted`,{status:k.status,redirectRefused:!0});let C=k.headers?.get?.("location"),L;try{L=ao(C,h)}catch(P){throw xe(k),P}let N=!co(L,h);if(xe(k),N&&r==="POST"){let P=new Error(`HTTP ${k.status} ${r} cross-origin redirect refused`);throw P.status=k.status,P}if(N&&u){let P=new Error(`HTTP ${k.status} ${r} cross-origin redirect refused`);throw P.status=k.status,P.retryable=!1,P}if(N&&(R=io(R)),l)await $(L,{status:k.status});else if(N){let P=await wt(L,j);if(!P.ok){let I=new Error(`HTTP redirect from ${h} ${P.error}`);throw I.status=k.status,I.retryable=!1,I}a&&P.addresses?.length&&(g||(g=await gt(c?{importUndici:c}:{})),g&&(g.pin(new URL(L).hostname,P.addresses),S=g.fetch))}h=L;continue}if(typeof d=="function")try{await d(k,{url:h})}catch(v){throw xe(k),me(v?.message||String(v))}let y=await yo(k,f,{url:h,onOversize:()=>T.abort()}),_=wo(y);if(!k.ok){let v=new Error(`HTTP ${k.status} ${r} ${h}`);throw v.status=k.status,v.retryAfter=k.headers?.get?.("retry-after")??null,v.body=_??y.slice(0,300),v}return _??y}throw new Error(`HTTP redirect loop for ${e}`)}catch(h){if(T.signal.aborted&&!qe(m)){let R=h&&(typeof h=="object"||typeof h=="function")&&!de.isProxy(h)?h:null,U=R?Object.getOwnPropertyDescriptor(R,"oversize"):null;if(!(U&&Object.hasOwn(U,"value")&&U.value===!0))try{if(!R)throw new TypeError("unsafe rejection");Object.defineProperties(R,{oracleTimeout:{value:!0,enumerable:!1},retryable:{value:!1,enumerable:!1}})}catch{let k=new Error("HTTP request timed out");throw Object.defineProperties(k,{oracleTimeout:{value:!0,enumerable:!1},retryable:{value:!1,enumerable:!1}}),k}}throw h}finally{clearTimeout(x),g&&await g.close()}}async function gr(e,t={}){if(t!=null&&typeof t!="object"&&typeof t!="function")throw new TypeError("HTTP options must be an object");if(t!=null&&de.isProxy(t))throw new TypeError("HTTP options must not be a proxy");let r=new Set(["body","dedupe","fetchImpl","headers","importUndici","lookupFn","maxRedirects","maxResponseBytes","method","redirectPolicy","retries","sameOriginRedirectsOnly","signal","timeoutMs","untrustedUrl","validateResponse"]);if(t!=null){if(Object.getOwnPropertySymbols(t).length>0)throw new TypeError("HTTP options contain unknown fields");for(let I of Object.getOwnPropertyNames(t)){let A=Object.getOwnPropertyDescriptor(t,I);if(!(I==="toJSON"&&A&&Object.hasOwn(A,"value")&&A.value===void 0)){if(!r.has(I))throw new TypeError("HTTP options contain unknown fields");if(!A||!A.enumerable||!Object.hasOwn(A,"value"))throw new TypeError("HTTP options must contain enumerable own data properties")}}}let n=I=>{if(t==null||!Object.hasOwn(t,I))return;let A=Object.getOwnPropertyDescriptor(t,I);if(!A||!Object.hasOwn(A,"value"))throw new TypeError("HTTP options must contain own data properties");return A.value};if(typeof e!="string"||e.length===0||e.length>8192)throw new TypeError("HTTP URL must be a bounded string");let o=n("method");if(o!==void 0&&(typeof o!="string"||!/^[A-Za-z]+$/u.test(o)))throw new TypeError("HTTP method must be a string token");let i=n("timeoutMs");if(i!==void 0&&(!Number.isInteger(i)||i<1||i>12e4))throw new TypeError("HTTP timeoutMs must be a bounded integer");let s=n("retries");if(s!==void 0&&(!Number.isInteger(s)||s<0||s>10))throw new TypeError("HTTP retries must be a bounded integer");let a=n("redirectPolicy");if(a!==void 0&&a!=="follow"&&a!=="error")throw new TypeError('HTTP redirectPolicy must be "follow" or "error"');let l=n("maxRedirects");if(l!==void 0&&(!Number.isInteger(l)||l<0||l>rt))throw new TypeError(`HTTP maxRedirects must be an integer from 0 through ${rt}`);if(a==="error"&&l!==void 0&&l!==0)throw new TypeError('HTTP redirectPolicy "error" requires maxRedirects 0 when supplied');let f=a??"follow",u=f==="error"?0:l??rt;for(let I of["dedupe","untrustedUrl","sameOriginRedirectsOnly"]){let A=n(I);if(A!==void 0&&typeof A!="boolean")throw new TypeError(`HTTP ${I} must be boolean`)}let c=n("maxResponseBytes");if(c!==void 0&&(!Number.isInteger(c)||c<1||c>64*1024*1024))throw new TypeError("HTTP maxResponseBytes must be a bounded integer");let d=n("signal");if(d!==void 0){if(de.isProxy(d)||!(d instanceof AbortSignal))throw new TypeError("HTTP signal must be a native AbortSignal");try{qe(d)}catch{throw new TypeError("HTTP signal must be a native AbortSignal")}}for(let I of["importUndici","lookupFn","validateResponse"]){let A=n(I);if(A!==void 0&&typeof A!="function")throw new TypeError(`HTTP ${I} must be a function`)}let m=n("fetchImpl"),p=m||globalThis.fetch;if(typeof p!="function")throw new Error("fetch unavailable \u2014 pass opts.fetchImpl");let w=i??12e3,g=(o||"GET").toUpperCase(),S=n("headers"),j=so(S),T=Object.assign(Object.create(null),j);Object.keys(T).some(I=>I.toLowerCase()==="accept")||(T.Accept="application/json");let x=n("body");x!=null&&typeof x!="string"&&(Object.keys(T).find(A=>A.toLowerCase()==="content-type")||(T["Content-Type"]="application/json"),x=oo(x));let M=s??Wn,$=n("lookupFn"),h=!m,R=n("untrustedUrl")===!0,U=n("sameOriginRedirectsOnly")===!0,K=n("importUndici"),k=n("validateResponse"),y=d,_=c??null,v=async()=>{let I;for(let A=0;A<=M;A++){y&&Qn.call(y);let Q=Qe("http");try{let X=await go(e,{fetchImpl:p,method:g,headers:T,body:x,timeoutMs:w,lookupFn:$,realFetch:h,untrustedUrl:R,maxResponseBytes:_,sameOriginRedirectsOnly:U,importUndici:K,validateResponse:k,signal:y,redirectPolicy:f,maxRedirects:u});return Q?.("succeeded"),X}catch(X){I=X;let re=ge=>{if(!X||typeof X!="object"&&typeof X!="function"||de.isProxy(X))return;let le=Object.getOwnPropertyDescriptor(X,ge);return le&&Object.hasOwn(le,"value")?le.value:void 0},ce=re("status");Q?.("failed",ce);let Ze=re("oracleTimeout")===!0||re("name")==="AbortError"||re("name")==="TimeoutError"||qe(y),Xe=new Set([408,425,429]),or=re("retryable")===!1?!1:ce!=null?Xe.has(ce)||Yn.has(ce)&&ur.has(g):!Ze&&ur.has(g);if(A===M||!or)throw X;let He=po(A,re("retryAfter")),dt=Qe("retry"),Fe=!1;try{y?await new Promise((ge,le)=>{let $e,be=()=>{clearTimeout($e),dr.call(y,"abort",be),le(to(y)||new DOMException("Aborted","AbortError"))};if(qe(y)){be();return}$e=setTimeout(()=>{dr.call(y,"abort",be),ge()},He),eo.call(y,"abort",be,{once:!0}),qe(y)&&be()}):await mo(He),Fe=!0}finally{dt?.(Fe?"succeeded":"failed")}}}throw I};if(!(n("dedupe")!==!1&&!y&&wr(g,x)))return v();let L=fo(g,e,T,{untrustedUrl:R,maxResponseBytes:_,sameOriginRedirectsOnly:U,redirectPolicy:f,maxRedirects:u,timeoutMs:w,retries:M,fetchImpl:tt(p),realFetch:h,lookupFn:tt($),importUndici:tt(K),validateResponse:tt(k)},x),N=xt.get(L);if(N){let I=Qe("shared");try{let A=await N;return I?.("succeeded"),A}catch(A){throw I?.("failed"),A}}let P=v().finally(()=>xt.delete(L));return xt.set(L,P),P}var Yn,ur,Wn,fr,Zn,Xn,Qn,eo,dr,pr,qe,to,ro,rt,Bi,fe,xt,mr,hr,lo,uo,mo,br=V(()=>{ar();lr();Yn=new Set([408,425,429,500,502,503,504]),ur=new Set(["GET","HEAD","OPTIONS","PUT","DELETE"]),Wn=2,fr=4e3,Zn=Object.getOwnPropertyDescriptor(AbortSignal.prototype,"aborted")?.get,Xn=Object.getOwnPropertyDescriptor(AbortSignal.prototype,"reason")?.get,Qn=AbortSignal.prototype.throwIfAborted,eo=EventTarget.prototype.addEventListener,dr=EventTarget.prototype.removeEventListener,pr=typeof AbortSignal.any=="function"?AbortSignal.any.bind(AbortSignal):null,qe=e=>e?Zn.call(e):!1,to=e=>e?Xn.call(e):void 0,ro=new Set([301,302,303,307,308]),rt=3,Bi=64*1024,fe=Object.freeze({depth:32,nodes:1e4,fields:1e4,arrayLength:1e4,bytes:1024*1024});xt=new Map,mr=new WeakMap,hr=1;lo=new Set(["eth_blockNumber","eth_call","eth_chainId","eth_estimateGas","getHealth","minimumLedgerSlot","net_version","simulateTransaction","web3_clientVersion"]),uo=new Set(["allMids","l2Book","outcomeMeta","spotClearinghouseState","userFills","meta","metaAndAssetCtxs","perpDexs","candleSnapshot","fundingHistory","openOrders","frontendOpenOrders","clearinghouseState","spotMeta","validatorSummaries","delegatorSummary","delegations","delegatorRewards","delegatorHistory","maxBuilderFee"]);mo=e=>new Promise(t=>setTimeout(t,e))});import{types as Er}from"node:util";function bo(e){if(!e||typeof e!="object"||Er.isProxy(e)||Array.isArray(e))return!1;let t=Object.getPrototypeOf(e);return t===Object.prototype||t===null}function nt(e,t="provider response",r=0){if(r>64)throw new Error(`${t} exceeds the JSON nesting bound`);if(e===null||typeof e=="string"||typeof e=="boolean"||typeof e=="number"&&Number.isFinite(e))return e;if(Array.isArray(e)){if(Er.isProxy(e)||e.length>1e5)throw new Error(`${t} contains an invalid array`);let o=new Array(e.length);for(let i=0;i<e.length;i+=1){let s=Object.getOwnPropertyDescriptor(e,String(i));if(!s||!Object.hasOwn(s,"value"))throw new Error(`${t} arrays must contain dense own data`);o[i]=nt(s.value,t,r+1)}return o}if(!bo(e))throw new Error(`${t} contains a non-JSON value`);let n=Object.create(null);for(let o of Object.keys(e)){let i=Object.getOwnPropertyDescriptor(e,o);if(!i||!Object.hasOwn(i,"value"))throw new Error(`${t} objects must contain own data`);n[o]=nt(i.value,t,r+1)}return n}var xr=V(()=>{});function So({testnet:e,baseUrl:t}={}){if(t)return t.replace(/\/$/,"").endsWith("/info")?t:`${t.replace(/\/$/,"")}/info`;if(process.env.HL_INFO_URL)return process.env.HL_INFO_URL;if(process.env.HL_API_URL){let r=process.env.HL_API_URL.replace(/\/$/,"");return r.endsWith("/info")?r:`${r}/info`}return e||process.env.HL_TESTNET==="1"?xo:Eo}async function kt(e,t={}){if(!e||!e.type)throw new Error("hlInfo requires body.type");let r=So(t);return nt(await gr(r,{method:"POST",body:e,fetchImpl:t.fetchImpl,timeoutMs:t.timeoutMs,maxResponseBytes:t.maxResponseBytes,sameOriginRedirectsOnly:t.sameOriginRedirectsOnly}),"hyperliquid info response")}async function Sr(e={}){return kt({type:"meta"},e)}async function kr({coin:e,interval:t="1h",startTime:r,endTime:n},o={}){if(!e)throw new Error("hlCandleSnapshot requires coin");let i={type:"candleSnapshot",req:{coin:String(e),interval:t,startTime:r??Date.now()-24*3600*1e3,endTime:n??Date.now()}};return kt(i,o)}async function Or({coin:e,startTime:t,endTime:r},n={}){if(!e)throw new Error("hlFundingHistory requires coin");return kt({type:"fundingHistory",coin:String(e),startTime:t??Date.now()-24*3600*1e3,endTime:r??Date.now()},n)}var Eo,xo,Ot=V(()=>{br();xr();Eo="https://api.hyperliquid.xyz/info",xo="https://api.hyperliquid-testnet.xyz/info"});import{createHash as ko}from"node:crypto";function se(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function _e(e){return typeof e=="number"&&Number.isFinite(e)}function Tt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Tt(t);return Object.freeze(e)}for(let t of Object.keys(e))Tt(e[t]);return Object.freeze(e)}function Se(e){if(Array.isArray(e))return e.map(Se);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=Se(e[r]);return t}return e}function Pt(e){return{netPnlUsd:e.metrics.netPnlUsd,netPnlPct:e.metrics.netPnlPct,maxDrawdownPct:e.metrics.maxDrawdownPct,winRate:e.metrics.winRate,profitFactor:e.metrics.profitFactor,tradeCount:e.metrics.tradeCount,sharpe:e.metrics.sharpe,turnoverUsd:e.metrics.turnoverUsd,exposurePct:e.metrics.exposurePct}}function Pr(e){return{feesUsd:e.costs.feesUsd,builderFeesUsd:e.costs.builderFeesUsd,fundingUsd:e.costs.fundingUsd,slippageUsd:e.costs.slippageUsd}}function Po(e){return(e.feesUsd||0)+(e.builderFeesUsd||0)+Math.max(0,e.fundingUsd||0)+(e.slippageUsd||0)}function Ao(e){let t=0;for(let r of e.trades)r.grossPnlUsd>0&&(t+=r.grossPnlUsd);return t}function To(e,t,r){return!(!e||e.tradeCount<Math.max(1,Math.min(r,3))||!(e.netPnlUsd>0)||!(e.profitFactor>1)||!(e.maxDrawdownPct<=t.maxDailyLossPct))}function Tr(e){if(!se(e))throw new TypeError("evidence artifact must be a plain object");if(!Oo.includes(e.status))throw new TypeError("evidence artifact status is invalid");for(let t of["strategyHash","compilerHash","barsHash"])if(typeof e[t]!="string"||!/^[0-9a-f]{64}$/.test(e[t]))throw new TypeError(`evidence artifact ${t} must be a sha256 hash`);if(!se(e.split))throw new TypeError("evidence artifact split required");if(!Array.isArray(e.flags))throw new TypeError("evidence artifact flags must be an array");if(!se(e.walkForward)||!Array.isArray(e.walkForward.windows))throw new TypeError("evidence artifact walkForward windows required");if(e.status==="pass_live_eligible"&&(!se(e.train)||!se(e.holdout)))throw new TypeError("live-eligible evidence artifact requires train and holdout facts");return Se({barsHash:e.barsHash,compilerHash:e.compilerHash,flags:e.flags.map(t=>Se(t)),holdout:e.holdout??null,split:e.split,status:e.status,strategyHash:e.strategyHash,train:e.train??null,walkForward:{passRate:e.walkForward.passRate,windowsRun:e.walkForward.windowsRun??e.walkForward.windows.length,windows:e.walkForward.windows.map(t=>({index:t.index,trainStartIndex:t.trainStartIndex,trainEndIndex:t.trainEndIndex,passed:t.passed,reason:t.reason,evalStartIndex:t.evalStartIndex,evalEndIndex:t.evalEndIndex,metrics:t.metrics}))}})}function $r(e){return ko("sha256").update(JSON.stringify(Tr(e)),"utf8").digest("hex")}function ne(e,t,r=0){if(!Number.isInteger(e)||e<r)throw new Error(`${t} must be an integer >= ${r}`);return e}function At(e,t){if(!se(e)||!se(e.metrics))throw new Error(`${t} metrics required`);let r=ne(e.tradeCount,`${t}.tradeCount`);if(e.metrics.tradeCount!==r)throw new Error(`${t} tradeCount contradicts metrics.tradeCount`);for(let n of["netPnlUsd","profitFactor","maxDrawdownPct"])if(!_e(e.metrics[n]))throw new Error(`${t}.metrics.${n} must be finite`);if(e.metrics.maxDrawdownPct<0)throw new Error(`${t}.metrics.maxDrawdownPct must be >= 0`);return e.metrics}function $o(e,{maxDailyLossPct:t}={}){let r=e.split,n=ne(r.trainStartIndex,"split.trainStartIndex"),o=ne(r.trainEndIndex,"split.trainEndIndex"),i=ne(r.trainBarCount,"split.trainBarCount",1),s=ne(r.holdoutStartIndex,"split.holdoutStartIndex"),a=ne(r.holdoutEndIndex,"split.holdoutEndIndex"),l=ne(r.holdoutBarCount,"split.holdoutBarCount",1);if(n!==0||o-n+1!==i||s!==o+1||a-s+1!==l)throw new Error("evidence split must be contiguous, chronological, and count-consistent");if(!_e(r.trainFraction)||r.trainFraction<=0||r.trainFraction>=1)throw new Error("split.trainFraction must be in (0,1)");At(e.train,"train");let f=At(e.holdout,"holdout");if(f.tradeCount<1||f.netPnlUsd<=0||f.profitFactor<=1)throw new Error("live-eligible holdout metrics do not pass");if(_e(t)&&f.maxDrawdownPct>t)throw new Error("live-eligible holdout drawdown exceeds strategy risk");if(e.flags.length>0)throw new Error("live-eligible evidence cannot contain failure flags");let u=e.walkForward,c=u.windows;if(c.length<1||u.windowsRun!==c.length)throw new Error("live-eligible walk-forward windowsRun must match nonempty windows");let d=0,m=-1;for(let w=0;w<c.length;w++){let g=c[w];if(!se(g)||g.index!==w||typeof g.passed!="boolean")throw new Error("walk-forward windows must be ordered and structurally valid");let S=ne(g.trainStartIndex,`walkForward.windows[${w}].trainStartIndex`),j=ne(g.trainEndIndex,`walkForward.windows[${w}].trainEndIndex`),T=ne(g.evalStartIndex,`walkForward.windows[${w}].evalStartIndex`),x=ne(g.evalEndIndex,`walkForward.windows[${w}].evalEndIndex`);if(S!==0||j>=T||T>x||T<=m)throw new Error("walk-forward windows must be chronological and disjoint");if(m=x,g.passed){if(d+=1,g.reason!=="pass")throw new Error("passed walk-forward window reason must be pass");let M=At({metrics:g.metrics,tradeCount:g.metrics?.tradeCount},`walkForward.windows[${w}]`);if(M.tradeCount<1||M.netPnlUsd<=0||M.profitFactor<=1)throw new Error("passed walk-forward window metrics do not pass");if(_e(t)&&M.maxDrawdownPct>t)throw new Error("passed walk-forward drawdown exceeds strategy risk")}else if(g.reason==="pass")throw new Error("failed walk-forward window cannot have pass reason")}let p=d/c.length;if(!_e(u.passRate)||Math.abs(u.passRate-p)>Number.EPSILON||p<.6)throw new Error("walk-forward passRate contradicts concrete windows or is below live threshold")}function _r(e,t={}){if(typeof e?.id!="string"||!/^[0-9a-f]{64}$/.test(e.id))throw new Error("evidence.id must be a sha256 evidence artifact hash");let r=Tr(e),n=Se({id:e.id,...r});if(JSON.stringify(Se(e))!==JSON.stringify(n))throw new Error("evidence artifact contains fields unbound from its deterministic identity");let o=$r(e);if(e.id!==o)throw new Error("evidence.id does not match its deterministic artifact facts digest");return e.status==="pass_live_eligible"&&$o(e,t),e}function $t({strategy:e,bars:t,backtestOptions:r={},trainFraction:n=.7,walkForwardWindows:o=3,minTrades:i=10}={}){let s=[];if(!se(e))throw new TypeError("strategy must be a plain object");if(!Array.isArray(t))throw new TypeError("bars must be an array");if(!se(r))throw new TypeError("backtestOptions must be a plain object");if(!_e(n)||n<=0||n>=1)throw new TypeError("trainFraction must be in (0,1)");if(!Number.isInteger(o)||o<1)throw new TypeError("walkForwardWindows must be a positive integer");if(!Number.isInteger(i)||i<0)throw new TypeError("minTrades must be an integer >= 0");let a=W(e),l=ve(a),f=De(t),u=t.length,c=(N=[],P={})=>Ar({status:"fail",strategy:a,sHash:l,barsHash:f,split:P.split||{trainStartIndex:0,trainEndIndex:-1,trainBarCount:0,holdoutStartIndex:0,holdoutEndIndex:-1,holdoutBarCount:0,trainFraction:n},train:P.train||null,holdout:P.holdout||null,walkForward:P.walkForward||{windows:[],passRate:0},flags:[...s,...N]});if(u<10)return c([{type:"insufficient_bars",message:"need at least 10 bars for evidence"}]);let d=Math.floor(u*n),m=d,p=u-m;if(d<5||p<3)return c([{type:"invalid_windowing",message:"train/holdout split too small",trainCount:d,holdoutCount:p}]);let w=t.slice(0,d),g=t.slice(m),S,j;try{S=he(a,w,r),j=he(a,g,r)}catch(N){return c([{type:"backtest_error",message:String(N.message||N)}])}let T={metrics:Pt(S),costs:Pr(S),tradeCount:S.metrics.tradeCount},x={metrics:Pt(j),costs:Pr(j),tradeCount:j.metrics.tradeCount},M={trainStartIndex:0,trainEndIndex:d-1,trainBarCount:d,holdoutStartIndex:m,holdoutEndIndex:u-1,holdoutBarCount:p,trainFraction:n},$=[],h=Math.floor(u/(o+1));if(h<3)s.push({type:"invalid_windowing",message:"walk-forward window size too small",wfSize:h});else for(let N=0;N<o;N++){let P=h*(N+1),I=P,A=Math.min(u,I+h);if(A-I<3||P<3){$.push({index:N,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:!1,reason:"window_too_small",metrics:null});continue}let Q=t.slice(I,A),X;try{X=he(a,Q,r)}catch{$.push({index:N,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:!1,reason:"backtest_error",metrics:null});continue}let re=Pt(X),ce=To(re,a.risk,i);$.push({index:N,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:ce,reason:ce?"pass":"fail_metrics",metrics:re})}let R=$.filter(N=>N.passed).length,U=$.length===0?0:R/$.length,K={windows:$,passRate:U,windowsRun:$.length};x.metrics.tradeCount===0&&T.metrics.tradeCount===0&&s.push({type:"no_trades",message:"no trades in train or holdout"}),x.metrics.tradeCount===0&&s.push({type:"absent_oos_trades",message:"holdout produced no trades"}),x.metrics.netPnlUsd<0&&s.push({type:"holdout_loss",message:"holdout netPnlUsd is negative"}),T.metrics.netPnlUsd>0&&x.metrics.netPnlUsd<0&&T.metrics.netPnlUsd>Math.abs(x.metrics.netPnlUsd)*.25?s.push({type:"overfit",message:"profitable train with losing holdout (OOS collapse)"}):T.metrics.netPnlUsd>0&&x.metrics.netPnlUsd>0&&x.metrics.netPnlUsd<T.metrics.netPnlUsd*.1&&T.metrics.tradeCount>=i&&s.push({type:"severe_oos_collapse",message:"holdout pnl collapsed vs train"});let k=Po(x.costs),y=Ao(j);y>0&&k>y&&s.push({type:"costs_exceed_gross",message:"holdout costs exceed gross gains"});let _=s.some(N=>["insufficient_bars","invalid_windowing","absent_oos_trades","holdout_loss","no_trades","severe_oos_collapse","backtest_error"].includes(N.type)),v=s.some(N=>N.type==="overfit"),C="fail";return x.metrics.tradeCount>=i&&x.metrics.netPnlUsd>0&&x.metrics.profitFactor>1&&x.metrics.maxDrawdownPct<=a.risk.maxDailyLossPct&&U>=.6&&!(y>0&&k>y)&&!v&&!s.some(N=>N.type==="severe_oos_collapse"||N.type==="invalid_windowing")?C="pass_live_eligible":!_&&x.metrics.tradeCount>0&&T.metrics.tradeCount>0&&Number.isFinite(x.metrics.netPnlUsd)?(C="pass_paper_only",x.metrics.tradeCount<i&&s.push({type:"undersampled",message:"holdout trades below minTrades"})):v&&x.metrics.tradeCount>0&&T.metrics.netPnlUsd>0?C="fail":x.metrics.tradeCount>0&&T.metrics.tradeCount>0&&!_?C="pass_paper_only":C="fail",x.metrics.netPnlUsd<0&&(C=C==="pass_live_eligible"?"fail":C==="pass_paper_only"?"pass_paper_only":"fail",C="fail"),Ar({status:C,strategy:a,sHash:l,barsHash:f,split:M,train:T,holdout:x,walkForward:K,flags:s})}function Ar({status:e,strategy:t,sHash:r,barsHash:n,split:o,train:i,holdout:s,walkForward:a,flags:l}){let f={status:e,strategyHash:r,compilerHash:Oe,barsHash:n,split:o,train:i,holdout:s,walkForward:a,flags:l};return f.id=$r(f),Tt(Se(JSON.parse(JSON.stringify(f))))}var Oo,_t=V(()=>{Pe();ke();ot();Oo=Object.freeze(["fail","pass_paper_only","pass_live_eligible"])});import{createHash as _o,createHmac as vo,timingSafeEqual as ra}from"node:crypto";function vt(e){return e===null||typeof e!="object"?JSON.stringify(e):Array.isArray(e)?`[${e.map(vt).join(",")}]`:`{${Object.keys(e).sort().map(r=>`${JSON.stringify(r)}:${vt(e[r])}`).join(",")}}`}function vr(e){let t=String(e?.ORACLE_STAMP_HMAC_SECRET||"").trim();return t.length>=16?t:""}function Ir(e=process.env){return vr(process.env)||vr(e)}function Mo(e){let{prepareHash:t,prepareMac:r,note:n,...o}=e||{};return o}function Ro(e){let t=Mo(e);return _o("sha256").update(vt(t)).digest("hex")}function Lo(e,t=Ir()){return t?vo("sha256",t).update(String(e)).digest("hex"):""}function jr(e,{provider:t,kind:r,env:n=process.env,nowMs:o=Date.now(),expiresAtMs:i}={}){if(!e||typeof e!="object")throw new Error("stampPrepared: payload object required");let s=Object.prototype.hasOwnProperty.call(e,"oraclePrepared");if(s&&typeof e.oraclePrepared!="boolean")throw new Error("stampPrepared: oraclePrepared must be boolean");let a={...e,provider:e.provider||t,kind:e.kind||r,requiresUserSignature:e.requiresUserSignature!==!1,signingReady:!1,broadcastReady:!1,executionReady:!1,oraclePrepared:s?e.oraclePrepared:!0};if(!a.provider)throw new Error("stampPrepared: provider required");if(!a.kind)throw new Error("stampPrepared: kind required");let l=Number(o),f=i==null?l+jo:Number(i),u=f-l;if(!Number.isSafeInteger(l)||!Number.isSafeInteger(f)||u<=0||u>No)throw new Error("stampPrepared: bounded preparedAt/expiresAt required");let d={...a,preparedAt:l,expiresAt:f,prepareVersion:Io},m=Ro(d),p=Ir(n),w=p?Lo(m,p):void 0,g={...d,prepareHash:m};return w&&(g.prepareMac=w),g}var Io,jo,No,Nr=V(()=>{Io=2,jo=300*1e3,No=(()=>{let e=Number(process.env.ORACLE_PREPARE_HARD_MAX_AGE_MS);return Number.isFinite(e)&&e>0?e:1800*1e3})()});function Be(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Fo(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function jt(e,t="value"){if(Array.isArray(e)){e.forEach((r,n)=>jt(r,`${t}[${n}]`));return}if(Be(e))for(let[r,n]of Object.entries(e)){let o=Fo(r);if(Ho.some(i=>o.includes(i)))throw new Error(`handoff: forbidden secret-like field at ${t}.${r}`);jt(n,`${t}.${r}`)}}function It(e){return typeof e=="number"&&Number.isFinite(e)&&e>0}function Mr({strategy:e,evidence:t,shadow:r,caps:n,nowMs:o=Date.now(),env:i=process.env}={}){if(jt({strategy:e,evidence:t,shadow:r,caps:n},"handoff"),!Be(e))throw new Error("handoff: strategy required");if(!Be(t))throw new Error("handoff: evidence required");if(!Be(r))throw new Error("handoff: shadow required");if(!Be(n))throw new Error("handoff: caps required");if(typeof r.id!="string"||!r.id.trim())throw new Error("handoff: shadow.id required");if(typeof r.stateHash!="string"||!/^[0-9a-f]{64}$/.test(r.stateHash))throw new Error("handoff: shadow.stateHash must be a sha256 hash");if(r.status!=="running")throw new Error("handoff: shadow.status must be running");if(!Number.isInteger(r.cursor)||r.cursor<=0)throw new Error("handoff: shadow.cursor must be a positive integer");if(!Number.isInteger(r.updatedAt)||r.updatedAt<=0||r.updatedAt>o)throw new Error("handoff: shadow.updatedAt must be a positive integer <= nowMs");let s=W(e,{nowMs:o}),a=Z(s);if(_r(t,{maxDailyLossPct:s.risk.maxDailyLossPct}),t.status!=="pass_live_eligible")throw new Error("handoff: evidence.status must be pass_live_eligible");if(t.strategyHash!==a.strategyHash)throw new Error("handoff: evidence.strategyHash mismatch");if(t.compilerHash!==a.compilerHash)throw new Error("handoff: evidence.compilerHash mismatch");let l=["perStrategyNotionalUsd","maxLeverage","dailyLossCapUsd","chainAllowlist","assetAllowlist","expiresAt","killSwitchRequired"];for(let d of l)if(!(d in n)||n[d]==null)throw new Error(`handoff: caps.${d} required`);if(!It(n.perStrategyNotionalUsd))throw new Error("handoff: caps.perStrategyNotionalUsd must be positive");if(n.perStrategyNotionalUsd>a.strategy.risk.maxNotionalUsd)throw new Error("handoff: caps.perStrategyNotionalUsd exceeds strategy.risk.maxNotionalUsd");if(!It(n.maxLeverage))throw new Error("handoff: caps.maxLeverage must be positive");if(n.maxLeverage>a.strategy.risk.maxLeverage)throw new Error("handoff: caps.maxLeverage exceeds strategy.risk.maxLeverage");if(!It(n.dailyLossCapUsd))throw new Error("handoff: caps.dailyLossCapUsd must be positive");let f=a.strategy.risk.maxNotionalUsd*(a.strategy.risk.maxDailyLossPct/100);if(n.dailyLossCapUsd>f)throw new Error("handoff: caps.dailyLossCapUsd exceeds strategy daily loss ceiling");if(!Array.isArray(n.chainAllowlist)||n.chainAllowlist.length===0)throw new Error("handoff: caps.chainAllowlist must be a non-empty array");if(!n.chainAllowlist.every(d=>d==="hyperliquid"))throw new Error("handoff: caps.chainAllowlist must include only hyperliquid");if(!n.chainAllowlist.includes("hyperliquid"))throw new Error("handoff: caps.chainAllowlist must include hyperliquid");if(!Array.isArray(n.assetAllowlist)||n.assetAllowlist.length===0)throw new Error("handoff: caps.assetAllowlist must be a non-empty array");if(n.assetAllowlist.length!==1||n.assetAllowlist[0]!==a.strategy.market.coin)throw new Error("handoff: caps.assetAllowlist must contain only the strategy market coin");if(!Number.isInteger(n.expiresAt)||!(n.expiresAt>o))throw new Error("handoff: caps.expiresAt must be an integer > nowMs");if(n.expiresAt>a.strategy.risk.expiresAt)throw new Error("handoff: caps.expiresAt exceeds strategy.risk.expiresAt");if(n.killSwitchRequired!==!0)throw new Error("handoff: caps.killSwitchRequired must be exactly true");let u={perStrategyNotionalUsd:n.perStrategyNotionalUsd,maxLeverage:n.maxLeverage,dailyLossCapUsd:n.dailyLossCapUsd,chainAllowlist:[...n.chainAllowlist],assetAllowlist:[...n.assetAllowlist],expiresAt:n.expiresAt,killSwitchRequired:!0},c={strategyHash:a.strategyHash,compilerHash:a.compilerHash,evidence:JSON.parse(JSON.stringify(t)),shadow:{id:r.id,stateHash:r.stateHash,status:r.status,cursor:r.cursor,updatedAt:r.updatedAt},compiled:{strategyHash:a.strategyHash,compilerHash:a.compilerHash,compilerVersion:ze,venue:"hyperliquid",market:{coin:a.strategy.market.coin,kind:"perp",interval:a.strategy.market.interval},risk:{...a.strategy.risk},strategy:JSON.parse(JSON.stringify(a.strategy))},arming:{liveBroadcast:!1,requiresExplicitUserArm:!0,caps:u},requiresUserSignature:!0,signingReady:!1,broadcastReady:!1,executionReady:!1};return jr(c,{provider:"hl-strategy",kind:"strategy-live-handoff",env:i})}var Ho,Rr=V(()=>{Pe();_t();ke();Nr();Ho=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"]});function Ie(e,t){let r=Number(e);if(!Number.isFinite(r))throw new TypeError(`${t} must be finite`);return r}function je(e,t){if(!Number.isSafeInteger(e)||e<0)throw new TypeError(`${t} must be a non-negative safe integer`);return e}function Ve(e){if(Array.isArray(e))for(let t of e)Ve(t);else if(e&&typeof e=="object")for(let t of Object.values(e))Ve(t);return Object.freeze(e)}function Uo(e){let t=Co[e];if(!t)throw new TypeError(`unsupported strategy interval: ${e}`);return t}function qo(e,{endTime:t=Number.MAX_SAFE_INTEGER}={}){if(!Array.isArray(e))throw new TypeError("Hyperliquid candles must be an array");je(t,"endTime");let r=new Map;for(let n=0;n<e.length;n++){let o=e[n];if(!o||typeof o!="object"||Array.isArray(o))throw new TypeError(`candles[${n}] must be an object`);let i=je(Number(o.t),`candles[${n}].t`);if(je(Number(o.T),`candles[${n}].T`)>t)continue;let a={t:i,o:Ie(o.o,`candles[${n}].o`),h:Ie(o.h,`candles[${n}].h`),l:Ie(o.l,`candles[${n}].l`),c:Ie(o.c,`candles[${n}].c`),v:Ie(o.v,`candles[${n}].v`)};if(a.h<Math.max(a.o,a.c,a.l))throw new TypeError(`candles[${n}].h is below another price`);if(a.l>Math.min(a.o,a.c,a.h))throw new TypeError(`candles[${n}].l is above another price`);if(a.v<0)throw new TypeError(`candles[${n}].v must be non-negative`);let l=r.get(i);if(l&&JSON.stringify(l)!==JSON.stringify(a))throw new TypeError(`conflicting duplicate candle at timestamp ${i}`);l||r.set(i,a)}return Ve([...r.values()].sort((n,o)=>n.t-o.t))}function Do(e,t){if(!Array.isArray(e))throw new TypeError("Hyperliquid funding history must be an array");let r=new Map;for(let n=0;n<e.length;n++){let o=e[n];if(!o||typeof o!="object"||Array.isArray(o))throw new TypeError(`funding[${n}] must be an object`);let i=je(Number(o.time),`funding[${n}].time`);i>t||r.set(i,{time:i,fundingRate:Ie(o.fundingRate,`funding[${n}].fundingRate`)})}return[...r.values()].sort((n,o)=>n.time-o.time)}async function Bo({coin:e,startTime:t,endTime:r},n){let o=[],i=Math.max(0,t-288e5),s=!1;for(let a=0;a<16&&i<=r;a++){let l=await Or({coin:e,startTime:i,endTime:r},n);if(!Array.isArray(l))throw new TypeError("Hyperliquid funding history must be an array");o.push(...l);let f=i;for(let u of l){let c=Number(u?.time);Number.isSafeInteger(c)&&c>f&&(f=c)}if(l.length<500||f>=r){s=!0;break}if(f<=i)throw new Error("Hyperliquid funding history pagination did not advance");i=f+1}if(!s)throw new Error("strategy history exceeds the bounded funding history limit");return Do(o,r)}function zo(e,t,r){let n=0,o=null;return e.map(i=>{let s=i.t+r,a=0;for(;n<t.length&&t[n].time<s;){let l=t[n];o=l.fundingRate,l.time>=i.t&&(a+=l.fundingRate),n+=1}return o==null?{...i,fundingPaymentRate:a}:{...i,fundingRate:o,fundingPaymentRate:a}})}async function Lr(e,t={}){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("strategy history input must be an object");let r=String(e.coin||"").trim().toUpperCase();if(!/^[A-Z0-9][A-Z0-9._-]{0,11}$/.test(r))throw new TypeError("coin must be an uppercase Hyperliquid asset id");let n=String(e.interval||"15m"),o=Uo(n);if(e.endTime==null)throw new TypeError("endTime is required for deterministic history");let i=je(e.endTime,"endTime"),s=e.count==null?1500:e.count;if(!Number.isInteger(s)||s<20||s>5e3)throw new TypeError("count must be an integer from 20 to 5000");let a=e.startTime==null?Math.max(0,i-s*o):je(e.startTime,"startTime");if(a>=i)throw new TypeError("startTime must be before endTime");let[l,f]=await Promise.all([kr({coin:r,interval:n,startTime:a,endTime:i},t),Bo({coin:r,startTime:a,endTime:i},t)]),u=qo(l,{endTime:i}),c=Ve(zo(u,f,o));return Ve({coin:r,interval:n,range:{startTime:a,endTime:i},bars:c})}var Co,Hr=V(()=>{Ot();Co=Object.freeze({"1m":6e4,"3m":18e4,"5m":3e5,"15m":9e5,"30m":18e5,"1h":36e5,"2h":72e5,"4h":144e5,"8h":288e5,"12h":432e5,"1d":864e5})});function Go(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!1,errors:[{path:"market",message:"must be a plain object"}],market:null};for(let r of Object.keys(e))Jo.has(r)||t.push({path:`market.${r}`,message:"unknown field is not allowed"});return(typeof e.coin!="string"||e.coin.length===0||e.coin.length>32)&&t.push({path:"market.coin",message:"must be a non-empty string max 32"}),(typeof e.interval!="string"||!Vo.has(e.interval))&&t.push({path:"market.interval",message:"must be a supported interval"}),t.length?{ok:!1,errors:t,market:null}:{ok:!0,errors:[],market:{coin:e.coin,interval:e.interval}}}async function Ko(e={}){let t=await Sr(e);if(!t||!Array.isArray(t.universe))throw new TypeError("Hyperliquid market metadata must contain universe");return Object.freeze(t.universe.map((r,n)=>{if(!r||typeof r.name!="string"||!r.name)throw new TypeError(`Hyperliquid market metadata universe[${n}].name is invalid`);return r.name}))}var Vo,Jo,Fr,Cr=V(()=>{Ot();Rr();Hr();Vo=new Set(["1m","3m","5m","15m","30m","1h","2h","4h","8h","12h","1d"]),Jo=new Set(["coin","interval"]);Fr=Object.freeze({id:"hyperliquid",validateMarket:Go,fetchBars:Lr,listMarkets:Ko,prepareIntent(e){return Mr(e)}})});function Wo(e){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("strategy venue adapter must be an object");if(typeof e.id!="string"||!/^[a-z0-9][a-z0-9._-]{0,63}$/.test(e.id))throw new TypeError("strategy venue adapter id is malformed");for(let t of Yo.slice(1))if(typeof e[t]!="function")throw new TypeError(`strategy venue adapter ${e.id} requires ${t}()`);for(let t of["fetchBars","listMarkets"])if(e[t]!=null&&typeof e[t]!="function")throw new TypeError(`strategy venue adapter ${e.id} ${t} must be a function`);return e}function Nt(e){return typeof e!="string"?null:Zo.get(e)??null}function Mt(e){let t=Nt(e);if(!t)throw new Error(`unknown strategy venue: ${String(e)}`);return t}var Yo,Ur,Zo,ya,Rt=V(()=>{Cr();Yo=Object.freeze(["id","validateMarket","prepareIntent"]);Ur=[Fr].map(Wo),Zo=new Map(Ur.map(e=>[e.id,e])),ya=Object.freeze([...Ur])});import{createHash as Xo}from"node:crypto";function te(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function z(e){return typeof e=="number"&&Number.isFinite(e)}function Kr(e){return Number.isInteger(e)&&e>0}function Ut(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Ut(t);return Object.freeze(e)}for(let t of Object.keys(e))Ut(e[t]);return Object.freeze(e)}function qt(e){if(Array.isArray(e))return e.map(qt);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=qt(e[r]);return t}return e}function b(e,t,r){e.push({path:t,message:r})}function ye(e,t,r,n){for(let o of Object.keys(e))t.has(o)||b(n,r?`${r}.${o}`:o,"unknown field is not allowed")}function Xr(e,t,r,n){if(!z(e)||!z(t)||!z(r)||!z(n)||n<=0||e<t||e>r)return!1;let o=(e-t)/n;if(!Number.isFinite(o))return!1;let i=Math.round(o);return Math.abs(o-i)<=1e-9}function Ct(e,t,r,n){if(te(e)){if(ye(e,new Set(["param"]),t,n),typeof e.param!="string"||!e.param)return b(n,`${t}.param`,"must be a parameter name string"),null;if(!Object.prototype.hasOwnProperty.call(r,e.param))return b(n,`${t}.param`,`unknown parameter "${e.param}"`),null;let o=r[e.param];return!te(o)||![o.value,o.min,o.max,o.step].every(Kr)?(b(n,`${t}.param`,"referenced period parameter value min max and step must be positive integers"),null):{param:e.param}}return Kr(e)?e:(b(n,t,"must be a positive integer or {param}"),null)}function Yr(e,t,r,n){return te(e)?(ye(e,new Set(["param"]),t,n),typeof e.param!="string"||!e.param?(b(n,`${t}.param`,"must be a parameter name string"),null):Object.prototype.hasOwnProperty.call(r,e.param)?{param:e.param}:(b(n,`${t}.param`,`unknown parameter "${e.param}"`),null)):z(e)?e:(b(n,t,"must be a finite number or {param}"),null)}function st(e){switch(e.type){case"input":case"constant":return[];case"indicator":return e.input?[e.input]:[];case"compare":case"cross":return[e.left,e.right].filter(Boolean);case"logic":return Array.isArray(e.inputs)?[...e.inputs]:[];default:return[]}}function as(e){let t=new Map,r=n=>{let o=t.get(n)||0;if(o===1)return!0;if(o===2)return!1;t.set(n,1);let i=e.get(n);if(i){for(let s of st(i))if(e.has(s)&&r(s))return!0}return t.set(n,2),!1};for(let n of e.keys())if(r(n))return!0;return!1}function cs(e,t){if(!te(e))return b(t,"parameters","must be a plain object"),null;let r=Object.keys(e);if(r.length>Vr)return b(t,"parameters",`too many parameters (max ${Vr})`),null;let n={};for(let o of r){if(!Wr.test(o)){b(t,`parameters.${o}`,"parameter name is malformed");continue}let i=e[o],s=`parameters.${o}`;if(!te(i)){b(t,s,"must be a plain object");continue}ye(i,Dr,s,t);for(let c of Dr)c in i||b(t,`${s}.${c}`,"required field is missing");let{value:a,min:l,max:f,step:u}=i;z(l)||b(t,`${s}.min`,"must be a finite number"),z(f)||b(t,`${s}.max`,"must be a finite number"),(!z(u)||u<=0)&&b(t,`${s}.step`,"must be a positive finite number"),z(a)||b(t,`${s}.value`,"must be a finite number"),z(l)&&z(f)&&l>f&&b(t,`${s}.min`,"min must be <= max"),z(a)&&z(l)&&z(f)&&z(u)&&u>0&&(Xr(a,l,f,u)||b(t,`${s}.value`,"value must lie on the declared min/max/step grid")),n[o]={value:a,min:l,max:f,step:u}}return n}function ls(e,t,r,n){let o=`nodes.${t}`;if(!te(e))return b(n,o,"must be a plain object"),null;if(typeof e.type!="string"||!zr[e.type])return b(n,`${o}.type`,"unknown or missing node type"),ye(e,is,o,n),null;switch(ye(e,zr[e.type],o,n),(typeof e.id!="string"||!Zr.test(e.id))&&b(n,`${o}.id`,"must be a 1-64 char id starting with alphanumeric"),e.type){case"input":return(typeof e.field!="string"||!Qo.has(e.field))&&b(n,`${o}.field`,"must be one of open|high|low|close|volume|fundingRate|openInterest|premium|oiDelta|bookImbalance"),{id:e.id,type:"input",field:e.field};case"constant":{let i=Yr(e.value,`${o}.value`,r,n);return{id:e.id,type:"constant",value:i}}case"indicator":{(typeof e.indicator!="string"||!es.has(e.indicator))&&b(n,`${o}.indicator`,"must be one of sma|ema|rsi|macd|bollinger|atr");let i=e.indicator,s={id:e.id,type:"indicator",indicator:i};if(i==="atr"){"input"in e&&(typeof e.input!="string"||!e.input?b(n,`${o}.input`,"must be a node id string when provided"):s.input=e.input);let a=Ct(e.period,`${o}.period`,r,n);a!=null&&(s.period=a)}else typeof e.input!="string"||!e.input?b(n,`${o}.input`,"must be a node id string"):s.input=e.input;if((i==="sma"||i==="ema"||i==="rsi"||i==="bollinger"||i==="atr")&&("period"in e,i!=="macd"))if(!("period"in e))b(n,`${o}.period`,"required field is missing");else{let a=Ct(e.period,`${o}.period`,r,n);a!=null&&(s.period=a)}if(i==="macd"){for(let a of["fastPeriod","slowPeriod","signalPeriod"])if(!(a in e))b(n,`${o}.${a}`,"required field is missing");else{let l=Ct(e[a],`${o}.${a}`,r,n);l!=null&&(s[a]=l)}"output"in e?os.has(e.output)?s.output=e.output:b(n,`${o}.output`,"must be line|signal|histogram"):b(n,`${o}.output`,"required field is missing"),"period"in e&&b(n,`${o}.period`,"forbidden for macd"),"stdDev"in e&&b(n,`${o}.stdDev`,"forbidden for macd")}else if(i==="bollinger"){if(!("stdDev"in e))b(n,`${o}.stdDev`,"required field is missing");else{let a=Yr(e.stdDev,`${o}.stdDev`,r,n);a!=null&&(typeof a=="number"&&a<=0?b(n,`${o}.stdDev`,"must be > 0"):s.stdDev=a)}"output"in e?ss.has(e.output)?s.output=e.output:b(n,`${o}.output`,"must be upper|middle|lower"):b(n,`${o}.output`,"required field is missing");for(let a of["fastPeriod","slowPeriod","signalPeriod"])a in e&&b(n,`${o}.${a}`,`forbidden for ${i}`)}else{"output"in e&&b(n,`${o}.output`,`forbidden for ${i}`),"stdDev"in e&&i!=="bollinger"&&b(n,`${o}.stdDev`,`forbidden for ${i}`);for(let a of["fastPeriod","slowPeriod","signalPeriod"])a in e&&b(n,`${o}.${a}`,`forbidden for ${i}`)}return s}case"compare":return(typeof e.op!="string"||!ts.has(e.op))&&b(n,`${o}.op`,"must be gt|gte|lt|lte|eq"),(typeof e.left!="string"||!e.left)&&b(n,`${o}.left`,"must be a node id"),(typeof e.right!="string"||!e.right)&&b(n,`${o}.right`,"must be a node id"),{id:e.id,type:"compare",op:e.op,left:e.left,right:e.right};case"logic":{if((typeof e.op!="string"||!rs.has(e.op))&&b(n,`${o}.op`,"must be and|or|not"),!Array.isArray(e.inputs))return b(n,`${o}.inputs`,"must be an array of node ids"),{id:e.id,type:"logic",op:e.op,inputs:[]};let i=[];for(let s=0;s<e.inputs.length;s++){let a=e.inputs[s];typeof a!="string"||!a?b(n,`${o}.inputs.${s}`,"must be a node id"):i.push(a)}return e.op==="not"?i.length!==1&&b(n,`${o}.inputs`,"not requires exactly one input"):(e.op==="and"||e.op==="or")&&i.length<2&&b(n,`${o}.inputs`,`${e.op} requires at least two inputs`),{id:e.id,type:"logic",op:e.op,inputs:i}}case"cross":return(typeof e.direction!="string"||!ns.has(e.direction))&&b(n,`${o}.direction`,"must be above|below"),(typeof e.left!="string"||!e.left)&&b(n,`${o}.left`,"must be a node id"),(typeof e.right!="string"||!e.right)&&b(n,`${o}.right`,"must be a node id"),{id:e.id,type:"cross",direction:e.direction,left:e.left,right:e.right};default:return null}}function us(e,t,r){if(!te(e))return b(t,"risk","must be a plain object"),null;ye(e,Br,"risk",t);for(let d of Br)(!(d in e)||e[d]==null)&&b(t,`risk.${d}`,"required field is missing");let n={},o=e.maxLeverage;!z(o)||o<=0||o>50?b(t,"risk.maxLeverage","must be a number > 0 and <= 50"):n.maxLeverage=o;let i=e.maxNotionalUsd;!z(i)||i<=0?b(t,"risk.maxNotionalUsd","must be a number > 0"):n.maxNotionalUsd=i;let s=e.positionSizePct;!z(s)||s<=0||s>100?b(t,"risk.positionSizePct","must be a number > 0 and <= 100"):n.positionSizePct=s;let a=e.stopLossPct;!z(a)||a<=0||a>100?b(t,"risk.stopLossPct","must be a number > 0 and <= 100"):n.stopLossPct=a;let l=e.takeProfitPct;!z(l)||l<=0||l>1e3?b(t,"risk.takeProfitPct","must be a number > 0 and <= 1000"):n.takeProfitPct=l;let f=e.cooldownBars;!Number.isInteger(f)||f<0||f>1e5?b(t,"risk.cooldownBars","must be an integer >= 0 and <= 100000"):n.cooldownBars=f;let u=e.maxDailyLossPct;!z(u)||u<=0||u>100?b(t,"risk.maxDailyLossPct","must be a number > 0 and <= 100"):n.maxDailyLossPct=u;let c=e.expiresAt;return!Number.isInteger(c)||c<=0?b(t,"risk.expiresAt","must be an integer epoch milliseconds > 0"):(r.nowMs!==void 0&&(Number.isInteger(r.nowMs)?c<=r.nowMs&&b(t,"risk.expiresAt","must be strictly greater than nowMs"):b(t,"nowMs","must be an integer epoch milliseconds")),n.expiresAt=c),n}function Dt(e,t={}){let r=[];if(!te(e))return b(r,"","strategy must be a plain object"),{ok:!1,errors:r,strategy:null};ye(e,qr,"",r);for(let c of qr)(!(c in e)||e[c]==null)&&b(r,c,"required field is missing");e.version!==Lt&&b(r,"version",`must be ${Lt}`),(typeof e.id!="string"||!Wr.test(e.id))&&b(r,"id","must match /^[a-z0-9][a-z0-9._-]{0,63}$/"),(typeof e.name!="string"||e.name.length===0||e.name.length>Gr)&&b(r,"name",`must be a non-empty string max ${Gr}`);let n=Nt(e.venue);n||b(r,"venue",`unknown strategy venue "${String(e.venue)}"`);let o=null;if(!n)te(e.market)||b(r,"market","must be a plain object");else{let c=n.validateMarket(e.market);if(!c||typeof c.ok!="boolean"||!Array.isArray(c.errors))b(r,"market",`venue ${n.id} returned an invalid market validation result`);else if(c.ok)o=c.market;else for(let d of c.errors)b(r,d.path,d.message)}let i=cs(e.parameters,r),s=null,a=new Map;if(!Array.isArray(e.nodes))b(r,"nodes","must be an array");else if(e.nodes.length>Jr)b(r,"nodes",`too many nodes (max ${Jr})`);else{s=[];for(let c=0;c<e.nodes.length;c++){let d=ls(e.nodes[c],c,i||{},r);d&&(typeof d.id=="string"&&Zr.test(d.id)&&(a.has(d.id)?b(r,`nodes.${c}.id`,`duplicate node id "${d.id}"`):a.set(d.id,d)),s.push(d))}for(let c=0;c<s.length;c++){let d=s[c],m=`nodes.${c}`;for(let p of st(d))a.has(p)||b(r,m,`unknown node ref "${p}"`);if(d.type==="indicator"||d.type==="compare"||d.type==="cross")for(let p of st(d)){let w=a.get(p);w&&Ht.has(w.type)&&b(r,m,`node ref "${p}" must be numeric`)}if(d.type==="logic")for(let p of st(d)){let w=a.get(p);w&&!Ht.has(w.type)&&b(r,m,`node ref "${p}" must be boolean`)}}as(a)&&b(r,"nodes","graph contains a cycle")}let l=null;if(!te(e.rules))b(r,"rules","must be a plain object");else{ye(e.rules,Ft,"rules",r);for(let c of Ft)c in e.rules||b(r,`rules.${c}`,"required field is missing");l={};for(let c of Ft){let d=e.rules[c];if(d===null){l[c]=null;continue}if(typeof d!="string"||!d){b(r,`rules.${c}`,"must be a node id or null"),l[c]=d;continue}if(!a.has(d)){b(r,`rules.${c}`,`unknown node ref "${d}"`),l[c]=d;continue}let m=a.get(d);Ht.has(m.type)||b(r,`rules.${c}`,`rule must reference a boolean node, not ${m.type}`),l[c]=d}}let f=us(e.risk,r,t);if(r.length)return{ok:!1,errors:r,strategy:null};let u=Ut({version:Lt,id:e.id,name:e.name,venue:n.id,market:o,parameters:i,nodes:s,rules:l,risk:f});return{ok:!0,errors:[],strategy:u}}function W(e,t={}){let r=Dt(e,t);if(!r.ok)throw new Ne(r.errors);return r.strategy}function fs(e){let t=W(e);return JSON.stringify(qt(t))}function ve(e){let t=fs(e);return Xo("sha256").update(t,"utf8").digest("hex")}function Je(e,t){if(!te(e))throw new Ne([{path:"",message:"strategy must be a plain object"}]);if(!te(t))throw new Ne([{path:"overrides",message:"must be a plain object"}]);let r=W(e),n={};for(let[i,s]of Object.entries(r.parameters))n[i]={value:s.value,min:s.min,max:s.max,step:s.step};let o=[];for(let[i,s]of Object.entries(t)){if(!Object.prototype.hasOwnProperty.call(n,i)){b(o,i,`unknown parameter "${i}"`);continue}let a=n[i];if(!z(s)){b(o,i,"override must be a finite number");continue}if(!Xr(s,a.min,a.max,a.step)){b(o,i,"override must lie on the declared min/max/step grid");continue}n[i]={...a,value:s}}if(o.length)throw new Ne(o);return W({version:r.version,id:r.id,name:r.name,venue:r.venue,market:{coin:r.market.coin,interval:r.market.interval},parameters:n,nodes:r.nodes.map(i=>{let s={...i};return Array.isArray(i.inputs)&&(s.inputs=[...i.inputs]),s}),rules:{...r.rules},risk:{...r.risk}})}var Lt,Wr,Zr,Qo,es,ts,rs,ns,os,ss,Ht,qr,Dr,Ft,Br,is,zr,Vr,Jr,Gr,Ne,ke=V(()=>{Rt();Lt=1,Wr=/^[a-z0-9][a-z0-9._-]{0,63}$/,Zr=/^[A-Za-z0-9][A-Za-z0-9._-]{0,63}$/,Qo=new Set(["open","high","low","close","volume","fundingRate","openInterest","premium","oiDelta","bookImbalance"]),es=new Set(["sma","ema","rsi","macd","bollinger","atr"]),ts=new Set(["gt","gte","lt","lte","eq"]),rs=new Set(["and","or","not"]),ns=new Set(["above","below"]),os=new Set(["line","signal","histogram"]),ss=new Set(["upper","middle","lower"]),Ht=new Set(["compare","logic","cross"]),qr=new Set(["version","id","name","venue","market","parameters","nodes","rules","risk"]),Dr=new Set(["value","min","max","step"]),Ft=new Set(["entryLong","entryShort","exitLong","exitShort"]),Br=new Set(["maxLeverage","maxNotionalUsd","positionSizePct","stopLossPct","takeProfitPct","cooldownBars","maxDailyLossPct","expiresAt"]),is=new Set(["id","type"]),zr={input:new Set(["id","type","field"]),constant:new Set(["id","type","value"]),indicator:new Set(["id","type","indicator","input","period","fastPeriod","slowPeriod","signalPeriod","stdDev","output"]),compare:new Set(["id","type","op","left","right"]),logic:new Set(["id","type","op","inputs"]),cross:new Set(["id","type","direction","left","right"])},Vr=16,Jr=128,Gr=100,Ne=class extends Error{constructor(t){let r=t.map(n=>`${n.path}: ${n.message}`);super(`invalid strategy (${t.length} error${t.length===1?"":"s"}): ${r.join("; ")}`),this.name="StrategyValidationError",this.errors=t}}});function Ge(e){if(!Array.isArray(e))throw new TypeError("values must be an array");for(let t=0;t<e.length;t++){let r=e[t];if(typeof r!="number"||!Number.isFinite(r))throw new TypeError(`values[${t}] must be a finite number`)}}function we(e){if(!Number.isInteger(e)||e<=0)throw new TypeError("period must be a positive integer")}function ds(e){if(!Array.isArray(e))throw new TypeError("bars must be an array");for(let t=0;t<e.length;t++){let r=e[t];if(r==null||typeof r!="object")throw new TypeError(`bars[${t}] must be an object`);for(let n of["o","h","l","c"]){let o=r[n];if(typeof o!="number"||!Number.isFinite(o))throw new TypeError(`bars[${t}].${n} must be a finite number`)}if(r.h<r.l)throw new TypeError(`bars[${t}] high must be >= low`)}}function en(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=0;for(let o=0;o<e.length;o++)n+=e[o],o>=t&&(n-=e[o-t]),o>=t-1&&(r[o]=n/t);return r}function it(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=0;for(let s=0;s<t;s++)n+=e[s];let o=n/t;r[t-1]=o;let i=2/(t+1);for(let s=t;s<e.length;s++)o=i*e[s]+(1-i)*o,r[s]=o;return r}function tn(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<=t)return r;let n=0,o=0;for(let a=1;a<=t;a++){let l=e[a]-e[a-1];l>=0?n+=l:o-=l}let i=n/t,s=o/t;r[t]=Qr(i,s);for(let a=t+1;a<e.length;a++){let l=e[a]-e[a-1],f=l>0?l:0,u=l<0?-l:0;i=(i*(t-1)+f)/t,s=(s*(t-1)+u)/t,r[a]=Qr(i,s)}return r}function Qr(e,t){return e===0&&t===0?50:t===0?100:e===0?0:100-100/(1+e/t)}function rn(e,t={}){Ge(e);let r=t.fastPeriod,n=t.slowPeriod,o=t.signalPeriod;if(we(r),we(n),we(o),r>=n)throw new TypeError("fastPeriod must be < slowPeriod");let i=it(e,r),s=it(e,n),a=new Array(e.length).fill(null);for(let c=0;c<e.length;c++)i[c]!=null&&s[c]!=null&&(a[c]=i[c]-s[c]);let l=new Array(e.length).fill(null),f=new Array(e.length).fill(null),u=[];for(let c=0;c<a.length;c++)a[c]!=null&&u.push(c);if(u.length>=o){let c=0;for(let w=0;w<o;w++)c+=a[u[w]];let d=c/o,m=u[o-1];l[m]=d,f[m]=a[m]-d;let p=2/(o+1);for(let w=o;w<u.length;w++){let g=u[w];d=p*a[g]+(1-p)*d,l[g]=d,f[g]=a[g]-d}}return{line:a,signal:l,histogram:f}}function nn(e,t={}){Ge(e);let r=t.period,n=t.stdDev;if(we(r),typeof n!="number"||!Number.isFinite(n)||n<=0)throw new TypeError("stdDev must be a finite number > 0");let o=new Array(e.length).fill(null),i=new Array(e.length).fill(null),s=new Array(e.length).fill(null);if(e.length<r)return{upper:i,middle:o,lower:s};let a=0,l=0;for(let f=0;f<e.length;f++){let u=e[f];if(a+=u,l+=u*u,f>=r){let c=e[f-r];a-=c,l-=c*c}if(f>=r-1){let c=a/r,d=l/r-c*c;d<0&&d>-1e-12&&(d=0);let m=Math.sqrt(d);o[f]=c,i[f]=c+n*m,s[f]=c-n*m}}return{upper:i,middle:o,lower:s}}function on(e,t){ds(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=new Array(e.length);for(let s=0;s<e.length;s++){let a=e[s];if(s===0)n[s]=a.h-a.l;else{let l=e[s-1].c;n[s]=Math.max(a.h-a.l,Math.abs(a.h-l),Math.abs(a.l-l))}}let o=0;for(let s=0;s<t;s++)o+=n[s];let i=o/t;r[t-1]=i;for(let s=t;s<e.length;s++)i=(i*(t-1)+n[s])/t,r[s]=i;return r}var sn=V(()=>{});import{createHash as ps}from"node:crypto";var Bt,ms,hs,ys,an,cn=V(()=>{Bt=3,ms="7477966facc4ef928a94e6221c8fd238eef4fcbeec46b96ae1b89178e13c2d5f",hs="68f5b412a9975f04024cf9b9b6209b4bccedd52f176e95f34f786b3f53479c6a",ys="967fd45ecddd0d59ac0f662fe92ea813c32620ba751f249b4ace6cb6b809fb5e",an=ps("sha256").update(JSON.stringify({version:Bt,compilerSourceHash:ms,indicatorsSourceHash:hs,schemaSourceHash:ys})).digest("hex")});function ee(e){return typeof e=="number"&&Number.isFinite(e)}function bs(e){let t=new Map(e.map(a=>[a.id,a])),r=a=>{switch(a.type){case"indicator":return a.input?[a.input]:[];case"compare":case"cross":return[a.left,a.right];case"logic":return[...a.inputs];default:return[]}},n=new Map,o=new Map;for(let a of e)n.set(a.id,0),o.set(a.id,[]);for(let a of e)for(let l of r(a))t.has(l)&&(o.get(l).push(a.id),n.set(a.id,n.get(a.id)+1));let i=[];for(let[a,l]of n)l===0&&i.push(a);let s=[];for(;i.length;){let a=i.shift();s.push(a);for(let l of o.get(a))n.set(l,n.get(l)-1),n.get(l)===0&&i.push(l)}if(s.length!==e.length)throw new Error("strategy graph is cyclic");return s}function Me(e,t){return e!=null&&typeof e=="object"&&"param"in e?t[e.param].value:e}function Es(e,t,r){if(!Array.isArray(e)||e.length===0)throw new TypeError("bars must be a non-empty array");if(!Number.isInteger(t)||t<0||t>=e.length)throw new RangeError("index out of range");let n=null;for(let o=0;o<=t;o++){let i=e[o];if(i==null||typeof i!="object"||Array.isArray(i))throw new TypeError(`bars[${o}] must be an object`);let{t:s,o:a,h:l,l:f,c:u,v:c}=i;if(!ee(s)&&(typeof s=="number"&&Number.isFinite(s)),!Number.isFinite(s))throw new TypeError(`bars[${o}].t must be finite`);for(let[d,m]of[["o",a],["h",l],["l",f],["c",u],["v",c]])if(!ee(m))throw new TypeError(`bars[${o}].${d} must be a finite number`);for(let[d,m]of[["o",a],["h",l],["l",f],["c",u]])if(!(m>0))throw new TypeError(`bars[${o}].${d} price must be positive`);if(c<0)throw new TypeError(`bars[${o}].v volume must be non-negative`);if(l<Math.max(a,u,f))throw new TypeError(`bars[${o}] high must be >= max(open, close, low)`);if(f>Math.min(a,u,l))throw new TypeError(`bars[${o}] low must be <= min(open, close, high)`);if(n!=null){if(!(s>n))throw new TypeError("bars t must be strictly increasing");if(s-n!==gs[r])throw new TypeError(`bars t must match ${r} cadence`)}if(n=s,"fundingRate"in i&&i.fundingRate!=null&&!ee(i.fundingRate))throw new TypeError(`bars[${o}].fundingRate must be finite when present`);if("openInterest"in i&&i.openInterest!=null){if(!ee(i.openInterest))throw new TypeError(`bars[${o}].openInterest must be finite when present`);if(i.openInterest<0)throw new TypeError(`bars[${o}].openInterest must be non-negative`)}for(let d of["premium","oiDelta"])if(d in i&&i[d]!=null&&!ee(i[d]))throw new TypeError(`bars[${o}].${d} must be finite when present`);if("bookImbalance"in i&&i.bookImbalance!=null){if(!ee(i.bookImbalance))throw new TypeError(`bars[${o}].bookImbalance must be finite when present`);if(i.bookImbalance<-1||i.bookImbalance>1)throw new TypeError(`bars[${o}].bookImbalance must be within [-1, 1]`)}}}function Ae(e,t,r,n,o,i){if(i.has(e))return i.get(e);let s=t.get(e),a;switch(s.type){case"input":{let l=ws[s.field];a=new Array(o+1);for(let f=0;f<=o;f++){let u=n[f][l];a[f]=u===void 0?null:u}break}case"constant":{let l=Me(s.value,r);a=new Array(o+1).fill(l);break}case"indicator":{let l=s.period!=null?Me(s.period,r):void 0;if(s.indicator==="atr"){let c=[];for(let d=0;d<=o;d++){let m=n[d];c.push({o:m.o,h:m.h,l:m.l,c:m.c})}a=on(c,l);break}let u=Ae(s.input,t,r,n,o,i).map((c,d)=>{if(c==null||!ee(c))throw new TypeError(`indicator input ${s.input} has non-finite value at ${d}`);return c});if(s.indicator==="sma")a=en(u,l);else if(s.indicator==="ema")a=it(u,l);else if(s.indicator==="rsi")a=tn(u,l);else if(s.indicator==="macd")a=rn(u,{fastPeriod:Me(s.fastPeriod,r),slowPeriod:Me(s.slowPeriod,r),signalPeriod:Me(s.signalPeriod,r)})[s.output];else if(s.indicator==="bollinger")a=nn(u,{period:l,stdDev:Me(s.stdDev,r)})[s.output];else throw new Error(`unsupported indicator ${s.indicator}`);break}case"compare":{let l=Ae(s.left,t,r,n,o,i),f=Ae(s.right,t,r,n,o,i);a=new Array(o+1);for(let u=0;u<=o;u++){let c=l[u],d=f[u];if(c==null||d==null||!ee(c)||!ee(d)){a[u]=!1;continue}switch(s.op){case"gt":a[u]=c>d;break;case"gte":a[u]=c>=d;break;case"lt":a[u]=c<d;break;case"lte":a[u]=c<=d;break;case"eq":a[u]=c===d;break;default:a[u]=!1}}break}case"logic":{let l=s.inputs.map(f=>Ae(f,t,r,n,o,i));a=new Array(o+1);for(let f=0;f<=o;f++)if(s.op==="not"){let u=l[0][f];a[f]=u===!0?!1:u===!1}else if(s.op==="and"){let u=!0;for(let c of l)if(c[f]!==!0){u=!1;break}a[f]=u}else if(s.op==="or"){let u=!1;for(let c of l)if(c[f]===!0){u=!0;break}a[f]=u}else a[f]=!1;break}case"cross":{let l=Ae(s.left,t,r,n,o,i),f=Ae(s.right,t,r,n,o,i);a=new Array(o+1),a[0]=!1;for(let u=1;u<=o;u++){let c=l[u-1],d=f[u-1],m=l[u],p=f[u];if(c==null||d==null||m==null||p==null||!ee(c)||!ee(d)||!ee(m)||!ee(p)){a[u]=!1;continue}s.direction==="above"?a[u]=c<=d&&m>p:a[u]=c>=d&&m<p}break}default:throw new Error(`unknown node type ${s.type}`)}return i.set(e,a),a}function Z(e,t={}){let r=W(e);t&&Object.keys(t).length&&(r=Je(r,t));let n=new Map(r.nodes.map(m=>[m.id,m])),o=Object.freeze(bs(r.nodes)),i=r.parameters,s=new Set(r.nodes.filter(m=>m.type==="input").map(m=>m.field));if(r.nodes.some(m=>m.type==="indicator"&&m.indicator==="atr"))for(let m of["open","high","low","close"])s.add(m);let a=Object.freeze([...s].sort()),l=ve(r);function f(m,p){let w={};for(let S of o){let j=m.get(S);w[S]=j[p]}let g=S=>S!=null&&w[S]===!0;return{values:w,signals:{entryLong:g(r.rules.entryLong),entryShort:g(r.rules.entryShort),exitLong:g(r.rules.exitLong),exitShort:g(r.rules.exitShort)}}}function u(m,p){Es(m,p,r.market.interval);let w=new Map;for(let g of o)Ae(g,n,i,m,p,w);return w}function c(m,p){return f(u(m,p),p)}function d(m){if(!Array.isArray(m)||m.length===0)throw new TypeError("bars must be a non-empty array");let p=m.length-1,w=u(m,p);return Object.freeze(m.map((g,S)=>Object.freeze(f(w,S))))}return Object.freeze({strategy:r,strategyHash:l,compilerVersion:ze,compilerHash:Oe,requiredSeries:a,nodeOrder:o,evaluate:c,evaluateAll:d})}var ze,Oe,ws,gs,Pe=V(()=>{ke();sn();cn();ze=Bt,Oe=an,ws=Object.freeze({open:"o",high:"h",low:"l",close:"c",volume:"v",fundingRate:"fundingRate",openInterest:"openInterest",premium:"premium",oiDelta:"oiDelta",bookImbalance:"bookImbalance"}),gs=Object.freeze({"1m":6e4,"3m":18e4,"5m":3e5,"15m":9e5,"30m":18e5,"1h":36e5,"2h":72e5,"4h":144e5,"8h":288e5,"12h":432e5,"1d":864e5})});import{createHash as xs}from"node:crypto";function ks(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function ie(e){return typeof e=="number"&&Number.isFinite(e)}function zt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)zt(t);return Object.freeze(e)}for(let t of Object.keys(e))zt(e[t]);return Object.freeze(e)}function at(e){if(Array.isArray(e))return e.map(at);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=at(e[r]);return t}return e}function Vt(e,t="result"){if(typeof e=="number"){if(!Number.isFinite(e))throw new Error(`non-finite backtest result at ${t}`);return}if(!(e==null||typeof e!="object")){if(Array.isArray(e)){e.forEach((r,n)=>Vt(r,`${t}[${n}]`));return}for(let[r,n]of Object.entries(e))Vt(n,`${t}.${r}`)}}function un(e){if(!Array.isArray(e)||e.length===0)throw new TypeError("bars must be a non-empty array");let t=null;for(let r=0;r<e.length;r++){let n=e[r];if(n==null||typeof n!="object"||Array.isArray(n))throw new TypeError(`bars[${r}] must be an object`);let{t:o,o:i,h:s,l:a,c:l,v:f}=n;if(!ie(o))throw new TypeError(`bars[${r}].t must be finite`);for(let[u,c]of[["o",i],["h",s],["l",a],["c",l],["v",f]])if(!ie(c))throw new TypeError(`bars[${r}].${u} must be a finite number`);for(let[u,c]of[["o",i],["h",s],["l",a],["c",l]])if(!(c>0))throw new TypeError(`bars[${r}].${u} price must be positive`);if(f<0)throw new TypeError(`bars[${r}].v volume must be non-negative`);if(s<Math.max(i,l,a))throw new TypeError(`bars[${r}] high must be >= max(open, close, low)`);if(a>Math.min(i,l,s))throw new TypeError(`bars[${r}] low must be <= min(open, close, high)`);if(t!=null&&!(o>t))throw new TypeError("bars t must be strictly increasing");if(t=o,"fundingRate"in n&&n.fundingRate!=null&&!ie(n.fundingRate))throw new TypeError(`bars[${r}].fundingRate must be finite when present`);if("fundingPaymentRate"in n&&n.fundingPaymentRate!=null&&!ie(n.fundingPaymentRate))throw new TypeError(`bars[${r}].fundingPaymentRate must be finite when present`);if("openInterest"in n&&n.openInterest!=null&&!ie(n.openInterest))throw new TypeError(`bars[${r}].openInterest must be finite when present`)}}function De(e){if(!Array.isArray(e))throw new TypeError("bars must be an array");return e.length>0&&un(e),xs("sha256").update(JSON.stringify(at(e)),"utf8").digest("hex")}function Os(e){if(e==null&&(e={}),!ks(e))throw new TypeError("options must be a plain object");let t={...Ss},r=new Set(["initialEquityUsd","takerFeeBps","builderFeeBps","slippageBps","latencyBars","maxVolumeParticipationPct","nowMs"]);for(let n of Object.keys(e))if(!r.has(n))throw new TypeError(`unknown option "${n}"`);if("initialEquityUsd"in e){if(!ie(e.initialEquityUsd)||e.initialEquityUsd<=0)throw new TypeError("initialEquityUsd must be a positive finite number");t.initialEquityUsd=e.initialEquityUsd}for(let n of["takerFeeBps","builderFeeBps","slippageBps"])if(n in e){let o=e[n];if(!ie(o)||o<0)throw new TypeError(`${n} must be a finite number >= 0`);if(n==="slippageBps"?o>=1e4:o>1e4)throw new TypeError(`${n} exceeds its safe basis-point bound`);t[n]=o}if("latencyBars"in e){let n=e.latencyBars;if(!Number.isInteger(n)||n<1)throw new TypeError("latencyBars must be an integer >= 1");t.latencyBars=n}if("maxVolumeParticipationPct"in e){let n=e.maxVolumeParticipationPct;if(!ie(n)||n<=0||n>100)throw new TypeError("maxVolumeParticipationPct must be in (0,100]");t.maxVolumeParticipationPct=n}if("nowMs"in e){if(!Number.isInteger(e.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");t.nowMs=e.nowMs}return t}function ct(e){return e/1e4}function Ps(e,t,r){let n=ct(r);return t==="long"?e*(1+n):e*(1-n)}function As(e,t,r){let n=ct(r);return t==="long"?e*(1-n):e*(1+n)}function ln(e,t,r){let n=Math.abs(e)*ct(t),o=Math.abs(e)*ct(r);return{taker:n,builder:o,total:n+o}}function Ts(e,t){let r=e*(t.positionSizePct/100)*t.maxLeverage;return Math.min(r,t.maxNotionalUsd)}function $s(e,t,r){let n=r/100;return t==="long"?e*(1-n):e*(1+n)}function _s(e,t,r){let n=r/100;return t==="long"?e*(1+n):e*(1-n)}function vs(e,t,r,n){if(!(r>0))return t==="long"?0:Number.POSITIVE_INFINITY;let o=Math.min(.99,1/(2*r)+n/1e4);return t==="long"?e*(1-1/r)/(1-o):e*(1+1/r)/(1+o)}function Is(e,t,r){return t==="long"?e.l<=r:e.h>=r}function js(e,t,r){return t==="long"?e.h>=r:e.l<=r}function Ns(e,t,r){return t==="long"?e.l<=r:e.h>=r}function Ke(e,t){for(let r of e.requiredSeries)if(Ms.includes(r)&&!t.every(n=>ie(n?.[r])))throw new Error(`strategy required series is absent: ${r}`)}function Rs(e){if(e.length<3)return 0;let t=[];for(let s=1;s<e.length;s++){let a=e[s-1].equity,l=e[s].equity;a>0&&t.push((l-a)/a)}if(t.length<2)return 0;let r=0;for(let s of t)r+=s;let n=r/t.length,o=0;for(let s of t)o+=(s-n)**2;let i=Math.sqrt(o/(t.length-1));return i>0?n/i:0}function Ls(e){let t=-1/0,r=0;for(let n of e){let o=n.equity;if(o>t&&(t=o),t>0){let i=(t-o)/t*100;i>r&&(r=i)}}return r}function he(e,t,r={}){let n=Os(r);un(t);let o=De(t);n.nowMs!==void 0&&W(e,{nowMs:n.nowMs});let i=Z(e);if(Ke(i,t),n.nowMs!==void 0&&i.strategy.risk.expiresAt<=n.nowMs)throw new Error("strategy is expired: risk.expiresAt must be strictly greater than nowMs");let s=i.strategy.risk,a=i.evaluateAll(t),l=n.latencyBars,f=n.slippageBps,u=n.takerFeeBps,c=n.builderFeeBps,d=n.initialEquityUsd,m=0,p=0,w=0,g=0,S=0,j=[],T=[],x=[],M=[],$=[],h=null,R=0,U=null,K=d,k=!1,y=0,_=0,v=[],C=new Array(t.length).fill(0);function L(E){v.push(E)}function N(E){let H=t[E].v*(n.maxVolumeParticipationPct/100);return Math.max(0,H-C[E])}function P(E){if(!h)return d;let H=h.side==="long"?(E-h.entryPrice)*h.qty:(h.entryPrice-E)*h.qty;return d+H}function I(E,H,O){let D=O.o,F=Ts(d,s);if(!(F>0)||!(D>0))return;let B=Ps(D,H,f),q=F/B,G=N(E),Ce=B*G;if(q>G){x.push({kind:"entry",barIndex:E,time:O.t,side:H,requestedNotionalUsd:F,maxFillNotionalUsd:Ce,reason:"volume_participation"});return}C[E]+=q;let oe=Math.abs(B-D)*q,ue=ln(F,u,c);d-=ue.total,m+=ue.taker,p+=ue.builder,g+=oe,S+=F,h={lifecycleEpoch:++_,side:H,entryBarIndex:E,entryReferencePrice:D,entryPrice:B,qty:q,notionalUsd:F,stop:$s(B,H,s.stopLossPct),take:_s(B,H,s.takeProfitPct),liq:vs(B,H,s.maxLeverage,u+c),entryFees:ue.taker,entryBuilderFees:ue.builder,entrySlippageUsd:oe,fundingAccrued:0}}function A(E,H,O,D){if(!h)return!1;let F=h.side,B=H,q=B;O!=="liquidation"&&D&&(q=As(B,F,f));let G=h.qty,Ce=G*q;if(O!=="liquidation"){let ir=N(E),Hn=q*ir;if(G>ir)return x.push({kind:"exit",barIndex:E,time:t[E].t,side:F,requestedNotionalUsd:Ce,maxFillNotionalUsd:Hn,reason:"volume_participation",triggerReason:O}),!1;C[E]+=G}let oe=ln(Ce,u,c),ue=O==="liquidation"?0:Math.abs(q-B)*G,Ue,mt;F==="long"?(Ue=(B-h.entryReferencePrice)*G,mt=(q-h.entryPrice)*G):(Ue=(h.entryReferencePrice-B)*G,mt=(h.entryPrice-q)*G),d+=mt,d-=oe.total,m+=oe.taker,p+=oe.builder,g+=ue,S+=Ce;let Ln={side:F,entryBarIndex:h.entryBarIndex,entryTime:t[h.entryBarIndex].t,entryPrice:h.entryPrice,exitBarIndex:E,exitTime:t[E].t,exitPrice:q,exitReason:O,qty:G,notionalUsd:h.notionalUsd,grossPnlUsd:Ue,feesUsd:h.entryFees+oe.taker,builderFeesUsd:h.entryBuilderFees+oe.builder,fundingUsd:h.fundingAccrued,slippageUsd:h.entrySlippageUsd+ue,netPnlUsd:Ue-(h.entryFees+oe.taker+h.entryBuilderFees+oe.builder)-h.fundingAccrued-(h.entrySlippageUsd+ue)};return j.push(Ln),O==="liquidation"&&T.push({barIndex:E,time:t[E].t,side:F,price:q,tradeIndex:j.length-1}),h=null,_+=1,y=E+1+(s.cooldownBars||0),!0}function Q(E,H,O,D){let F=E+1;if(F>=t.length)return;v.some(q=>q.kind==="exit"&&q.side===H&&q.fillBar===F&&q.epoch===D)||L({kind:"exit",side:H,signalBar:E,fillBar:F,reason:O,epoch:D})}function X(E){let H=v.filter(O=>O.fillBar===E);for(let O=v.length-1;O>=0;O--)v[O].fillBar===E&&v.splice(O,1);H.sort((O,D)=>{let F=B=>B.kind==="exit"?0:1;return F(O)-F(D)});for(let O of H)if(O.kind==="exit"){if(!h||h.side!==O.side||h.lifecycleEpoch!==O.epoch)continue;let D=O.reason||"rule";A(E,t[E].o,D,!0)||Q(E,O.side,D,O.epoch)}else if(O.kind==="entry"){if(h||O.epoch!==_||E<y)continue;I(E,O.side,t[E])}}function re(E){if(!h)return;let H=t[E],O=H.fundingPaymentRate;if(O==null||!ie(O)||O===0)return;let D=Math.abs(h.qty*H.c),F=O*D;h.side==="long"?(d-=F,h.fundingAccrued+=F,w+=F):(d+=F,h.fundingAccrued-=F,w-=F)}function ce(E){if(!h)return;let H=t[E].o;(h.side==="long"?H<=h.liq:H>=h.liq)&&A(E,H,"liquidation",!1)}function Ze(E){if(!h)return;let H=t[E],O=h.side,D=Ns(H,O,h.liq),F=Is(H,O,h.stop),B=js(H,O,h.take),q=G=>O==="long"?Math.min(G,H.o):Math.max(G,H.o);if(D){A(E,q(h.liq),"liquidation",!1);return}if(F&&B){A(E,q(h.stop),"stop_loss",!0)||Q(E,O,"stop_loss",h.lifecycleEpoch);return}if(F){A(E,q(h.stop),"stop_loss",!0)||Q(E,O,"stop_loss",h.lifecycleEpoch);return}B&&(A(E,h.take,"take_profit",!0)||Q(E,O,"take_profit",h.lifecycleEpoch))}for(let E=0;E<t.length;E++){let H=Math.floor(t[E].t/864e5);H!==U&&(U=H,K=P(t[E].o),k=!1),ce(E),X(E),Ze(E),re(E),!k&&P(t[E].c)<=K*(1-s.maxDailyLossPct/100)&&(k=!0,M.push({type:"daily_loss_limit",barIndex:E,time:t[E].t,message:"daily loss limit reached; new entries blocked for UTC day"}));let O=a[E].signals,D=E+l;if(h)(h.side==="long"&&O.exitLong===!0||h.side==="short"&&O.exitShort===!0)&&D<t.length&&(v.some(G=>G.kind==="exit"&&G.side===h.side&&G.fillBar===D&&G.epoch===h.lifecycleEpoch)||L({kind:"exit",side:h.side,signalBar:E,fillBar:D,reason:"rule",epoch:h.lifecycleEpoch}));else{let B=O.entryLong===!0,q=O.entryShort===!0;B&&q?M.push({type:"conflicting_entry_signals",barIndex:E,time:t[E].t,message:"conflicting entry signals; no position opened"}):!k&&(B||q)&&D<t.length&&E>=y&&L({kind:"entry",side:B?"long":"short",signalBar:E,fillBar:D,epoch:_})}let F=d;h&&(R+=1,F=P(t[E].c)),$.push({barIndex:E,time:t[E].t,equity:F,positionSide:h?h.side:null})}let Xe=null;if(h){let E=t.length-1;if(A(E,t[E].c,"end_of_data",!0))$[E]={barIndex:E,time:t[E].t,equity:d,positionSide:null};else{let O=P(t[E].c);Xe={side:h.side,entryBarIndex:h.entryBarIndex,entryTime:t[h.entryBarIndex].t,entryPrice:h.entryPrice,qty:h.qty,notionalUsd:h.notionalUsd,markPrice:t[E].c,markedEquityUsd:O},M.push({type:"open_position_at_end",barIndex:E,time:t[E].t,message:"end-of-data exit missed; position remains open and marked"})}}let He=(h?P(t[t.length-1].c):d)-n.initialEquityUsd,dt=He/n.initialEquityUsd*100,Fe=0,ge=0,le=0;for(let E of j)E.netPnlUsd>0?(Fe+=1,ge+=E.netPnlUsd):E.netPnlUsd<0&&(le+=-E.netPnlUsd);let $e=j.length,be=$e===0?0:Fe/$e,pt=0;le>0?pt=ge/le:ge>0&&(pt=1e12);let Mn={netPnlUsd:He,netPnlPct:dt,maxDrawdownPct:Ls($),winRate:be,profitFactor:pt,tradeCount:$e,sharpe:Rs($),turnoverUsd:S,exposurePct:R/t.length*100},Rn={initialEquityUsd:n.initialEquityUsd,takerFeeBps:n.takerFeeBps,builderFeeBps:n.builderFeeBps,slippageBps:n.slippageBps,latencyBars:n.latencyBars,maxVolumeParticipationPct:n.maxVolumeParticipationPct},sr={barsHash:o,strategyHash:i.strategyHash,compilerHash:Oe,compilerVersion:ze,config:Rn,trades:j,equityCurve:$,metrics:Mn,costs:{feesUsd:m,builderFeesUsd:p,fundingUsd:w,slippageUsd:g},liquidations:T,missedFills:x,openPositionAtEnd:Xe,flags:M};return Vt(sr),zt(at(sr))}var Ss,Ms,ot=V(()=>{Pe();ke();Ss=Object.freeze({initialEquityUsd:1e4,takerFeeBps:3.5,builderFeeBps:2,slippageBps:2,latencyBars:1,maxVolumeParticipationPct:100});Ms=Object.freeze(["fundingRate","openInterest","premium","oiDelta","bookImbalance"])});import{createHash as Hs}from"node:crypto";function Vs(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Jt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Jt(t);return Object.freeze(e)}for(let t of Object.keys(e))Jt(e[t]);return Object.freeze(e)}function Js(e){return String(e).trim().replace(/\s+/g," ")}function Gs(e){let t=e.match(/\b(long|short)\b/i);return t?t[1].toLowerCase():null}function Ks(e){for(let r of Cs)if(new RegExp(`\\b${r}\\b`,"i").test(e))return r;let t=e.match(/\b([A-Z][A-Z0-9]{1,11})\b/);return t?t[1]:null}function Ys(e){let t=e.match(/\bon\s+(1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/i);if(!t)return"15m";let r=t[1].toLowerCase();return Fs.has(r)?r:null}function Ws(e){let t={...qs},r=e.match(/stop\s*loss\s*(\d+(?:\.\d+)?)\s*%?/i);r&&(t.stopLossPct=Number(r[1]));let n=e.match(/take\s*profit\s*(\d+(?:\.\d+)?)\s*%?/i);n&&(t.takeProfitPct=Number(n[1]));let o=e.match(/leverage\s*(\d+(?:\.\d+)?)/i);o&&(t.maxLeverage=Number(o[1]));let i=e.match(/position\s*size\s*(\d+(?:\.\d+)?)\s*%?/i);i&&(t.positionSizePct=Number(i[1]));let s=e.match(/max\s*notional\s*(?:usd\s*)?\$?\s*(\d+(?:\.\d+)?)/i);return s&&(t.maxNotionalUsd=Number(s[1])),t}function Zs(e){return[/\bon\s+(?:1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/gi,/\bstop\s*loss\s*\d+(?:\.\d+)?\s*%?/gi,/\btake\s*profit\s*\d+(?:\.\d+)?\s*%?/gi,/\bleverage\s*\d+(?:\.\d+)?/gi,/\bposition\s*size\s*\d+(?:\.\d+)?\s*%?/gi,/\bmax\s*notional\s*(?:usd\s*)?\$?\s*\d+(?:\.\d+)?/gi].some(r=>(e.match(r)??[]).length>1)}function Xs(e){let t=Hs("sha256").update(e,"utf8").digest("hex").slice(0,10),r=e.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-+|-+$/g,"").slice(0,40),o=`${r.length?r:"draft"}-${t}`.replace(/[^a-z0-9._-]/g,"").slice(0,64);return/^[a-z0-9]/.test(o)?o:`d${o}`.slice(0,64)}function Qs(e){let t=e.match(/\bema\s*(\d+)\s*cross(?:es)?\s*(above|below)\s*ema\s*(\d+)\b/i);if(!t)return null;let r=Number(t[1]),n=t[2].toLowerCase(),o=Number(t[3]);if(!(r>0)||!(o>0)||r===o)return null;let i=/\b(exit\s+on\s+reverse|reverse\s+exit)\b/i.test(e);return{kind:"ema_cross",fast:r,slow:o,direction:n,reverse:i}}function ei(e){let t=e.match(/\brsi\s*(\d+)\s*(above|below)\s*(-?\d+(?:\.\d+)?)/i);if(!t)return null;let r=Number(t[3]);return!Number.isFinite(r)||r<=0||r>=100?null:{kind:"rsi",period:Number(t[1]),op:t[2].toLowerCase(),threshold:r}}function ti(e){let t=e.match(/\bfunding\s*rate\s*(above|below)\s*(-?\d+(?:\.\d+)?)(%?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return t[3]==="%"&&(r=r/100),{kind:"funding",op:t[1].toLowerCase(),threshold:r}}function ri(e){let t=e.match(/\bopen\s*interest\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return!Number.isFinite(r)||r<0?null:{kind:"open_interest",op:t[1].toLowerCase(),threshold:r}}function ni(e){let t=e.match(/\bpremium\s*(above|below)\s*(-?\d+(?:\.\d+)?)(%?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return Number.isFinite(r)?(t[3]==="%"&&(r=r/100),{kind:"premium",op:t[1].toLowerCase(),threshold:r}):null}function oi(e){let t=e.match(/\boi\s*delta\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return Number.isFinite(r)?{kind:"oi_delta",op:t[1].toLowerCase(),threshold:r}:null}function si(e){let t=e.match(/\bbook\s*imbalance\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return!Number.isFinite(r)||r<-1||r>1?null:{kind:"book_imbalance",op:t[1].toLowerCase(),threshold:r}}function ii(e,t){let r=e.replace(/^(long|short)\s+[A-Z][A-Z0-9]{1,11}\s+when\s+/i,"");if(r===e)return!1;t.kind==="ema_cross"?r=r.replace(/^ema\s*\d+\s*cross(?:es)?\s*(?:above|below)\s*ema\s*\d+\b/i,""):t.kind==="rsi"?r=r.replace(/^rsi\s*\d+\s*(?:above|below)\s*\d+(?:\.\d+)?\b/i,""):t.kind==="open_interest"?r=r.replace(/^open\s*interest\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):t.kind==="premium"?r=r.replace(/^premium\s*(?:above|below)\s*-?\d+(?:\.\d+)?%?(?=\s|,|$)/i,""):t.kind==="oi_delta"?r=r.replace(/^oi\s*delta\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):t.kind==="book_imbalance"?r=r.replace(/^book\s*imbalance\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):r=r.replace(/^funding\s*rate\s*(?:above|below)\s*-?\d+(?:\.\d+)?%?(?=\s|,|$)/i,"");let n=[/(?:,\s*)?\bon\s+(?:1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/gi,/(?:,\s*)?\bstop\s*loss\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\btake\s*profit\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\bleverage\s*\d+(?:\.\d+)?/gi,/(?:,\s*)?\bposition\s*size\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\bmax\s*notional\s*(?:usd\s*)?\$?\s*\d+(?:\.\d+)?/gi];t.kind==="ema_cross"&&n.push(/(?:,\s*)?\b(?:exit\s+on\s+reverse|reverse\s+exit)\b/gi);for(let o of n)r=r.replace(o,"");return r.replace(/[\s,;]+/g,"")===""}function fn(e){let t=Math.max(2,Math.floor(e/2));return{value:e,min:Math.max(2,e-t),max:Math.min(500,e+t),step:1}}function ai({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let l=[{id:"c",type:"input",field:"close"},{id:"emaLeft",type:"indicator",indicator:"ema",input:"c",period:{param:"ema_left_period"}},{id:"emaRight",type:"indicator",indicator:"ema",input:"c",period:{param:"ema_right_period"}},{id:"cross",type:"cross",direction:a.direction,left:"emaLeft",right:"emaRight"}],f={entryLong:null,entryShort:null,exitLong:null,exitShort:null};if(e==="long"?f.entryLong="cross":f.entryShort="cross",a.reverse){let u=a.direction==="above"?"below":"above";l.push({id:"crossRev",type:"cross",direction:u,left:"emaLeft",right:"emaRight"}),e==="long"?f.exitLong="crossRev":f.exitShort="crossRev"}return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{ema_left_period:fn(a.fast),ema_right_period:fn(a.slow)},nodes:l,rules:f,risk:{...n,expiresAt:o}}}function ci({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let l=[{id:"c",type:"input",field:"close"},{id:"rsi",type:"indicator",indicator:"rsi",input:"c",period:a.period},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"rsi",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:l,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function li({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let l=[{id:"fr",type:"input",field:"fundingRate"},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"fr",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:l,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function ui({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let l=[{id:"oi",type:"input",field:"openInterest"},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"oi",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:l,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function di({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let f=[{id:"sig_input",type:"input",field:fi[a.kind]},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"sig_input",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:f,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function dn(e,t={}){if(typeof e!="string")throw new Y("prompt must be a string");if(e.length>1e3)throw new Y("prompt length must be <= 1000");if(!Vs(t))throw new Y("options must be a plain object");if(!Number.isInteger(t.nowMs))throw new Y("options.nowMs is required integer epoch ms");let r=t.nowMs,n=zs;if("expiresInMs"in t){if(!Number.isInteger(t.expiresInMs))throw new Y("expiresInMs must be an integer");if(n=t.expiresInMs,n<Ds||n>Bs)throw new Y("expiresInMs must be between 1h and 30d")}if(Us.test(e))throw new Y(`prompt appears to contain secrets and is rejected. ${Re}`);let o=Js(e);if(!o)throw new Y(`empty prompt. ${Re}`);if(Zs(o))throw new Y(`duplicate interval or risk clause. ${Re}`);let i=Gs(o),s=Ks(o),a=Ys(o);if(!i||!s||!a)throw new Y(`could not parse side/coin/interval. ${Re}`);let l=Ws(o);if(!(l.maxLeverage>0)||l.maxLeverage>50)throw new Y("leverage out of range");if(!(l.positionSizePct>0)||l.positionSizePct>100)throw new Y("position size out of range");let f=r+n,u=Xs(o),c=`Draft ${s} ${i}`.slice(0,100),d=Qs(o),m=ei(o),p=ti(o),w=ri(o),g=ni(o),S=oi(o),j=si(o),T=[d,m,p,w,g,S,j].filter(Boolean);if(T.length!==1)throw new Y(`unsupported or ambiguous prompt. ${Re}`);if(!ii(o,T[0]))throw new Y(`unsupported or ambiguous prompt. ${Re}`);let x,M=T[0],$={side:i,coin:s,interval:a,risk:l,expiresAt:f,id:u,name:c,spec:M};M.kind==="ema_cross"?x=ai($):M.kind==="rsi"?x=ci($):M.kind==="open_interest"?x=ui($):M.kind==="funding"?x=li($):x=di($);let h=Dt(x,{nowMs:r});if(!h.ok)throw new Y(`draft failed validation: ${h.errors.map(R=>R.message).join("; ")}`);return Jt(W(x,{nowMs:r}))}var Y,Fs,Cs,Us,Re,qs,Ds,Bs,zs,fi,pn=V(()=>{ke();Y=class extends Error{constructor(t){super(t),this.name="StrategyDraftError"}},Fs=new Set(["1m","3m","5m","15m","30m","1h","2h","4h","8h","12h","1d"]),Cs=new Set(["BTC","ETH","SOL","HYPE"]),Us=/\b(mnemonic|private\s*key|privkey|seed\s*phrase|seed\b|api[_-]?key|secret\s*key|wallet\s*key|passphrase)\b/i,Re="Supported grammar: (1) EMA cross: <long|short> <COIN> when EMA <n> crosses <above|below> EMA <m> [on <interval>] [, exit on reverse] [, risk knobs]; (2) RSI: <long|short> <COIN> when RSI <n> <above|below> <threshold> [on <interval>] [, risk knobs]; (3) funding: <long|short> <COIN> when funding rate <above|below> <decimal|percent%> [on <interval>] [, risk knobs]; (4) open interest: <long|short> <COIN> when open interest <above|below> <non-negative number> [on <interval>] [, risk knobs]; (5) premium: <long|short> <COIN> when premium <above|below> <decimal|percent%> [on <interval>] [, risk knobs]; (6) oi delta: <long|short> <COIN> when oi delta <above|below> <number> [on <interval>] [, risk knobs]; (7) book imbalance: <long|short> <COIN> when book imbalance <above|below> <-1..1> [on <interval>] [, risk knobs]. Risk knobs: stop loss %, take profit %, leverage, position size %, max notional USD. Coins: BTC ETH SOL HYPE or uppercase token <=12 chars. Intervals: 1m 3m 5m 15m 30m 1h 2h 4h 8h 12h 1d.",qs=Object.freeze({maxLeverage:1,maxNotionalUsd:100,positionSizePct:5,stopLossPct:2,takeProfitPct:4,cooldownBars:1,maxDailyLossPct:3}),Ds=36e5,Bs=30*864e5,zs=864e5;fi=Object.freeze({funding:"fundingRate",open_interest:"openInterest",premium:"premium",oi_delta:"oiDelta",book_imbalance:"bookImbalance"})});import{createHash as pi}from"node:crypto";function yn(e){let t=String(e).toLowerCase();return t==="holdout"||t==="test"||t==="oos"||t.includes("holdout")||t.includes("oos")?!0:t==="testbars"||t.endsWith("testbars")||t.startsWith("test")||t.endsWith("test")?!t.includes("backtest"):!1}function wn(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Kt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Kt(t);return Object.freeze(e)}for(let t of Object.keys(e))Kt(e[t]);return Object.freeze(e)}function Ye(e){if(Array.isArray(e))return e.map(Ye);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=Ye(e[r]);return t}return e}function lt(e){return JSON.stringify(Ye(e))}function mi(e){let{min:t,max:r,step:n}=e;if(!(n>0)||t>r)return[];let o=[],i=Math.floor((r-t)/n+1e-9);for(let a=0;a<=i;a++){let l=t+a*n;if(l>r+1e-9)break;let f=Math.abs(l-Math.round(l))<1e-9?Math.round(l):Number(l.toPrecision(12));f<t-1e-9||f>r+1e-9||o.push(f)}if(o.length===0)return[];let s=o[o.length-1];if(Math.abs(s-r)>1e-9){let a=(r-t)/n;Math.abs(a-Math.round(a))<=1e-9&&o.push(r)}return o}function hi(e,t){if(e.length===0)return[];let r=[{}];for(let n of e){let o=t[n],i=[];for(let s of r)for(let a of o)i.push({...s,[n]:a});r=i}return r.sort((n,o)=>{let i=lt(n),s=lt(o);return i<s?-1:i>s?1:0}),r}function Gt(e,t,r,n,o){let i=0;if(e==="maxDrawdownPct"){if(i=t.maxDrawdownPct-n.maxDrawdownPct,i!==0)return i<0}else if(i=t[e]-n[e],i!==0)return i>0;let s=lt(r),a=lt(o);return s<a}function gn(e,t,r={}){if(!wn(r))throw new TypeError("options must be a plain object");for(let x of Object.keys(r))if(yn(x))throw new TypeError(`options must not include holdout/test/oos key "${x}"`);let n=new Set(["maxTrials","objective","backtestOptions"]);for(let x of Object.keys(r))if(!n.has(x))throw new TypeError(`unknown option "${x}"`);let o=64;if("maxTrials"in r){let x=r.maxTrials;if(!Number.isInteger(x)||x<1||x>mn)throw new TypeError(`maxTrials must be an integer 1..${mn}`);o=x}let i=r.objective??"netPnlUsd";if(!hn.has(i))throw new TypeError(`objective must be one of ${[...hn].join("|")}`);let s=r.backtestOptions??{};if(!wn(s))throw new TypeError("backtestOptions must be a plain object");for(let x of Object.keys(s))if(yn(x))throw new TypeError(`backtestOptions must not include holdout/test/oos key "${x}"`);let a=W(e),l=Object.keys(a.parameters).sort();if(l.length===0)throw new Error("optimizeStrategy requires at least one declared parameter");let f={},u=1;for(let x of l){let M=mi(a.parameters[x]);if(M.length===0)throw new Error(`parameter "${x}" produces an empty grid`);f[x]=M,u*=M.length}let c=hi(l,f);if(c.length===0)throw new Error("parameter grid is empty");let d=c.slice(0,o),m=[],p=null,w=null;for(let x of d){let M=Je(a,x),$=he(M,t,s);w==null&&(w=$.config);let h={netPnlUsd:$.metrics.netPnlUsd,netPnlPct:$.metrics.netPnlPct,maxDrawdownPct:$.metrics.maxDrawdownPct,winRate:$.metrics.winRate,profitFactor:$.metrics.profitFactor,tradeCount:$.metrics.tradeCount,sharpe:$.metrics.sharpe,turnoverUsd:$.metrics.turnoverUsd},R={parameters:{...x},metrics:h};m.push(R),(!p||Gt(i,h,x,p.metrics,p.parameters))&&(p=R)}m.sort((x,M)=>Gt(i,x.metrics,x.parameters,M.metrics,M.parameters)?-1:Gt(i,M.metrics,M.parameters,x.metrics,x.parameters)?1:0);let g={...p.parameters},S=Je(a,g),j={strategyHash:ve(a),compilerHash:Oe,trainBarsHash:De(t),backtestConfig:w,objective:i,maxTrials:o,trialsRun:m.length,candidates:m,bestParameters:g,bestStrategy:S},T={id:pi("sha256").update(JSON.stringify(Ye(j)),"utf8").digest("hex"),...j};return Kt(Ye(JSON.parse(JSON.stringify(T))))}var mn,hn,bn=V(()=>{Pe();ke();ot();mn=256,hn=new Set(["netPnlUsd","profitFactor","sharpe","maxDrawdownPct"])});import pe from"node:fs";import ut from"node:path";function ft(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function ae(e){return e==null?e:JSON.parse(JSON.stringify(e))}function wi(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function Le(e,t="record"){if(Array.isArray(e)){e.forEach((r,n)=>Le(r,`${t}[${n}]`));return}if(ft(e))for(let[r,n]of Object.entries(e)){let o=wi(r);if(yi.some(i=>o.includes(i)))throw new Error(`shadow-store: forbidden secret-like field at ${t}.${r}`);Le(n,`${t}.${r}`)}}function gi(e){if(typeof e!="string"||!e||!ut.isAbsolute(e))throw new Error("shadow-store: path must be an absolute path")}function En(e){let t;try{t=pe.lstatSync(e)}catch(n){if(n&&n.code==="ENOENT")return;throw n}if(t.isSymbolicLink())throw new Error("shadow-store: store path must not be a symlink");if(!t.isFile())throw new Error("shadow-store: store path must be a regular file");if(t.mode&511&18)throw new Error("shadow-store: store file must not be group or world writable")}function bi(){return{version:Wt,runners:[]}}function xn(e,t){let r;try{r=JSON.parse(e)}catch{throw new Error("shadow-store: malformed JSON")}if(!ft(r))throw new Error("shadow-store: malformed JSON root");if(r.version!==Wt)throw new Error(`shadow-store: unsupported version ${r.version}`);if(!Array.isArray(r.runners))throw new Error("shadow-store: runners must be an array");return Le(r,ut.basename(t)),{version:Wt,runners:r.runners.map(n=>ae(n))}}function Sn(e,t){Le(t,"store");let r=ut.dirname(e);pe.mkdirSync(r,{recursive:!0,mode:448});let n=ut.join(r,`.shadow-store.${process.pid}.${Date.now()}.tmp`),o=`${JSON.stringify(t)}
|
|
3
|
-
`;try{pe.writeFileSync(n,o,{mode:384,flag:"wx"}),pe.renameSync(n,e);try{pe.chmodSync(e,384)}catch{}}catch(i){try{pe.unlinkSync(n)}catch{}throw i}}function kn(e={}){let t=e.path;if(gi(t),En(t),pe.existsSync(t)?xn(pe.readFileSync(t,"utf8"),t):Sn(t,bi()),Yt.has(t))return Yt.get(t);let r=!1,n=[];function o(){if(r)return;let p=n.shift();if(p){r=!0;try{let w=p.fn();r=!1,p.resolve(w),o()}catch(w){r=!1,p.reject(w),o()}}}function i(p){if(!r&&n.length===0){r=!0;try{return p()}finally{r=!1,queueMicrotask(o)}}return new Promise((w,g)=>{n.push({fn:p,resolve:w,reject:g}),queueMicrotask(o)})}function s(){return En(t),xn(pe.readFileSync(t,"utf8"),t)}function a(p){Sn(t,p)}function l(p){if(!ft(p)||typeof p.id!="string"||!p.id)throw new Error("shadow-store: create requires record with string id");Le(p,"record");let w=s();if(w.runners.some(S=>S.id===p.id))throw new Error(`shadow-store: runner id already exists: ${p.id}`);let g=ae(p);return w.runners.push(g),a(w),ae(g)}function f(p){let w=s().runners.find(g=>g.id===p);return w?ae(w):null}function u(){return s().runners.map(p=>ae(p))}function c(p,w){if(typeof w!="function")throw new Error("shadow-store: updater must be a function");let g=s(),S=g.runners.findIndex(x=>x.id===p);if(S<0)throw new Error(`shadow-store: runner not found: ${p}`);let j=ae(g.runners[S]),T=w(j);if(!ft(T)||T.id!==p)throw new Error("shadow-store: updater must return record with same id");return Le(T,"record"),g.runners[S]=ae(T),a(g),ae(g.runners[S])}function d(p){let w=s(),g=w.runners.findIndex(j=>j.id===p);if(g<0)throw new Error(`shadow-store: runner not found: ${p}`);let S=ae(w.runners[g]);return S.status!=="stopped"&&(S.status="stopped",w.runners[g]=S,a(w)),ae(w.runners[g])}let m={create(p){return i(()=>l(p))},get(p){return f(p)},list(){return u()},update(p,w){return i(()=>c(p,w))},stop(p){return i(()=>d(p))}};return Yt.set(t,m),m}var Wt,yi,Yt,On=V(()=>{Wt=1,yi=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"];Yt=new Map});import{createHash as Qt}from"node:crypto";function Zt(e){return e==null?e:JSON.parse(JSON.stringify(e))}function Xt(e){return Array.isArray(e)?e.map(Xt):e&&typeof e=="object"?Object.fromEntries(Object.keys(e).sort().map(t=>[t,Xt(e[t])])):e}function An(e){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("shadow-runner: record must be an object");return Qt("sha256").update(JSON.stringify(Xt(e))).digest("hex")}function Ei(e,t,r,n,o){return Qt("sha256").update(`${e}|${t}|${r}|${n}|${o}`).digest("hex")}function xi(e,t,r,n){return Qt("sha256").update(`shadow|${e}|${t}|${r}|${n??""}`).digest("hex")}function Si(e){return e==="entryLong"||e==="exitShort"?"buy":e==="entryShort"||e==="exitLong"?"sell":e}function Pn(e){return e==="entryLong"||e==="entryShort"}function er({storePath:e,clock:t=Date.now}={}){if(typeof e!="string"||!e)throw new Error("shadow-runner: storePath required");let r=kn({path:e});function n({strategy:l,evidenceId:f=null}={}){let u=Z(l),c=f==null?null:String(f),d=r.list().filter(S=>S.status==="running"&&S.strategyHash===u.strategyHash&&S.compilerHash===u.compilerHash&&S.evidenceId===c).sort((S,j)=>S.createdAt-j.createdAt||S.id.localeCompare(j.id))[0];if(d)return Zt(d);let m=t(),p=xi(m,u.strategyHash,u.compilerHash,c),w=r.get(p);if(w)return Zt(w);let g={id:p,strategy:Zt(u.strategy),strategyHash:u.strategyHash,compilerHash:u.compilerHash,evidenceId:c,status:"running",cursor:null,intendedOrders:[],fills:[],missedFills:[],markouts:[],createdAt:m,updatedAt:m,position:null,cooldownBarsRemaining:0,cooldownStartT:null,lastProcessedBarIndex:-1};return r.create(g)}function o(l){return r.get(l)}function i(){return r.list()}function s(l){return r.stop(l)}function a(l,f,{markoutHorizons:u=[1,4,12]}={}){if(!Array.isArray(f))throw new TypeError("shadow-runner: bars must be an array");return r.update(l,c=>{if(c.status!=="running")throw new Error("shadow-runner: runner is stopped");if(f.length===0)return c;let m=Z(c.strategy).evaluateAll(f),p=new Map;for(let y=0;y<f.length;y++)p.set(f[y].t,y);let w=c.cursor,g=[];for(let y=0;y<f.length;y++){let _=f[y].t;(w==null||_>w)&&g.push(y)}if(g.length===0)return c;let S=new Map(c.intendedOrders.map(y=>[y.id,y])),j=new Set(c.fills.map(y=>y.orderId)),T=new Map(c.missedFills.map(y=>[y.orderId,y])),x=(y,_)=>`${y}|${_}`,M=new Map(c.markouts.map(y=>[x(y.orderId,y.horizon),y])),$=c.position?{...c.position}:null,h=Number.isInteger(c.cooldownBarsRemaining)?Math.max(0,c.cooldownBarsRemaining):0,R=Number.isFinite(c.cooldownStartT)?c.cooldownStartT:null;function U({action:y,signalBarT:_,signalIndex:v}){let C=Si(y),L=Ei(c.id,c.strategyHash,_,C,y);if(S.has(L))return S.get(L);let N=v+1,P=N<f.length,I={id:L,action:y,type:y,side:C,signalBarT:_,fillBarT:P?f[N].t:null,status:P?"open":"missed"};return S.set(L,I),c.intendedOrders.push(I),I}function K(y,_,v){if(j.has(y.id))return;let C={orderId:y.id,action:Pn(y.action)?"entry":"exit",side:y.side,price:_.o,barT:_.t,signalBarT:y.signalBarT,barIndex:v};if(c.fills.push(C),j.add(y.id),y.status="filled",y.fillBarT=_.t,T.has(y.id)&&(T.delete(y.id),c.missedFills=c.missedFills.filter(L=>L.orderId!==y.id)),Pn(y.action)){$={side:y.action==="entryLong"?"long":"short",entryOrderId:y.id,entryBarT:_.t,entryPrice:_.o,entryBarIndex:v};for(let L of u){let N=x(y.id,L);if(M.has(N))continue;let P={orderId:y.id,horizon:L,entryBarT:_.t,entryPrice:_.o,side:$.side,status:"pending",close:null,barT:null};M.set(N,P),c.markouts.push(P)}}else $=null,h=Number(c.strategy?.risk?.cooldownBars)||0,R=_.t}function k(y){if(j.has(y.id)||T.has(y.id))return;let _={orderId:y.id,action:y.action,side:y.side,signalBarT:y.signalBarT,status:"missed"};T.set(y.id,_),c.missedFills.push(_),y.status="missed"}for(let y of c.intendedOrders){if(y.status==="filled"||j.has(y.id))continue;let _=p.get(y.signalBarT);if(_==null)continue;let v=_+1;v<f.length&&(w==null||f[v].t>w)&&K(y,f[v],v)}for(let y of g){let _=f[y],v=m[y].signals,C=$,L=P=>{if($||h>0&&(R==null||_.t>=R))return;let A=U({action:P,signalBarT:_.t,signalIndex:y}),Q=y+1;Q<f.length?K(A,f[Q],Q):k(A)},N=P=>{if(!$||$.side==="long"&&P!=="exitLong"||$.side==="short"&&P!=="exitShort")return;let I=U({action:P,signalBarT:_.t,signalIndex:y}),A=y+1;A<f.length?K(I,f[A],A):k(I)};C?(v.exitLong&&N("exitLong"),v.exitShort&&N("exitShort")):v.entryLong&&v.entryShort||(v.entryLong&&L("entryLong"),v.entryShort&&L("entryShort")),h>0&&R!=null&&_.t>=R&&(h-=1,h===0&&(R=null)),c.cursor=_.t,c.lastProcessedBarIndex=y}for(let y of c.markouts){if(y.status!=="pending")continue;let _=c.fills.find(L=>L.orderId===y.orderId&&L.action==="entry");if(!_)continue;let v=p.get(_.barT);if(v==null)continue;let C=v+y.horizon;if(C<f.length){y.close=f[C].c,y.barT=f[C].t,y.status="filled";let L=y.entryPrice;y.markout=y.side==="long"?(y.close-L)/L:(L-y.close)/L}}return c.position=$,c.cooldownBarsRemaining=h,c.cooldownStartT=R,c.updatedAt=t(),c})}return{start:n,step:a,list:i,get:o,stop:s}}var Tn=V(()=>{Pe();On()});var vn={};Cn(vn,{runStrategyOperation:()=>vi});import ki from"node:os";import Oi from"node:path";function We(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Ai(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function rr(e){if(Array.isArray(e)){for(let t of e)rr(t);return}if(We(e))for(let[t,r]of Object.entries(e)){if(Pi.some(n=>Ai(t).includes(n)))throw new Error(`strategy service: secret-like field "${t}" is forbidden`);rr(r)}}function Ti(e){if(!We(e))throw new TypeError("strategy input must be a plain object");return rr(e),e}function $i(e,t={}){if(t.nowMs!==void 0){if(!Number.isInteger(t.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");return t.nowMs}let r=Date.now();if(e.nowMs===void 0||e.nowMs===null)return r;if(!Number.isInteger(e.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");if(Math.abs(e.nowMs-r)>12e4)throw new Error("nowMs outside allowed wall-clock skew (120s); omit nowMs to use server time");return e.nowMs}async function tr(e,t,r,n){if(Array.isArray(t.bars))return t.bars;let o=Mt(e.venue),i=r.fetchBars??o.fetchBars;if(typeof i!="function")throw new Error(`strategy venue ${o.id} does not support history`);r.signal?.throwIfAborted?.();let s=await i({coin:e.market.coin,interval:e.market.interval,count:t.count??1500,endTime:t.endTime??n},{signal:r.signal});r.signal?.throwIfAborted?.();let a=Array.isArray(s)?s:s?.bars;if(!Array.isArray(a))throw new Error("strategy history provider returned no bars");return a}function nr(e,t){let r=e.backtestOptions??{};if(!We(r))throw new TypeError("backtestOptions must be a plain object");return{...r,nowMs:t}}function $n(e,t,r,n,o={}){let i=e.evidenceOptions??{};if(!We(i))throw new TypeError("evidenceOptions must be a plain object");return{...i,...o,strategy:t,bars:r,backtestOptions:nr(e,n)}}function _n(){return Oi.join(ki.homedir(),".oracle","strategy-shadow.json")}function _i(e,t){return{perStrategyNotionalUsd:e.risk.maxNotionalUsd,maxLeverage:e.risk.maxLeverage,dailyLossCapUsd:e.risk.maxNotionalUsd*(e.risk.maxDailyLossPct/100),chainAllowlist:[e.venue],assetAllowlist:[e.market.coin],expiresAt:Math.min(e.risk.expiresAt,t+864e5),killSwitchRequired:!0}}async function vi(e,t={},r={}){r.signal?.throwIfAborted?.();let n=Ti(t),o=$i(n,r);if(e==="draft")return{strategy:dn(n.prompt,{nowMs:o})};if(e==="validate"){let i=Z(n.strategy);if(i.strategy.risk.expiresAt<=o)throw new Error("strategy is expired");return{valid:!0,strategy:i.strategy,strategyHash:i.strategyHash,compilerHash:i.compilerHash,compilerVersion:i.compilerVersion,requiredSeries:i.requiredSeries}}if(e==="backtest"||e==="evidence"){let i=Z(n.strategy),s=await tr(i.strategy,n,r,o);Ke(i,s);let a=$t($n(n,i.strategy,s,o));return e==="evidence"?a:{backtest:he(i.strategy,s,nr(n,o)),evidence:a}}if(e==="optimize"){let i=Z(n.strategy),s=await tr(i.strategy,n,r,o);Ke(i,s);let a=n.trainFraction,l=n.evidenceOptions?.trainFraction;if(a!=null&&l!=null&&a!==l)throw new TypeError("conflicting trainFraction controls are forbidden");let f=a??l??.7;if(typeof f!="number"||f<=0||f>=1)throw new TypeError("trainFraction must be in (0,1)");let u=s.slice(0,Math.floor(s.length*f)),c=n.options??{};if(!We(c))throw new TypeError("options must be a plain object");let d=gn(i.strategy,u,{...c,...n.maxTrials==null?{}:{maxTrials:n.maxTrials},backtestOptions:nr(n,o)}),m=d.bestStrategy;return{strategy:m,optimization:d,evidence:$t($n(n,m,s,o,{trainFraction:f}))}}if(e==="shadow"){let i=er({storePath:r.storePath??_n(),clock:()=>o}),s=n.action;if(s==="start")return await i.start({strategy:n.strategy,evidenceId:n.evidenceId??n.evidence?.id??null});if(s==="list")return await i.list();if(s==="get")return await i.get(n.id);if(s==="stop")return await i.stop(n.id);if(s==="step"){let a=await i.get(n.id);if(!a)throw new Error(`shadow runner not found: ${n.id}`);let l=await tr(a.strategy,n,r,o);return Ke(Z(a.strategy),l),await i.step(n.id,l,n.stepOptions??{})}throw new Error(`unknown shadow action: ${s}`)}if(e==="prepare"){let i=Z(n.strategy),s=Mt(i.strategy.venue);if(typeof n.shadowId!="string"||!n.shadowId)throw new Error("strategy prepare requires a matching shadow runner id");let l=await er({storePath:r.storePath??_n(),clock:()=>o}).get(n.shadowId);if(!l)throw new Error("strategy prepare shadow runner not found");if(l.status!=="running")throw new Error("strategy prepare requires an active shadow runner");if(!Number.isFinite(l.cursor))throw new Error("strategy prepare requires a stepped shadow runner");if(l.strategyHash!==i.strategyHash||l.compilerHash!==i.compilerHash)throw new Error("strategy prepare shadow runner does not match strategy artifacts");if(l.evidenceId!==n.evidence?.id)throw new Error("strategy prepare shadow runner does not match evidence artifact");let f=n.caps??_i(i.strategy,o);return s.prepareIntent({strategy:i.strategy,evidence:n.evidence,shadow:{id:l.id,stateHash:An(l),status:l.status,cursor:l.cursor,updatedAt:l.updatedAt},caps:f,nowMs:o,env:r.env??process.env})}throw new Error(`unknown strategy operation: ${e}`)}var Pi,In=V(()=>{ot();Pe();_t();pn();bn();Tn();Rt();Pi=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"]});import jn from"node:fs";function Ii(e){let t={},r=[];for(let n=0;n<e.length;n++){let o=e[n];if(!o.startsWith("--")){r.push(o);continue}let i=o.slice(2),s=e[n+1];s!=null&&!s.startsWith("--")?(t[i]=s,n++):t[i]=!0}return{flags:t,positional:r}}function Te(e,t){if(!e)throw new Error(`${t} path required`);let r=e==="-"?jn.readFileSync(0,"utf8"):jn.readFileSync(e,"utf8");try{return JSON.parse(r)}catch{throw new Error(`${t} must contain valid JSON`)}}function Nn(e,t){if(e==null)return;let r=Number(e);if(!Number.isFinite(r))throw new Error(`${t} must be a finite number`);return r}var ji=`oracle strategy <draft|validate|backtest|optimize|evidence|shadow|prepare> [args]
|
|
1
|
+
var Fn=Object.defineProperty;var V=(e,t,r)=>()=>{if(r)throw r[0];try{return e&&(t=e(e=0)),t}catch(n){throw r=[n],n}};var Cn=(e,t)=>{for(var r in t)Fn(e,r,{get:t[r],enumerable:!0})};import{AsyncLocalStorage as Un}from"node:async_hooks";function Qe(e){let t=Dn.getStore();if(!t||t.closed||!qn.includes(e))return null;if(t.spans.length>=Bn)return t.droppedSpans++,null;let r={stage:e,startMs:t.now()-t.start,durationMs:null,outcome:"pending",status:null};return t.spans.push(r),(n,o=null)=>{t.closed||r.durationMs!==null||(r.durationMs=Math.max(0,t.now()-t.start-r.startMs),r.outcome=n==="succeeded"?"succeeded":"failed",r.status=Number.isInteger(o)&&o>=100&&o<=599?o:null)}}var Dn,qn,Bn,ar=V(()=>{Dn=new Un,qn=["http","retry","shared"],Bn=512});import Ee from"node:net";import zn from"node:dns";function et(e){let t=String(e).toLowerCase().split("%")[0];if((t.match(/::/g)||[]).length>1)return null;let r=u=>{if(!u)return[];let l=u.split(":"),d=l.at(-1);if(d?.includes(".")){let m=d.split(".").map(Number);if(m.length!==4||m.some(p=>!Number.isInteger(p)||p<0||p>255))return null;l.splice(l.length-1,1,(m[0]<<8|m[1]).toString(16),(m[2]<<8|m[3]).toString(16))}return l.some(m=>!/^[0-9a-f]{1,4}$/.test(m))?null:l.map(m=>Number.parseInt(m,16))},[n,o]=t.split("::"),i=r(n),s=r(o);if(!i||!s)return null;let a=t.includes("::"),c=8-i.length-s.length;if(!a&&c!==0||a&&c<1)return null;let f=[...i,...Array(Math.max(0,c)).fill(0),...s];return f.length!==8?null:Uint8Array.from(f.flatMap(u=>[u>>8,u&255]))}function ht(e,t,r){let n=Math.floor(r/8),o=r%8;for(let s=0;s<n;s+=1)if(e[s]!==t[s])return!1;if(!o)return!0;let i=255<<8-o;return(e[n]&i)===(t[n]&i)}function yt(e){if(Ee.isIPv4(e)){let t=e.split(".").map(Number);return!(t[0]===0||t[0]===10||t[0]===127||t[0]>=224||t[0]===100&&t[1]>=64&&t[1]<=127||t[0]===169&&t[1]===254||t[0]===172&&t[1]>=16&&t[1]<=31||t[0]===192&&(t[1]===0||t[1]===2||t[1]===168)||t[0]===192&&t[1]===88&&t[2]===99||t[0]===198&&(t[1]===18||t[1]===19||t[1]===51)||t[0]===203&&t[1]===0&&t[2]===113)}if(Ee.isIPv6(e)){let t=et(e);if(!t)return!1;let r=et("::ffff:0:0");return ht(t,r,96)?yt([...t.slice(12)].join(".")):ht(t,et("2000::"),3)?![["2001::",23],["2001:db8::",32],["2001:10::",28],["2001:2::",48],["2002::",16],["3fff::",20]].some(([o,i])=>ht(t,et(o),i)):!1}return!1}function Jn(e){let t;try{t=new URL(String(e))}catch{return{ok:!1,error:`not a valid URL: ${String(e).slice(0,120)}`}}if(t.protocol!=="http:"&&t.protocol!=="https:")return{ok:!1,error:`refused protocol ${t.protocol} (only http/https)`};let r=t.hostname.toLowerCase().replace(/^\[|\]$/g,"").replace(/\.+$/,"");if(Vn.has(r)||r.endsWith(".localhost")||r.endsWith(".internal"))return{ok:!1,error:`refused internal host ${r}`};let n=Ee.isIP(r);return n!==0&&!yt(r)?{ok:!1,error:`refused private address ${r}`}:{ok:!0,url:t,host:r,isLiteralIp:n!==0}}async function wt(e,{lookupFn:t=zn.promises.lookup}={}){let r=Jn(e);if(!r.ok)return r;if(r.isLiteralIp)return{ok:!0,url:r.url,addresses:[{address:r.host,family:Ee.isIPv6(r.host)?6:4}]};let n;if(process.env.ORACLE_HOSTED_EGRESS_PROXY)return{ok:!0,url:r.url,addresses:[]};try{n=await t(r.host,{all:!0,verbatim:!0})}catch{return{ok:!1,error:`refused: ${r.host} did not resolve`}}return!Array.isArray(n)||n.length===0||n.some(o=>!yt(o.address))?{ok:!1,error:`refused: ${r.host} resolves to a non-public address`}:{ok:!0,url:r.url,addresses:n}}function Gn(e=process.env){let t=e.ORACLE_HOSTED_EGRESS_PROXY||"";if(!t)return null;let r;try{r=new URL(t)}catch{throw new Error("egress-guard: ORACLE_HOSTED_EGRESS_PROXY is not a URL")}if(r.protocol!=="http:"||!["127.0.0.1","::1","localhost","[::1]"].includes(r.hostname)||!r.port||r.username||r.password)throw new Error("egress-guard: egress proxy must be an exact loopback http origin");let n=e.ORACLE_HOSTED_EGRESS_TOKEN||"";if(!/^[A-Za-z0-9_-]{43}$/.test(n))throw new Error("egress-guard: egress proxy token is missing");return{uri:r.origin,token:n}}async function gt({requireUndici:e=!1,importUndici:t=()=>import("undici")}={}){let r,n,o;try{o=await t(),r=o.Agent,n=o.fetch}catch(m){if(e)throw new Error(`egress-guard: untrustedUrl pinning requires the undici package, which failed to load: ${m?.message||m}`);return null}if(typeof r!="function"||typeof n!="function"){if(e)throw new Error("egress-guard: untrustedUrl pinning requires undici's Agent and fetch exports, which were not found on the imported module");return null}let i=m=>String(m).toLowerCase().replace(/^\[|\]$/g,"").replace(/\.+$/,""),s=new Map,a=m=>(Array.isArray(m)?m:[m]).map(p=>typeof p=="string"?{address:p}:p).filter(p=>p&&p.address).map(p=>({address:p.address,family:p.family||(Ee.isIPv6(p.address)?6:4)})),c=(m,p,w)=>{s.set(i(m),a(typeof p=="string"?[{address:p,family:w}]:p))},f=m=>{let p=i(m);if(Ee.isIP(p))return[{address:p,family:Ee.isIPv6(p)?6:4}];let w=s.get(p);if(!w||!w.length)throw new Error(`refused: unpinned host ${m} during pinned fetch`);return w},u=Gn(),l=u&&typeof o.ProxyAgent=="function"?new o.ProxyAgent({uri:u.uri,token:`Bearer ${u.token}`,connectTimeout:1e4}):new r({connect:{lookup(m,p,w){let g;try{g=f(m)}catch(S){return w(S)}return p?.all?w(null,g):w(null,g[0].address,g[0].family)}}}),d=Kn((m,p={})=>n(m,{...p,dispatcher:l}),c);return{dispatcher:l,fetch:d,pin:c,resolve:f,async close(){try{await l.destroy()}catch{}}}}function Kn(e,t){if(typeof e!="function")throw new Error("markPinCapableFetch: fetchImpl must be a function");if(typeof t!="function")throw new Error("markPinCapableFetch: pin must be a function");return e[bt]=Object.freeze({pin:t}),e}function Et(e){return typeof e=="function"&&typeof e[bt]?.pin=="function"}function cr(e,t,r){if(!Et(e))throw new Error("pinFetchToAddresses: fetchImpl is not pin-capable");e[bt].pin(t,r)}var Vn,bt,lr=V(()=>{Vn=new Set(["localhost","metadata.google.internal","metadata.goog"]);bt=Symbol.for("oracle.egressGuard.pinCapableFetch")});import{createHash as Yn}from"node:crypto";import{types as de}from"node:util";function J(e){return me(`HTTP JSON body refused: ${e}`)}function oo(e){return["isArgumentsObject","isArrayBuffer","isAnyArrayBuffer","isArrayBufferView","isBoxedPrimitive","isDataView","isDate","isExternal","isGeneratorObject","isKeyObject","isCryptoKey","isMap","isMapIterator","isModuleNamespaceObject","isNativeError","isPromise","isRegExp","isSet","isSetIterator","isTypedArray","isWeakMap","isWeakSet"].some(t=>typeof de[t]=="function"&&de[t](e))}function so(e){let t=[],r=0,n=0,o=0,i=0,s=new WeakSet,a=u=>{if(r+=Buffer.byteLength(u,"utf8"),r>fe.bytes)throw J("serialized byte limit exceeded");t.push(u)},c=u=>{if(Buffer.byteLength(u,"utf8")>fe.bytes)throw J("serialized byte limit exceeded");return JSON.stringify(u)},f=(u,l)=>{if(n+=1,n>fe.nodes)throw J("node limit exceeded");if(l>fe.depth)throw J("depth limit exceeded");if(u===null){a("null");return}if(typeof u=="string"){a(c(u));return}if(typeof u=="boolean"){a(u?"true":"false");return}if(typeof u=="number"){if(!Number.isFinite(u))throw J("non-finite number");a(Object.is(u,-0)?"0":String(u));return}if(typeof u!="object")throw J("unsupported non-JSON value");if(de.isProxy(u))throw J("proxy value");if(oo(u))throw J("unsupported exotic object");if(s.has(u))throw J("cyclic value");s.add(u);try{if(Object.getOwnPropertySymbols(u).length>0)throw J("symbol-keyed fields are unsupported");if(Array.isArray(u)){let p=Object.getPrototypeOf(u),w=0;for(;p!==null;){if(de.isProxy(p))throw J("proxy array prototype");if(w+=1,w>fe.depth)throw J("array prototype depth limit exceeded");p=Object.getPrototypeOf(p)}if(u.length>fe.arrayLength)throw J("array length limit exceeded");for(let S=0;S<u.length;S+=1){let j=Object.getOwnPropertyDescriptor(u,String(S));if(!j||!Object.hasOwn(j,"value")||j.enumerable!==!0)throw J("array entries must be dense enumerable own data")}let g=0;for(let S in u){if(i+=1,i>fe.fields)throw J("enumeration limit exceeded");if(Object.hasOwn(u,S)&&(g+=1,g>u.length))throw J("named array fields are unsupported")}if(g!==u.length)throw J("array entries must be dense enumerable own data");a("[");for(let S=0;S<u.length;S+=1)S&&a(","),f(Object.getOwnPropertyDescriptor(u,String(S)).value,l+1);a("]");return}let d=Object.getPrototypeOf(u);if(d!==Object.prototype&&d!==null)throw J("non-plain object");let m=[];for(let p in u){if(i+=1,i>fe.fields)throw J("enumeration limit exceeded");if(!Object.hasOwn(u,p))continue;if(o+=1,o>fe.fields)throw J("field limit exceeded");let w=Object.getOwnPropertyDescriptor(u,p);if(!w||!Object.hasOwn(w,"value")||w.enumerable!==!0)throw J("object fields must be enumerable own data");m.push([p,w.value])}a("{");for(let p=0;p<m.length;p+=1)p&&a(","),a(c(m[p][0])),a(":"),f(m[p][1],l+1);a("}")}finally{s.delete(u)}};return f(e,0),t.join("")}function io(e){let t=Object.create(null);if(e==null)return t;if(typeof e!="object"&&typeof e!="function")throw new TypeError("HTTP headers must be an object");if(de.isProxy(e))throw new TypeError("HTTP headers must not be a proxy");if(Object.getOwnPropertySymbols(e).length>0)throw new TypeError("HTTP headers must not contain symbol fields");let r=new Set;for(let n of Object.keys(e)){if(!/^[!#$%&'*+.^_`|~0-9A-Za-z-]+$/u.test(n))throw new TypeError("HTTP header names must be valid tokens");let o=n.toLowerCase();if(r.has(o))throw new TypeError("HTTP headers contain a duplicate canonical name");r.add(o);let i=Object.getOwnPropertyDescriptor(e,n);if(!i||!Object.hasOwn(i,"value"))throw new TypeError("HTTP headers must contain own data properties");let s=i.value;if(s==null||["object","function","symbol"].includes(typeof s))throw new TypeError("HTTP header values must be scalar");t[n]=String(s)}return t}function ao(){return Object.assign(Object.create(null),{Accept:"application/json"})}function co(e,t){if(!e)throw new Error(`HTTP redirect from ${t} missing Location`);let r=new URL(String(e),String(t));if(r.protocol!=="http:"&&r.protocol!=="https:")throw new Error(`HTTP redirect from ${t} used unsupported protocol ${r.protocol}`);return r.toString()}function lo(e,t){return new URL(String(e)).origin===new URL(String(t)).origin}function tt(e){if((typeof e!="object"||e===null)&&typeof e!="function")return`${typeof e}:${String(e)}`;let t=mr.get(e);return t||(t=hr,hr+=1,mr.set(e,t)),`reference:${t}`}function yr(e){if(!e||typeof e!="object"||Array.isArray(e)||!Object.hasOwn(e,"jsonrpc")||!Object.hasOwn(e,"method")||e.jsonrpc!=="2.0")return!1;let t=typeof e.method=="string"?e.method:"";return t?uo.has(t)||/^get[A-Z0-9_]/u.test(t)||/^is[A-Z0-9_]/u.test(t)||/^eth_get[A-Z0-9_]/u.test(t):!1}function wr(e,t){if(e==="GET"&&t==null)return!0;if(e!=="POST"||t==null)return!1;let r=t;if(typeof t=="string")try{r=JSON.parse(t)}catch{return!1}if(Array.isArray(r))return r.length>0&&r.every(yr);if(!r||typeof r!="object")return!1;if(Object.hasOwn(r,"jsonrpc")||Object.hasOwn(r,"method"))return yr(r);let n=Object.hasOwn(r,"type")?r.type:null;return typeof n=="string"&&fo.has(n)&&(!Object.hasOwn(r,"action")||r.action==null)&&(!Object.hasOwn(r,"signature")||r.signature==null)&&(!Object.hasOwn(r,"nonce")||r.nonce==null)}function po(e,t,r,n={},o=null){let i=Yn("sha256"),s=(c,f)=>{let u=String(f);i.update(String(Buffer.byteLength(c,"utf8"))).update(":").update(c),i.update("=").update(String(Buffer.byteLength(u,"utf8"))).update(":").update(u).update(`
|
|
2
|
+
`)};s("method",e),s("url",t),Object.keys(r||{}).map((c,f)=>({name:c.toLowerCase(),order:f,value:String(r[c])})).sort((c,f)=>c.name.localeCompare(f.name)||c.order-f.order).forEach((c,f)=>{s(`header-name-${f}`,c.name),s(`header-value-${f}`,c.value)}),s("body",o??"-");for(let c of["untrustedUrl","maxResponseBytes","sameOriginRedirectsOnly","redirectPolicy","maxRedirects","timeoutMs","retries","fetchImpl","realFetch","lookupFn","importUndici","validateResponse"])s(`context-${c}`,n[c]??"-");return i.digest("hex")}function mo(e,t){let r=Number(t);return Number.isFinite(r)&&r>0?Math.min(r*1e3,fr):Math.min(250*2**e,fr)+Math.floor(Math.random()*100)}function me(e,t={}){let r=new Error(e);return r.retryable=!1,Object.assign(r,t),r}function St(e,t,r){return me(`HTTP response from ${e} exceeded maxResponseBytes ${r} (${t})`,{oversize:!0})}function xe(e){try{let t=e?.body?.cancel?.();t&&typeof t.then=="function"&&t.catch(()=>{})}catch{}}function yo(e){return e?e.byteLength??e.length??0:0}async function wo(e,t,{url:r,truncate:n=!1,onOversize:o}={}){if(t==null)return await e.text();let i=Number(e.headers?.get?.("content-length"));if(Number.isFinite(i)&&i>t&&(xe(e),!n))throw St(r,`content-length ${i}`,t);let s=e.body?.getReader?.();if(!s){let l=await e.text(),d=Buffer.byteLength(l,"utf8");if(d>t){if(!n)throw St(r,`body ${d} bytes`,t);return Buffer.from(l,"utf8").subarray(0,t).toString("utf8")}return l}let a=[],c=0,f=!1;try{for(;;){let{value:l,done:d}=await s.read();if(d)break;if(l&&(a.push(Buffer.from(l)),c+=yo(l),c>t)){f=!0;break}}}finally{if(f)try{await s.cancel()}catch{}try{s.releaseLock?.()}catch{}}if(f&&(typeof o=="function"&&o(),!n))throw St(r,`streamed ${c} bytes`,t);let u=Buffer.concat(a);return(f?u.subarray(0,t):u).toString("utf8")}function go(e){if(!e)return null;try{return JSON.parse(e)}catch{return null}}async function bo(e,{fetchImpl:t,method:r,headers:n,body:o,timeoutMs:i,lookupFn:s,realFetch:a,untrustedUrl:c=!1,maxResponseBytes:f=null,sameOriginRedirectsOnly:u=!1,importUndici:l,validateResponse:d,signal:m,redirectPolicy:p="follow",maxRedirects:w=rt}){let g=null,S=t,j=s?{lookupFn:s}:{};if(c&&!a&&!Et(S))throw me(`HTTP refused ${e}: untrustedUrl requires a pin-capable fetchImpl (see markPinCapableFetch in egress-guard.mjs) or no fetchImpl override so Oracle can pin the connection itself`);let T=new AbortController,x=setTimeout(()=>T.abort(),i),N=m?pr?pr([m,T.signal]):m:T.signal,$=async(h,{status:M=null}={})=>{let U=await wt(h,j);if(!U.ok)throw me(M==null?`HTTP refused ${h}: ${U.error}`:`HTTP redirect to ${h} ${U.error}`,M==null?{}:{status:M});let K=new URL(h).hostname;if(a){if(g&&(await g.close(),g=null),!g)try{g=await gt({requireUndici:!0,...l?{importUndici:l}:{}})}catch(k){throw me(M==null?`HTTP refused ${h}: ${k?.message||k}`:`HTTP redirect to ${h} refused: ${k?.message||k}`,M==null?{}:{status:M})}g.pin(K,U.addresses),S=g.fetch}else cr(S,K,U.addresses);return U};try{let h=String(e),M=Object.assign(Object.create(null),n||{});c&&await $(h);for(let U=0;U<=w;U+=1){let K=Object.assign(Object.create(null),{method:r,headers:M,body:o,signal:N,redirect:"manual",dispatcher:void 0}),k=await S(h,K);if((p==="error"||w===0)&&k.status>=300&&k.status<400)throw xe(k),me(`HTTP ${k.status} ${r} redirect refused`,{status:k.status,redirectRefused:!0});if(no.has(k.status)){let v=u===!0&&r==="POST"&&[307,308].includes(k.status)&&wr(r,o);if(r!=="GET"&&r!=="HEAD"&&!v){xe(k);let P=new Error(`HTTP ${k.status} ${r} ${h} redirected non-idempotent request`);throw P.status=k.status,P}if(U===w)throw xe(k),me(`HTTP ${k.status} ${r} redirect budget exhausted`,{status:k.status,redirectRefused:!0});let C=k.headers?.get?.("location"),L;try{L=co(C,h)}catch(P){throw xe(k),P}let R=!lo(L,h);if(xe(k),R&&r==="POST"){let P=new Error(`HTTP ${k.status} ${r} cross-origin redirect refused`);throw P.status=k.status,P}if(R&&u){let P=new Error(`HTTP ${k.status} ${r} cross-origin redirect refused`);throw P.status=k.status,P.retryable=!1,P}if(R&&(M=ao(M)),c)await $(L,{status:k.status});else if(R){let P=await wt(L,j);if(!P.ok){let I=new Error(`HTTP redirect from ${h} ${P.error}`);throw I.status=k.status,I.retryable=!1,I}a&&P.addresses?.length&&(g||(g=await gt(l?{importUndici:l}:{})),g&&(g.pin(new URL(L).hostname,P.addresses),S=g.fetch))}h=L;continue}if(typeof d=="function")try{await d(k,{url:h})}catch(v){throw xe(k),me(v?.message||String(v))}let y=await wo(k,f,{url:h,onOversize:()=>T.abort()}),_=go(y);if(!k.ok){let v=new Error(`HTTP ${k.status} ${r} ${h}`);throw v.status=k.status,v.retryAfter=k.headers?.get?.("retry-after")??null,v.body=_??y.slice(0,300),v}return _??y}throw new Error(`HTTP redirect loop for ${e}`)}catch(h){if(T.signal.aborted&&!De(m)){let M=h&&(typeof h=="object"||typeof h=="function")&&!de.isProxy(h)?h:null,U=M?Object.getOwnPropertyDescriptor(M,"oversize"):null;if(!(U&&Object.hasOwn(U,"value")&&U.value===!0))try{if(!M)throw new TypeError("unsafe rejection");Object.defineProperties(M,{oracleTimeout:{value:!0,enumerable:!1},retryable:{value:!1,enumerable:!1}})}catch{let k=new Error("HTTP request timed out");throw Object.defineProperties(k,{oracleTimeout:{value:!0,enumerable:!1},retryable:{value:!1,enumerable:!1}}),k}}throw h}finally{clearTimeout(x),g&&await g.close()}}async function gr(e,t={}){if(t!=null&&typeof t!="object"&&typeof t!="function")throw new TypeError("HTTP options must be an object");if(t!=null&&de.isProxy(t))throw new TypeError("HTTP options must not be a proxy");let r=new Set(["body","dedupe","fetchImpl","headers","importUndici","lookupFn","maxRedirects","maxResponseBytes","method","redirectPolicy","retries","sameOriginRedirectsOnly","signal","timeoutMs","untrustedUrl","validateResponse"]);if(t!=null){if(Object.getOwnPropertySymbols(t).length>0)throw new TypeError("HTTP options contain unknown fields");for(let I of Object.getOwnPropertyNames(t)){let A=Object.getOwnPropertyDescriptor(t,I);if(!(I==="toJSON"&&A&&Object.hasOwn(A,"value")&&A.value===void 0)){if(!r.has(I))throw new TypeError("HTTP options contain unknown fields");if(!A||!A.enumerable||!Object.hasOwn(A,"value"))throw new TypeError("HTTP options must contain enumerable own data properties")}}}let n=I=>{if(t==null||!Object.hasOwn(t,I))return;let A=Object.getOwnPropertyDescriptor(t,I);if(!A||!Object.hasOwn(A,"value"))throw new TypeError("HTTP options must contain own data properties");return A.value};if(typeof e!="string"||e.length===0||e.length>8192)throw new TypeError("HTTP URL must be a bounded string");let o=n("method");if(o!==void 0&&(typeof o!="string"||!/^[A-Za-z]+$/u.test(o)))throw new TypeError("HTTP method must be a string token");let i=n("timeoutMs");if(i!==void 0&&(!Number.isInteger(i)||i<1||i>12e4))throw new TypeError("HTTP timeoutMs must be a bounded integer");let s=n("retries");if(s!==void 0&&(!Number.isInteger(s)||s<0||s>10))throw new TypeError("HTTP retries must be a bounded integer");let a=n("redirectPolicy");if(a!==void 0&&a!=="follow"&&a!=="error")throw new TypeError('HTTP redirectPolicy must be "follow" or "error"');let c=n("maxRedirects");if(c!==void 0&&(!Number.isInteger(c)||c<0||c>rt))throw new TypeError(`HTTP maxRedirects must be an integer from 0 through ${rt}`);if(a==="error"&&c!==void 0&&c!==0)throw new TypeError('HTTP redirectPolicy "error" requires maxRedirects 0 when supplied');let f=a??"follow",u=f==="error"?0:c??rt;for(let I of["dedupe","untrustedUrl","sameOriginRedirectsOnly"]){let A=n(I);if(A!==void 0&&typeof A!="boolean")throw new TypeError(`HTTP ${I} must be boolean`)}let l=n("maxResponseBytes");if(l!==void 0&&(!Number.isInteger(l)||l<1||l>64*1024*1024))throw new TypeError("HTTP maxResponseBytes must be a bounded integer");let d=n("signal");if(d!==void 0){if(de.isProxy(d)||!(d instanceof AbortSignal))throw new TypeError("HTTP signal must be a native AbortSignal");try{De(d)}catch{throw new TypeError("HTTP signal must be a native AbortSignal")}}for(let I of["importUndici","lookupFn","validateResponse"]){let A=n(I);if(A!==void 0&&typeof A!="function")throw new TypeError(`HTTP ${I} must be a function`)}let m=n("fetchImpl"),p=m||globalThis.fetch;if(typeof p!="function")throw new Error("fetch unavailable \u2014 pass opts.fetchImpl");let w=i??12e3,g=(o||"GET").toUpperCase(),S=n("headers"),j=io(S),T=Object.assign(Object.create(null),j);Object.keys(T).some(I=>I.toLowerCase()==="accept")||(T.Accept="application/json");let x=n("body");x!=null&&typeof x!="string"&&(Object.keys(T).find(A=>A.toLowerCase()==="content-type")||(T["Content-Type"]="application/json"),x=so(x));let N=s??Xn,$=n("lookupFn"),h=!m,M=n("untrustedUrl")===!0,U=n("sameOriginRedirectsOnly")===!0,K=n("importUndici"),k=n("validateResponse"),y=d,_=l??null,v=async()=>{let I;for(let A=0;A<=N;A++){y&&eo.call(y);let Q=Qe("http");try{let Z=await bo(e,{fetchImpl:p,method:g,headers:T,body:x,timeoutMs:w,lookupFn:$,realFetch:h,untrustedUrl:M,maxResponseBytes:_,sameOriginRedirectsOnly:U,importUndici:K,validateResponse:k,signal:y,redirectPolicy:f,maxRedirects:u});return Q?.("succeeded"),Z}catch(Z){I=Z;let re=ge=>{if(!Z||typeof Z!="object"&&typeof Z!="function"||de.isProxy(Z))return;let le=Object.getOwnPropertyDescriptor(Z,ge);return le&&Object.hasOwn(le,"value")?le.value:void 0},ce=re("status");Q?.("failed",ce);let Xe=re("oracleTimeout")===!0||re("name")==="AbortError"||re("name")==="TimeoutError"||De(y),Ze=new Set([408,425,429]),or=re("retryable")===!1?!1:ce!=null?Ze.has(ce)||Wn.has(ce)&&ur.has(g):!Xe&&ur.has(g);if(A===N||!or)throw Z;let He=mo(A,re("retryAfter")),dt=Qe("retry"),Fe=!1;try{y?await new Promise((ge,le)=>{let $e,be=()=>{clearTimeout($e),dr.call(y,"abort",be),le(ro(y)||new DOMException("Aborted","AbortError"))};if(De(y)){be();return}$e=setTimeout(()=>{dr.call(y,"abort",be),ge()},He),to.call(y,"abort",be,{once:!0}),De(y)&&be()}):await ho(He),Fe=!0}finally{dt?.(Fe?"succeeded":"failed")}}}throw I};if(!(n("dedupe")!==!1&&!y&&wr(g,x)))return v();let L=po(g,e,T,{untrustedUrl:M,maxResponseBytes:_,sameOriginRedirectsOnly:U,redirectPolicy:f,maxRedirects:u,timeoutMs:w,retries:N,fetchImpl:tt(p),realFetch:h,lookupFn:tt($),importUndici:tt(K),validateResponse:tt(k)},x),R=xt.get(L);if(R){let I=Qe("shared");try{let A=await R;return I?.("succeeded"),A}catch(A){throw I?.("failed"),A}}let P=v().finally(()=>xt.delete(L));return xt.set(L,P),P}var Wn,ur,Xn,fr,Zn,Qn,eo,to,dr,pr,De,ro,no,rt,zi,fe,xt,mr,hr,uo,fo,ho,br=V(()=>{ar();lr();Wn=new Set([408,425,429,500,502,503,504]),ur=new Set(["GET","HEAD","OPTIONS","PUT","DELETE"]),Xn=2,fr=4e3,Zn=Object.getOwnPropertyDescriptor(AbortSignal.prototype,"aborted")?.get,Qn=Object.getOwnPropertyDescriptor(AbortSignal.prototype,"reason")?.get,eo=AbortSignal.prototype.throwIfAborted,to=EventTarget.prototype.addEventListener,dr=EventTarget.prototype.removeEventListener,pr=typeof AbortSignal.any=="function"?AbortSignal.any.bind(AbortSignal):null,De=e=>e?Zn.call(e):!1,ro=e=>e?Qn.call(e):void 0,no=new Set([301,302,303,307,308]),rt=3,zi=64*1024,fe=Object.freeze({depth:32,nodes:1e4,fields:1e4,arrayLength:1e4,bytes:1024*1024});xt=new Map,mr=new WeakMap,hr=1;uo=new Set(["eth_blockNumber","eth_call","eth_chainId","eth_estimateGas","getHealth","minimumLedgerSlot","net_version","simulateTransaction","web3_clientVersion"]),fo=new Set(["allMids","l2Book","outcomeMeta","spotClearinghouseState","userFills","meta","metaAndAssetCtxs","perpDexs","candleSnapshot","fundingHistory","openOrders","frontendOpenOrders","clearinghouseState","spotMeta","validatorSummaries","delegatorSummary","delegations","delegatorRewards","delegatorHistory","maxBuilderFee"]);ho=e=>new Promise(t=>setTimeout(t,e))});import{types as Er}from"node:util";function Eo(e){if(!e||typeof e!="object"||Er.isProxy(e)||Array.isArray(e))return!1;let t=Object.getPrototypeOf(e);return t===Object.prototype||t===null}function nt(e,t="provider response",r=0){if(r>64)throw new Error(`${t} exceeds the JSON nesting bound`);if(e===null||typeof e=="string"||typeof e=="boolean"||typeof e=="number"&&Number.isFinite(e))return e;if(Array.isArray(e)){if(Er.isProxy(e)||e.length>1e5)throw new Error(`${t} contains an invalid array`);let o=new Array(e.length);for(let i=0;i<e.length;i+=1){let s=Object.getOwnPropertyDescriptor(e,String(i));if(!s||!Object.hasOwn(s,"value"))throw new Error(`${t} arrays must contain dense own data`);o[i]=nt(s.value,t,r+1)}return o}if(!Eo(e))throw new Error(`${t} contains a non-JSON value`);let n=Object.create(null);for(let o of Object.keys(e)){let i=Object.getOwnPropertyDescriptor(e,o);if(!i||!Object.hasOwn(i,"value"))throw new Error(`${t} objects must contain own data`);n[o]=nt(i.value,t,r+1)}return n}var xr=V(()=>{});function ko({testnet:e,baseUrl:t}={}){if(t)return t.replace(/\/$/,"").endsWith("/info")?t:`${t.replace(/\/$/,"")}/info`;if(process.env.HL_INFO_URL)return process.env.HL_INFO_URL;if(process.env.HL_API_URL){let r=process.env.HL_API_URL.replace(/\/$/,"");return r.endsWith("/info")?r:`${r}/info`}return e||process.env.HL_TESTNET==="1"?So:xo}async function kt(e,t={}){if(!e||!e.type)throw new Error("hlInfo requires body.type");let r=ko(t);return nt(await gr(r,{method:"POST",body:e,fetchImpl:t.fetchImpl,timeoutMs:t.timeoutMs,maxResponseBytes:t.maxResponseBytes,sameOriginRedirectsOnly:t.sameOriginRedirectsOnly}),"hyperliquid info response")}async function Sr(e={}){return kt({type:"meta"},e)}async function kr({coin:e,interval:t="1h",startTime:r,endTime:n},o={}){if(!e)throw new Error("hlCandleSnapshot requires coin");let i={type:"candleSnapshot",req:{coin:String(e),interval:t,startTime:r??Date.now()-24*3600*1e3,endTime:n??Date.now()}};return kt(i,o)}async function Or({coin:e,startTime:t,endTime:r},n={}){if(!e)throw new Error("hlFundingHistory requires coin");return kt({type:"fundingHistory",coin:String(e),startTime:t??Date.now()-24*3600*1e3,endTime:r??Date.now()},n)}var xo,So,Ot=V(()=>{br();xr();xo="https://api.hyperliquid.xyz/info",So="https://api.hyperliquid-testnet.xyz/info"});import{createHash as Oo}from"node:crypto";function se(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function _e(e){return typeof e=="number"&&Number.isFinite(e)}function Tt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Tt(t);return Object.freeze(e)}for(let t of Object.keys(e))Tt(e[t]);return Object.freeze(e)}function Se(e){if(Array.isArray(e))return e.map(Se);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=Se(e[r]);return t}return e}function Pt(e){return{netPnlUsd:e.metrics.netPnlUsd,netPnlPct:e.metrics.netPnlPct,maxDrawdownPct:e.metrics.maxDrawdownPct,winRate:e.metrics.winRate,profitFactor:e.metrics.profitFactor,tradeCount:e.metrics.tradeCount,sharpe:e.metrics.sharpe,turnoverUsd:e.metrics.turnoverUsd,exposurePct:e.metrics.exposurePct}}function Pr(e){return{feesUsd:e.costs.feesUsd,builderFeesUsd:e.costs.builderFeesUsd,fundingUsd:e.costs.fundingUsd,slippageUsd:e.costs.slippageUsd}}function Ao(e){return(e.feesUsd||0)+(e.builderFeesUsd||0)+Math.max(0,e.fundingUsd||0)+(e.slippageUsd||0)}function To(e){let t=0;for(let r of e.trades)r.grossPnlUsd>0&&(t+=r.grossPnlUsd);return t}function $o(e,t,r){return!(!e||e.tradeCount<Math.max(1,Math.min(r,3))||!(e.netPnlUsd>0)||!(e.profitFactor>1)||!(e.maxDrawdownPct<=t.maxDailyLossPct))}function Tr(e){if(!se(e))throw new TypeError("evidence artifact must be a plain object");if(!Po.includes(e.status))throw new TypeError("evidence artifact status is invalid");for(let t of["strategyHash","compilerHash","barsHash"])if(typeof e[t]!="string"||!/^[0-9a-f]{64}$/.test(e[t]))throw new TypeError(`evidence artifact ${t} must be a sha256 hash`);if(!se(e.split))throw new TypeError("evidence artifact split required");if(!Array.isArray(e.flags))throw new TypeError("evidence artifact flags must be an array");if(!se(e.walkForward)||!Array.isArray(e.walkForward.windows))throw new TypeError("evidence artifact walkForward windows required");if(e.status==="pass_live_eligible"&&(!se(e.train)||!se(e.holdout)))throw new TypeError("live-eligible evidence artifact requires train and holdout facts");return Se({barsHash:e.barsHash,compilerHash:e.compilerHash,flags:e.flags.map(t=>Se(t)),holdout:e.holdout??null,split:e.split,status:e.status,strategyHash:e.strategyHash,train:e.train??null,walkForward:{passRate:e.walkForward.passRate,windowsRun:e.walkForward.windowsRun??e.walkForward.windows.length,windows:e.walkForward.windows.map(t=>({index:t.index,trainStartIndex:t.trainStartIndex,trainEndIndex:t.trainEndIndex,passed:t.passed,reason:t.reason,evalStartIndex:t.evalStartIndex,evalEndIndex:t.evalEndIndex,metrics:t.metrics}))}})}function $r(e){return Oo("sha256").update(JSON.stringify(Tr(e)),"utf8").digest("hex")}function ne(e,t,r=0){if(!Number.isInteger(e)||e<r)throw new Error(`${t} must be an integer >= ${r}`);return e}function At(e,t){if(!se(e)||!se(e.metrics))throw new Error(`${t} metrics required`);let r=ne(e.tradeCount,`${t}.tradeCount`);if(e.metrics.tradeCount!==r)throw new Error(`${t} tradeCount contradicts metrics.tradeCount`);for(let n of["netPnlUsd","profitFactor","maxDrawdownPct"])if(!_e(e.metrics[n]))throw new Error(`${t}.metrics.${n} must be finite`);if(e.metrics.maxDrawdownPct<0)throw new Error(`${t}.metrics.maxDrawdownPct must be >= 0`);return e.metrics}function _o(e,{maxDailyLossPct:t}={}){let r=e.split,n=ne(r.trainStartIndex,"split.trainStartIndex"),o=ne(r.trainEndIndex,"split.trainEndIndex"),i=ne(r.trainBarCount,"split.trainBarCount",1),s=ne(r.holdoutStartIndex,"split.holdoutStartIndex"),a=ne(r.holdoutEndIndex,"split.holdoutEndIndex"),c=ne(r.holdoutBarCount,"split.holdoutBarCount",1);if(n!==0||o-n+1!==i||s!==o+1||a-s+1!==c)throw new Error("evidence split must be contiguous, chronological, and count-consistent");if(!_e(r.trainFraction)||r.trainFraction<=0||r.trainFraction>=1)throw new Error("split.trainFraction must be in (0,1)");At(e.train,"train");let f=At(e.holdout,"holdout");if(f.tradeCount<1||f.netPnlUsd<=0||f.profitFactor<=1)throw new Error("live-eligible holdout metrics do not pass");if(_e(t)&&f.maxDrawdownPct>t)throw new Error("live-eligible holdout drawdown exceeds strategy risk");if(e.flags.length>0)throw new Error("live-eligible evidence cannot contain failure flags");let u=e.walkForward,l=u.windows;if(l.length<1||u.windowsRun!==l.length)throw new Error("live-eligible walk-forward windowsRun must match nonempty windows");let d=0,m=-1;for(let w=0;w<l.length;w++){let g=l[w];if(!se(g)||g.index!==w||typeof g.passed!="boolean")throw new Error("walk-forward windows must be ordered and structurally valid");let S=ne(g.trainStartIndex,`walkForward.windows[${w}].trainStartIndex`),j=ne(g.trainEndIndex,`walkForward.windows[${w}].trainEndIndex`),T=ne(g.evalStartIndex,`walkForward.windows[${w}].evalStartIndex`),x=ne(g.evalEndIndex,`walkForward.windows[${w}].evalEndIndex`);if(S!==0||j>=T||T>x||T<=m)throw new Error("walk-forward windows must be chronological and disjoint");if(m=x,g.passed){if(d+=1,g.reason!=="pass")throw new Error("passed walk-forward window reason must be pass");let N=At({metrics:g.metrics,tradeCount:g.metrics?.tradeCount},`walkForward.windows[${w}]`);if(N.tradeCount<1||N.netPnlUsd<=0||N.profitFactor<=1)throw new Error("passed walk-forward window metrics do not pass");if(_e(t)&&N.maxDrawdownPct>t)throw new Error("passed walk-forward drawdown exceeds strategy risk")}else if(g.reason==="pass")throw new Error("failed walk-forward window cannot have pass reason")}let p=d/l.length;if(!_e(u.passRate)||Math.abs(u.passRate-p)>Number.EPSILON||p<.6)throw new Error("walk-forward passRate contradicts concrete windows or is below live threshold")}function _r(e,t={}){if(typeof e?.id!="string"||!/^[0-9a-f]{64}$/.test(e.id))throw new Error("evidence.id must be a sha256 evidence artifact hash");let r=Tr(e),n=Se({id:e.id,...r});if(JSON.stringify(Se(e))!==JSON.stringify(n))throw new Error("evidence artifact contains fields unbound from its deterministic identity");let o=$r(e);if(e.id!==o)throw new Error("evidence.id does not match its deterministic artifact facts digest");return e.status==="pass_live_eligible"&&_o(e,t),e}function $t({strategy:e,bars:t,backtestOptions:r={},trainFraction:n=.7,walkForwardWindows:o=3,minTrades:i=10}={}){let s=[];if(!se(e))throw new TypeError("strategy must be a plain object");if(!Array.isArray(t))throw new TypeError("bars must be an array");if(!se(r))throw new TypeError("backtestOptions must be a plain object");if(!_e(n)||n<=0||n>=1)throw new TypeError("trainFraction must be in (0,1)");if(!Number.isInteger(o)||o<1)throw new TypeError("walkForwardWindows must be a positive integer");if(!Number.isInteger(i)||i<0)throw new TypeError("minTrades must be an integer >= 0");let a=W(e),c=ve(a),f=qe(t),u=t.length,l=(R=[],P={})=>Ar({status:"fail",strategy:a,sHash:c,barsHash:f,split:P.split||{trainStartIndex:0,trainEndIndex:-1,trainBarCount:0,holdoutStartIndex:0,holdoutEndIndex:-1,holdoutBarCount:0,trainFraction:n},train:P.train||null,holdout:P.holdout||null,walkForward:P.walkForward||{windows:[],passRate:0},flags:[...s,...R]});if(u<10)return l([{type:"insufficient_bars",message:"need at least 10 bars for evidence"}]);let d=Math.floor(u*n),m=d,p=u-m;if(d<5||p<3)return l([{type:"invalid_windowing",message:"train/holdout split too small",trainCount:d,holdoutCount:p}]);let w=t.slice(0,d),g=t.slice(m),S,j;try{S=he(a,w,r),j=he(a,g,r)}catch(R){return l([{type:"backtest_error",message:String(R.message||R)}])}let T={metrics:Pt(S),costs:Pr(S),tradeCount:S.metrics.tradeCount},x={metrics:Pt(j),costs:Pr(j),tradeCount:j.metrics.tradeCount},N={trainStartIndex:0,trainEndIndex:d-1,trainBarCount:d,holdoutStartIndex:m,holdoutEndIndex:u-1,holdoutBarCount:p,trainFraction:n},$=[],h=Math.floor(u/(o+1));if(h<3)s.push({type:"invalid_windowing",message:"walk-forward window size too small",wfSize:h});else for(let R=0;R<o;R++){let P=h*(R+1),I=P,A=Math.min(u,I+h);if(A-I<3||P<3){$.push({index:R,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:!1,reason:"window_too_small",metrics:null});continue}let Q=t.slice(I,A),Z;try{Z=he(a,Q,r)}catch{$.push({index:R,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:!1,reason:"backtest_error",metrics:null});continue}let re=Pt(Z),ce=$o(re,a.risk,i);$.push({index:R,trainStartIndex:0,trainEndIndex:P-1,evalStartIndex:I,evalEndIndex:A-1,passed:ce,reason:ce?"pass":"fail_metrics",metrics:re})}let M=$.filter(R=>R.passed).length,U=$.length===0?0:M/$.length,K={windows:$,passRate:U,windowsRun:$.length};x.metrics.tradeCount===0&&T.metrics.tradeCount===0&&s.push({type:"no_trades",message:"no trades in train or holdout"}),x.metrics.tradeCount===0&&s.push({type:"absent_oos_trades",message:"holdout produced no trades"}),x.metrics.netPnlUsd<0&&s.push({type:"holdout_loss",message:"holdout netPnlUsd is negative"}),T.metrics.netPnlUsd>0&&x.metrics.netPnlUsd<0&&T.metrics.netPnlUsd>Math.abs(x.metrics.netPnlUsd)*.25?s.push({type:"overfit",message:"profitable train with losing holdout (OOS collapse)"}):T.metrics.netPnlUsd>0&&x.metrics.netPnlUsd>0&&x.metrics.netPnlUsd<T.metrics.netPnlUsd*.1&&T.metrics.tradeCount>=i&&s.push({type:"severe_oos_collapse",message:"holdout pnl collapsed vs train"});let k=Ao(x.costs),y=To(j);y>0&&k>y&&s.push({type:"costs_exceed_gross",message:"holdout costs exceed gross gains"});let _=s.some(R=>["insufficient_bars","invalid_windowing","absent_oos_trades","holdout_loss","no_trades","severe_oos_collapse","backtest_error"].includes(R.type)),v=s.some(R=>R.type==="overfit"),C="fail";return x.metrics.tradeCount>=i&&x.metrics.netPnlUsd>0&&x.metrics.profitFactor>1&&x.metrics.maxDrawdownPct<=a.risk.maxDailyLossPct&&U>=.6&&!(y>0&&k>y)&&!v&&!s.some(R=>R.type==="severe_oos_collapse"||R.type==="invalid_windowing")?C="pass_live_eligible":!_&&x.metrics.tradeCount>0&&T.metrics.tradeCount>0&&Number.isFinite(x.metrics.netPnlUsd)?(C="pass_paper_only",x.metrics.tradeCount<i&&s.push({type:"undersampled",message:"holdout trades below minTrades"})):v&&x.metrics.tradeCount>0&&T.metrics.netPnlUsd>0?C="fail":x.metrics.tradeCount>0&&T.metrics.tradeCount>0&&!_?C="pass_paper_only":C="fail",x.metrics.netPnlUsd<0&&(C=C==="pass_live_eligible"?"fail":C==="pass_paper_only"?"pass_paper_only":"fail",C="fail"),Ar({status:C,strategy:a,sHash:c,barsHash:f,split:N,train:T,holdout:x,walkForward:K,flags:s})}function Ar({status:e,strategy:t,sHash:r,barsHash:n,split:o,train:i,holdout:s,walkForward:a,flags:c}){let f={status:e,strategyHash:r,compilerHash:Oe,barsHash:n,split:o,train:i,holdout:s,walkForward:a,flags:c};return f.id=$r(f),Tt(Se(JSON.parse(JSON.stringify(f))))}var Po,_t=V(()=>{Pe();ke();ot();Po=Object.freeze(["fail","pass_paper_only","pass_live_eligible"])});import{createHash as vo,createHmac as Io,timingSafeEqual as na}from"node:crypto";function vt(e){return e===null||typeof e!="object"?JSON.stringify(e):Array.isArray(e)?`[${e.map(vt).join(",")}]`:`{${Object.keys(e).sort().map(r=>`${JSON.stringify(r)}:${vt(e[r])}`).join(",")}}`}function vr(e){let t=String(e?.ORACLE_STAMP_HMAC_SECRET||"").trim();return t.length>=16?t:""}function Ir(e=process.env){return vr(process.env)||vr(e)}function Mo(e){let{prepareHash:t,prepareMac:r,note:n,...o}=e||{};return o}function Lo(e){let t=Mo(e);return vo("sha256").update(vt(t)).digest("hex")}function Ho(e,t=Ir()){return t?Io("sha256",t).update(String(e)).digest("hex"):""}function jr(e,{provider:t,kind:r,env:n=process.env,nowMs:o=Date.now(),expiresAtMs:i}={}){if(!e||typeof e!="object")throw new Error("stampPrepared: payload object required");let s=Object.prototype.hasOwnProperty.call(e,"oraclePrepared");if(s&&typeof e.oraclePrepared!="boolean")throw new Error("stampPrepared: oraclePrepared must be boolean");let a={...e,provider:e.provider||t,kind:e.kind||r,requiresUserSignature:e.requiresUserSignature!==!1,signingReady:!1,broadcastReady:!1,executionReady:!1,oraclePrepared:s?e.oraclePrepared:!0};if(!a.provider)throw new Error("stampPrepared: provider required");if(!a.kind)throw new Error("stampPrepared: kind required");let c=Number(o),f=i==null?c+Ro:Number(i),u=f-c;if(!Number.isSafeInteger(c)||!Number.isSafeInteger(f)||u<=0||u>No)throw new Error("stampPrepared: bounded preparedAt/expiresAt required");let d={...a,preparedAt:c,expiresAt:f,prepareVersion:jo},m=Lo(d),p=Ir(n),w=p?Ho(m,p):void 0,g={...d,prepareHash:m};return w&&(g.prepareMac=w),g}var jo,Ro,No,Rr=V(()=>{jo=2,Ro=300*1e3,No=(()=>{let e=Number(process.env.ORACLE_PREPARE_HARD_MAX_AGE_MS);return Number.isFinite(e)&&e>0?e:1800*1e3})()});function Be(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Co(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function jt(e,t="value"){if(Array.isArray(e)){e.forEach((r,n)=>jt(r,`${t}[${n}]`));return}if(Be(e))for(let[r,n]of Object.entries(e)){let o=Co(r);if(Fo.some(i=>o.includes(i)))throw new Error(`handoff: forbidden secret-like field at ${t}.${r}`);jt(n,`${t}.${r}`)}}function It(e){return typeof e=="number"&&Number.isFinite(e)&&e>0}function Nr({strategy:e,evidence:t,shadow:r,caps:n,nowMs:o=Date.now(),env:i=process.env}={}){if(jt({strategy:e,evidence:t,shadow:r,caps:n},"handoff"),!Be(e))throw new Error("handoff: strategy required");if(!Be(t))throw new Error("handoff: evidence required");if(!Be(r))throw new Error("handoff: shadow required");if(!Be(n))throw new Error("handoff: caps required");if(typeof r.id!="string"||!r.id.trim())throw new Error("handoff: shadow.id required");if(typeof r.stateHash!="string"||!/^[0-9a-f]{64}$/.test(r.stateHash))throw new Error("handoff: shadow.stateHash must be a sha256 hash");if(r.status!=="running")throw new Error("handoff: shadow.status must be running");if(!Number.isInteger(r.cursor)||r.cursor<=0)throw new Error("handoff: shadow.cursor must be a positive integer");if(!Number.isInteger(r.updatedAt)||r.updatedAt<=0||r.updatedAt>o)throw new Error("handoff: shadow.updatedAt must be a positive integer <= nowMs");let s=W(e,{nowMs:o}),a=X(s);if(_r(t,{maxDailyLossPct:s.risk.maxDailyLossPct}),t.status!=="pass_live_eligible")throw new Error("handoff: evidence.status must be pass_live_eligible");if(t.strategyHash!==a.strategyHash)throw new Error("handoff: evidence.strategyHash mismatch");if(t.compilerHash!==a.compilerHash)throw new Error("handoff: evidence.compilerHash mismatch");let c=["perStrategyNotionalUsd","maxLeverage","dailyLossCapUsd","chainAllowlist","assetAllowlist","expiresAt","killSwitchRequired"];for(let d of c)if(!(d in n)||n[d]==null)throw new Error(`handoff: caps.${d} required`);if(!It(n.perStrategyNotionalUsd))throw new Error("handoff: caps.perStrategyNotionalUsd must be positive");if(n.perStrategyNotionalUsd>a.strategy.risk.maxNotionalUsd)throw new Error("handoff: caps.perStrategyNotionalUsd exceeds strategy.risk.maxNotionalUsd");if(!It(n.maxLeverage))throw new Error("handoff: caps.maxLeverage must be positive");if(n.maxLeverage>a.strategy.risk.maxLeverage)throw new Error("handoff: caps.maxLeverage exceeds strategy.risk.maxLeverage");if(!It(n.dailyLossCapUsd))throw new Error("handoff: caps.dailyLossCapUsd must be positive");let f=a.strategy.risk.maxNotionalUsd*(a.strategy.risk.maxDailyLossPct/100);if(n.dailyLossCapUsd>f)throw new Error("handoff: caps.dailyLossCapUsd exceeds strategy daily loss ceiling");if(!Array.isArray(n.chainAllowlist)||n.chainAllowlist.length===0)throw new Error("handoff: caps.chainAllowlist must be a non-empty array");if(!n.chainAllowlist.every(d=>d==="hyperliquid"))throw new Error("handoff: caps.chainAllowlist must include only hyperliquid");if(!n.chainAllowlist.includes("hyperliquid"))throw new Error("handoff: caps.chainAllowlist must include hyperliquid");if(!Array.isArray(n.assetAllowlist)||n.assetAllowlist.length===0)throw new Error("handoff: caps.assetAllowlist must be a non-empty array");if(n.assetAllowlist.length!==1||n.assetAllowlist[0]!==a.strategy.market.coin)throw new Error("handoff: caps.assetAllowlist must contain only the strategy market coin");if(!Number.isInteger(n.expiresAt)||!(n.expiresAt>o))throw new Error("handoff: caps.expiresAt must be an integer > nowMs");if(n.expiresAt>a.strategy.risk.expiresAt)throw new Error("handoff: caps.expiresAt exceeds strategy.risk.expiresAt");if(n.killSwitchRequired!==!0)throw new Error("handoff: caps.killSwitchRequired must be exactly true");let u={perStrategyNotionalUsd:n.perStrategyNotionalUsd,maxLeverage:n.maxLeverage,dailyLossCapUsd:n.dailyLossCapUsd,chainAllowlist:[...n.chainAllowlist],assetAllowlist:[...n.assetAllowlist],expiresAt:n.expiresAt,killSwitchRequired:!0},l={strategyHash:a.strategyHash,compilerHash:a.compilerHash,evidence:JSON.parse(JSON.stringify(t)),shadow:{id:r.id,stateHash:r.stateHash,status:r.status,cursor:r.cursor,updatedAt:r.updatedAt},compiled:{strategyHash:a.strategyHash,compilerHash:a.compilerHash,compilerVersion:ze,venue:"hyperliquid",market:{coin:a.strategy.market.coin,kind:"perp",interval:a.strategy.market.interval},risk:{...a.strategy.risk},strategy:JSON.parse(JSON.stringify(a.strategy))},arming:{liveBroadcast:!1,requiresExplicitUserArm:!0,caps:u},requiresUserSignature:!0,signingReady:!1,broadcastReady:!1,executionReady:!1};return jr(l,{provider:"hl-strategy",kind:"strategy-live-handoff",env:i})}var Fo,Mr=V(()=>{Pe();_t();ke();Rr();Fo=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"]});function Ie(e,t){let r=Number(e);if(!Number.isFinite(r))throw new TypeError(`${t} must be finite`);return r}function je(e,t){if(!Number.isSafeInteger(e)||e<0)throw new TypeError(`${t} must be a non-negative safe integer`);return e}function Ve(e){if(Array.isArray(e))for(let t of e)Ve(t);else if(e&&typeof e=="object")for(let t of Object.values(e))Ve(t);return Object.freeze(e)}function Do(e){let t=Uo[e];if(!t)throw new TypeError(`unsupported strategy interval: ${e}`);return t}function qo(e,{endTime:t=Number.MAX_SAFE_INTEGER}={}){if(!Array.isArray(e))throw new TypeError("Hyperliquid candles must be an array");je(t,"endTime");let r=new Map;for(let n=0;n<e.length;n++){let o=e[n];if(!o||typeof o!="object"||Array.isArray(o))throw new TypeError(`candles[${n}] must be an object`);let i=je(Number(o.t),`candles[${n}].t`);if(je(Number(o.T),`candles[${n}].T`)>t)continue;let a={t:i,o:Ie(o.o,`candles[${n}].o`),h:Ie(o.h,`candles[${n}].h`),l:Ie(o.l,`candles[${n}].l`),c:Ie(o.c,`candles[${n}].c`),v:Ie(o.v,`candles[${n}].v`)};if(a.h<Math.max(a.o,a.c,a.l))throw new TypeError(`candles[${n}].h is below another price`);if(a.l>Math.min(a.o,a.c,a.h))throw new TypeError(`candles[${n}].l is above another price`);if(a.v<0)throw new TypeError(`candles[${n}].v must be non-negative`);let c=r.get(i);if(c&&JSON.stringify(c)!==JSON.stringify(a))throw new TypeError(`conflicting duplicate candle at timestamp ${i}`);c||r.set(i,a)}return Ve([...r.values()].sort((n,o)=>n.t-o.t))}function Bo(e,t){if(!Array.isArray(e))throw new TypeError("Hyperliquid funding history must be an array");let r=new Map;for(let n=0;n<e.length;n++){let o=e[n];if(!o||typeof o!="object"||Array.isArray(o))throw new TypeError(`funding[${n}] must be an object`);let i=je(Number(o.time),`funding[${n}].time`);i>t||r.set(i,{time:i,fundingRate:Ie(o.fundingRate,`funding[${n}].fundingRate`)})}return[...r.values()].sort((n,o)=>n.time-o.time)}async function zo({coin:e,startTime:t,endTime:r},n){let o=[],i=Math.max(0,t-288e5),s=!1;for(let a=0;a<16&&i<=r;a++){let c=await Or({coin:e,startTime:i,endTime:r},n);if(!Array.isArray(c))throw new TypeError("Hyperliquid funding history must be an array");o.push(...c);let f=i;for(let u of c){let l=Number(u?.time);Number.isSafeInteger(l)&&l>f&&(f=l)}if(c.length<500||f>=r){s=!0;break}if(f<=i)throw new Error("Hyperliquid funding history pagination did not advance");i=f+1}if(!s)throw new Error("strategy history exceeds the bounded funding history limit");return Bo(o,r)}function Vo(e,t,r){let n=0,o=null;return e.map(i=>{let s=i.t+r,a=0;for(;n<t.length&&t[n].time<s;){let c=t[n];o=c.fundingRate,c.time>=i.t&&(a+=c.fundingRate),n+=1}return o==null?{...i,fundingPaymentRate:a}:{...i,fundingRate:o,fundingPaymentRate:a}})}async function Lr(e,t={}){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("strategy history input must be an object");let r=String(e.coin||"").trim().toUpperCase();if(!/^[A-Z0-9][A-Z0-9._-]{0,11}$/.test(r))throw new TypeError("coin must be an uppercase Hyperliquid asset id");let n=String(e.interval||"15m"),o=Do(n);if(e.endTime==null)throw new TypeError("endTime is required for deterministic history");let i=je(e.endTime,"endTime"),s=e.count==null?1500:e.count;if(!Number.isInteger(s)||s<20||s>5e3)throw new TypeError("count must be an integer from 20 to 5000");let a=e.startTime==null?Math.max(0,i-s*o):je(e.startTime,"startTime");if(a>=i)throw new TypeError("startTime must be before endTime");let[c,f]=await Promise.all([kr({coin:r,interval:n,startTime:a,endTime:i},t),zo({coin:r,startTime:a,endTime:i},t)]),u=qo(c,{endTime:i}),l=Ve(Vo(u,f,o));return Ve({coin:r,interval:n,range:{startTime:a,endTime:i},bars:l})}var Uo,Hr=V(()=>{Ot();Uo=Object.freeze({"1m":6e4,"3m":18e4,"5m":3e5,"15m":9e5,"30m":18e5,"1h":36e5,"2h":72e5,"4h":144e5,"8h":288e5,"12h":432e5,"1d":864e5})});function Ko(e){let t=[];if(!e||typeof e!="object"||Array.isArray(e))return{ok:!1,errors:[{path:"market",message:"must be a plain object"}],market:null};for(let r of Object.keys(e))Go.has(r)||t.push({path:`market.${r}`,message:"unknown field is not allowed"});return(typeof e.coin!="string"||e.coin.length===0||e.coin.length>32)&&t.push({path:"market.coin",message:"must be a non-empty string max 32"}),(typeof e.interval!="string"||!Jo.has(e.interval))&&t.push({path:"market.interval",message:"must be a supported interval"}),t.length?{ok:!1,errors:t,market:null}:{ok:!0,errors:[],market:{coin:e.coin,interval:e.interval}}}async function Yo(e={}){let t=await Sr(e);if(!t||!Array.isArray(t.universe))throw new TypeError("Hyperliquid market metadata must contain universe");return Object.freeze(t.universe.map((r,n)=>{if(!r||typeof r.name!="string"||!r.name)throw new TypeError(`Hyperliquid market metadata universe[${n}].name is invalid`);return r.name}))}var Jo,Go,Fr,Cr=V(()=>{Ot();Mr();Hr();Jo=new Set(["1m","3m","5m","15m","30m","1h","2h","4h","8h","12h","1d"]),Go=new Set(["coin","interval"]);Fr=Object.freeze({id:"hyperliquid",validateMarket:Ko,fetchBars:Lr,listMarkets:Yo,prepareIntent(e){return Nr(e)}})});function Xo(e){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("strategy venue adapter must be an object");if(typeof e.id!="string"||!/^[a-z0-9][a-z0-9._-]{0,63}$/.test(e.id))throw new TypeError("strategy venue adapter id is malformed");for(let t of Wo.slice(1))if(typeof e[t]!="function")throw new TypeError(`strategy venue adapter ${e.id} requires ${t}()`);for(let t of["fetchBars","listMarkets"])if(e[t]!=null&&typeof e[t]!="function")throw new TypeError(`strategy venue adapter ${e.id} ${t} must be a function`);return e}function Rt(e){return typeof e!="string"?null:Zo.get(e)??null}function Nt(e){let t=Rt(e);if(!t)throw new Error(`unknown strategy venue: ${String(e)}`);return t}var Wo,Ur,Zo,wa,Mt=V(()=>{Cr();Wo=Object.freeze(["id","validateMarket","prepareIntent"]);Ur=[Fr].map(Xo),Zo=new Map(Ur.map(e=>[e.id,e])),wa=Object.freeze([...Ur])});import{createHash as Qo}from"node:crypto";function te(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function z(e){return typeof e=="number"&&Number.isFinite(e)}function Kr(e){return Number.isInteger(e)&&e>0}function Ut(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Ut(t);return Object.freeze(e)}for(let t of Object.keys(e))Ut(e[t]);return Object.freeze(e)}function Dt(e){if(Array.isArray(e))return e.map(Dt);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=Dt(e[r]);return t}return e}function b(e,t,r){e.push({path:t,message:r})}function ye(e,t,r,n){for(let o of Object.keys(e))t.has(o)||b(n,r?`${r}.${o}`:o,"unknown field is not allowed")}function Zr(e,t,r,n){if(!z(e)||!z(t)||!z(r)||!z(n)||n<=0||e<t||e>r)return!1;let o=(e-t)/n;if(!Number.isFinite(o))return!1;let i=Math.round(o);return Math.abs(o-i)<=1e-9}function Ct(e,t,r,n){if(te(e)){if(ye(e,new Set(["param"]),t,n),typeof e.param!="string"||!e.param)return b(n,`${t}.param`,"must be a parameter name string"),null;if(!Object.prototype.hasOwnProperty.call(r,e.param))return b(n,`${t}.param`,`unknown parameter "${e.param}"`),null;let o=r[e.param];return!te(o)||![o.value,o.min,o.max,o.step].every(Kr)?(b(n,`${t}.param`,"referenced period parameter value min max and step must be positive integers"),null):{param:e.param}}return Kr(e)?e:(b(n,t,"must be a positive integer or {param}"),null)}function Yr(e,t,r,n){return te(e)?(ye(e,new Set(["param"]),t,n),typeof e.param!="string"||!e.param?(b(n,`${t}.param`,"must be a parameter name string"),null):Object.prototype.hasOwnProperty.call(r,e.param)?{param:e.param}:(b(n,`${t}.param`,`unknown parameter "${e.param}"`),null)):z(e)?e:(b(n,t,"must be a finite number or {param}"),null)}function st(e){switch(e.type){case"input":case"constant":return[];case"indicator":return e.input?[e.input]:[];case"compare":case"cross":return[e.left,e.right].filter(Boolean);case"logic":return Array.isArray(e.inputs)?[...e.inputs]:[];default:return[]}}function cs(e){let t=new Map,r=n=>{let o=t.get(n)||0;if(o===1)return!0;if(o===2)return!1;t.set(n,1);let i=e.get(n);if(i){for(let s of st(i))if(e.has(s)&&r(s))return!0}return t.set(n,2),!1};for(let n of e.keys())if(r(n))return!0;return!1}function ls(e,t){if(!te(e))return b(t,"parameters","must be a plain object"),null;let r=Object.keys(e);if(r.length>Vr)return b(t,"parameters",`too many parameters (max ${Vr})`),null;let n={};for(let o of r){if(!Wr.test(o)){b(t,`parameters.${o}`,"parameter name is malformed");continue}let i=e[o],s=`parameters.${o}`;if(!te(i)){b(t,s,"must be a plain object");continue}ye(i,qr,s,t);for(let l of qr)l in i||b(t,`${s}.${l}`,"required field is missing");let{value:a,min:c,max:f,step:u}=i;z(c)||b(t,`${s}.min`,"must be a finite number"),z(f)||b(t,`${s}.max`,"must be a finite number"),(!z(u)||u<=0)&&b(t,`${s}.step`,"must be a positive finite number"),z(a)||b(t,`${s}.value`,"must be a finite number"),z(c)&&z(f)&&c>f&&b(t,`${s}.min`,"min must be <= max"),z(a)&&z(c)&&z(f)&&z(u)&&u>0&&(Zr(a,c,f,u)||b(t,`${s}.value`,"value must lie on the declared min/max/step grid")),n[o]={value:a,min:c,max:f,step:u}}return n}function us(e,t,r,n){let o=`nodes.${t}`;if(!te(e))return b(n,o,"must be a plain object"),null;if(typeof e.type!="string"||!zr[e.type])return b(n,`${o}.type`,"unknown or missing node type"),ye(e,as,o,n),null;switch(ye(e,zr[e.type],o,n),(typeof e.id!="string"||!Xr.test(e.id))&&b(n,`${o}.id`,"must be a 1-64 char id starting with alphanumeric"),e.type){case"input":return(typeof e.field!="string"||!es.has(e.field))&&b(n,`${o}.field`,"must be one of open|high|low|close|volume|fundingRate|openInterest|premium|oiDelta|bookImbalance"),{id:e.id,type:"input",field:e.field};case"constant":{let i=Yr(e.value,`${o}.value`,r,n);return{id:e.id,type:"constant",value:i}}case"indicator":{(typeof e.indicator!="string"||!ts.has(e.indicator))&&b(n,`${o}.indicator`,"must be one of sma|ema|rsi|macd|bollinger|atr");let i=e.indicator,s={id:e.id,type:"indicator",indicator:i};if(i==="atr"){"input"in e&&(typeof e.input!="string"||!e.input?b(n,`${o}.input`,"must be a node id string when provided"):s.input=e.input);let a=Ct(e.period,`${o}.period`,r,n);a!=null&&(s.period=a)}else typeof e.input!="string"||!e.input?b(n,`${o}.input`,"must be a node id string"):s.input=e.input;if((i==="sma"||i==="ema"||i==="rsi"||i==="bollinger"||i==="atr")&&("period"in e,i!=="macd"))if(!("period"in e))b(n,`${o}.period`,"required field is missing");else{let a=Ct(e.period,`${o}.period`,r,n);a!=null&&(s.period=a)}if(i==="macd"){for(let a of["fastPeriod","slowPeriod","signalPeriod"])if(!(a in e))b(n,`${o}.${a}`,"required field is missing");else{let c=Ct(e[a],`${o}.${a}`,r,n);c!=null&&(s[a]=c)}"output"in e?ss.has(e.output)?s.output=e.output:b(n,`${o}.output`,"must be line|signal|histogram"):b(n,`${o}.output`,"required field is missing"),"period"in e&&b(n,`${o}.period`,"forbidden for macd"),"stdDev"in e&&b(n,`${o}.stdDev`,"forbidden for macd")}else if(i==="bollinger"){if(!("stdDev"in e))b(n,`${o}.stdDev`,"required field is missing");else{let a=Yr(e.stdDev,`${o}.stdDev`,r,n);a!=null&&(typeof a=="number"&&a<=0?b(n,`${o}.stdDev`,"must be > 0"):s.stdDev=a)}"output"in e?is.has(e.output)?s.output=e.output:b(n,`${o}.output`,"must be upper|middle|lower"):b(n,`${o}.output`,"required field is missing");for(let a of["fastPeriod","slowPeriod","signalPeriod"])a in e&&b(n,`${o}.${a}`,`forbidden for ${i}`)}else{"output"in e&&b(n,`${o}.output`,`forbidden for ${i}`),"stdDev"in e&&i!=="bollinger"&&b(n,`${o}.stdDev`,`forbidden for ${i}`);for(let a of["fastPeriod","slowPeriod","signalPeriod"])a in e&&b(n,`${o}.${a}`,`forbidden for ${i}`)}return s}case"compare":return(typeof e.op!="string"||!rs.has(e.op))&&b(n,`${o}.op`,"must be gt|gte|lt|lte|eq"),(typeof e.left!="string"||!e.left)&&b(n,`${o}.left`,"must be a node id"),(typeof e.right!="string"||!e.right)&&b(n,`${o}.right`,"must be a node id"),{id:e.id,type:"compare",op:e.op,left:e.left,right:e.right};case"logic":{if((typeof e.op!="string"||!ns.has(e.op))&&b(n,`${o}.op`,"must be and|or|not"),!Array.isArray(e.inputs))return b(n,`${o}.inputs`,"must be an array of node ids"),{id:e.id,type:"logic",op:e.op,inputs:[]};let i=[];for(let s=0;s<e.inputs.length;s++){let a=e.inputs[s];typeof a!="string"||!a?b(n,`${o}.inputs.${s}`,"must be a node id"):i.push(a)}return e.op==="not"?i.length!==1&&b(n,`${o}.inputs`,"not requires exactly one input"):(e.op==="and"||e.op==="or")&&i.length<2&&b(n,`${o}.inputs`,`${e.op} requires at least two inputs`),{id:e.id,type:"logic",op:e.op,inputs:i}}case"cross":return(typeof e.direction!="string"||!os.has(e.direction))&&b(n,`${o}.direction`,"must be above|below"),(typeof e.left!="string"||!e.left)&&b(n,`${o}.left`,"must be a node id"),(typeof e.right!="string"||!e.right)&&b(n,`${o}.right`,"must be a node id"),{id:e.id,type:"cross",direction:e.direction,left:e.left,right:e.right};default:return null}}function fs(e,t,r){if(!te(e))return b(t,"risk","must be a plain object"),null;ye(e,Br,"risk",t);for(let d of Br)(!(d in e)||e[d]==null)&&b(t,`risk.${d}`,"required field is missing");let n={},o=e.maxLeverage;!z(o)||o<=0||o>50?b(t,"risk.maxLeverage","must be a number > 0 and <= 50"):n.maxLeverage=o;let i=e.maxNotionalUsd;!z(i)||i<=0?b(t,"risk.maxNotionalUsd","must be a number > 0"):n.maxNotionalUsd=i;let s=e.positionSizePct;!z(s)||s<=0||s>100?b(t,"risk.positionSizePct","must be a number > 0 and <= 100"):n.positionSizePct=s;let a=e.stopLossPct;!z(a)||a<=0||a>100?b(t,"risk.stopLossPct","must be a number > 0 and <= 100"):n.stopLossPct=a;let c=e.takeProfitPct;!z(c)||c<=0||c>1e3?b(t,"risk.takeProfitPct","must be a number > 0 and <= 1000"):n.takeProfitPct=c;let f=e.cooldownBars;!Number.isInteger(f)||f<0||f>1e5?b(t,"risk.cooldownBars","must be an integer >= 0 and <= 100000"):n.cooldownBars=f;let u=e.maxDailyLossPct;!z(u)||u<=0||u>100?b(t,"risk.maxDailyLossPct","must be a number > 0 and <= 100"):n.maxDailyLossPct=u;let l=e.expiresAt;return!Number.isInteger(l)||l<=0?b(t,"risk.expiresAt","must be an integer epoch milliseconds > 0"):(r.nowMs!==void 0&&(Number.isInteger(r.nowMs)?l<=r.nowMs&&b(t,"risk.expiresAt","must be strictly greater than nowMs"):b(t,"nowMs","must be an integer epoch milliseconds")),n.expiresAt=l),n}function qt(e,t={}){let r=[];if(!te(e))return b(r,"","strategy must be a plain object"),{ok:!1,errors:r,strategy:null};ye(e,Dr,"",r);for(let l of Dr)(!(l in e)||e[l]==null)&&b(r,l,"required field is missing");e.version!==Lt&&b(r,"version",`must be ${Lt}`),(typeof e.id!="string"||!Wr.test(e.id))&&b(r,"id","must match /^[a-z0-9][a-z0-9._-]{0,63}$/"),(typeof e.name!="string"||e.name.length===0||e.name.length>Gr)&&b(r,"name",`must be a non-empty string max ${Gr}`);let n=Rt(e.venue);n||b(r,"venue",`unknown strategy venue "${String(e.venue)}"`);let o=null;if(!n)te(e.market)||b(r,"market","must be a plain object");else{let l=n.validateMarket(e.market);if(!l||typeof l.ok!="boolean"||!Array.isArray(l.errors))b(r,"market",`venue ${n.id} returned an invalid market validation result`);else if(l.ok)o=l.market;else for(let d of l.errors)b(r,d.path,d.message)}let i=ls(e.parameters,r),s=null,a=new Map;if(!Array.isArray(e.nodes))b(r,"nodes","must be an array");else if(e.nodes.length>Jr)b(r,"nodes",`too many nodes (max ${Jr})`);else{s=[];for(let l=0;l<e.nodes.length;l++){let d=us(e.nodes[l],l,i||{},r);d&&(typeof d.id=="string"&&Xr.test(d.id)&&(a.has(d.id)?b(r,`nodes.${l}.id`,`duplicate node id "${d.id}"`):a.set(d.id,d)),s.push(d))}for(let l=0;l<s.length;l++){let d=s[l],m=`nodes.${l}`;for(let p of st(d))a.has(p)||b(r,m,`unknown node ref "${p}"`);if(d.type==="indicator"||d.type==="compare"||d.type==="cross")for(let p of st(d)){let w=a.get(p);w&&Ht.has(w.type)&&b(r,m,`node ref "${p}" must be numeric`)}if(d.type==="logic")for(let p of st(d)){let w=a.get(p);w&&!Ht.has(w.type)&&b(r,m,`node ref "${p}" must be boolean`)}}cs(a)&&b(r,"nodes","graph contains a cycle")}let c=null;if(!te(e.rules))b(r,"rules","must be a plain object");else{ye(e.rules,Ft,"rules",r);for(let l of Ft)l in e.rules||b(r,`rules.${l}`,"required field is missing");c={};for(let l of Ft){let d=e.rules[l];if(d===null){c[l]=null;continue}if(typeof d!="string"||!d){b(r,`rules.${l}`,"must be a node id or null"),c[l]=d;continue}if(!a.has(d)){b(r,`rules.${l}`,`unknown node ref "${d}"`),c[l]=d;continue}let m=a.get(d);Ht.has(m.type)||b(r,`rules.${l}`,`rule must reference a boolean node, not ${m.type}`),c[l]=d}}let f=fs(e.risk,r,t);if(r.length)return{ok:!1,errors:r,strategy:null};let u=Ut({version:Lt,id:e.id,name:e.name,venue:n.id,market:o,parameters:i,nodes:s,rules:c,risk:f});return{ok:!0,errors:[],strategy:u}}function W(e,t={}){let r=qt(e,t);if(!r.ok)throw new Re(r.errors);return r.strategy}function ds(e){let t=W(e);return JSON.stringify(Dt(t))}function ve(e){let t=ds(e);return Qo("sha256").update(t,"utf8").digest("hex")}function Je(e,t){if(!te(e))throw new Re([{path:"",message:"strategy must be a plain object"}]);if(!te(t))throw new Re([{path:"overrides",message:"must be a plain object"}]);let r=W(e),n={};for(let[i,s]of Object.entries(r.parameters))n[i]={value:s.value,min:s.min,max:s.max,step:s.step};let o=[];for(let[i,s]of Object.entries(t)){if(!Object.prototype.hasOwnProperty.call(n,i)){b(o,i,`unknown parameter "${i}"`);continue}let a=n[i];if(!z(s)){b(o,i,"override must be a finite number");continue}if(!Zr(s,a.min,a.max,a.step)){b(o,i,"override must lie on the declared min/max/step grid");continue}n[i]={...a,value:s}}if(o.length)throw new Re(o);return W({version:r.version,id:r.id,name:r.name,venue:r.venue,market:{coin:r.market.coin,interval:r.market.interval},parameters:n,nodes:r.nodes.map(i=>{let s={...i};return Array.isArray(i.inputs)&&(s.inputs=[...i.inputs]),s}),rules:{...r.rules},risk:{...r.risk}})}var Lt,Wr,Xr,es,ts,rs,ns,os,ss,is,Ht,Dr,qr,Ft,Br,as,zr,Vr,Jr,Gr,Re,ke=V(()=>{Mt();Lt=1,Wr=/^[a-z0-9][a-z0-9._-]{0,63}$/,Xr=/^[A-Za-z0-9][A-Za-z0-9._-]{0,63}$/,es=new Set(["open","high","low","close","volume","fundingRate","openInterest","premium","oiDelta","bookImbalance"]),ts=new Set(["sma","ema","rsi","macd","bollinger","atr"]),rs=new Set(["gt","gte","lt","lte","eq"]),ns=new Set(["and","or","not"]),os=new Set(["above","below"]),ss=new Set(["line","signal","histogram"]),is=new Set(["upper","middle","lower"]),Ht=new Set(["compare","logic","cross"]),Dr=new Set(["version","id","name","venue","market","parameters","nodes","rules","risk"]),qr=new Set(["value","min","max","step"]),Ft=new Set(["entryLong","entryShort","exitLong","exitShort"]),Br=new Set(["maxLeverage","maxNotionalUsd","positionSizePct","stopLossPct","takeProfitPct","cooldownBars","maxDailyLossPct","expiresAt"]),as=new Set(["id","type"]),zr={input:new Set(["id","type","field"]),constant:new Set(["id","type","value"]),indicator:new Set(["id","type","indicator","input","period","fastPeriod","slowPeriod","signalPeriod","stdDev","output"]),compare:new Set(["id","type","op","left","right"]),logic:new Set(["id","type","op","inputs"]),cross:new Set(["id","type","direction","left","right"])},Vr=16,Jr=128,Gr=100,Re=class extends Error{constructor(t){let r=t.map(n=>`${n.path}: ${n.message}`);super(`invalid strategy (${t.length} error${t.length===1?"":"s"}): ${r.join("; ")}`),this.name="StrategyValidationError",this.errors=t}}});function Ge(e){if(!Array.isArray(e))throw new TypeError("values must be an array");for(let t=0;t<e.length;t++){let r=e[t];if(typeof r!="number"||!Number.isFinite(r))throw new TypeError(`values[${t}] must be a finite number`)}}function we(e){if(!Number.isInteger(e)||e<=0)throw new TypeError("period must be a positive integer")}function ps(e){if(!Array.isArray(e))throw new TypeError("bars must be an array");for(let t=0;t<e.length;t++){let r=e[t];if(r==null||typeof r!="object")throw new TypeError(`bars[${t}] must be an object`);for(let n of["o","h","l","c"]){let o=r[n];if(typeof o!="number"||!Number.isFinite(o))throw new TypeError(`bars[${t}].${n} must be a finite number`)}if(r.h<r.l)throw new TypeError(`bars[${t}] high must be >= low`)}}function en(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=0;for(let o=0;o<e.length;o++)n+=e[o],o>=t&&(n-=e[o-t]),o>=t-1&&(r[o]=n/t);return r}function it(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=0;for(let s=0;s<t;s++)n+=e[s];let o=n/t;r[t-1]=o;let i=2/(t+1);for(let s=t;s<e.length;s++)o=i*e[s]+(1-i)*o,r[s]=o;return r}function tn(e,t){Ge(e),we(t);let r=new Array(e.length).fill(null);if(e.length<=t)return r;let n=0,o=0;for(let a=1;a<=t;a++){let c=e[a]-e[a-1];c>=0?n+=c:o-=c}let i=n/t,s=o/t;r[t]=Qr(i,s);for(let a=t+1;a<e.length;a++){let c=e[a]-e[a-1],f=c>0?c:0,u=c<0?-c:0;i=(i*(t-1)+f)/t,s=(s*(t-1)+u)/t,r[a]=Qr(i,s)}return r}function Qr(e,t){return e===0&&t===0?50:t===0?100:e===0?0:100-100/(1+e/t)}function rn(e,t={}){Ge(e);let r=t.fastPeriod,n=t.slowPeriod,o=t.signalPeriod;if(we(r),we(n),we(o),r>=n)throw new TypeError("fastPeriod must be < slowPeriod");let i=it(e,r),s=it(e,n),a=new Array(e.length).fill(null);for(let l=0;l<e.length;l++)i[l]!=null&&s[l]!=null&&(a[l]=i[l]-s[l]);let c=new Array(e.length).fill(null),f=new Array(e.length).fill(null),u=[];for(let l=0;l<a.length;l++)a[l]!=null&&u.push(l);if(u.length>=o){let l=0;for(let w=0;w<o;w++)l+=a[u[w]];let d=l/o,m=u[o-1];c[m]=d,f[m]=a[m]-d;let p=2/(o+1);for(let w=o;w<u.length;w++){let g=u[w];d=p*a[g]+(1-p)*d,c[g]=d,f[g]=a[g]-d}}return{line:a,signal:c,histogram:f}}function nn(e,t={}){Ge(e);let r=t.period,n=t.stdDev;if(we(r),typeof n!="number"||!Number.isFinite(n)||n<=0)throw new TypeError("stdDev must be a finite number > 0");let o=new Array(e.length).fill(null),i=new Array(e.length).fill(null),s=new Array(e.length).fill(null);if(e.length<r)return{upper:i,middle:o,lower:s};let a=0,c=0;for(let f=0;f<e.length;f++){let u=e[f];if(a+=u,c+=u*u,f>=r){let l=e[f-r];a-=l,c-=l*l}if(f>=r-1){let l=a/r,d=c/r-l*l;d<0&&d>-1e-12&&(d=0);let m=Math.sqrt(d);o[f]=l,i[f]=l+n*m,s[f]=l-n*m}}return{upper:i,middle:o,lower:s}}function on(e,t){ps(e),we(t);let r=new Array(e.length).fill(null);if(e.length<t)return r;let n=new Array(e.length);for(let s=0;s<e.length;s++){let a=e[s];if(s===0)n[s]=a.h-a.l;else{let c=e[s-1].c;n[s]=Math.max(a.h-a.l,Math.abs(a.h-c),Math.abs(a.l-c))}}let o=0;for(let s=0;s<t;s++)o+=n[s];let i=o/t;r[t-1]=i;for(let s=t;s<e.length;s++)i=(i*(t-1)+n[s])/t,r[s]=i;return r}var sn=V(()=>{});import{createHash as ms}from"node:crypto";var Bt,hs,ys,ws,an,cn=V(()=>{Bt=3,hs="7477966facc4ef928a94e6221c8fd238eef4fcbeec46b96ae1b89178e13c2d5f",ys="68f5b412a9975f04024cf9b9b6209b4bccedd52f176e95f34f786b3f53479c6a",ws="967fd45ecddd0d59ac0f662fe92ea813c32620ba751f249b4ace6cb6b809fb5e",an=ms("sha256").update(JSON.stringify({version:Bt,compilerSourceHash:hs,indicatorsSourceHash:ys,schemaSourceHash:ws})).digest("hex")});function ee(e){return typeof e=="number"&&Number.isFinite(e)}function Es(e){let t=new Map(e.map(a=>[a.id,a])),r=a=>{switch(a.type){case"indicator":return a.input?[a.input]:[];case"compare":case"cross":return[a.left,a.right];case"logic":return[...a.inputs];default:return[]}},n=new Map,o=new Map;for(let a of e)n.set(a.id,0),o.set(a.id,[]);for(let a of e)for(let c of r(a))t.has(c)&&(o.get(c).push(a.id),n.set(a.id,n.get(a.id)+1));let i=[];for(let[a,c]of n)c===0&&i.push(a);let s=[];for(;i.length;){let a=i.shift();s.push(a);for(let c of o.get(a))n.set(c,n.get(c)-1),n.get(c)===0&&i.push(c)}if(s.length!==e.length)throw new Error("strategy graph is cyclic");return s}function Ne(e,t){return e!=null&&typeof e=="object"&&"param"in e?t[e.param].value:e}function xs(e,t,r){if(!Array.isArray(e)||e.length===0)throw new TypeError("bars must be a non-empty array");if(!Number.isInteger(t)||t<0||t>=e.length)throw new RangeError("index out of range");let n=null;for(let o=0;o<=t;o++){let i=e[o];if(i==null||typeof i!="object"||Array.isArray(i))throw new TypeError(`bars[${o}] must be an object`);let{t:s,o:a,h:c,l:f,c:u,v:l}=i;if(!ee(s)&&(typeof s=="number"&&Number.isFinite(s)),!Number.isFinite(s))throw new TypeError(`bars[${o}].t must be finite`);for(let[d,m]of[["o",a],["h",c],["l",f],["c",u],["v",l]])if(!ee(m))throw new TypeError(`bars[${o}].${d} must be a finite number`);for(let[d,m]of[["o",a],["h",c],["l",f],["c",u]])if(!(m>0))throw new TypeError(`bars[${o}].${d} price must be positive`);if(l<0)throw new TypeError(`bars[${o}].v volume must be non-negative`);if(c<Math.max(a,u,f))throw new TypeError(`bars[${o}] high must be >= max(open, close, low)`);if(f>Math.min(a,u,c))throw new TypeError(`bars[${o}] low must be <= min(open, close, high)`);if(n!=null){if(!(s>n))throw new TypeError("bars t must be strictly increasing");if(s-n!==bs[r])throw new TypeError(`bars t must match ${r} cadence`)}if(n=s,"fundingRate"in i&&i.fundingRate!=null&&!ee(i.fundingRate))throw new TypeError(`bars[${o}].fundingRate must be finite when present`);if("openInterest"in i&&i.openInterest!=null){if(!ee(i.openInterest))throw new TypeError(`bars[${o}].openInterest must be finite when present`);if(i.openInterest<0)throw new TypeError(`bars[${o}].openInterest must be non-negative`)}for(let d of["premium","oiDelta"])if(d in i&&i[d]!=null&&!ee(i[d]))throw new TypeError(`bars[${o}].${d} must be finite when present`);if("bookImbalance"in i&&i.bookImbalance!=null){if(!ee(i.bookImbalance))throw new TypeError(`bars[${o}].bookImbalance must be finite when present`);if(i.bookImbalance<-1||i.bookImbalance>1)throw new TypeError(`bars[${o}].bookImbalance must be within [-1, 1]`)}}}function Ae(e,t,r,n,o,i){if(i.has(e))return i.get(e);let s=t.get(e),a;switch(s.type){case"input":{let c=gs[s.field];a=new Array(o+1);for(let f=0;f<=o;f++){let u=n[f][c];a[f]=u===void 0?null:u}break}case"constant":{let c=Ne(s.value,r);a=new Array(o+1).fill(c);break}case"indicator":{let c=s.period!=null?Ne(s.period,r):void 0;if(s.indicator==="atr"){let l=[];for(let d=0;d<=o;d++){let m=n[d];l.push({o:m.o,h:m.h,l:m.l,c:m.c})}a=on(l,c);break}let u=Ae(s.input,t,r,n,o,i).map((l,d)=>{if(l==null||!ee(l))throw new TypeError(`indicator input ${s.input} has non-finite value at ${d}`);return l});if(s.indicator==="sma")a=en(u,c);else if(s.indicator==="ema")a=it(u,c);else if(s.indicator==="rsi")a=tn(u,c);else if(s.indicator==="macd")a=rn(u,{fastPeriod:Ne(s.fastPeriod,r),slowPeriod:Ne(s.slowPeriod,r),signalPeriod:Ne(s.signalPeriod,r)})[s.output];else if(s.indicator==="bollinger")a=nn(u,{period:c,stdDev:Ne(s.stdDev,r)})[s.output];else throw new Error(`unsupported indicator ${s.indicator}`);break}case"compare":{let c=Ae(s.left,t,r,n,o,i),f=Ae(s.right,t,r,n,o,i);a=new Array(o+1);for(let u=0;u<=o;u++){let l=c[u],d=f[u];if(l==null||d==null||!ee(l)||!ee(d)){a[u]=!1;continue}switch(s.op){case"gt":a[u]=l>d;break;case"gte":a[u]=l>=d;break;case"lt":a[u]=l<d;break;case"lte":a[u]=l<=d;break;case"eq":a[u]=l===d;break;default:a[u]=!1}}break}case"logic":{let c=s.inputs.map(f=>Ae(f,t,r,n,o,i));a=new Array(o+1);for(let f=0;f<=o;f++)if(s.op==="not"){let u=c[0][f];a[f]=u===!0?!1:u===!1}else if(s.op==="and"){let u=!0;for(let l of c)if(l[f]!==!0){u=!1;break}a[f]=u}else if(s.op==="or"){let u=!1;for(let l of c)if(l[f]===!0){u=!0;break}a[f]=u}else a[f]=!1;break}case"cross":{let c=Ae(s.left,t,r,n,o,i),f=Ae(s.right,t,r,n,o,i);a=new Array(o+1),a[0]=!1;for(let u=1;u<=o;u++){let l=c[u-1],d=f[u-1],m=c[u],p=f[u];if(l==null||d==null||m==null||p==null||!ee(l)||!ee(d)||!ee(m)||!ee(p)){a[u]=!1;continue}s.direction==="above"?a[u]=l<=d&&m>p:a[u]=l>=d&&m<p}break}default:throw new Error(`unknown node type ${s.type}`)}return i.set(e,a),a}function X(e,t={}){let r=W(e);t&&Object.keys(t).length&&(r=Je(r,t));let n=new Map(r.nodes.map(m=>[m.id,m])),o=Object.freeze(Es(r.nodes)),i=r.parameters,s=new Set(r.nodes.filter(m=>m.type==="input").map(m=>m.field));if(r.nodes.some(m=>m.type==="indicator"&&m.indicator==="atr"))for(let m of["open","high","low","close"])s.add(m);let a=Object.freeze([...s].sort()),c=ve(r);function f(m,p){let w={};for(let S of o){let j=m.get(S);w[S]=j[p]}let g=S=>S!=null&&w[S]===!0;return{values:w,signals:{entryLong:g(r.rules.entryLong),entryShort:g(r.rules.entryShort),exitLong:g(r.rules.exitLong),exitShort:g(r.rules.exitShort)}}}function u(m,p){xs(m,p,r.market.interval);let w=new Map;for(let g of o)Ae(g,n,i,m,p,w);return w}function l(m,p){return f(u(m,p),p)}function d(m){if(!Array.isArray(m)||m.length===0)throw new TypeError("bars must be a non-empty array");let p=m.length-1,w=u(m,p);return Object.freeze(m.map((g,S)=>Object.freeze(f(w,S))))}return Object.freeze({strategy:r,strategyHash:c,compilerVersion:ze,compilerHash:Oe,requiredSeries:a,nodeOrder:o,evaluate:l,evaluateAll:d})}var ze,Oe,gs,bs,Pe=V(()=>{ke();sn();cn();ze=Bt,Oe=an,gs=Object.freeze({open:"o",high:"h",low:"l",close:"c",volume:"v",fundingRate:"fundingRate",openInterest:"openInterest",premium:"premium",oiDelta:"oiDelta",bookImbalance:"bookImbalance"}),bs=Object.freeze({"1m":6e4,"3m":18e4,"5m":3e5,"15m":9e5,"30m":18e5,"1h":36e5,"2h":72e5,"4h":144e5,"8h":288e5,"12h":432e5,"1d":864e5})});import{createHash as Ss}from"node:crypto";function Os(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function ie(e){return typeof e=="number"&&Number.isFinite(e)}function zt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)zt(t);return Object.freeze(e)}for(let t of Object.keys(e))zt(e[t]);return Object.freeze(e)}function at(e){if(Array.isArray(e))return e.map(at);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=at(e[r]);return t}return e}function Vt(e,t="result"){if(typeof e=="number"){if(!Number.isFinite(e))throw new Error(`non-finite backtest result at ${t}`);return}if(!(e==null||typeof e!="object")){if(Array.isArray(e)){e.forEach((r,n)=>Vt(r,`${t}[${n}]`));return}for(let[r,n]of Object.entries(e))Vt(n,`${t}.${r}`)}}function un(e){if(!Array.isArray(e)||e.length===0)throw new TypeError("bars must be a non-empty array");let t=null;for(let r=0;r<e.length;r++){let n=e[r];if(n==null||typeof n!="object"||Array.isArray(n))throw new TypeError(`bars[${r}] must be an object`);let{t:o,o:i,h:s,l:a,c,v:f}=n;if(!ie(o))throw new TypeError(`bars[${r}].t must be finite`);for(let[u,l]of[["o",i],["h",s],["l",a],["c",c],["v",f]])if(!ie(l))throw new TypeError(`bars[${r}].${u} must be a finite number`);for(let[u,l]of[["o",i],["h",s],["l",a],["c",c]])if(!(l>0))throw new TypeError(`bars[${r}].${u} price must be positive`);if(f<0)throw new TypeError(`bars[${r}].v volume must be non-negative`);if(s<Math.max(i,c,a))throw new TypeError(`bars[${r}] high must be >= max(open, close, low)`);if(a>Math.min(i,c,s))throw new TypeError(`bars[${r}] low must be <= min(open, close, high)`);if(t!=null&&!(o>t))throw new TypeError("bars t must be strictly increasing");if(t=o,"fundingRate"in n&&n.fundingRate!=null&&!ie(n.fundingRate))throw new TypeError(`bars[${r}].fundingRate must be finite when present`);if("fundingPaymentRate"in n&&n.fundingPaymentRate!=null&&!ie(n.fundingPaymentRate))throw new TypeError(`bars[${r}].fundingPaymentRate must be finite when present`);if("openInterest"in n&&n.openInterest!=null&&!ie(n.openInterest))throw new TypeError(`bars[${r}].openInterest must be finite when present`)}}function qe(e){if(!Array.isArray(e))throw new TypeError("bars must be an array");return e.length>0&&un(e),Ss("sha256").update(JSON.stringify(at(e)),"utf8").digest("hex")}function Ps(e){if(e==null&&(e={}),!Os(e))throw new TypeError("options must be a plain object");let t={...ks},r=new Set(["initialEquityUsd","takerFeeBps","builderFeeBps","slippageBps","latencyBars","maxVolumeParticipationPct","nowMs"]);for(let n of Object.keys(e))if(!r.has(n))throw new TypeError(`unknown option "${n}"`);if("initialEquityUsd"in e){if(!ie(e.initialEquityUsd)||e.initialEquityUsd<=0)throw new TypeError("initialEquityUsd must be a positive finite number");t.initialEquityUsd=e.initialEquityUsd}for(let n of["takerFeeBps","builderFeeBps","slippageBps"])if(n in e){let o=e[n];if(!ie(o)||o<0)throw new TypeError(`${n} must be a finite number >= 0`);if(n==="slippageBps"?o>=1e4:o>1e4)throw new TypeError(`${n} exceeds its safe basis-point bound`);t[n]=o}if("latencyBars"in e){let n=e.latencyBars;if(!Number.isInteger(n)||n<1)throw new TypeError("latencyBars must be an integer >= 1");t.latencyBars=n}if("maxVolumeParticipationPct"in e){let n=e.maxVolumeParticipationPct;if(!ie(n)||n<=0||n>100)throw new TypeError("maxVolumeParticipationPct must be in (0,100]");t.maxVolumeParticipationPct=n}if("nowMs"in e){if(!Number.isInteger(e.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");t.nowMs=e.nowMs}return t}function ct(e){return e/1e4}function As(e,t,r){let n=ct(r);return t==="long"?e*(1+n):e*(1-n)}function Ts(e,t,r){let n=ct(r);return t==="long"?e*(1-n):e*(1+n)}function ln(e,t,r){let n=Math.abs(e)*ct(t),o=Math.abs(e)*ct(r);return{taker:n,builder:o,total:n+o}}function $s(e,t){let r=e*(t.positionSizePct/100)*t.maxLeverage;return Math.min(r,t.maxNotionalUsd)}function _s(e,t,r){let n=r/100;return t==="long"?e*(1-n):e*(1+n)}function vs(e,t,r){let n=r/100;return t==="long"?e*(1+n):e*(1-n)}function Is(e,t,r,n){if(!(r>0))return t==="long"?0:Number.POSITIVE_INFINITY;let o=Math.min(.99,1/(2*r)+n/1e4);return t==="long"?e*(1-1/r)/(1-o):e*(1+1/r)/(1+o)}function js(e,t,r){return t==="long"?e.l<=r:e.h>=r}function Rs(e,t,r){return t==="long"?e.h>=r:e.l<=r}function Ns(e,t,r){return t==="long"?e.l<=r:e.h>=r}function Ke(e,t){for(let r of e.requiredSeries)if(Ms.includes(r)&&!t.every(n=>ie(n?.[r])))throw new Error(`strategy required series is absent: ${r}`)}function Ls(e){if(e.length<3)return 0;let t=[];for(let s=1;s<e.length;s++){let a=e[s-1].equity,c=e[s].equity;a>0&&t.push((c-a)/a)}if(t.length<2)return 0;let r=0;for(let s of t)r+=s;let n=r/t.length,o=0;for(let s of t)o+=(s-n)**2;let i=Math.sqrt(o/(t.length-1));return i>0?n/i:0}function Hs(e){let t=-1/0,r=0;for(let n of e){let o=n.equity;if(o>t&&(t=o),t>0){let i=(t-o)/t*100;i>r&&(r=i)}}return r}function he(e,t,r={}){let n=Ps(r);un(t);let o=qe(t);n.nowMs!==void 0&&W(e,{nowMs:n.nowMs});let i=X(e);if(Ke(i,t),n.nowMs!==void 0&&i.strategy.risk.expiresAt<=n.nowMs)throw new Error("strategy is expired: risk.expiresAt must be strictly greater than nowMs");let s=i.strategy.risk,a=i.evaluateAll(t),c=n.latencyBars,f=n.slippageBps,u=n.takerFeeBps,l=n.builderFeeBps,d=n.initialEquityUsd,m=0,p=0,w=0,g=0,S=0,j=[],T=[],x=[],N=[],$=[],h=null,M=0,U=null,K=d,k=!1,y=0,_=0,v=[],C=new Array(t.length).fill(0);function L(E){v.push(E)}function R(E){let H=t[E].v*(n.maxVolumeParticipationPct/100);return Math.max(0,H-C[E])}function P(E){if(!h)return d;let H=h.side==="long"?(E-h.entryPrice)*h.qty:(h.entryPrice-E)*h.qty;return d+H}function I(E,H,O){let q=O.o,F=$s(d,s);if(!(F>0)||!(q>0))return;let B=As(q,H,f),D=F/B,G=R(E),Ce=B*G;if(D>G){x.push({kind:"entry",barIndex:E,time:O.t,side:H,requestedNotionalUsd:F,maxFillNotionalUsd:Ce,reason:"volume_participation"});return}C[E]+=D;let oe=Math.abs(B-q)*D,ue=ln(F,u,l);d-=ue.total,m+=ue.taker,p+=ue.builder,g+=oe,S+=F,h={lifecycleEpoch:++_,side:H,entryBarIndex:E,entryReferencePrice:q,entryPrice:B,qty:D,notionalUsd:F,stop:_s(B,H,s.stopLossPct),take:vs(B,H,s.takeProfitPct),liq:Is(B,H,s.maxLeverage,u+l),entryFees:ue.taker,entryBuilderFees:ue.builder,entrySlippageUsd:oe,fundingAccrued:0}}function A(E,H,O,q){if(!h)return!1;let F=h.side,B=H,D=B;O!=="liquidation"&&q&&(D=Ts(B,F,f));let G=h.qty,Ce=G*D;if(O!=="liquidation"){let ir=R(E),Hn=D*ir;if(G>ir)return x.push({kind:"exit",barIndex:E,time:t[E].t,side:F,requestedNotionalUsd:Ce,maxFillNotionalUsd:Hn,reason:"volume_participation",triggerReason:O}),!1;C[E]+=G}let oe=ln(Ce,u,l),ue=O==="liquidation"?0:Math.abs(D-B)*G,Ue,mt;F==="long"?(Ue=(B-h.entryReferencePrice)*G,mt=(D-h.entryPrice)*G):(Ue=(h.entryReferencePrice-B)*G,mt=(h.entryPrice-D)*G),d+=mt,d-=oe.total,m+=oe.taker,p+=oe.builder,g+=ue,S+=Ce;let Ln={side:F,entryBarIndex:h.entryBarIndex,entryTime:t[h.entryBarIndex].t,entryPrice:h.entryPrice,exitBarIndex:E,exitTime:t[E].t,exitPrice:D,exitReason:O,qty:G,notionalUsd:h.notionalUsd,grossPnlUsd:Ue,feesUsd:h.entryFees+oe.taker,builderFeesUsd:h.entryBuilderFees+oe.builder,fundingUsd:h.fundingAccrued,slippageUsd:h.entrySlippageUsd+ue,netPnlUsd:Ue-(h.entryFees+oe.taker+h.entryBuilderFees+oe.builder)-h.fundingAccrued-(h.entrySlippageUsd+ue)};return j.push(Ln),O==="liquidation"&&T.push({barIndex:E,time:t[E].t,side:F,price:D,tradeIndex:j.length-1}),h=null,_+=1,y=E+1+(s.cooldownBars||0),!0}function Q(E,H,O,q){let F=E+1;if(F>=t.length)return;v.some(D=>D.kind==="exit"&&D.side===H&&D.fillBar===F&&D.epoch===q)||L({kind:"exit",side:H,signalBar:E,fillBar:F,reason:O,epoch:q})}function Z(E){let H=v.filter(O=>O.fillBar===E);for(let O=v.length-1;O>=0;O--)v[O].fillBar===E&&v.splice(O,1);H.sort((O,q)=>{let F=B=>B.kind==="exit"?0:1;return F(O)-F(q)});for(let O of H)if(O.kind==="exit"){if(!h||h.side!==O.side||h.lifecycleEpoch!==O.epoch)continue;let q=O.reason||"rule";A(E,t[E].o,q,!0)||Q(E,O.side,q,O.epoch)}else if(O.kind==="entry"){if(h||O.epoch!==_||E<y)continue;I(E,O.side,t[E])}}function re(E){if(!h)return;let H=t[E],O=H.fundingPaymentRate;if(O==null||!ie(O)||O===0)return;let q=Math.abs(h.qty*H.c),F=O*q;h.side==="long"?(d-=F,h.fundingAccrued+=F,w+=F):(d+=F,h.fundingAccrued-=F,w-=F)}function ce(E){if(!h)return;let H=t[E].o;(h.side==="long"?H<=h.liq:H>=h.liq)&&A(E,H,"liquidation",!1)}function Xe(E){if(!h)return;let H=t[E],O=h.side,q=Ns(H,O,h.liq),F=js(H,O,h.stop),B=Rs(H,O,h.take),D=G=>O==="long"?Math.min(G,H.o):Math.max(G,H.o);if(q){A(E,D(h.liq),"liquidation",!1);return}if(F&&B){A(E,D(h.stop),"stop_loss",!0)||Q(E,O,"stop_loss",h.lifecycleEpoch);return}if(F){A(E,D(h.stop),"stop_loss",!0)||Q(E,O,"stop_loss",h.lifecycleEpoch);return}B&&(A(E,h.take,"take_profit",!0)||Q(E,O,"take_profit",h.lifecycleEpoch))}for(let E=0;E<t.length;E++){let H=Math.floor(t[E].t/864e5);H!==U&&(U=H,K=P(t[E].o),k=!1),ce(E),Z(E),Xe(E),re(E),!k&&P(t[E].c)<=K*(1-s.maxDailyLossPct/100)&&(k=!0,N.push({type:"daily_loss_limit",barIndex:E,time:t[E].t,message:"daily loss limit reached; new entries blocked for UTC day"}));let O=a[E].signals,q=E+c;if(h)(h.side==="long"&&O.exitLong===!0||h.side==="short"&&O.exitShort===!0)&&q<t.length&&(v.some(G=>G.kind==="exit"&&G.side===h.side&&G.fillBar===q&&G.epoch===h.lifecycleEpoch)||L({kind:"exit",side:h.side,signalBar:E,fillBar:q,reason:"rule",epoch:h.lifecycleEpoch}));else{let B=O.entryLong===!0,D=O.entryShort===!0;B&&D?N.push({type:"conflicting_entry_signals",barIndex:E,time:t[E].t,message:"conflicting entry signals; no position opened"}):!k&&(B||D)&&q<t.length&&E>=y&&L({kind:"entry",side:B?"long":"short",signalBar:E,fillBar:q,epoch:_})}let F=d;h&&(M+=1,F=P(t[E].c)),$.push({barIndex:E,time:t[E].t,equity:F,positionSide:h?h.side:null})}let Ze=null;if(h){let E=t.length-1;if(A(E,t[E].c,"end_of_data",!0))$[E]={barIndex:E,time:t[E].t,equity:d,positionSide:null};else{let O=P(t[E].c);Ze={side:h.side,entryBarIndex:h.entryBarIndex,entryTime:t[h.entryBarIndex].t,entryPrice:h.entryPrice,qty:h.qty,notionalUsd:h.notionalUsd,markPrice:t[E].c,markedEquityUsd:O},N.push({type:"open_position_at_end",barIndex:E,time:t[E].t,message:"end-of-data exit missed; position remains open and marked"})}}let He=(h?P(t[t.length-1].c):d)-n.initialEquityUsd,dt=He/n.initialEquityUsd*100,Fe=0,ge=0,le=0;for(let E of j)E.netPnlUsd>0?(Fe+=1,ge+=E.netPnlUsd):E.netPnlUsd<0&&(le+=-E.netPnlUsd);let $e=j.length,be=$e===0?0:Fe/$e,pt=0;le>0?pt=ge/le:ge>0&&(pt=1e12);let Nn={netPnlUsd:He,netPnlPct:dt,maxDrawdownPct:Hs($),winRate:be,profitFactor:pt,tradeCount:$e,sharpe:Ls($),turnoverUsd:S,exposurePct:M/t.length*100},Mn={initialEquityUsd:n.initialEquityUsd,takerFeeBps:n.takerFeeBps,builderFeeBps:n.builderFeeBps,slippageBps:n.slippageBps,latencyBars:n.latencyBars,maxVolumeParticipationPct:n.maxVolumeParticipationPct},sr={barsHash:o,strategyHash:i.strategyHash,compilerHash:Oe,compilerVersion:ze,config:Mn,trades:j,equityCurve:$,metrics:Nn,costs:{feesUsd:m,builderFeesUsd:p,fundingUsd:w,slippageUsd:g},liquidations:T,missedFills:x,openPositionAtEnd:Ze,flags:N};return Vt(sr),zt(at(sr))}var ks,Ms,ot=V(()=>{Pe();ke();ks=Object.freeze({initialEquityUsd:1e4,takerFeeBps:3.5,builderFeeBps:2,slippageBps:2,latencyBars:1,maxVolumeParticipationPct:100});Ms=Object.freeze(["fundingRate","openInterest","premium","oiDelta","bookImbalance"])});import{createHash as Fs}from"node:crypto";function Js(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Jt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Jt(t);return Object.freeze(e)}for(let t of Object.keys(e))Jt(e[t]);return Object.freeze(e)}function Gs(e){return String(e).trim().replace(/\s+/g," ")}function Ks(e){let t=e.match(/\b(long|short)\b/i);return t?t[1].toLowerCase():null}function Ys(e){for(let r of Us)if(new RegExp(`\\b${r}\\b`,"i").test(e))return r;let t=e.match(/\b([A-Z][A-Z0-9]{1,11})\b/);return t?t[1]:null}function Ws(e){let t=e.match(/\bon\s+(1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/i);if(!t)return"15m";let r=t[1].toLowerCase();return Cs.has(r)?r:null}function Xs(e){let t={...qs},r=e.match(/stop\s*loss\s*(\d+(?:\.\d+)?)\s*%?/i);r&&(t.stopLossPct=Number(r[1]));let n=e.match(/take\s*profit\s*(\d+(?:\.\d+)?)\s*%?/i);n&&(t.takeProfitPct=Number(n[1]));let o=e.match(/leverage\s*(\d+(?:\.\d+)?)/i);o&&(t.maxLeverage=Number(o[1]));let i=e.match(/position\s*size\s*(\d+(?:\.\d+)?)\s*%?/i);i&&(t.positionSizePct=Number(i[1]));let s=e.match(/max\s*notional\s*(?:usd\s*)?\$?\s*(\d+(?:\.\d+)?)/i);return s&&(t.maxNotionalUsd=Number(s[1])),t}function Zs(e){return[/\bon\s+(?:1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/gi,/\bstop\s*loss\s*\d+(?:\.\d+)?\s*%?/gi,/\btake\s*profit\s*\d+(?:\.\d+)?\s*%?/gi,/\bleverage\s*\d+(?:\.\d+)?/gi,/\bposition\s*size\s*\d+(?:\.\d+)?\s*%?/gi,/\bmax\s*notional\s*(?:usd\s*)?\$?\s*\d+(?:\.\d+)?/gi].some(r=>(e.match(r)??[]).length>1)}function Qs(e){let t=Fs("sha256").update(e,"utf8").digest("hex").slice(0,10),r=e.toLowerCase().replace(/[^a-z0-9]+/g,"-").replace(/^-+|-+$/g,"").slice(0,40),o=`${r.length?r:"draft"}-${t}`.replace(/[^a-z0-9._-]/g,"").slice(0,64);return/^[a-z0-9]/.test(o)?o:`d${o}`.slice(0,64)}function ei(e){let t=e.match(/\bema\s*(\d+)\s*cross(?:es)?\s*(above|below)\s*ema\s*(\d+)\b/i);if(!t)return null;let r=Number(t[1]),n=t[2].toLowerCase(),o=Number(t[3]);if(!(r>0)||!(o>0)||r===o)return null;let i=/\b(exit\s+on\s+reverse|reverse\s+exit)\b/i.test(e);return{kind:"ema_cross",fast:r,slow:o,direction:n,reverse:i}}function ti(e){let t=e.match(/\brsi\s*(\d+)\s*(above|below)\s*(-?\d+(?:\.\d+)?)/i);if(!t)return null;let r=Number(t[3]);return!Number.isFinite(r)||r<=0||r>=100?null:{kind:"rsi",period:Number(t[1]),op:t[2].toLowerCase(),threshold:r}}function ri(e){let t=e.match(/\bfunding\s*rate\s*(above|below)\s*(-?\d+(?:\.\d+)?)(%?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return t[3]==="%"&&(r=r/100),{kind:"funding",op:t[1].toLowerCase(),threshold:r}}function ni(e){let t=e.match(/\bopen\s*interest\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return!Number.isFinite(r)||r<0?null:{kind:"open_interest",op:t[1].toLowerCase(),threshold:r}}function oi(e){let t=e.match(/\bpremium\s*(above|below)\s*(-?\d+(?:\.\d+)?)(%?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return Number.isFinite(r)?(t[3]==="%"&&(r=r/100),{kind:"premium",op:t[1].toLowerCase(),threshold:r}):null}function si(e){let t=e.match(/\boi\s*delta\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return Number.isFinite(r)?{kind:"oi_delta",op:t[1].toLowerCase(),threshold:r}:null}function ii(e){let t=e.match(/\bbook\s*imbalance\s*(above|below)\s*(-?\d+(?:\.\d+)?)(?=\s|,|$)/i);if(!t)return null;let r=Number(t[2]);return!Number.isFinite(r)||r<-1||r>1?null:{kind:"book_imbalance",op:t[1].toLowerCase(),threshold:r}}function ai(e,t){let r=e.replace(/^(long|short)\s+[A-Z][A-Z0-9]{1,11}\s+when\s+/i,"");if(r===e)return!1;t.kind==="ema_cross"?r=r.replace(/^ema\s*\d+\s*cross(?:es)?\s*(?:above|below)\s*ema\s*\d+\b/i,""):t.kind==="rsi"?r=r.replace(/^rsi\s*\d+\s*(?:above|below)\s*\d+(?:\.\d+)?\b/i,""):t.kind==="open_interest"?r=r.replace(/^open\s*interest\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):t.kind==="premium"?r=r.replace(/^premium\s*(?:above|below)\s*-?\d+(?:\.\d+)?%?(?=\s|,|$)/i,""):t.kind==="oi_delta"?r=r.replace(/^oi\s*delta\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):t.kind==="book_imbalance"?r=r.replace(/^book\s*imbalance\s*(?:above|below)\s*-?\d+(?:\.\d+)?(?=\s|,|$)/i,""):r=r.replace(/^funding\s*rate\s*(?:above|below)\s*-?\d+(?:\.\d+)?%?(?=\s|,|$)/i,"");let n=[/(?:,\s*)?\bon\s+(?:1m|3m|5m|15m|30m|1h|2h|4h|8h|12h|1d)\b/gi,/(?:,\s*)?\bstop\s*loss\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\btake\s*profit\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\bleverage\s*\d+(?:\.\d+)?/gi,/(?:,\s*)?\bposition\s*size\s*\d+(?:\.\d+)?\s*%?/gi,/(?:,\s*)?\bmax\s*notional\s*(?:usd\s*)?\$?\s*\d+(?:\.\d+)?/gi];t.kind==="ema_cross"&&n.push(/(?:,\s*)?\b(?:exit\s+on\s+reverse|reverse\s+exit)\b/gi);for(let o of n)r=r.replace(o,"");return r.replace(/[\s,;]+/g,"")===""}function fn(e){let t=Math.max(2,Math.floor(e/2));return{value:e,min:Math.max(2,e-t),max:Math.min(500,e+t),step:1}}function ci({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let c=[{id:"c",type:"input",field:"close"},{id:"emaLeft",type:"indicator",indicator:"ema",input:"c",period:{param:"ema_left_period"}},{id:"emaRight",type:"indicator",indicator:"ema",input:"c",period:{param:"ema_right_period"}},{id:"cross",type:"cross",direction:a.direction,left:"emaLeft",right:"emaRight"}],f={entryLong:null,entryShort:null,exitLong:null,exitShort:null};if(e==="long"?f.entryLong="cross":f.entryShort="cross",a.reverse){let u=a.direction==="above"?"below":"above";c.push({id:"crossRev",type:"cross",direction:u,left:"emaLeft",right:"emaRight"}),e==="long"?f.exitLong="crossRev":f.exitShort="crossRev"}return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{ema_left_period:fn(a.fast),ema_right_period:fn(a.slow)},nodes:c,rules:f,risk:{...n,expiresAt:o}}}function li({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let c=[{id:"c",type:"input",field:"close"},{id:"rsi",type:"indicator",indicator:"rsi",input:"c",period:a.period},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"rsi",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:c,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function ui({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let c=[{id:"fr",type:"input",field:"fundingRate"},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"fr",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:c,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function fi({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let c=[{id:"oi",type:"input",field:"openInterest"},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"oi",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:c,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function pi({side:e,coin:t,interval:r,risk:n,expiresAt:o,id:i,name:s,spec:a}){let f=[{id:"sig_input",type:"input",field:di[a.kind]},{id:"thr",type:"constant",value:a.threshold},{id:"sig",type:"compare",op:a.op==="above"?"gt":"lt",left:"sig_input",right:"thr"}];return{version:1,id:i,name:s,venue:"hyperliquid",market:{coin:t,interval:r},parameters:{},nodes:f,rules:{entryLong:e==="long"?"sig":null,entryShort:e==="short"?"sig":null,exitLong:null,exitShort:null},risk:{...n,expiresAt:o}}}function dn(e,t={}){if(typeof e!="string")throw new Y("prompt must be a string");if(e.length>1e3)throw new Y("prompt length must be <= 1000");if(!Js(t))throw new Y("options must be a plain object");if(!Number.isInteger(t.nowMs))throw new Y("options.nowMs is required integer epoch ms");let r=t.nowMs,n=Vs;if("expiresInMs"in t){if(!Number.isInteger(t.expiresInMs))throw new Y("expiresInMs must be an integer");if(n=t.expiresInMs,n<Bs||n>zs)throw new Y("expiresInMs must be between 1h and 30d")}if(Ds.test(e))throw new Y(`prompt appears to contain secrets and is rejected. ${Me}`);let o=Gs(e);if(!o)throw new Y(`empty prompt. ${Me}`);if(Zs(o))throw new Y(`duplicate interval or risk clause. ${Me}`);let i=Ks(o),s=Ys(o),a=Ws(o);if(!i||!s||!a)throw new Y(`could not parse side/coin/interval. ${Me}`);let c=Xs(o);if(!(c.maxLeverage>0)||c.maxLeverage>50)throw new Y("leverage out of range");if(!(c.positionSizePct>0)||c.positionSizePct>100)throw new Y("position size out of range");let f=r+n,u=Qs(o),l=`Draft ${s} ${i}`.slice(0,100),d=ei(o),m=ti(o),p=ri(o),w=ni(o),g=oi(o),S=si(o),j=ii(o),T=[d,m,p,w,g,S,j].filter(Boolean);if(T.length!==1)throw new Y(`unsupported or ambiguous prompt. ${Me}`);if(!ai(o,T[0]))throw new Y(`unsupported or ambiguous prompt. ${Me}`);let x,N=T[0],$={side:i,coin:s,interval:a,risk:c,expiresAt:f,id:u,name:l,spec:N};N.kind==="ema_cross"?x=ci($):N.kind==="rsi"?x=li($):N.kind==="open_interest"?x=fi($):N.kind==="funding"?x=ui($):x=pi($);let h=qt(x,{nowMs:r});if(!h.ok)throw new Y(`draft failed validation: ${h.errors.map(M=>M.message).join("; ")}`);return Jt(W(x,{nowMs:r}))}var Y,Cs,Us,Ds,Me,qs,Bs,zs,Vs,di,pn=V(()=>{ke();Y=class extends Error{constructor(t){super(t),this.name="StrategyDraftError"}},Cs=new Set(["1m","3m","5m","15m","30m","1h","2h","4h","8h","12h","1d"]),Us=new Set(["BTC","ETH","SOL","HYPE"]),Ds=/\b(mnemonic|private\s*key|privkey|seed\s*phrase|seed\b|api[_-]?key|secret\s*key|wallet\s*key|passphrase)\b/i,Me="Supported grammar: (1) EMA cross: <long|short> <COIN> when EMA <n> crosses <above|below> EMA <m> [on <interval>] [, exit on reverse] [, risk knobs]; (2) RSI: <long|short> <COIN> when RSI <n> <above|below> <threshold> [on <interval>] [, risk knobs]; (3) funding: <long|short> <COIN> when funding rate <above|below> <decimal|percent%> [on <interval>] [, risk knobs]; (4) open interest: <long|short> <COIN> when open interest <above|below> <non-negative number> [on <interval>] [, risk knobs]; (5) premium: <long|short> <COIN> when premium <above|below> <decimal|percent%> [on <interval>] [, risk knobs]; (6) oi delta: <long|short> <COIN> when oi delta <above|below> <number> [on <interval>] [, risk knobs]; (7) book imbalance: <long|short> <COIN> when book imbalance <above|below> <-1..1> [on <interval>] [, risk knobs]. Risk knobs: stop loss %, take profit %, leverage, position size %, max notional USD. Coins: BTC ETH SOL HYPE or uppercase token <=12 chars. Intervals: 1m 3m 5m 15m 30m 1h 2h 4h 8h 12h 1d.",qs=Object.freeze({maxLeverage:1,maxNotionalUsd:100,positionSizePct:5,stopLossPct:2,takeProfitPct:4,cooldownBars:1,maxDailyLossPct:3}),Bs=36e5,zs=30*864e5,Vs=864e5;di=Object.freeze({funding:"fundingRate",open_interest:"openInterest",premium:"premium",oi_delta:"oiDelta",book_imbalance:"bookImbalance"})});import{createHash as mi}from"node:crypto";function yn(e){let t=String(e).toLowerCase();return t==="holdout"||t==="test"||t==="oos"||t.includes("holdout")||t.includes("oos")?!0:t==="testbars"||t.endsWith("testbars")||t.startsWith("test")||t.endsWith("test")?!t.includes("backtest"):!1}function wn(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Kt(e){if(e==null||typeof e!="object"||Object.isFrozen(e))return e;if(Array.isArray(e)){for(let t of e)Kt(t);return Object.freeze(e)}for(let t of Object.keys(e))Kt(e[t]);return Object.freeze(e)}function Ye(e){if(Array.isArray(e))return e.map(Ye);if(e!=null&&typeof e=="object"){let t={};for(let r of Object.keys(e).sort())t[r]=Ye(e[r]);return t}return e}function lt(e){return JSON.stringify(Ye(e))}function hi(e){let{min:t,max:r,step:n}=e;if(!(n>0)||t>r)return[];let o=[],i=Math.floor((r-t)/n+1e-9);for(let a=0;a<=i;a++){let c=t+a*n;if(c>r+1e-9)break;let f=Math.abs(c-Math.round(c))<1e-9?Math.round(c):Number(c.toPrecision(12));f<t-1e-9||f>r+1e-9||o.push(f)}if(o.length===0)return[];let s=o[o.length-1];if(Math.abs(s-r)>1e-9){let a=(r-t)/n;Math.abs(a-Math.round(a))<=1e-9&&o.push(r)}return o}function yi(e,t){if(e.length===0)return[];let r=[{}];for(let n of e){let o=t[n],i=[];for(let s of r)for(let a of o)i.push({...s,[n]:a});r=i}return r.sort((n,o)=>{let i=lt(n),s=lt(o);return i<s?-1:i>s?1:0}),r}function Gt(e,t,r,n,o){let i=0;if(e==="maxDrawdownPct"){if(i=t.maxDrawdownPct-n.maxDrawdownPct,i!==0)return i<0}else if(i=t[e]-n[e],i!==0)return i>0;let s=lt(r),a=lt(o);return s<a}function gn(e,t,r={}){if(!wn(r))throw new TypeError("options must be a plain object");for(let x of Object.keys(r))if(yn(x))throw new TypeError(`options must not include holdout/test/oos key "${x}"`);let n=new Set(["maxTrials","objective","backtestOptions"]);for(let x of Object.keys(r))if(!n.has(x))throw new TypeError(`unknown option "${x}"`);let o=64;if("maxTrials"in r){let x=r.maxTrials;if(!Number.isInteger(x)||x<1||x>mn)throw new TypeError(`maxTrials must be an integer 1..${mn}`);o=x}let i=r.objective??"netPnlUsd";if(!hn.has(i))throw new TypeError(`objective must be one of ${[...hn].join("|")}`);let s=r.backtestOptions??{};if(!wn(s))throw new TypeError("backtestOptions must be a plain object");for(let x of Object.keys(s))if(yn(x))throw new TypeError(`backtestOptions must not include holdout/test/oos key "${x}"`);let a=W(e),c=Object.keys(a.parameters).sort();if(c.length===0)throw new Error("optimizeStrategy requires at least one declared parameter");let f={},u=1;for(let x of c){let N=hi(a.parameters[x]);if(N.length===0)throw new Error(`parameter "${x}" produces an empty grid`);f[x]=N,u*=N.length}let l=yi(c,f);if(l.length===0)throw new Error("parameter grid is empty");let d=l.slice(0,o),m=[],p=null,w=null;for(let x of d){let N=Je(a,x),$=he(N,t,s);w==null&&(w=$.config);let h={netPnlUsd:$.metrics.netPnlUsd,netPnlPct:$.metrics.netPnlPct,maxDrawdownPct:$.metrics.maxDrawdownPct,winRate:$.metrics.winRate,profitFactor:$.metrics.profitFactor,tradeCount:$.metrics.tradeCount,sharpe:$.metrics.sharpe,turnoverUsd:$.metrics.turnoverUsd},M={parameters:{...x},metrics:h};m.push(M),(!p||Gt(i,h,x,p.metrics,p.parameters))&&(p=M)}m.sort((x,N)=>Gt(i,x.metrics,x.parameters,N.metrics,N.parameters)?-1:Gt(i,N.metrics,N.parameters,x.metrics,x.parameters)?1:0);let g={...p.parameters},S=Je(a,g),j={strategyHash:ve(a),compilerHash:Oe,trainBarsHash:qe(t),backtestConfig:w,objective:i,maxTrials:o,trialsRun:m.length,candidates:m,bestParameters:g,bestStrategy:S},T={id:mi("sha256").update(JSON.stringify(Ye(j)),"utf8").digest("hex"),...j};return Kt(Ye(JSON.parse(JSON.stringify(T))))}var mn,hn,bn=V(()=>{Pe();ke();ot();mn=256,hn=new Set(["netPnlUsd","profitFactor","sharpe","maxDrawdownPct"])});import pe from"node:fs";import ut from"node:path";function ft(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function ae(e){return e==null?e:JSON.parse(JSON.stringify(e))}function gi(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function Le(e,t="record"){if(Array.isArray(e)){e.forEach((r,n)=>Le(r,`${t}[${n}]`));return}if(ft(e))for(let[r,n]of Object.entries(e)){let o=gi(r);if(wi.some(i=>o.includes(i)))throw new Error(`shadow-store: forbidden secret-like field at ${t}.${r}`);Le(n,`${t}.${r}`)}}function bi(e){if(typeof e!="string"||!e||!ut.isAbsolute(e))throw new Error("shadow-store: path must be an absolute path")}function En(e){let t;try{t=pe.lstatSync(e)}catch(n){if(n&&n.code==="ENOENT")return;throw n}if(t.isSymbolicLink())throw new Error("shadow-store: store path must not be a symlink");if(!t.isFile())throw new Error("shadow-store: store path must be a regular file");if(t.mode&511&18)throw new Error("shadow-store: store file must not be group or world writable")}function Ei(){return{version:Wt,runners:[]}}function xn(e,t){let r;try{r=JSON.parse(e)}catch{throw new Error("shadow-store: malformed JSON")}if(!ft(r))throw new Error("shadow-store: malformed JSON root");if(r.version!==Wt)throw new Error(`shadow-store: unsupported version ${r.version}`);if(!Array.isArray(r.runners))throw new Error("shadow-store: runners must be an array");return Le(r,ut.basename(t)),{version:Wt,runners:r.runners.map(n=>ae(n))}}function Sn(e,t){Le(t,"store");let r=ut.dirname(e);pe.mkdirSync(r,{recursive:!0,mode:448});let n=ut.join(r,`.shadow-store.${process.pid}.${Date.now()}.tmp`),o=`${JSON.stringify(t)}
|
|
3
|
+
`;try{pe.writeFileSync(n,o,{mode:384,flag:"wx"}),pe.renameSync(n,e);try{pe.chmodSync(e,384)}catch{}}catch(i){try{pe.unlinkSync(n)}catch{}throw i}}function kn(e={}){let t=e.path;if(bi(t),En(t),pe.existsSync(t)?xn(pe.readFileSync(t,"utf8"),t):Sn(t,Ei()),Yt.has(t))return Yt.get(t);let r=!1,n=[];function o(){if(r)return;let p=n.shift();if(p){r=!0;try{let w=p.fn();r=!1,p.resolve(w),o()}catch(w){r=!1,p.reject(w),o()}}}function i(p){if(!r&&n.length===0){r=!0;try{return p()}finally{r=!1,queueMicrotask(o)}}return new Promise((w,g)=>{n.push({fn:p,resolve:w,reject:g}),queueMicrotask(o)})}function s(){return En(t),xn(pe.readFileSync(t,"utf8"),t)}function a(p){Sn(t,p)}function c(p){if(!ft(p)||typeof p.id!="string"||!p.id)throw new Error("shadow-store: create requires record with string id");Le(p,"record");let w=s();if(w.runners.some(S=>S.id===p.id))throw new Error(`shadow-store: runner id already exists: ${p.id}`);let g=ae(p);return w.runners.push(g),a(w),ae(g)}function f(p){let w=s().runners.find(g=>g.id===p);return w?ae(w):null}function u(){return s().runners.map(p=>ae(p))}function l(p,w){if(typeof w!="function")throw new Error("shadow-store: updater must be a function");let g=s(),S=g.runners.findIndex(x=>x.id===p);if(S<0)throw new Error(`shadow-store: runner not found: ${p}`);let j=ae(g.runners[S]),T=w(j);if(!ft(T)||T.id!==p)throw new Error("shadow-store: updater must return record with same id");return Le(T,"record"),g.runners[S]=ae(T),a(g),ae(g.runners[S])}function d(p){let w=s(),g=w.runners.findIndex(j=>j.id===p);if(g<0)throw new Error(`shadow-store: runner not found: ${p}`);let S=ae(w.runners[g]);return S.status!=="stopped"&&(S.status="stopped",w.runners[g]=S,a(w)),ae(w.runners[g])}let m={create(p){return i(()=>c(p))},get(p){return f(p)},list(){return u()},update(p,w){return i(()=>l(p,w))},stop(p){return i(()=>d(p))}};return Yt.set(t,m),m}var Wt,wi,Yt,On=V(()=>{Wt=1,wi=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"];Yt=new Map});import{createHash as Qt}from"node:crypto";function Xt(e){return e==null?e:JSON.parse(JSON.stringify(e))}function Zt(e){return Array.isArray(e)?e.map(Zt):e&&typeof e=="object"?Object.fromEntries(Object.keys(e).sort().map(t=>[t,Zt(e[t])])):e}function An(e){if(!e||typeof e!="object"||Array.isArray(e))throw new TypeError("shadow-runner: record must be an object");return Qt("sha256").update(JSON.stringify(Zt(e))).digest("hex")}function xi(e,t,r,n,o){return Qt("sha256").update(`${e}|${t}|${r}|${n}|${o}`).digest("hex")}function Si(e,t,r,n){return Qt("sha256").update(`shadow|${e}|${t}|${r}|${n??""}`).digest("hex")}function ki(e){return e==="entryLong"||e==="exitShort"?"buy":e==="entryShort"||e==="exitLong"?"sell":e}function Pn(e){return e==="entryLong"||e==="entryShort"}function er({storePath:e,clock:t=Date.now}={}){if(typeof e!="string"||!e)throw new Error("shadow-runner: storePath required");let r=kn({path:e});function n({strategy:c,evidenceId:f=null}={}){let u=X(c),l=f==null?null:String(f),d=r.list().filter(S=>S.status==="running"&&S.strategyHash===u.strategyHash&&S.compilerHash===u.compilerHash&&S.evidenceId===l).sort((S,j)=>S.createdAt-j.createdAt||S.id.localeCompare(j.id))[0];if(d)return Xt(d);let m=t(),p=Si(m,u.strategyHash,u.compilerHash,l),w=r.get(p);if(w)return Xt(w);let g={id:p,strategy:Xt(u.strategy),strategyHash:u.strategyHash,compilerHash:u.compilerHash,evidenceId:l,status:"running",cursor:null,intendedOrders:[],fills:[],missedFills:[],markouts:[],createdAt:m,updatedAt:m,position:null,cooldownBarsRemaining:0,cooldownStartT:null,lastProcessedBarIndex:-1};return r.create(g)}function o(c){return r.get(c)}function i(){return r.list()}function s(c){return r.stop(c)}function a(c,f,{markoutHorizons:u=[1,4,12]}={}){if(!Array.isArray(f))throw new TypeError("shadow-runner: bars must be an array");return r.update(c,l=>{if(l.status!=="running")throw new Error("shadow-runner: runner is stopped");if(f.length===0)return l;let m=X(l.strategy).evaluateAll(f),p=new Map;for(let y=0;y<f.length;y++)p.set(f[y].t,y);let w=l.cursor,g=[];for(let y=0;y<f.length;y++){let _=f[y].t;(w==null||_>w)&&g.push(y)}if(g.length===0)return l;let S=new Map(l.intendedOrders.map(y=>[y.id,y])),j=new Set(l.fills.map(y=>y.orderId)),T=new Map(l.missedFills.map(y=>[y.orderId,y])),x=(y,_)=>`${y}|${_}`,N=new Map(l.markouts.map(y=>[x(y.orderId,y.horizon),y])),$=l.position?{...l.position}:null,h=Number.isInteger(l.cooldownBarsRemaining)?Math.max(0,l.cooldownBarsRemaining):0,M=Number.isFinite(l.cooldownStartT)?l.cooldownStartT:null;function U({action:y,signalBarT:_,signalIndex:v}){let C=ki(y),L=xi(l.id,l.strategyHash,_,C,y);if(S.has(L))return S.get(L);let R=v+1,P=R<f.length,I={id:L,action:y,type:y,side:C,signalBarT:_,fillBarT:P?f[R].t:null,status:P?"open":"missed"};return S.set(L,I),l.intendedOrders.push(I),I}function K(y,_,v){if(j.has(y.id))return;let C={orderId:y.id,action:Pn(y.action)?"entry":"exit",side:y.side,price:_.o,barT:_.t,signalBarT:y.signalBarT,barIndex:v};if(l.fills.push(C),j.add(y.id),y.status="filled",y.fillBarT=_.t,T.has(y.id)&&(T.delete(y.id),l.missedFills=l.missedFills.filter(L=>L.orderId!==y.id)),Pn(y.action)){$={side:y.action==="entryLong"?"long":"short",entryOrderId:y.id,entryBarT:_.t,entryPrice:_.o,entryBarIndex:v};for(let L of u){let R=x(y.id,L);if(N.has(R))continue;let P={orderId:y.id,horizon:L,entryBarT:_.t,entryPrice:_.o,side:$.side,status:"pending",close:null,barT:null};N.set(R,P),l.markouts.push(P)}}else $=null,h=Number(l.strategy?.risk?.cooldownBars)||0,M=_.t}function k(y){if(j.has(y.id)||T.has(y.id))return;let _={orderId:y.id,action:y.action,side:y.side,signalBarT:y.signalBarT,status:"missed"};T.set(y.id,_),l.missedFills.push(_),y.status="missed"}for(let y of l.intendedOrders){if(y.status==="filled"||j.has(y.id))continue;let _=p.get(y.signalBarT);if(_==null)continue;let v=_+1;v<f.length&&(w==null||f[v].t>w)&&K(y,f[v],v)}for(let y of g){let _=f[y],v=m[y].signals,C=$,L=P=>{if($||h>0&&(M==null||_.t>=M))return;let A=U({action:P,signalBarT:_.t,signalIndex:y}),Q=y+1;Q<f.length?K(A,f[Q],Q):k(A)},R=P=>{if(!$||$.side==="long"&&P!=="exitLong"||$.side==="short"&&P!=="exitShort")return;let I=U({action:P,signalBarT:_.t,signalIndex:y}),A=y+1;A<f.length?K(I,f[A],A):k(I)};C?(v.exitLong&&R("exitLong"),v.exitShort&&R("exitShort")):v.entryLong&&v.entryShort||(v.entryLong&&L("entryLong"),v.entryShort&&L("entryShort")),h>0&&M!=null&&_.t>=M&&(h-=1,h===0&&(M=null)),l.cursor=_.t,l.lastProcessedBarIndex=y}for(let y of l.markouts){if(y.status!=="pending")continue;let _=l.fills.find(L=>L.orderId===y.orderId&&L.action==="entry");if(!_)continue;let v=p.get(_.barT);if(v==null)continue;let C=v+y.horizon;if(C<f.length){y.close=f[C].c,y.barT=f[C].t,y.status="filled";let L=y.entryPrice;y.markout=y.side==="long"?(y.close-L)/L:(L-y.close)/L}}return l.position=$,l.cooldownBarsRemaining=h,l.cooldownStartT=M,l.updatedAt=t(),l})}return{start:n,step:a,list:i,get:o,stop:s}}var Tn=V(()=>{Pe();On()});var vn={};Cn(vn,{runStrategyOperation:()=>Ii});import Oi from"node:os";import Pi from"node:path";function We(e){return e!=null&&typeof e=="object"&&!Array.isArray(e)}function Ti(e){return String(e).toLowerCase().replace(/[^a-z0-9]/g,"")}function rr(e){if(Array.isArray(e)){for(let t of e)rr(t);return}if(We(e))for(let[t,r]of Object.entries(e)){if(Ai.some(n=>Ti(t).includes(n)))throw new Error(`strategy service: secret-like field "${t}" is forbidden`);rr(r)}}function $i(e){if(!We(e))throw new TypeError("strategy input must be a plain object");return rr(e),e}function _i(e,t={}){if(t.nowMs!==void 0){if(!Number.isInteger(t.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");return t.nowMs}let r=Date.now();if(e.nowMs===void 0||e.nowMs===null)return r;if(!Number.isInteger(e.nowMs))throw new TypeError("nowMs must be an integer epoch milliseconds");if(Math.abs(e.nowMs-r)>12e4)throw new Error("nowMs outside allowed wall-clock skew (120s); omit nowMs to use server time");return e.nowMs}async function tr(e,t,r,n){if(Array.isArray(t.bars))return t.bars;let o=Nt(e.venue),i=r.fetchBars??o.fetchBars;if(typeof i!="function")throw new Error(`strategy venue ${o.id} does not support history`);r.signal?.throwIfAborted?.();let s=await i({coin:e.market.coin,interval:e.market.interval,count:t.count??1500,endTime:t.endTime??n},{signal:r.signal});r.signal?.throwIfAborted?.();let a=Array.isArray(s)?s:s?.bars;if(!Array.isArray(a))throw new Error("strategy history provider returned no bars");return a}function nr(e,t){let r=e.backtestOptions??{};if(!We(r))throw new TypeError("backtestOptions must be a plain object");return{...r,nowMs:t}}function $n(e,t,r,n,o={}){let i=e.evidenceOptions??{};if(!We(i))throw new TypeError("evidenceOptions must be a plain object");return{...i,...o,strategy:t,bars:r,backtestOptions:nr(e,n)}}function _n(){return Pi.join(Oi.homedir(),".oracle","strategy-shadow.json")}function vi(e,t){return{perStrategyNotionalUsd:e.risk.maxNotionalUsd,maxLeverage:e.risk.maxLeverage,dailyLossCapUsd:e.risk.maxNotionalUsd*(e.risk.maxDailyLossPct/100),chainAllowlist:[e.venue],assetAllowlist:[e.market.coin],expiresAt:Math.min(e.risk.expiresAt,t+864e5),killSwitchRequired:!0}}async function Ii(e,t={},r={}){r.signal?.throwIfAborted?.();let n=$i(t),o=_i(n,r);if(e==="draft")return{strategy:dn(n.prompt,{nowMs:o})};if(e==="validate"){let i=X(n.strategy);if(i.strategy.risk.expiresAt<=o)throw new Error("strategy is expired");return{valid:!0,strategy:i.strategy,strategyHash:i.strategyHash,compilerHash:i.compilerHash,compilerVersion:i.compilerVersion,requiredSeries:i.requiredSeries}}if(e==="backtest"||e==="evidence"){let i=X(n.strategy),s=await tr(i.strategy,n,r,o);Ke(i,s);let a=$t($n(n,i.strategy,s,o));return e==="evidence"?a:{backtest:he(i.strategy,s,nr(n,o)),evidence:a}}if(e==="optimize"){let i=X(n.strategy),s=await tr(i.strategy,n,r,o);Ke(i,s);let a=n.trainFraction,c=n.evidenceOptions?.trainFraction;if(a!=null&&c!=null&&a!==c)throw new TypeError("conflicting trainFraction controls are forbidden");let f=a??c??.7;if(typeof f!="number"||f<=0||f>=1)throw new TypeError("trainFraction must be in (0,1)");let u=s.slice(0,Math.floor(s.length*f)),l=n.options??{};if(!We(l))throw new TypeError("options must be a plain object");let d=gn(i.strategy,u,{...l,...n.maxTrials==null?{}:{maxTrials:n.maxTrials},backtestOptions:nr(n,o)}),m=d.bestStrategy;return{strategy:m,optimization:d,evidence:$t($n(n,m,s,o,{trainFraction:f}))}}if(e==="shadow"){let i=er({storePath:r.storePath??_n(),clock:()=>o}),s=n.action;if(s==="start")return await i.start({strategy:n.strategy,evidenceId:n.evidenceId??n.evidence?.id??null});if(s==="list")return await i.list();if(s==="get")return await i.get(n.id);if(s==="stop")return await i.stop(n.id);if(s==="step"){let a=await i.get(n.id);if(!a)throw new Error(`shadow runner not found: ${n.id}`);let c=await tr(a.strategy,n,r,o);return Ke(X(a.strategy),c),await i.step(n.id,c,n.stepOptions??{})}throw new Error(`unknown shadow action: ${s}`)}if(e==="prepare"){let i=X(n.strategy),s=Nt(i.strategy.venue);if(typeof n.shadowId!="string"||!n.shadowId)throw new Error("strategy prepare requires a matching shadow runner id");let c=await er({storePath:r.storePath??_n(),clock:()=>o}).get(n.shadowId);if(!c)throw new Error("strategy prepare shadow runner not found");if(c.status!=="running")throw new Error("strategy prepare requires an active shadow runner");if(!Number.isFinite(c.cursor))throw new Error("strategy prepare requires a stepped shadow runner");if(c.strategyHash!==i.strategyHash||c.compilerHash!==i.compilerHash)throw new Error("strategy prepare shadow runner does not match strategy artifacts");if(c.evidenceId!==n.evidence?.id)throw new Error("strategy prepare shadow runner does not match evidence artifact");let f=n.caps??vi(i.strategy,o);return s.prepareIntent({strategy:i.strategy,evidence:n.evidence,shadow:{id:c.id,stateHash:An(c),status:c.status,cursor:c.cursor,updatedAt:c.updatedAt},caps:f,nowMs:o,env:r.env??process.env})}throw new Error(`unknown strategy operation: ${e}`)}var Ai,In=V(()=>{ot();Pe();_t();pn();bn();Tn();Mt();Ai=["privatekey","secretkey","seed","mnemonic","passphrase","password","keystore","keymaterial","apikey","authtoken","accesstoken","refreshtoken","credential","bearer","signature","authorization","xprv","xpriv","wif"]});import jn from"node:fs";function ji(e){let t={},r=[];for(let n=0;n<e.length;n++){let o=e[n];if(!o.startsWith("--")){r.push(o);continue}let i=o.slice(2),s=e[n+1];s!=null&&!s.startsWith("--")?(t[i]=s,n++):t[i]=!0}return{flags:t,positional:r}}function Te(e,t){if(!e)throw new Error(`${t} path required`);let r=e==="-"?jn.readFileSync(0,"utf8"):jn.readFileSync(e,"utf8");try{return JSON.parse(r)}catch{throw new Error(`${t} must contain valid JSON`)}}function Rn(e,t){if(e==null)return;let r=Number(e);if(!Number.isFinite(r))throw new Error(`${t} must be a finite number`);return r}var Ri=`oracle strategy <draft|validate|backtest|optimize|evidence|shadow|prepare> [args]
|
|
4
4
|
|
|
5
5
|
oracle strategy draft "Long BTC when the 20 EMA crosses above the 50 EMA"
|
|
6
6
|
oracle strategy validate strategy.json
|
|
@@ -14,5 +14,5 @@ var Fn=Object.defineProperty;var V=(e,t,r)=>()=>{if(r)throw r[0];try{return e&&(
|
|
|
14
14
|
oracle strategy prepare strategy.json --evidence evidence.json --shadow-id <id> [--caps caps.json]
|
|
15
15
|
|
|
16
16
|
Strategy simulation and shadowing are local and deterministic. Prepare returns an integrity-bound artifact, HMAC-authenticated when local attestation is configured. Sign and broadcast through an approved execution path.
|
|
17
|
-
`,
|
|
18
|
-
`),0}};export{
|
|
17
|
+
`,oc={name:"strategy",summary:"deterministic Hyperliquid strategy lab, evidence, shadow, prepare-only handoff",group:"read",usage:"oracle strategy <draft|validate|backtest|optimize|evidence|shadow|prepare> [args]",async run(e){let{flags:t,positional:r}=ji(e.argv);if(t.help||r.length===0)return process.stdout.write(Ri),0;let[n,...o]=r,{runStrategyOperation:i}=await Promise.resolve().then(()=>(In(),vn)),s={nowMs:Date.now(),count:Rn(t.count,"count")};if(n==="draft")s.prompt=o.join(" ").trim();else if(["validate","backtest","optimize","evidence"].includes(n))s.strategy=Te(o[0],"strategy"),t.bars&&(s.bars=Te(t.bars,"bars")),s.maxTrials=Rn(t["max-trials"],"max-trials");else if(n==="shadow"){let c=o[0];if(!c)throw new Error("shadow action required");s.action=c,c==="start"&&(s.strategy=Te(o[1],"strategy")),c==="step"&&(s.id=o[1],t.bars&&(s.bars=Te(t.bars,"bars"))),c==="stop"&&(s.id=o[1])}else if(n==="prepare")s.strategy=Te(o[0],"strategy"),s.evidence=Te(t.evidence,"evidence"),s.shadowId=t["shadow-id"],t.caps&&(s.caps=Te(t.caps,"caps"));else throw new Error(`unknown strategy operation: ${n}`);let a=await i(n,s);return process.stdout.write(`${JSON.stringify(a,null,2)}
|
|
18
|
+
`),0}};export{oc as default};
|