@beepflow/mcp 2026.7.5 → 2026.7.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -24,7 +24,7 @@ var aR=Object.create;var ah=Object.defineProperty;var sR=Object.getOwnPropertyDe
|
|
|
24
24
|
saved_at_ms integer not null,
|
|
25
25
|
primary key (scope, resource, key)
|
|
26
26
|
)
|
|
27
|
-
`),this.database)}};function Th(e){let t=e??"unknown-user";return CR.createHash("sha256").update(t).digest("hex")}function Ah(e,t,n){let r=e.replace(/^http/,"ws"),i=encodeURIComponent(t),o=encodeURIComponent(n);return`${r}/base/${i}/${o}`}var Vc=class{websocket;sessionId=Nc();backendUrl;accessToken;channelListeners=new Map;disconnectListeners=new Set;ackWaiters=new Map;intentionallyClosed=!1;constructor(t,n){this.backendUrl=t,this.accessToken=n}async connect(t){this.intentionallyClosed=!1,this.sessionId=Nc();let n=Ah(this.backendUrl,this.accessToken,this.sessionId),r=new WebSocket(n,"echo");this.websocket=r,await new Promise((i,o)=>{let a=setTimeout(()=>o(new Error("websocket open timeout")),t);r.onopen=()=>{clearTimeout(a),i()},r.onerror=()=>{clearTimeout(a),o(new Error("websocket open failed"))}}),r.onmessage=i=>this.processMessage(i.data),r.onclose=()=>this.processClose(),r.onerror=()=>this.processClose()}getSessionId(){return this.sessionId}send(t,n){if(!this.websocket||this.websocket.readyState!==WebSocket.OPEN)throw new Error("gateway websocket not connected");this.websocket.send(`${t};${JSON.stringify(n)}`)}sendWithAck(t,n,r=5e3){let i=Nc(),o={...n,eventId:i};return new Promise(a=>{let s=setTimeout(()=>{this.ackWaiters.delete(i),a({ok:!1,reason:"timeout"})},r);this.ackWaiters.set(i,{resolve:a,timeout:s}),this.send(t,o)})}onChannel(t,n){return this.channelListeners.has(t)||this.channelListeners.set(t,new Set),this.channelListeners.get(t).add(n),()=>this.channelListeners.get(t)?.delete(n)}onDisconnected(t){return this.disconnectListeners.add(t),()=>this.disconnectListeners.delete(t)}waitForChannelEvent(t,n,r){return new Promise((i,o)=>{let a=setTimeout(()=>{s(),o(new Error(`channel event timeout: ${t}`))},r),s=this.onChannel(t,c=>{n(c)&&(clearTimeout(a),s(),i(c))})})}collectChannelEvents(t,n,r,i){return new Promise((o,a)=>{let s=[],c,d=setTimeout(()=>{m(),c&&clearTimeout(c),a(new Error(`channel event timeout: ${t}`))},r),p=()=>{clearTimeout(d),m(),o(s)},m=this.onChannel(t,g=>{n(g)&&(s.push(g),c&&clearTimeout(c),c=setTimeout(p,i))})})}close(){this.intentionallyClosed=!0,this.websocket?.close(),this.websocket=void 0;for(let t of this.ackWaiters.values())clearTimeout(t.timeout),t.resolve({ok:!1,reason:"closed"});this.ackWaiters.clear()}processMessage(t){let n=typeof t=="string"?t:"",r=n.indexOf(";");if(r===-1)return;let i=n.slice(0,r),o=n.slice(r+1),a;try{a=JSON.parse(o)}catch{return}if(i.startsWith("ack:")){this.resolveAck(i.slice(4),a);return}a=IR(a);let s=this.channelListeners.get(i);if(s)for(let c of s)c(a)}resolveAck(t,n){let r=this.ackWaiters.get(t);r&&(this.ackWaiters.delete(t),clearTimeout(r.timeout),r.resolve(n.value??{ok:!1}))}processClose(){if(!this.intentionallyClosed)for(let t of this.disconnectListeners)t()}};function IR(e){if(e.resource!=="connections")return e;switch(e.action){case"snapshot":return{...e,value:NR(e.value)};case"delta":return{...e,value:PR(e.value)};default:return e}}function NR(e){if(!Qf(e))return e;let t={};for(let n in e)t[n]=wh(e[n]);return t}function PR(e){return Qf(e)?{...e,pre:Rh(e.pre),post:Rh(e.post)}:e}function Rh(e){return e===null?null:wh(e)}function wh(e){if(!Qf(e))return e;let t={...e};return delete t.config,t}function Qf(e){return typeof e=="object"&&e!==null&&!Array.isArray(e)}var Jf="beepflow://resource-schemas/",nn={type:"number",description:"Nanoseconds since Unix epoch. Omit updatedAt on creates and manual edits unless preserving an existing value; replicated state updates it after accepted writes."},_e={type:"string"},Ho={type:"number"},Dh={type:"integer"},Nr={type:"boolean"};var Ch={type:"object",additionalProperties:_e},Zf={type:"object",additionalProperties:Nr},qc={type:"object",additionalProperties:{type:"object",additionalProperties:Nr,properties:{list:Nr,detail:Nr,create:Nr,edit:Nr,delete:Nr,authorize:Nr}}},Da=["boolean","string","number","datetime","map","binary","wildcard","list of boolean","list of string","list of number","list of datetime","list of map","list of binary","list of wildcard"],Oh=["ManualTick","AerospikeSet","ApacheKafkaTopic","MQTTTopic","KaggleFile","RabbitMQQueue","RabbitMQStream","QdrantCollection","BaseVectorCollection","BaseEventCollection","BaseLookupCollection","GorgiasTicketsView","GoogleDriveFile","GmailMessage","GmailThread","GmailEvent"],Ca={anyOf:[Nr,{type:"null"}]},FR=["Use resource_query first when editing existing items; upsert sends whole item state, not a JSON patch. Preserve unchanged fields.","Omit updatedAt on creates and manual edits unless preserving an existing value; replicated state updates it after accepted writes."];function rn(e,t,n){let r=`${Jf}${e}`;return{resource:e,uri:r,sourceType:t,notes:FR,itemSchema:{$schema:"https://json-schema.org/draft/2020-12/schema",title:`Beepflow ${e} item`,type:"object",additionalProperties:!1,required:n.required,properties:n.properties,...n.defs?{$defs:n.defs}:{}}}}var ed={$ref:"#/$defs/operatorType"},MR={type:"object",additionalProperties:!1,required:["value"],properties:{value:{description:"Raw option value written to node input literal when selected."},label:{..._e,description:"Optional label shown in operator input dropdowns."}}},LR={type:"object",additionalProperties:!1,required:["type"],properties:{type:{type:"string",enum:Da,description:'Blueprint value type name. Use "list of X" for lists, never "list".'},options:{anyOf:[{type:"array",items:MR},{type:"null"}],description:"Allowed literal values for dropdown-style widgets."},isArray:{type:"boolean",description:"Whether this pin accepts multiple values."},allowedTypes:{anyOf:[{type:"array",items:ed},{type:"null"}],description:"Allowed concrete types for wildcard pins."},linkType:{..._e,description:"Type-linking group used to propagate wildcard types across pins."},widgetType:{..._e,description:'Frontend input widget id. Supports built-in widgets, integration selectors, and "<IntegrationType>-connection" connection dropdowns.'},defaultValue:{description:"Default literal value used when node input omits a value."},defaultValueForArrayElement:{description:"Default literal value for newly added array input elements."}}},BR={type:"object",additionalProperties:!1,required:["name","doc","type"],properties:{name:{..._e,description:"Output pin name."},doc:{..._e,description:"Operator output documentation shown to users."},type:ed}},UR={type:"object",additionalProperties:!1,required:["name","doc","type"],properties:{name:{..._e,description:"Input pin name; node inputs are keyed by this value."},doc:{..._e,description:"Operator input documentation shown to users."},type:ed,isLiteral:{...Nr,description:"Whether this input must be edited as literal value instead of upstream connection."}}},kh=rn("blueprint-operators","frontend/src/tabs/blueprint/types.ts:Operator",{required:["id","type","name","doc","categoryPath","inputs"],properties:{id:{..._e,description:"Stable registered operator id referenced by blueprint nodes."},type:{..._e,description:"Operator kind, usually function, variable, or localVariable."},name:{..._e,description:"Display name used in operator search and node labels."},aliases:{type:"array",items:_e,description:"Additional search terms for this operator."},doc:{..._e,description:"Operator documentation shown to users."},categoryPath:{type:"array",items:_e,description:"Menu category path segments."},inputs:{type:"array",items:UR,description:"Input pins in display order."},output:{anyOf:[BR,{type:"null"}],description:"Output pin definition, or null for side-effect-only operators."},isDeprecated:{...Nr,description:"Whether operator is deprecated and hidden from default search."},hidden:{...Nr,description:"Whether operator is hidden from menus and search."},canMock:{...Nr,description:"Whether test mode can mock this operator."},updatedAt:nn},defs:{operatorType:LR}});var VR={type:"object",additionalProperties:!1,properties:{x:{...Ho,description:"Optional node world x coordinate in blueprint editor. For new nodes, never specify style.x; omit it so the frontend can place nodes after measuring dimensions."},y:{...Ho,description:"Optional node world y coordinate in blueprint editor. For new nodes, never specify style.y; omit it so the frontend can place nodes after measuring dimensions."},title:{..._e,description:"Optional display title shown on node."},comment:{..._e,description:"Optional user-authored node comment."}}},qR={type:"object",additionalProperties:!0,description:"Blueprint view node. For new nodes, never specify style.x or style.y; omit coordinates so the frontend can place nodes after measuring dimensions. Known visualization blocks are intentionally accepted as additional properties.",required:["id"],properties:{id:{..._e,description:"Node id; must match key in blueprint view nodes record."},style:VR}},xh=rn("blueprint-views","frontend/src/tabs/blueprint/types.ts:BlueprintView",{required:["id","nodes"],properties:{id:{..._e,description:"Blueprint tab id; must match tabs and blueprints resource id."},updatedAt:nn,nodes:{type:"object",additionalProperties:qR,description:"Editor view state keyed by node id."}}});var Kc={type:"string",description:"Integration resource type processed by this blueprint, such as ApacheKafkaTopic or QdrantCollection. Call integration_blueprint_contexts_list first; use only resource types returned by that tool. The returned executionKind determines trigger choice: managed resources use executor, finite resources use manual/cron/loop/blueprint/webhook based on user intent."},Gc={type:"object",additionalProperties:!0,description:"Integration-specific config for context.type. Start from contextTemplate.config returned by integration_blueprint_contexts_list, fill every configFields item where required=true, and preserve optional defaults such as consumerGroupId, clientId, parser, offsetResetStrategy, orderBy, or webhook topic maps when provided."},Wc={type:"object",additionalProperties:!1,required:["enabled"],properties:{enabled:{type:"boolean",description:"Must be true. Backend ignores this trigger branch when enabled is false."}}},td={...Wc.properties.enabled,enum:[!0]},zR=["auto","application/json","text/plain","text/html","application/xml","application/x-www-form-urlencoded","multipart/form-data","application/octet-stream"],KR={type:"object",additionalProperties:!1,required:["count"],description:"Run immediately when explore runtime starts or restarts. Use for finite resource sampling, one-shot imports, and ad hoc reads.",properties:{count:{type:"integer",minimum:1,description:"Number of executions to run back-to-back. Frontend default is 1; backend coerces values below 1 to 1."}}},GR={type:"object",additionalProperties:!1,required:["expression"],description:"Run on a seconds-field cron schedule while explore runtime is active. Use for scheduled finite-resource refreshes.",properties:{expression:{type:"string",description:"Cron expression with six fields including seconds, parsed by robfig/cron. Example: 0 */5 * * * * runs every five minutes."},timezone:{type:"string",description:"Optional IANA timezone name such as UTC or America/New_York. Backend uses UTC when omitted or empty."}}},WR={type:"object",additionalProperties:!1,required:["delayMs"],description:"Run immediately, then wait delayMs before repeating while explore runtime is active. Use only for deliberate fixed-delay polling.",properties:{delayMs:{type:"integer",minimum:1,description:"Delay between executions in milliseconds. Must be positive to avoid a hot loop."}}},Ih={...Wc,description:"Wait while active until another blueprint or Trigger Self operator invokes this blueprint. Trigger argument is available through Get Trigger Argument."},nd={type:"object",additionalProperties:!1,required:["enabled"],description:"Wait while active for generic GET/POST /:tabId/trigger HTTP calls. Request method, URL, parsed body, headers, and timestamp become trigger argument. Webhook URL is `${status.backendUrl}/${encodeURIComponent(blueprint.id)}/trigger` and runs only while blueprint is active in explore mode.",properties:{enabled:Wc.properties.enabled,timeoutMs:{type:"integer",minimum:1,description:"Maximum synchronous webhook execution time in milliseconds. Backend uses 30000 when omitted or below 1."},contentType:{type:"string",enum:zR,description:"Request body parser. Omit or use auto to infer from incoming Content-Type, then fall back to JSON sniffing, UTF-8 text, then binary. Not for provider webhook resources managed through BaseEvent; use BaseEventCollection."}}},Nh={...Wc,description:"Use for managed integration resources where runtime owns stream, event, webhook, or poll lifecycle, such as ApacheKafkaTopic, RabbitMQStream, GmailMessage, GmailThread, GmailEvent, BaseEventCollection, and MQTTTopic."},zc={type:"object",additionalProperties:!1,minProperties:1,maxProperties:1,description:"Exactly one trigger branch. For executionKind=managed from integration_blueprint_contexts_list, use executor. For executionKind=finite, choose manual for ad hoc/sample/start-once runs, cron for scheduled refresh, loop for fixed-delay polling, blueprint for invocation by another blueprint, or webhook for generic GET/POST /:tabId/trigger HTTP calls.",properties:{manual:KR,cron:GR,loop:WR,blueprint:Ih,webhook:nd,executor:Nh},oneOf:[{required:["manual"]},{required:["cron"]},{required:["loop"]},{required:["blueprint"]},{required:["webhook"]},{required:["executor"]}]},Ph={...zc,properties:{...zc.properties,blueprint:{...Ih,properties:{enabled:td}},webhook:{...nd,properties:{...nd.properties,enabled:td}},executor:{...Nh,properties:{enabled:td}}}};var HR={type:"object",additionalProperties:!1,required:["literal"],properties:{literal:{description:"Literal JSON value for this input element; null is valid when connected upstream."},nodeId:{..._e,description:"Upstream node id when this value is connected to another node output."},operatorInputId:{..._e,description:"Upstream output pin name used by this connection."},nodeInputIndex:{..._e,description:'CRDT list index of upstream output value. Use "0.5" for any connected node output.'}}},XR={type:"object",additionalProperties:!1,required:["values"],properties:{isArray:{...Ca,description:"Whether input accepts multiple values for one operator input."},values:{type:"object",additionalProperties:HR,description:"Input values keyed by CRDT list index strings."},type:{type:"string",enum:Da,description:"Resolved input type override."},forceZipping:{...Ca,description:"Force list zipping behavior for multiple upstream values."},listInputMode:{type:"string",enum:["list","items"],description:"Whether this input receives one whole list value or assembles a list from item values."}}},$R={type:"object",additionalProperties:!1,required:["id","operatorId","inputs"],properties:{id:{..._e,description:"Stable node id; must match key in blueprint nodes record."},operatorId:{..._e,description:"Id of registered blueprint operator this node executes."},inputs:{type:"object",additionalProperties:XR,description:"Node inputs keyed by operator input name."},mockNever:{...Ca,description:"Disable mocking for this node."},skipBehavior:{type:"string",enum:["skip","null"],description:"Behavior when upstream value is skipped."},disabled:{...Ca,description:"Whether this node and downstream dependent nodes are disabled."},outputType:{type:"string",enum:Da,description:"Resolved output type for wildcard operators."}}},jR={type:"object",additionalProperties:!1,required:["type","trigger"],properties:{type:Kc,trigger:Ph,config:Gc}},Fh=rn("blueprints","frontend/src/tabs/blueprint/types.ts:Blueprint",{required:["id","mode","nodes","context"],properties:{id:{..._e,description:"Blueprint tab id; must match tabs resource id."},updatedAt:nn,mode:{type:"string",enum:["test","explore"],description:'Execution mode; result id is blueprint id plus "-test" or "-explore".'},nodes:{type:"object",additionalProperties:$R,description:"Blueprint nodes keyed by node id."},context:jR,testRecordsAmount:{...Dh,description:"Target number of test records to keep for test mode."},recomputeOnChange:{type:"string",enum:["always","manual"],description:"Whether edits automatically restart execution."},mockNever:{...Nr,description:"Global flag to disable node mocking."},desiredState:{type:"string",enum:["active","inactive"],description:"Requested runtime state for test or explore mode."}}});var YR=["Aerospike","ApacheKafka","MQTT","Kaggle","FacebookAds","RabbitMQ","Shopify","YouTube","Webshare","Playwright","AWS","Qdrant","OpenAI","BaseVector","BaseEvent","BaseLookup","Gorgias","LMStudio","OpenRouter","VoyageAI","GoogleDrive","GoogleSheets","Gmail","DiscordChannelWebhook"],Mh=rn("connections","frontend/src/integrations/types.ts:Connection",{required:["id","label","type","spaceId"],properties:{id:_e,updatedAt:nn,label:_e,type:{type:"string",enum:YR},spaceId:_e}});var Lh=rn("roles","frontend/src/auth/roles/types.ts:Role",{required:["id","label","authorizations"],properties:{id:_e,updatedAt:nn,label:_e,authorizations:qc}});var Bh=rn("pages","frontend/src/tabs/types.ts:Page",{required:["id","sourceUrl","distUrl"],properties:{id:{..._e,description:"Page tab id; must match tabs resource id."},updatedAt:nn,sourceUrl:{..._e,description:"File-service URL for raw source HTML."},distUrl:{..._e,description:"File-service URL for optimized HTML rendered in a sandbox iframe."}}});var Uh=rn("schemas","frontend/src/integrations/types.ts:Schema",{required:["id","type","connectionId","path","schema"],properties:{id:_e,updatedAt:nn,type:{type:"string",enum:Oh},connectionId:_e,path:Ch,schema:{type:"object",additionalProperties:{type:"string",enum:Da}},keySerdeType:{type:"string"},valueSerdeType:{type:"string"}}});var Vh=rn("space-join-requests","frontend/src/spaces/space-join-requests/types.ts:SpaceJoinRequest",{required:["id","createdAt","requestedBy","kind","status","spaceId","userId"],properties:{id:_e,createdAt:{type:"number",description:"Nanoseconds since Unix epoch."},updatedAt:nn,requestedBy:_e,kind:{type:"string",enum:["invite","request"]},status:{type:"string",enum:["pending","granted","denied"]},spaceId:_e,userId:_e}});var qh=rn("spaces","frontend/src/spaces/types.ts:Space",{required:["id","label"],properties:{id:_e,updatedAt:nn,label:_e,thumbnailUrl:_e,description:_e,isUserSpace:Ca}});var zh=rn("tabs","frontend/src/tabs/types.ts:Tab",{required:["id","name","order","type","parent","spaceId"],properties:{id:{..._e,description:"Stable tab id. Blueprint and page tabs normally have matching records keyed by this id."},updatedAt:nn,name:_e,order:Ho,type:{type:"string",enum:["blueprint","folder","page"],description:"Navigation item kind; blueprint and page tabs normally have matching records."},parent:_e,spaceId:_e}});var Kh=rn("user-locations","frontend/src/workspace/user-location/types.ts:UserLocation",{required:["id"],properties:{id:_e,updatedAt:nn,tab:{type:"object",additionalProperties:!1,required:["id"],properties:{id:_e}},blueprint:{type:"object",additionalProperties:!1,required:["id"],properties:{id:_e,worldPosition:{type:"object",additionalProperties:!1,required:["x","y"],properties:{x:Ho,y:Ho}}}}}});var Gh=rn("users","frontend/src/auth/users/types.ts:User",{required:["id","displayName","roleIds","authorizations","spaces"],properties:{id:_e,updatedAt:nn,displayName:_e,avatarUrl:_e,roleIds:Zf,authorizations:qc,spaces:Zf}});var Hc=[Gh,Lh,qh,zh,Bh,Mh,Uh,Fh,xh,kh,Kh,Vh];function Xc(e){return Hc.find(t=>t.resource===e)}var rd=[Ii("users","Workspace users and authorizations.",!0),Ii("roles","Workspace roles and resource authorizations.",!0),Ii("spaces","Workspace spaces.",!0),Ii("tabs","Tabs and folders visible to authorized user; blueprint and page tabs normally share ids with matching records.",!0),Ii("pages","Untrusted single-page HTML source and optimized file URLs keyed by matching page tab id.",!0),Ii("connections","Read-only integration connections without secret-bearing config; config is redacted and cannot be read through MCP.",!1),Ii("schemas","Integration schema metadata.",!0),Ii("blueprints","Blueprint definitions keyed by matching blueprint tab id.",!0),Ii("blueprint-views","Blueprint editor view state keyed by matching blueprint tab id.",!0),Ii("blueprint-operators","Registered blueprint operator definitions.",!1),Ii("user-locations","Live user location records.",!0),Ii("space-join-requests","Space invitation and join requests.",!0)],QR=["tabs","pages","blueprints","blueprint-views"],id=new Set(QR),Oa=rd.filter(e=>!id.has(e.name)),bu=Oa.map(e=>e.name),Wh=rd.map(e=>e.name);function JR(e){return rd.find(t=>t.name===e)}function Hh(e){return Oa.find(t=>t.name===e)}function Xh(e){if(JR(e))return e;throw new Error(`unsupported resource: ${e}`)}function od(e){if(id.has(e))throw new Error(`dedicated resource ${e}: use tab and blueprint intent tools instead of generic resource_* tools`);if(Hh(e))return e;throw new Error(`unsupported resource: ${e}`)}function ad(e){let t=Hh(e);if(id.has(e))throw new Error(`dedicated resource ${e}: use tab and blueprint intent tools instead of generic resource_* tools`);if(!t)throw new Error(`unsupported resource: ${e}`);if(!t.writable)throw new Error(`resource is read-only: ${e}`);return t.name}function Ii(e,t,n){return{name:e,description:t,writable:n,schemaUri:`${Jf}${e}`}}function Pr(){return Date.now()*1e6}function ud(e,t){if(e===null&&t===null)return{pre:null,post:null};if(e===null&&t!==null)return{pre:null,post:t};if(e!==null&&t===null)return{pre:e,post:null};if(typeof e!="object"||typeof t!="object")return e!==t?{pre:e,post:t}:{pre:null,post:null};if(Array.isArray(e)||Array.isArray(t))return{pre:null,post:null};let{pre:n,post:r}=$h(e,t);return n===null&&r===null?{pre:null,post:null}:{pre:n,post:r}}function $h(e,t){let n={},r={},i=!1,o=new Set([...mo(e),...mo(t)]);for(let a of o){if(a==="updatedAt")continue;let s=e[a],c=t[a];if(Array.isArray(s)||Array.isArray(c))continue;let d=Xo(s),p=Xo(c);if(!(a in t))d||(n[a]=s,r[a]=null,i=!0);else if(!(a in e))p||(n[a]=null,r[a]=c,i=!0);else{if(d&&p)continue;if(d&&!p)n[a]=null,r[a]=c,i=!0;else if(!d&&p)n[a]=s,r[a]=null,i=!0;else{let{pre:m,post:g}=ZR(s,c);(m!==void 0||g!==void 0)&&(m!==void 0&&(n[a]=sd(m)),g!==void 0&&(r[a]=sd(g)),i=!0)}}}return i?mo(n).length===0&&mo(r).length===0?{pre:null,post:null}:mo(n).length===0?{pre:null,post:r}:mo(r).length===0?{pre:n,post:null}:{pre:n,post:r}:{pre:null,post:null}}function ZR(e,t){if(ew(e,t))return{pre:void 0,post:void 0};let n=Xo(e),r=Xo(t);if(n&&r)return{pre:void 0,post:void 0};if(n)return{pre:null,post:t};if(r)return{pre:e,post:null};if(Array.isArray(e)||Array.isArray(t))return{pre:void 0,post:void 0};if(typeof e!=typeof t)return{pre:e,post:t};if(typeof e=="object"&&e!==null&&typeof t=="object"&&t!==null){let{pre:i,post:o}=$h(e,t);return i===null&&o===null?{pre:void 0,post:void 0}:{pre:i===null?void 0:i,post:o===null?void 0:o}}return{pre:e,post:t}}function Xo(e){return e==null?!0:typeof e=="object"&&e!==null?Array.isArray(e)?e.length===0:mo(e).length===0:!1}function ew(e,t){return Xo(e)&&Xo(t)?!0:cd(e,t)}function cd(e,t){if(e===t)return!0;if(e==null||t==null||typeof e!="object"||typeof t!="object")return!1;let n=mo(e),r=mo(t);if(n.length!==r.length)return!1;for(let i of n)if(!(i in t)||!cd(e[i],t[i]))return!1;return!0}function $c(e,t){return t.pre===null?e===null:e===null||typeof e!="object"||Array.isArray(e)?!1:jh(e,t.pre)}function jh(e,t){for(let n in t)if(n!=="updatedAt"&&!tw(e[n],t[n]))return!1;return!0}function tw(e,t){return t===null||nw(t)?Xo(e):e===void 0?!1:typeof t=="object"&&t!==null&&!Array.isArray(t)&&typeof e=="object"&&e!==null&&!Array.isArray(e)?jh(e,t):cd(e,t)}function nw(e){return e!==null&&typeof e=="object"&&!Array.isArray(e)&&mo(e).length===0}function sd(e){if(e==null)return null;if(typeof e=="object"&&e!==null){if(Array.isArray(e)&&e.length===0)return null;if(!Array.isArray(e)){let t={},n=!1;for(let r in e)t[r]=sd(e[r]),t[r]!==void 0&&(n=!0);return n?t:null}}return e}function ld(e,t){let n=fd(e,t);return n!==null&&typeof n=="object"&&!Array.isArray(n)&&(n.updatedAt=t.updatedAt),n}function fd(e,t){return t.post===null?null:e===null?t.post:typeof e!="object"||Array.isArray(e)?t.post:Yh(e,t.post)}function Yh(e,t){let n={};for(let r in e)if(r in t){let i=t[r];if(i===null)continue;typeof i=="object"&&!Array.isArray(i)&&typeof e[r]=="object"&&!Array.isArray(e[r])&&e[r]!==null?n[r]=Yh(e[r],i):n[r]=i}else n[r]=e[r];for(let r in t)!(r in e)&&t[r]!==null&&(n[r]=t[r]);return n}function mo(e){let t=[];for(let n in e)t.push(n);return t}var Qh="replicated-state",jc=class{ackedResources={};dirtyResources={};unauthorizedKeys={};loadingResources={};loadingPromises=new Map;loadedResources=new Set;registeredResources=new Set;resourceChangeListeners=new Set;snapshotWaiters=new Map;storage;socketSession;logger;inflightItems=new Map;constructor(t,n,r){this.storage=t,this.socketSession=n,this.logger=r}onResourceChange(t){return this.resourceChangeListeners.add(t),()=>this.resourceChangeListeners.delete(t)}registerResource(t){this.registeredResources.add(t),this.initializeResource(t)}isResourceRegistered(t){return this.registeredResources.has(t)}getRegisteredResources(){return Array.from(this.registeredResources)}setDirtyItems(t,n){this.registerResource(t),this.dirtyResources[t]=Yr(n)}setDirtyItem(t,n,r){if(this.registerResource(t),r===void 0){delete this.dirtyResources[t][n];return}this.dirtyResources[t][n]=Yr(r)}clearSessionState(){this.ackedResources={},this.loadingResources={},this.loadingPromises.clear(),this.loadedResources.clear(),this.inflightItems.clear();for(let t of this.registeredResources)this.dirtyResources[t]={},this.unauthorizedKeys[t]={},this.loadingResources[t]=!0,this.emitResourceChange(t)}async loadRegisteredResourcesFromStorage(){await Promise.all(Array.from(this.registeredResources,t=>this.loadResourceFromStorage(t)))}async hydrate(t,n){this.registerResource(t),await this.loadResourceFromStorage(t),this.logger.info(`Calculating lastUpdatedAtSeen from ${Zh(this.ackedResources[t])} items`);let r=this.prepareSnapshotQuery(t,n);this.logger.info(`\u{1F4F8} ${t} requested with query:`,r),this.socketSession.send(Qh,{resource:t,action:"snapshot",value:r})}hydrateAll(t){return this.hydrate(t,{all:!0})}async waitForSnapshot(t,n){await new Promise((r,i)=>{let o,a=()=>{clearTimeout(o),r()};o=setTimeout(()=>{this.snapshotWaiters.get(t)?.delete(a),i(new Error(`snapshot timeout for ${t}`))},n),this.snapshotWaiters.has(t)||this.snapshotWaiters.set(t,new Set),this.snapshotWaiters.get(t).add(a)})}processSocketEvent(t){switch(t.action){case"snapshot":this.applySnapshot(t.resource,t.value??{});break;case"delta":this.applyRemoteDelta(t);break}}async upsertItem(t,n){this.registerResource(t);let r=this.getAckedValue(t,n.id),i=ud(r,n);return i.pre===null&&i.post===null?!0:this.sendDelta(t,n.id,i,n)}async deleteItem(t,n){this.registerResource(t);let r=this.getAckedValue(t,n),i=ud(r,null);return i.pre===null&&i.post===null?!0:this.sendDelta(t,n,i,null)}isItemInflight(t,n){return this.inflightItems.get(t)?.has(n)===!0}async sendDelta(t,n,r,i){this.registerResource(t),this.inflightItems.has(t)||this.inflightItems.set(t,new Set);let o=this.inflightItems.get(t);if(o.has(n))return!1;let a=this.getDirtyValue(t,n);$c(a,r)&&(arguments.length>=4?this.setDirtyValue(t,n,Yr(i)):this.setDirtyValue(t,n,fd(a,Yr(r))),this.emitResourceChange(t)),o.add(n);let s;try{s=await this.socketSession.sendWithAck(Qh,{resource:t,action:"delta",key:n,value:r})}catch(c){s={ok:!1,reason:c instanceof Error?c.message:"error"}}return o.delete(n),s.ok?!0:(this.revertDirtyToAckedValue(t,n),this.emitResourceChange(t),this.logger.error(`!ack[${t}] Reverting to acked state for ${t}:${n}`,s.reason),!1)}getAckedValue(t,n){return this.initializeResource(t),this.ackedResources[t][n]??null}getDirtyValue(t,n){return this.initializeResource(t),this.dirtyResources[t][n]??null}getVisibleItems(t){this.initializeResource(t);let n={};for(let r in this.dirtyResources[t]){let i=this.dirtyResources[t][r];i!=null&&(n[r]=i)}return n}getRawItems(t){return this.initializeResource(t),Yr(this.dirtyResources[t])}getAckedItems(t){return this.initializeResource(t),Yr(this.ackedResources[t])}getUnauthorizedKeys(t){return this.initializeResource(t),Yr(this.unauthorizedKeys[t])}isResourceLoading(t){return this.initializeResource(t),this.loadingResources[t]}initializeResource(t){this.ackedResources[t]===void 0&&(this.ackedResources[t]={}),this.dirtyResources[t]===void 0&&(this.dirtyResources[t]={}),this.unauthorizedKeys[t]===void 0&&(this.unauthorizedKeys[t]={}),this.loadingResources[t]===void 0&&(this.loadingResources[t]=!0)}prepareSnapshotQuery(t,n){this.initializeResource(t);let r=Yr(n);if(r.lastUpdatedAtSeen!==void 0)return r;let i=this.buildLastUpdatedAtSeen(t,r);return Jh(i)||(r.lastUpdatedAtSeen=i),r}async loadResourceFromStorage(t){if(this.initializeResource(t),this.loadedResources.has(t))return;if(this.loadingPromises.has(t))return this.loadingPromises.get(t);let n=this.loadResourceItemsFromStorage(t);this.loadingPromises.set(t,n);try{await n}finally{this.loadingPromises.delete(t),this.loadedResources.add(t)}}async loadResourceItemsFromStorage(t){let n=!1,r=0;try{let i=await this.storage.loadItems(t);if(i&&Jh(this.ackedResources[t])){n=!0;for(let o in i)this.applyCachedItem(t,o,i[o])&&(r+=1)}}catch(i){this.logger.warn(`Failed to load cached ${t}: ${String(i)}`)}finally{this.loadingResources[t]=!1,this.emitResourceChange(t),n?this.logger.info(`\u{1F4C2} ${r}x ${t} from cache`):this.logger.info(`\u{1F4C2} no cached data for ${t}`)}}applyCachedItem(t,n,r){return r===null?(this.ackedResources[t][n]=null,this.dirtyResources[t][n]=null,!0):r==="unauthorized"?(this.unauthorizedKeys[t][n]=!0,!1):(this.ackedResources[t][n]=Yr(r),this.dirtyResources[t][n]=Yr(r),!0)}applySnapshot(t,n){this.initializeResource(t);for(let r in n){let i=n[r];i===null?(this.ackedResources[t][r]=null,(!this.isItemInflight(t,r)||this.getDirtyValue(t,r)==null)&&(this.dirtyResources[t][r]=null),delete this.unauthorizedKeys[t][r]):i==="unauthorized"?(delete this.ackedResources[t][r],delete this.dirtyResources[t][r],this.unauthorizedKeys[t][r]=!0):(this.ackedResources[t][r]=Yr(i),this.dirtyResources[t][r]=Yr(i),delete this.unauthorizedKeys[t][r]),this.storage.persistItem(t,r,i).catch(o=>{this.logger.warn(`Failed to persist ${t}:${r}: ${String(o)}`)})}this.loadingResources[t]=!1,this.emitResourceChange(t),this.logger.info(`\u{1F4F8} ${Zh(n)}x ${t} `),this.resolveSnapshotWaiters(t)}applyRemoteDelta(t){let n=t.resource,r=t.key;if(!r)return;this.initializeResource(n);let i=t.value,o={pre:i.pre,post:i.post},a=this.getAckedValue(n,r);if(!$c(a,o))this.logger.error(`\u{1D6AB}S precondition invalid on last acked for ${n}:${r}`,{pre:o.pre,post:o.post,current:a});else{let c=ld(a,Yr(i));this.ackedResources[n][r]=c,this.storage.persistItem(n,r,c).catch(d=>{this.logger.warn(`Failed to persist ${n}:${r}: ${String(d)}`)}),this.logger.info(dd(`\u{1D6AB}S[${n}] acked`,o))}let s=this.getDirtyValue(n,r);t.by!==this.socketSession.getSessionId()?$c(s,o)?o.post===null?(this.dirtyResources[n][r]=null,this.logger.info(dd(`\u{1D6AB}S[${n}] dirty`,o))):(this.dirtyResources[n][r]=ld(s,Yr(i)),this.logger.info(dd(`\u{1D6AB}S[${n}] dirty`,o))):(this.logger.warn(`Skip delta on dirty for ${n}:${r}`,{pre:o.pre,post:o.post,current:a}),this.revertDirtyToAckedValue(n,r)):o.post!=null&&s!=null&&typeof s=="object"&&(s.updatedAt=i.updatedAt,this.dirtyResources[n][r]=s,this.logger.info(`\u{1D6AB}S[${n}] dirty updatedAt for ${r}`)),this.emitResourceChange(n)}buildLastUpdatedAtSeen(t,n){let r=this.ackedResources[t],i={};if(n.all){for(let o in r)this.copyItemUpdatedAt(r[o],o,i);return i}if(n.keys&&n.keys.length>0)for(let o of n.keys)this.copyItemUpdatedAt(r[o],o,i);return i}copyItemUpdatedAt(t,n,r){t&&typeof t=="object"&&typeof t.updatedAt=="number"&&(r[n]=t.updatedAt)}setDirtyValue(t,n,r){if(r===null){this.dirtyResources[t][n]=null;return}this.dirtyResources[t][n]=r}revertDirtyToAckedValue(t,n){let r=this.ackedResources[t][n];if(r===void 0){delete this.dirtyResources[t][n];return}if(r===null){this.dirtyResources[t][n]=null;return}this.dirtyResources[t][n]=Yr(r)}emitResourceChange(t){let n={resource:t,acked:this.getAckedItems(t),dirty:this.getRawItems(t),unauthorized:this.getUnauthorizedKeys(t),loading:this.loadingResources[t]};for(let r of this.resourceChangeListeners)r(n)}resolveSnapshotWaiters(t){let n=this.snapshotWaiters.get(t);if(n){this.snapshotWaiters.delete(t);for(let r of n)r()}}};function Yr(e){if(e===void 0)return e;if(typeof structuredClone=="function")try{return structuredClone(e)}catch{}try{return JSON.parse(JSON.stringify(e))}catch{return e}}function Jh(e){for(let t in e)return!1;return!0}function Zh(e){let t=0;for(let n in e)t+=1;return t}function dd(e,t){return`${e}
|
|
27
|
+
`),this.database)}};function Th(e){let t=e??"unknown-user";return CR.createHash("sha256").update(t).digest("hex")}function Ah(e,t,n){let r=e.replace(/^http/,"ws"),i=encodeURIComponent(t),o=encodeURIComponent(n);return`${r}/base/${i}/${o}`}var Vc=class{websocket;sessionId=Nc();backendUrl;accessToken;channelListeners=new Map;disconnectListeners=new Set;ackWaiters=new Map;intentionallyClosed=!1;constructor(t,n){this.backendUrl=t,this.accessToken=n}async connect(t){this.intentionallyClosed=!1,this.sessionId=Nc();let n=Ah(this.backendUrl,this.accessToken,this.sessionId),r=new WebSocket(n,"echo");this.websocket=r,await new Promise((i,o)=>{let a=setTimeout(()=>o(new Error("websocket open timeout")),t);r.onopen=()=>{clearTimeout(a),i()},r.onerror=()=>{clearTimeout(a),o(new Error("websocket open failed"))}}),r.onmessage=i=>this.processMessage(i.data),r.onclose=()=>this.processClose(),r.onerror=()=>this.processClose()}getSessionId(){return this.sessionId}send(t,n){if(!this.websocket||this.websocket.readyState!==WebSocket.OPEN)throw new Error("gateway websocket not connected");this.websocket.send(`${t};${JSON.stringify(n)}`)}sendWithAck(t,n,r=15e3){let i=Nc(),o={...n,eventId:i};return new Promise(a=>{let s=setTimeout(()=>{this.ackWaiters.delete(i),a({ok:!1,reason:"timeout"})},r);this.ackWaiters.set(i,{resolve:a,timeout:s}),this.send(t,o)})}onChannel(t,n){return this.channelListeners.has(t)||this.channelListeners.set(t,new Set),this.channelListeners.get(t).add(n),()=>this.channelListeners.get(t)?.delete(n)}onDisconnected(t){return this.disconnectListeners.add(t),()=>this.disconnectListeners.delete(t)}waitForChannelEvent(t,n,r){return new Promise((i,o)=>{let a=setTimeout(()=>{s(),o(new Error(`channel event timeout: ${t}`))},r),s=this.onChannel(t,c=>{n(c)&&(clearTimeout(a),s(),i(c))})})}collectChannelEvents(t,n,r,i){return new Promise((o,a)=>{let s=[],c,d=setTimeout(()=>{m(),c&&clearTimeout(c),a(new Error(`channel event timeout: ${t}`))},r),p=()=>{clearTimeout(d),m(),o(s)},m=this.onChannel(t,g=>{n(g)&&(s.push(g),c&&clearTimeout(c),c=setTimeout(p,i))})})}close(){this.intentionallyClosed=!0,this.websocket?.close(),this.websocket=void 0;for(let t of this.ackWaiters.values())clearTimeout(t.timeout),t.resolve({ok:!1,reason:"closed"});this.ackWaiters.clear()}processMessage(t){let n=typeof t=="string"?t:"",r=n.indexOf(";");if(r===-1)return;let i=n.slice(0,r),o=n.slice(r+1),a;try{a=JSON.parse(o)}catch{return}if(i.startsWith("ack:")){this.resolveAck(i.slice(4),a);return}a=IR(a);let s=this.channelListeners.get(i);if(s)for(let c of s)c(a)}resolveAck(t,n){let r=this.ackWaiters.get(t);r&&(this.ackWaiters.delete(t),clearTimeout(r.timeout),r.resolve(n.value??{ok:!1}))}processClose(){if(!this.intentionallyClosed)for(let t of this.disconnectListeners)t()}};function IR(e){if(e.resource!=="connections")return e;switch(e.action){case"snapshot":return{...e,value:NR(e.value)};case"delta":return{...e,value:PR(e.value)};default:return e}}function NR(e){if(!Qf(e))return e;let t={};for(let n in e)t[n]=wh(e[n]);return t}function PR(e){return Qf(e)?{...e,pre:Rh(e.pre),post:Rh(e.post)}:e}function Rh(e){return e===null?null:wh(e)}function wh(e){if(!Qf(e))return e;let t={...e};return delete t.config,t}function Qf(e){return typeof e=="object"&&e!==null&&!Array.isArray(e)}var Jf="beepflow://resource-schemas/",nn={type:"number",description:"Nanoseconds since Unix epoch. Omit updatedAt on creates and manual edits unless preserving an existing value; replicated state updates it after accepted writes."},_e={type:"string"},Ho={type:"number"},Dh={type:"integer"},Nr={type:"boolean"};var Ch={type:"object",additionalProperties:_e},Zf={type:"object",additionalProperties:Nr},qc={type:"object",additionalProperties:{type:"object",additionalProperties:Nr,properties:{list:Nr,detail:Nr,create:Nr,edit:Nr,delete:Nr,authorize:Nr}}},Da=["boolean","string","number","datetime","map","binary","wildcard","list of boolean","list of string","list of number","list of datetime","list of map","list of binary","list of wildcard"],Oh=["ManualTick","AerospikeSet","ApacheKafkaTopic","MQTTTopic","KaggleFile","RabbitMQQueue","RabbitMQStream","QdrantCollection","BaseVectorCollection","BaseEventCollection","BaseLookupCollection","GorgiasTicketsView","GoogleDriveFile","GmailMessage","GmailThread","GmailEvent"],Ca={anyOf:[Nr,{type:"null"}]},FR=["Use resource_query first when editing existing items; upsert sends whole item state, not a JSON patch. Preserve unchanged fields.","Omit updatedAt on creates and manual edits unless preserving an existing value; replicated state updates it after accepted writes."];function rn(e,t,n){let r=`${Jf}${e}`;return{resource:e,uri:r,sourceType:t,notes:FR,itemSchema:{$schema:"https://json-schema.org/draft/2020-12/schema",title:`Beepflow ${e} item`,type:"object",additionalProperties:!1,required:n.required,properties:n.properties,...n.defs?{$defs:n.defs}:{}}}}var ed={$ref:"#/$defs/operatorType"},MR={type:"object",additionalProperties:!1,required:["value"],properties:{value:{description:"Raw option value written to node input literal when selected."},label:{..._e,description:"Optional label shown in operator input dropdowns."}}},LR={type:"object",additionalProperties:!1,required:["type"],properties:{type:{type:"string",enum:Da,description:'Blueprint value type name. Use "list of X" for lists, never "list".'},options:{anyOf:[{type:"array",items:MR},{type:"null"}],description:"Allowed literal values for dropdown-style widgets."},isArray:{type:"boolean",description:"Whether this pin accepts multiple values."},allowedTypes:{anyOf:[{type:"array",items:ed},{type:"null"}],description:"Allowed concrete types for wildcard pins."},linkType:{..._e,description:"Type-linking group used to propagate wildcard types across pins."},widgetType:{..._e,description:'Frontend input widget id. Supports built-in widgets, integration selectors, and "<IntegrationType>-connection" connection dropdowns.'},defaultValue:{description:"Default literal value used when node input omits a value."},defaultValueForArrayElement:{description:"Default literal value for newly added array input elements."}}},BR={type:"object",additionalProperties:!1,required:["name","doc","type"],properties:{name:{..._e,description:"Output pin name."},doc:{..._e,description:"Operator output documentation shown to users."},type:ed}},UR={type:"object",additionalProperties:!1,required:["name","doc","type"],properties:{name:{..._e,description:"Input pin name; node inputs are keyed by this value."},doc:{..._e,description:"Operator input documentation shown to users."},type:ed,isLiteral:{...Nr,description:"Whether this input must be edited as literal value instead of upstream connection."}}},kh=rn("blueprint-operators","frontend/src/tabs/blueprint/types.ts:Operator",{required:["id","type","name","doc","categoryPath","inputs"],properties:{id:{..._e,description:"Stable registered operator id referenced by blueprint nodes."},type:{..._e,description:"Operator kind, usually function, variable, or localVariable."},name:{..._e,description:"Display name used in operator search and node labels."},aliases:{type:"array",items:_e,description:"Additional search terms for this operator."},doc:{..._e,description:"Operator documentation shown to users."},categoryPath:{type:"array",items:_e,description:"Menu category path segments."},inputs:{type:"array",items:UR,description:"Input pins in display order."},output:{anyOf:[BR,{type:"null"}],description:"Output pin definition, or null for side-effect-only operators."},isDeprecated:{...Nr,description:"Whether operator is deprecated and hidden from default search."},hidden:{...Nr,description:"Whether operator is hidden from menus and search."},canMock:{...Nr,description:"Whether test mode can mock this operator."},updatedAt:nn},defs:{operatorType:LR}});var VR={type:"object",additionalProperties:!1,properties:{x:{...Ho,description:"Optional node world x coordinate in blueprint editor. For new nodes, never specify style.x; omit it so the frontend can place nodes after measuring dimensions."},y:{...Ho,description:"Optional node world y coordinate in blueprint editor. For new nodes, never specify style.y; omit it so the frontend can place nodes after measuring dimensions."},title:{..._e,description:"Optional display title shown on node."},comment:{..._e,description:"Optional user-authored node comment."}}},qR={type:"object",additionalProperties:!0,description:"Blueprint view node. For new nodes, never specify style.x or style.y; omit coordinates so the frontend can place nodes after measuring dimensions. Known visualization blocks are intentionally accepted as additional properties.",required:["id"],properties:{id:{..._e,description:"Node id; must match key in blueprint view nodes record."},style:VR}},xh=rn("blueprint-views","frontend/src/tabs/blueprint/types.ts:BlueprintView",{required:["id","nodes"],properties:{id:{..._e,description:"Blueprint tab id; must match tabs and blueprints resource id."},updatedAt:nn,nodes:{type:"object",additionalProperties:qR,description:"Editor view state keyed by node id."}}});var Kc={type:"string",description:"Integration resource type processed by this blueprint, such as ApacheKafkaTopic or QdrantCollection. Call integration_blueprint_contexts_list first; use only resource types returned by that tool. The returned executionKind determines trigger choice: managed resources use executor, finite resources use manual/cron/loop/blueprint/webhook based on user intent."},Gc={type:"object",additionalProperties:!0,description:"Integration-specific config for context.type. Start from contextTemplate.config returned by integration_blueprint_contexts_list, fill every configFields item where required=true, and preserve optional defaults such as consumerGroupId, clientId, parser, offsetResetStrategy, orderBy, or webhook topic maps when provided."},Wc={type:"object",additionalProperties:!1,required:["enabled"],properties:{enabled:{type:"boolean",description:"Must be true. Backend ignores this trigger branch when enabled is false."}}},td={...Wc.properties.enabled,enum:[!0]},zR=["auto","application/json","text/plain","text/html","application/xml","application/x-www-form-urlencoded","multipart/form-data","application/octet-stream"],KR={type:"object",additionalProperties:!1,required:["count"],description:"Run immediately when explore runtime starts or restarts. Use for finite resource sampling, one-shot imports, and ad hoc reads.",properties:{count:{type:"integer",minimum:1,description:"Number of executions to run back-to-back. Frontend default is 1; backend coerces values below 1 to 1."}}},GR={type:"object",additionalProperties:!1,required:["expression"],description:"Run on a seconds-field cron schedule while explore runtime is active. Use for scheduled finite-resource refreshes.",properties:{expression:{type:"string",description:"Cron expression with six fields including seconds, parsed by robfig/cron. Example: 0 */5 * * * * runs every five minutes."},timezone:{type:"string",description:"Optional IANA timezone name such as UTC or America/New_York. Backend uses UTC when omitted or empty."}}},WR={type:"object",additionalProperties:!1,required:["delayMs"],description:"Run immediately, then wait delayMs before repeating while explore runtime is active. Use only for deliberate fixed-delay polling.",properties:{delayMs:{type:"integer",minimum:1,description:"Delay between executions in milliseconds. Must be positive to avoid a hot loop."}}},Ih={...Wc,description:"Wait while active until another blueprint or Trigger Self operator invokes this blueprint. Trigger argument is available through Get Trigger Argument."},nd={type:"object",additionalProperties:!1,required:["enabled"],description:"Wait while active for generic GET/POST /:tabId/trigger HTTP calls. Request method, URL, parsed body, headers, and timestamp become trigger argument. Webhook URL is `${status.backendUrl}/${encodeURIComponent(blueprint.id)}/trigger` and runs only while blueprint is active in explore mode.",properties:{enabled:Wc.properties.enabled,timeoutMs:{type:"integer",minimum:1,description:"Maximum synchronous webhook execution time in milliseconds. Backend uses 30000 when omitted or below 1."},contentType:{type:"string",enum:zR,description:"Request body parser. Omit or use auto to infer from incoming Content-Type, then fall back to JSON sniffing, UTF-8 text, then binary. Not for provider webhook resources managed through BaseEvent; use BaseEventCollection."}}},Nh={...Wc,description:"Use for managed integration resources where runtime owns stream, event, webhook, or poll lifecycle, such as ApacheKafkaTopic, RabbitMQStream, GmailMessage, GmailThread, GmailEvent, BaseEventCollection, and MQTTTopic."},zc={type:"object",additionalProperties:!1,minProperties:1,maxProperties:1,description:"Exactly one trigger branch. For executionKind=managed from integration_blueprint_contexts_list, use executor. For executionKind=finite, choose manual for ad hoc/sample/start-once runs, cron for scheduled refresh, loop for fixed-delay polling, blueprint for invocation by another blueprint, or webhook for generic GET/POST /:tabId/trigger HTTP calls.",properties:{manual:KR,cron:GR,loop:WR,blueprint:Ih,webhook:nd,executor:Nh},oneOf:[{required:["manual"]},{required:["cron"]},{required:["loop"]},{required:["blueprint"]},{required:["webhook"]},{required:["executor"]}]},Ph={...zc,properties:{...zc.properties,blueprint:{...Ih,properties:{enabled:td}},webhook:{...nd,properties:{...nd.properties,enabled:td}},executor:{...Nh,properties:{enabled:td}}}};var HR={type:"object",additionalProperties:!1,required:["literal"],properties:{literal:{description:"Literal JSON value for this input element; null is valid when connected upstream."},nodeId:{..._e,description:"Upstream node id when this value is connected to another node output."},operatorInputId:{..._e,description:"Upstream output pin name used by this connection."},nodeInputIndex:{..._e,description:'CRDT list index of upstream output value. Use "0.5" for any connected node output.'}}},XR={type:"object",additionalProperties:!1,required:["values"],properties:{isArray:{...Ca,description:"Whether input accepts multiple values for one operator input."},values:{type:"object",additionalProperties:HR,description:"Input values keyed by CRDT list index strings."},type:{type:"string",enum:Da,description:"Resolved input type override."},forceZipping:{...Ca,description:"Force list zipping behavior for multiple upstream values."},listInputMode:{type:"string",enum:["list","items"],description:"Whether this input receives one whole list value or assembles a list from item values."}}},$R={type:"object",additionalProperties:!1,required:["id","operatorId","inputs"],properties:{id:{..._e,description:"Stable node id; must match key in blueprint nodes record."},operatorId:{..._e,description:"Id of registered blueprint operator this node executes."},inputs:{type:"object",additionalProperties:XR,description:"Node inputs keyed by operator input name."},mockNever:{...Ca,description:"Disable mocking for this node."},skipBehavior:{type:"string",enum:["skip","null"],description:"Behavior when upstream value is skipped."},disabled:{...Ca,description:"Whether this node and downstream dependent nodes are disabled."},outputType:{type:"string",enum:Da,description:"Resolved output type for wildcard operators."}}},jR={type:"object",additionalProperties:!1,required:["type","trigger"],properties:{type:Kc,trigger:Ph,config:Gc}},Fh=rn("blueprints","frontend/src/tabs/blueprint/types.ts:Blueprint",{required:["id","mode","nodes","context"],properties:{id:{..._e,description:"Blueprint tab id; must match tabs resource id."},updatedAt:nn,mode:{type:"string",enum:["test","explore"],description:'Execution mode; result id is blueprint id plus "-test" or "-explore".'},nodes:{type:"object",additionalProperties:$R,description:"Blueprint nodes keyed by node id."},context:jR,testRecordsAmount:{...Dh,description:"Target number of test records to keep for test mode."},recomputeOnChange:{type:"string",enum:["always","manual"],description:"Whether edits automatically restart execution."},mockNever:{...Nr,description:"Global flag to disable node mocking."},desiredState:{type:"string",enum:["active","inactive"],description:"Requested runtime state for test or explore mode."}}});var YR=["Aerospike","ApacheKafka","MQTT","Kaggle","FacebookAds","RabbitMQ","Shopify","YouTube","Webshare","Playwright","AWS","Qdrant","OpenAI","BaseVector","BaseEvent","BaseLookup","Gorgias","LMStudio","OpenRouter","VoyageAI","GoogleDrive","GoogleSheets","Gmail","DiscordChannelWebhook"],Mh=rn("connections","frontend/src/integrations/types.ts:Connection",{required:["id","label","type","spaceId"],properties:{id:_e,updatedAt:nn,label:_e,type:{type:"string",enum:YR},spaceId:_e}});var Lh=rn("roles","frontend/src/auth/roles/types.ts:Role",{required:["id","label","authorizations"],properties:{id:_e,updatedAt:nn,label:_e,authorizations:qc}});var Bh=rn("pages","frontend/src/tabs/types.ts:Page",{required:["id","sourceUrl","distUrl"],properties:{id:{..._e,description:"Page tab id; must match tabs resource id."},updatedAt:nn,sourceUrl:{..._e,description:"File-service URL for raw source HTML."},distUrl:{..._e,description:"File-service URL for optimized HTML rendered in a sandbox iframe."}}});var Uh=rn("schemas","frontend/src/integrations/types.ts:Schema",{required:["id","type","connectionId","path","schema"],properties:{id:_e,updatedAt:nn,type:{type:"string",enum:Oh},connectionId:_e,path:Ch,schema:{type:"object",additionalProperties:{type:"string",enum:Da}},keySerdeType:{type:"string"},valueSerdeType:{type:"string"}}});var Vh=rn("space-join-requests","frontend/src/spaces/space-join-requests/types.ts:SpaceJoinRequest",{required:["id","createdAt","requestedBy","kind","status","spaceId","userId"],properties:{id:_e,createdAt:{type:"number",description:"Nanoseconds since Unix epoch."},updatedAt:nn,requestedBy:_e,kind:{type:"string",enum:["invite","request"]},status:{type:"string",enum:["pending","granted","denied"]},spaceId:_e,userId:_e}});var qh=rn("spaces","frontend/src/spaces/types.ts:Space",{required:["id","label"],properties:{id:_e,updatedAt:nn,label:_e,thumbnailUrl:_e,description:_e,isUserSpace:Ca}});var zh=rn("tabs","frontend/src/tabs/types.ts:Tab",{required:["id","name","order","type","parent","spaceId"],properties:{id:{..._e,description:"Stable tab id. Blueprint and page tabs normally have matching records keyed by this id."},updatedAt:nn,name:_e,order:Ho,type:{type:"string",enum:["blueprint","folder","page"],description:"Navigation item kind; blueprint and page tabs normally have matching records."},parent:_e,spaceId:_e}});var Kh=rn("user-locations","frontend/src/workspace/user-location/types.ts:UserLocation",{required:["id"],properties:{id:_e,updatedAt:nn,tab:{type:"object",additionalProperties:!1,required:["id"],properties:{id:_e}},blueprint:{type:"object",additionalProperties:!1,required:["id"],properties:{id:_e,worldPosition:{type:"object",additionalProperties:!1,required:["x","y"],properties:{x:Ho,y:Ho}}}}}});var Gh=rn("users","frontend/src/auth/users/types.ts:User",{required:["id","displayName","roleIds","authorizations","spaces"],properties:{id:_e,updatedAt:nn,displayName:_e,avatarUrl:_e,roleIds:Zf,authorizations:qc,spaces:Zf}});var Hc=[Gh,Lh,qh,zh,Bh,Mh,Uh,Fh,xh,kh,Kh,Vh];function Xc(e){return Hc.find(t=>t.resource===e)}var rd=[Ii("users","Workspace users and authorizations.",!0),Ii("roles","Workspace roles and resource authorizations.",!0),Ii("spaces","Workspace spaces.",!0),Ii("tabs","Tabs and folders visible to authorized user; blueprint and page tabs normally share ids with matching records.",!0),Ii("pages","Untrusted single-page HTML source and optimized file URLs keyed by matching page tab id.",!0),Ii("connections","Read-only integration connections without secret-bearing config; config is redacted and cannot be read through MCP.",!1),Ii("schemas","Integration schema metadata.",!0),Ii("blueprints","Blueprint definitions keyed by matching blueprint tab id.",!0),Ii("blueprint-views","Blueprint editor view state keyed by matching blueprint tab id.",!0),Ii("blueprint-operators","Registered blueprint operator definitions.",!1),Ii("user-locations","Live user location records.",!0),Ii("space-join-requests","Space invitation and join requests.",!0)],QR=["tabs","pages","blueprints","blueprint-views"],id=new Set(QR),Oa=rd.filter(e=>!id.has(e.name)),bu=Oa.map(e=>e.name),Wh=rd.map(e=>e.name);function JR(e){return rd.find(t=>t.name===e)}function Hh(e){return Oa.find(t=>t.name===e)}function Xh(e){if(JR(e))return e;throw new Error(`unsupported resource: ${e}`)}function od(e){if(id.has(e))throw new Error(`dedicated resource ${e}: use tab and blueprint intent tools instead of generic resource_* tools`);if(Hh(e))return e;throw new Error(`unsupported resource: ${e}`)}function ad(e){let t=Hh(e);if(id.has(e))throw new Error(`dedicated resource ${e}: use tab and blueprint intent tools instead of generic resource_* tools`);if(!t)throw new Error(`unsupported resource: ${e}`);if(!t.writable)throw new Error(`resource is read-only: ${e}`);return t.name}function Ii(e,t,n){return{name:e,description:t,writable:n,schemaUri:`${Jf}${e}`}}function Pr(){return Date.now()*1e6}function ud(e,t){if(e===null&&t===null)return{pre:null,post:null};if(e===null&&t!==null)return{pre:null,post:t};if(e!==null&&t===null)return{pre:e,post:null};if(typeof e!="object"||typeof t!="object")return e!==t?{pre:e,post:t}:{pre:null,post:null};if(Array.isArray(e)||Array.isArray(t))return{pre:null,post:null};let{pre:n,post:r}=$h(e,t);return n===null&&r===null?{pre:null,post:null}:{pre:n,post:r}}function $h(e,t){let n={},r={},i=!1,o=new Set([...mo(e),...mo(t)]);for(let a of o){if(a==="updatedAt")continue;let s=e[a],c=t[a];if(Array.isArray(s)||Array.isArray(c))continue;let d=Xo(s),p=Xo(c);if(!(a in t))d||(n[a]=s,r[a]=null,i=!0);else if(!(a in e))p||(n[a]=null,r[a]=c,i=!0);else{if(d&&p)continue;if(d&&!p)n[a]=null,r[a]=c,i=!0;else if(!d&&p)n[a]=s,r[a]=null,i=!0;else{let{pre:m,post:g}=ZR(s,c);(m!==void 0||g!==void 0)&&(m!==void 0&&(n[a]=sd(m)),g!==void 0&&(r[a]=sd(g)),i=!0)}}}return i?mo(n).length===0&&mo(r).length===0?{pre:null,post:null}:mo(n).length===0?{pre:null,post:r}:mo(r).length===0?{pre:n,post:null}:{pre:n,post:r}:{pre:null,post:null}}function ZR(e,t){if(ew(e,t))return{pre:void 0,post:void 0};let n=Xo(e),r=Xo(t);if(n&&r)return{pre:void 0,post:void 0};if(n)return{pre:null,post:t};if(r)return{pre:e,post:null};if(Array.isArray(e)||Array.isArray(t))return{pre:void 0,post:void 0};if(typeof e!=typeof t)return{pre:e,post:t};if(typeof e=="object"&&e!==null&&typeof t=="object"&&t!==null){let{pre:i,post:o}=$h(e,t);return i===null&&o===null?{pre:void 0,post:void 0}:{pre:i===null?void 0:i,post:o===null?void 0:o}}return{pre:e,post:t}}function Xo(e){return e==null?!0:typeof e=="object"&&e!==null?Array.isArray(e)?e.length===0:mo(e).length===0:!1}function ew(e,t){return Xo(e)&&Xo(t)?!0:cd(e,t)}function cd(e,t){if(e===t)return!0;if(e==null||t==null||typeof e!="object"||typeof t!="object")return!1;let n=mo(e),r=mo(t);if(n.length!==r.length)return!1;for(let i of n)if(!(i in t)||!cd(e[i],t[i]))return!1;return!0}function $c(e,t){return t.pre===null?e===null:e===null||typeof e!="object"||Array.isArray(e)?!1:jh(e,t.pre)}function jh(e,t){for(let n in t)if(n!=="updatedAt"&&!tw(e[n],t[n]))return!1;return!0}function tw(e,t){return t===null||nw(t)?Xo(e):e===void 0?!1:typeof t=="object"&&t!==null&&!Array.isArray(t)&&typeof e=="object"&&e!==null&&!Array.isArray(e)?jh(e,t):cd(e,t)}function nw(e){return e!==null&&typeof e=="object"&&!Array.isArray(e)&&mo(e).length===0}function sd(e){if(e==null)return null;if(typeof e=="object"&&e!==null){if(Array.isArray(e)&&e.length===0)return null;if(!Array.isArray(e)){let t={},n=!1;for(let r in e)t[r]=sd(e[r]),t[r]!==void 0&&(n=!0);return n?t:null}}return e}function ld(e,t){let n=fd(e,t);return n!==null&&typeof n=="object"&&!Array.isArray(n)&&(n.updatedAt=t.updatedAt),n}function fd(e,t){return t.post===null?null:e===null?t.post:typeof e!="object"||Array.isArray(e)?t.post:Yh(e,t.post)}function Yh(e,t){let n={};for(let r in e)if(r in t){let i=t[r];if(i===null)continue;typeof i=="object"&&!Array.isArray(i)&&typeof e[r]=="object"&&!Array.isArray(e[r])&&e[r]!==null?n[r]=Yh(e[r],i):n[r]=i}else n[r]=e[r];for(let r in t)!(r in e)&&t[r]!==null&&(n[r]=t[r]);return n}function mo(e){let t=[];for(let n in e)t.push(n);return t}var Qh="replicated-state",jc=class{ackedResources={};dirtyResources={};unauthorizedKeys={};loadingResources={};loadingPromises=new Map;loadedResources=new Set;registeredResources=new Set;resourceChangeListeners=new Set;snapshotWaiters=new Map;storage;socketSession;logger;inflightItems=new Map;constructor(t,n,r){this.storage=t,this.socketSession=n,this.logger=r}onResourceChange(t){return this.resourceChangeListeners.add(t),()=>this.resourceChangeListeners.delete(t)}registerResource(t){this.registeredResources.add(t),this.initializeResource(t)}isResourceRegistered(t){return this.registeredResources.has(t)}getRegisteredResources(){return Array.from(this.registeredResources)}setDirtyItems(t,n){this.registerResource(t),this.dirtyResources[t]=Yr(n)}setDirtyItem(t,n,r){if(this.registerResource(t),r===void 0){delete this.dirtyResources[t][n];return}this.dirtyResources[t][n]=Yr(r)}clearSessionState(){this.ackedResources={},this.loadingResources={},this.loadingPromises.clear(),this.loadedResources.clear(),this.inflightItems.clear();for(let t of this.registeredResources)this.dirtyResources[t]={},this.unauthorizedKeys[t]={},this.loadingResources[t]=!0,this.emitResourceChange(t)}async loadRegisteredResourcesFromStorage(){await Promise.all(Array.from(this.registeredResources,t=>this.loadResourceFromStorage(t)))}async hydrate(t,n){this.registerResource(t),await this.loadResourceFromStorage(t),this.logger.info(`Calculating lastUpdatedAtSeen from ${Zh(this.ackedResources[t])} items`);let r=this.prepareSnapshotQuery(t,n);this.logger.info(`\u{1F4F8} ${t} requested with query:`,r),this.socketSession.send(Qh,{resource:t,action:"snapshot",value:r})}hydrateAll(t){return this.hydrate(t,{all:!0})}async waitForSnapshot(t,n){await new Promise((r,i)=>{let o,a=()=>{clearTimeout(o),r()};o=setTimeout(()=>{this.snapshotWaiters.get(t)?.delete(a),i(new Error(`snapshot timeout for ${t}`))},n),this.snapshotWaiters.has(t)||this.snapshotWaiters.set(t,new Set),this.snapshotWaiters.get(t).add(a)})}processSocketEvent(t){switch(t.action){case"snapshot":this.applySnapshot(t.resource,t.value??{});break;case"delta":this.applyRemoteDelta(t);break}}async upsertItem(t,n){this.registerResource(t);let r=this.getAckedValue(t,n.id),i=ud(r,n);return i.pre===null&&i.post===null?!0:this.sendDelta(t,n.id,i,n)}async deleteItem(t,n){this.registerResource(t);let r=this.getAckedValue(t,n),i=ud(r,null);return i.pre===null&&i.post===null?!0:this.sendDelta(t,n,i,null)}isItemInflight(t,n){return this.inflightItems.get(t)?.has(n)===!0}async sendDelta(t,n,r,i){this.registerResource(t),this.inflightItems.has(t)||this.inflightItems.set(t,new Set);let o=this.inflightItems.get(t);if(o.has(n))return!1;let a=this.getDirtyValue(t,n);$c(a,r)&&(arguments.length>=4?this.setDirtyValue(t,n,Yr(i)):this.setDirtyValue(t,n,fd(a,Yr(r))),this.emitResourceChange(t)),o.add(n);let s;try{s=await this.socketSession.sendWithAck(Qh,{resource:t,action:"delta",key:n,value:r})}catch(c){s={ok:!1,reason:c instanceof Error?c.message:"error"}}return o.delete(n),s.ok?!0:(this.revertDirtyToAckedValue(t,n),this.emitResourceChange(t),this.logger.error(`!ack[${t}] Reverting to acked state for ${t}:${n}`,s.reason),!1)}getAckedValue(t,n){return this.initializeResource(t),this.ackedResources[t][n]??null}getDirtyValue(t,n){return this.initializeResource(t),this.dirtyResources[t][n]??null}getVisibleItems(t){this.initializeResource(t);let n={};for(let r in this.dirtyResources[t]){let i=this.dirtyResources[t][r];i!=null&&(n[r]=i)}return n}getRawItems(t){return this.initializeResource(t),Yr(this.dirtyResources[t])}getAckedItems(t){return this.initializeResource(t),Yr(this.ackedResources[t])}getUnauthorizedKeys(t){return this.initializeResource(t),Yr(this.unauthorizedKeys[t])}isResourceLoading(t){return this.initializeResource(t),this.loadingResources[t]}initializeResource(t){this.ackedResources[t]===void 0&&(this.ackedResources[t]={}),this.dirtyResources[t]===void 0&&(this.dirtyResources[t]={}),this.unauthorizedKeys[t]===void 0&&(this.unauthorizedKeys[t]={}),this.loadingResources[t]===void 0&&(this.loadingResources[t]=!0)}prepareSnapshotQuery(t,n){this.initializeResource(t);let r=Yr(n);if(r.lastUpdatedAtSeen!==void 0)return r;let i=this.buildLastUpdatedAtSeen(t,r);return Jh(i)||(r.lastUpdatedAtSeen=i),r}async loadResourceFromStorage(t){if(this.initializeResource(t),this.loadedResources.has(t))return;if(this.loadingPromises.has(t))return this.loadingPromises.get(t);let n=this.loadResourceItemsFromStorage(t);this.loadingPromises.set(t,n);try{await n}finally{this.loadingPromises.delete(t),this.loadedResources.add(t)}}async loadResourceItemsFromStorage(t){let n=!1,r=0;try{let i=await this.storage.loadItems(t);if(i&&Jh(this.ackedResources[t])){n=!0;for(let o in i)this.applyCachedItem(t,o,i[o])&&(r+=1)}}catch(i){this.logger.warn(`Failed to load cached ${t}: ${String(i)}`)}finally{this.loadingResources[t]=!1,this.emitResourceChange(t),n?this.logger.info(`\u{1F4C2} ${r}x ${t} from cache`):this.logger.info(`\u{1F4C2} no cached data for ${t}`)}}applyCachedItem(t,n,r){return r===null?(this.ackedResources[t][n]=null,this.dirtyResources[t][n]=null,!0):r==="unauthorized"?(this.unauthorizedKeys[t][n]=!0,!1):(this.ackedResources[t][n]=Yr(r),this.dirtyResources[t][n]=Yr(r),!0)}applySnapshot(t,n){this.initializeResource(t);for(let r in n){let i=n[r];i===null?(this.ackedResources[t][r]=null,(!this.isItemInflight(t,r)||this.getDirtyValue(t,r)==null)&&(this.dirtyResources[t][r]=null),delete this.unauthorizedKeys[t][r]):i==="unauthorized"?(delete this.ackedResources[t][r],delete this.dirtyResources[t][r],this.unauthorizedKeys[t][r]=!0):(this.ackedResources[t][r]=Yr(i),this.dirtyResources[t][r]=Yr(i),delete this.unauthorizedKeys[t][r]),this.storage.persistItem(t,r,i).catch(o=>{this.logger.warn(`Failed to persist ${t}:${r}: ${String(o)}`)})}this.loadingResources[t]=!1,this.emitResourceChange(t),this.logger.info(`\u{1F4F8} ${Zh(n)}x ${t} `),this.resolveSnapshotWaiters(t)}applyRemoteDelta(t){let n=t.resource,r=t.key;if(!r)return;this.initializeResource(n);let i=t.value,o={pre:i.pre,post:i.post},a=this.getAckedValue(n,r);if(!$c(a,o))this.logger.error(`\u{1D6AB}S precondition invalid on last acked for ${n}:${r}`,{pre:o.pre,post:o.post,current:a});else{let c=ld(a,Yr(i));this.ackedResources[n][r]=c,this.storage.persistItem(n,r,c).catch(d=>{this.logger.warn(`Failed to persist ${n}:${r}: ${String(d)}`)}),this.logger.info(dd(`\u{1D6AB}S[${n}] acked`,o))}let s=this.getDirtyValue(n,r);t.by!==this.socketSession.getSessionId()?$c(s,o)?o.post===null?(this.dirtyResources[n][r]=null,this.logger.info(dd(`\u{1D6AB}S[${n}] dirty`,o))):(this.dirtyResources[n][r]=ld(s,Yr(i)),this.logger.info(dd(`\u{1D6AB}S[${n}] dirty`,o))):(this.logger.warn(`Skip delta on dirty for ${n}:${r}`,{pre:o.pre,post:o.post,current:a}),this.revertDirtyToAckedValue(n,r)):o.post!=null&&s!=null&&typeof s=="object"&&(s.updatedAt=i.updatedAt,this.dirtyResources[n][r]=s,this.logger.info(`\u{1D6AB}S[${n}] dirty updatedAt for ${r}`)),this.emitResourceChange(n)}buildLastUpdatedAtSeen(t,n){let r=this.ackedResources[t],i={};if(n.all){for(let o in r)this.copyItemUpdatedAt(r[o],o,i);return i}if(n.keys&&n.keys.length>0)for(let o of n.keys)this.copyItemUpdatedAt(r[o],o,i);return i}copyItemUpdatedAt(t,n,r){t&&typeof t=="object"&&typeof t.updatedAt=="number"&&(r[n]=t.updatedAt)}setDirtyValue(t,n,r){if(r===null){this.dirtyResources[t][n]=null;return}this.dirtyResources[t][n]=r}revertDirtyToAckedValue(t,n){let r=this.ackedResources[t][n];if(r===void 0){delete this.dirtyResources[t][n];return}if(r===null){this.dirtyResources[t][n]=null;return}this.dirtyResources[t][n]=Yr(r)}emitResourceChange(t){let n={resource:t,acked:this.getAckedItems(t),dirty:this.getRawItems(t),unauthorized:this.getUnauthorizedKeys(t),loading:this.loadingResources[t]};for(let r of this.resourceChangeListeners)r(n)}resolveSnapshotWaiters(t){let n=this.snapshotWaiters.get(t);if(n){this.snapshotWaiters.delete(t);for(let r of n)r()}}};function Yr(e){if(e===void 0)return e;if(typeof structuredClone=="function")try{return structuredClone(e)}catch{}try{return JSON.parse(JSON.stringify(e))}catch{return e}}function Jh(e){for(let t in e)return!1;return!0}function Zh(e){let t=0;for(let n in e)t+=1;return t}function dd(e,t){return`${e}
|
|
28
28
|
delta.pre: ${JSON.stringify(t.pre)}
|
|
29
29
|
delta.post: ${JSON.stringify(t.post)}`}var Yc=15e3,iw=2e3,hd=class{replicatedState;recordStorage;gatewaySocketSession;startPromise;reconnectTimer;registeredResources=new Set(Wh);closed=!1;start(){return this.startPromise?this.startPromise:(this.closed=!1,this.startPromise=this.connectAndHydrate().catch(t=>{throw this.startPromise=void 0,t}),this.startPromise)}async hydrateResource(t,n={all:!0}){this.registerResource(t),await this.start(),await this.hydrateConnectedResource(t,n)}async readResourceItems(t,n={all:!0}){return this.registerResource(t),await this.start(),this.filterVisibleItems(t,n)}async readResourceItem(t,n){this.registerResource(t),await this.start();let r=this.replicatedState?.getVisibleItems(t)[n]??null;return e0(t,r)}async upsertResourceItem(t,n){if(this.registerResource(t),await this.start(),!this.replicatedState)throw new Error("replicated state not initialized");return this.replicatedState.upsertItem(t,n)}async deleteResourceItem(t,n){if(this.registerResource(t),await this.start(),!this.replicatedState)throw new Error("replicated state not initialized");return this.replicatedState.deleteItem(t,n)}waitForChannelEvent(t,n,r=Yc){if(!this.gatewaySocketSession)throw new Error("gateway websocket not connected");return this.gatewaySocketSession.waitForChannelEvent(t,i=>n(i),r)}collectChannelEvents(t,n,r=Yc,i=250){if(!this.gatewaySocketSession)throw new Error("gateway websocket not connected");return this.gatewaySocketSession.collectChannelEvents(t,o=>n(o),r,i)}sendChannelEvent(t,n){if(!this.gatewaySocketSession)throw new Error("gateway websocket not connected");this.gatewaySocketSession.send(t,n)}close(){this.closed=!0,this.reconnectTimer&&clearTimeout(this.reconnectTimer),this.startPromise=void 0,this.gatewaySocketSession?.close(),this.recordStorage?.close(),this.gatewaySocketSession=void 0,this.recordStorage=void 0,this.replicatedState=void 0}registerResource(t){Xh(t),this.registeredResources.add(t),this.replicatedState?.registerResource(t)}async connectAndHydrate(){let t=await pi();if(!t)throw new Error("missing jwt: set BEEPFLOW_JWT or run auth tool to persist token");let n=await mi(t);await Eh(n);let r=Ht(),i=ko(n),o=Th(i.email);this.gatewaySocketSession?.close(),this.recordStorage?.close(),this.recordStorage=new Uc(r.replicatedStateDatabasePath,o),this.gatewaySocketSession=new Vc(r.backendUrl,n),this.replicatedState=new jc(this.recordStorage,this.gatewaySocketSession,uw),this.gatewaySocketSession.onChannel("replicated-state",a=>this.replicatedState?.processSocketEvent(a)),this.gatewaySocketSession.onDisconnected(()=>this.scheduleReconnect());for(let a of this.registeredResources)this.replicatedState.registerResource(a);await this.gatewaySocketSession.connect(Yc),await this.replicatedState.loadRegisteredResourcesFromStorage(),await this.hydrateRegisteredResources()}async hydrateRegisteredResources(){await Promise.all(Array.from(this.registeredResources,t=>this.hydrateConnectedResource(t,{all:!0})))}async hydrateConnectedResource(t,n){if(!this.replicatedState)throw new Error("replicated state not initialized");let r=this.replicatedState.waitForSnapshot(t,Yc);await this.replicatedState.hydrate(t,n),await r}filterVisibleItems(t,n){let r=this.replicatedState?.getVisibleItems(t)??{},i={};for(let o in r)ow(o,r[o],n)&&(i[o]=e0(t,r[o]));return i}scheduleReconnect(){this.closed||this.reconnectTimer||(this.startPromise=void 0,this.reconnectTimer=setTimeout(()=>{this.reconnectTimer=void 0,this.start().catch(()=>this.scheduleReconnect())},iw))}};function ow(e,t,n){return aw(e,t,n.lastUpdatedAtSeen)?!!(n.all||n.keys?.includes(e)||sw(t,n.fieldEqualTo)):!1}function e0(e,t){if(e!=="connections"||!t||typeof t!="object"||Array.isArray(t))return t;let n={...t};return delete n.config,n}function aw(e,t,n){let r=n?.[e];if(r===void 0||!t||typeof t!="object")return!0;let i=t.updatedAt;return typeof i!="number"||i>r}function sw(e,t){if(!t||!e||typeof e!="object")return!1;let n=e,r=!1;for(let i in t)if(r=!0,!rw(n[i],t[i]))return!1;return r}var uw={info(e,t){pd("info",e,t)},warn(e,t){pd("warn",e,t)},error(e,t){pd("error",e,t)}};function pd(e,t,n){let r=n===void 0?"":` ${JSON.stringify(n)}`;process.stderr.write(`[replicated-state:${e}] ${t}${r}
|
|
30
30
|
`)}var md;function bs(){return md||(md=new hd),md}import{isDeepStrictEqual as cw}from"node:util";function pr(e,t){let n=Xc(e);if(!n)throw new Error(`missing schema for resource: ${e}`);let r={failures:[],rootSchema:n.itemSchema};if(vs(n.itemSchema,t,"$",r),r.failures.length===0)return;let i=r.failures.slice(0,5).map(o=>`${o.path} ${o.message}`).join("; ");throw new Error(`item does not match ${e} schema: ${i}`)}function vs(e,t,n,r){if(e===!0)return;if(e===!1)return ho(r,n,"is not allowed");if(!Sw(e))return;let i=e.$ref;if(typeof i=="string"){vs(bw(i,r.rootSchema),t,n,r);return}lw(e,t,n,r)&&(fw(e,t,n,r),dw(e,t,n,r),pw(e,t,n,r),hw(e,t,n,r))}function lw(e,t,n,r){if(!Array.isArray(e.anyOf))return!0;for(let i of e.anyOf){let o={failures:[],rootSchema:r.rootSchema};if(vs(i,t,n,o),o.failures.length===0)return!1}return ho(r,n,"does not match any allowed schema"),!1}function fw(e,t,n,r){let i=e.enum;if(Array.isArray(i)){for(let o of i)if(cw(t,o))return;ho(r,n,`must be one of ${i.map(String).join(", ")}`)}}function dw(e,t,n,r){let i=e.type;if(typeof i=="string"&&!t0(t,i)){ho(r,n,`must be ${i}`);return}if(Array.isArray(i)){for(let o of i)if(typeof o=="string"&&t0(t,o))return;ho(r,n,`must be ${i.map(String).join(" or ")}`)}}function pw(e,t,n,r){if(e.type!=="object"||!vu(t))return;let i=vu(e.properties)?e.properties:{};mw(e,t,n,r);for(let o of gw(e))(!(o in t)||t[o]===void 0)&&ho(r,`${n}.${o}`,"is required");for(let o in t){if(t[o]===void 0){ho(r,`${n}.${o}`,"must not be undefined");continue}if(o in i){vs(i[o],t[o],`${n}.${o}`,r);continue}_w(e,t[o],`${n}.${o}`,r)}}function mw(e,t,n,r){let i=0;for(let s in t)Object.prototype.hasOwnProperty.call(t,s)&&i++;let o=e.minProperties;typeof o=="number"&&i<o&&ho(r,n,`must have at least ${o} properties`);let a=e.maxProperties;typeof a=="number"&&i>a&&ho(r,n,`must have at most ${a} properties`)}function hw(e,t,n,r){if(e.type!=="array"||!Array.isArray(t))return;let i=e.items;if(i!==void 0)for(let o=0;o<t.length;o++)vs(i,t[o],`${n}[${o}]`,r)}function _w(e,t,n,r){let i=e.additionalProperties;if(i===!1){ho(r,n,"is not allowed");return}i===void 0||i===!0||vs(i,t,n,r)}function gw(e){return Array.isArray(e.required)?e.required.filter(t=>typeof t=="string"):[]}function bw(e,t){if(!e.startsWith("#/"))return!1;let n=t,r=e.slice(2).split("/").map(vw);for(let i of r){if(!vu(n)||!(i in n))return!1;n=n[i]}return n}function vw(e){return e.replace(/~1/g,"/").replace(/~0/g,"~")}function t0(e,t){switch(t){case"array":return Array.isArray(e);case"boolean":return typeof e=="boolean";case"integer":return Number.isInteger(e);case"null":return e===null;case"number":return typeof e=="number"&&Number.isFinite(e);case"object":return vu(e);case"string":return typeof e=="string";default:return!0}}function Sw(e){return vu(e)}function vu(e){return typeof e=="object"&&e!==null&&!Array.isArray(e)}function ho(e,t,n){e.failures.push({path:t,message:n})}import _d from"node:fs/promises";import yw from"node:os";import n0 from"node:path";var Ew=15e3;async function Qc(e){let t=await i0({method:"GET",path:e});if(!t.ok)throw await o0(e,t);return await t.json()}async function r0(e){let t=await i0(e),n={status:t.status,statusText:t.statusText,headers:Cw(t.headers)};if(t.status>=300&&t.status<400)return{...n,location:t.headers.get("location")};if(!t.ok)throw await o0(e.path,t);return e.responseMode==="binary"?await Iw(t,e,n):(t.headers.get("content-type")??"").includes("application/json")?{...n,body:await t.json().catch(()=>null)}:{...n,body:await t.text().catch(()=>"")}}async function i0(e){let t=await Aw(),n=ww(e.path,e.query),r=new Headers({Authorization:`Bearer ${t}`}),i=e.timeoutMs??Ew;Rw(r,e.headers);let o={method:e.method,headers:r,redirect:"manual",signal:AbortSignal.timeout(i)};e.requestMode==="multipart"?o.body=await Ow(e):e.requestMode==="form"?(o.body=xw(e.body),r.set("Content-Type","application/x-www-form-urlencoded")):e.body!==void 0&&e.method!=="GET"&&e.method!=="HEAD"&&(r.set("Content-Type","application/json"),o.body=JSON.stringify(e.body));try{return await fetch(n,o)}catch(a){throw Tw(a)?new Error(`backend endpoint timed out after ${i}ms: ${e.path}`):a}}function Tw(e){return e instanceof DOMException&&(e.name==="TimeoutError"||e.name==="AbortError")}async function Aw(){let e=await pi();if(!e)throw new Error("missing jwt: set BEEPFLOW_JWT or run auth tool to persist token");return await mi(e)}function Rw(e,t){if(t)for(let n in t){let r=t[n];r!=null&&e.set(n,String(r))}}function ww(e,t){if(!e.startsWith("/"))throw new Error(`backend endpoint path must start with /: ${e}`);let n=Ht(),r=new URL(`${n.backendUrl}${e}`);return Dw(r,t),r.toString()}function Dw(e,t){if(t)for(let n in t){let r=t[n];if(r!=null){if(Array.isArray(r)){for(let i of r)e.searchParams.append(n,String(i));continue}e.searchParams.set(n,String(r))}}}function Cw(e){let t={};return e.forEach((n,r)=>{t[r]=n}),t}async function Ow(e){let t=new FormData,n=e.body;if(n&&typeof n=="object"&&!Array.isArray(n))for(let i in n){let o=n[i];o!=null&&t.set(i,String(o))}let r=e.files??{};for(let i in r)t.set(i,await kw(r[i]),r[i].fileName??i);return t}async function kw(e){if(e.filePath)return new Blob([await _d.readFile(e.filePath)],{type:e.contentType});if(e.base64)return new Blob([Buffer.from(e.base64,"base64")],{type:e.contentType});throw new Error("multipart file input must include filePath or base64")}function xw(e){let t=new URLSearchParams;if(!e||typeof e!="object"||Array.isArray(e))return t;for(let n in e){let r=e[n];r!=null&&t.set(n,String(r))}return t}async function Iw(e,t,n){let r=Buffer.from(await e.arrayBuffer()),i=t.outputFilePath??Nw(e);return await _d.mkdir(n0.dirname(i),{recursive:!0}),await _d.writeFile(i,r),{...n,filePath:i,sizeBytes:r.byteLength,contentType:e.headers.get("content-type")}}function Nw(e){let t=e.headers.get("content-disposition")??"",r=/filename="?([^";]+)"?/i.exec(t)?.[1]?.replace(/[^A-Za-z0-9._-]/g,"_")||`beepflow-download-${Date.now()}.bin`;return n0.join(yw.tmpdir(),"beepflow-mcp-downloads",r)}async function o0(e,t){let n=await t.text().catch(()=>"");return new Error(`${e} failed: ${t.status} ${n}`.trim())}async function gd(e){return Mw(await bd(e))}async function s0(){return await Qc("/integrations")}async function u0(e,t){return await Qc(`/integrations/blueprint-contexts${Pw(e,t)}`)}async function bd(e){return Fw(await Qc(`/integrations/${encodeURIComponent(e)}/openapi`))}function Pw(e,t){let n=new URLSearchParams;e&&n.set("integrationType",e),t&&n.set("resourceType",t);let r=n.toString();return r?`?${r}`:""}async function c0(e){let n=(await gd(e.integrationType)).find(i=>i.operationId===e.operationId);if(!n)throw new Error(`unsupported integration endpoint: ${e.operationId}`);Kw(n,e.confirm);let r=Gw(n,e.payload);if(n.requestMode==="none"&&r.body!==void 0)throw new Error(`integration endpoint ${n.operationId} has requestBody=null; remove body-only fields from payload`);return await r0({method:n.method,path:jw(n,r.path),query:r.query,headers:r.headers,body:r.body,requestMode:n.requestMode,responseMode:n.responseMode,files:r.files,outputFilePath:e.outputFilePath})}function Fw(e){let t=Su(e,"paths");for(let n in t){let r=t[n];if(dn(r))for(let i in r){let o=r[i];dn(o)&&(o.payloadSchema=l0(o))}}return e}function Mw(e){let t=Su(e,"paths"),n=[];for(let r in t){let i=t[r];if(dn(i))for(let o in i){let a=i[o];dn(a)&&n.push(Lw(o.toUpperCase(),r,a))}}return n}function Lw(e,t,n){let r=Su(n,"x-beepflow");return{operationId:ka(n,"operationId"),integrationType:ka(r,"integrationType"),resourceType:Qw(r,"resourceType"),method:e,path:t,originalPath:ka(r,"originalPath"),summary:ka(n,"summary"),access:ka(r,"access"),sideEffect:ka(r,"sideEffect"),mcpExposure:ka(r,"mcpExposure"),requestMode:p0(n),responseMode:qw(n),pathParameters:Yw(t),parameters:d0(n),payloadSchema:l0(n),requestBody:hi(n,"requestBody"),responses:Su(n,"responses"),runtimeUse:"mcp-only",externalAppUse:"forbidden",externalAppAlternative:"Create/use a blueprint with webhook trigger and call /api/:tabId/trigger."}}function l0(e){let t=p0(e),n=Vw(e,t),r={type:"object",additionalProperties:!1,properties:{}},i=r.properties,o=[];for(let a of d0(e))!dn(a)||typeof a.name!="string"||!dn(a.schema)||(i[a.name]=a.schema,a.required===!0&&o.push(a.name));return Bw(r,i,o,n,t),o.length&&(r.required=o),r}function Bw(e,t,n,r,i){if(!r)return;let o=hi(r,"properties");if(!o){e.additionalProperties=r.additionalProperties??!0;return}for(let s in o)t[s]=Uw(o[s],i);r.additionalProperties!==void 0&&r.additionalProperties!==!1&&(e.additionalProperties=r.additionalProperties);let a=r.required;if(Array.isArray(a))for(let s of a)typeof s=="string"&&n.push(s)}function Uw(e,t){return t!=="multipart"||!dn(e)||e.format!=="binary"?e:{type:"object",additionalProperties:!1,description:"Multipart file input. Provide filePath or base64 content.",properties:{filePath:{type:"string",description:"Local file path to read and upload."},base64:{type:"string",description:"Base64-encoded file content."},fileName:{type:"string",description:"File name to send for base64 content."},contentType:{type:"string",description:"MIME type for uploaded content."}}}}function Vw(e,t){let n=hi(e,"requestBody");if(!n)return null;let r=hi(n,"content");if(!r)return null;let i=f0(t),o=hi(r,i);return o?hi(o,"schema"):null}function f0(e){switch(e){case"multipart":return"multipart/form-data";case"form":return"application/x-www-form-urlencoded";default:return"application/json"}}function d0(e){let t=e.parameters;if(t==null)return[];if(!Array.isArray(t))throw new Error("invalid integration OpenAPI schema: parameters must be array");return t}function p0(e){let t=hi(e,"requestBody");if(!t)return"none";let n=hi(t,"content");return n?dn(n["multipart/form-data"])?"multipart":dn(n["application/x-www-form-urlencoded"])?"form":(dn(n["application/json"]),"json"):"none"}function qw(e){let t=Su(e,"responses");for(let i in t)if(i.startsWith("3")&&dn(t[i]))return"redirect";let n=zw(t);if(!n)return"empty";let r=hi(n,"content");return r?dn(r["application/octet-stream"])?"binary":dn(r["text/plain"])?"text":(dn(r["application/json"]),"json"):"empty"}function zw(e){if(dn(e[200]))return e[200];for(let t in e)if(t.startsWith("2")&&dn(e[t]))return e[t];return null}function Kw(e,t){if(!(e.mcpExposure==="safe"&&e.sideEffect!=="destructive")&&t!==!0)throw new Error(`integration endpoint requires confirm=true: ${e.operationId}`)}function Gw(e,t){let n={path:{},query:{},headers:{}},r=t??{},i=$w(e);for(let o of e.parameters){if(!dn(o)||typeof o.name!="string"||typeof o.in!="string")continue;let a=r[o.name];a!==void 0&&(o.in==="path"&&(n.path[o.name]=a),o.in==="query"&&(n.query[o.name]=a),o.in==="header"&&(n.headers[o.name]=a))}if(e.requestMode!=="none")Ww(e,r,i,n);else for(let o in r)i.has(o)||(n.body={[o]:r[o]});return n}function Ww(e,t,n,r){let i=Xw(e),o=i?hi(i,"properties"):null,a={},s={};if(o){for(let c in o)Hw(e,c,t[c],a,s);if(i?.additionalProperties!==void 0&&i.additionalProperties!==!1)for(let c in t)!n.has(c)&&o[c]===void 0&&(a[c]=t[c])}else if(i?.additionalProperties!==!1)for(let c in t)n.has(c)||(a[c]=t[c]);a0(a)&&(r.body=a),a0(s)&&(r.files=s)}function Hw(e,t,n,r,i){if(n!==void 0){if(e.requestMode==="multipart"&&dn(n)&&(typeof n.filePath=="string"||typeof n.base64=="string")){i[t]=n;return}r[t]=n}}function Xw(e){if(!e.requestBody)return null;let t=hi(e.requestBody,"content"),n=t?hi(t,f0(e.requestMode)):null;return n?hi(n,"schema"):null}function $w(e){let t=new Set;for(let n of e.parameters)dn(n)&&typeof n.name=="string"&&t.add(n.name);return t}function a0(e){for(let t in e)if(e[t]!==void 0)return!0;return!1}function jw(e,t){let n=e.path;for(let r of e.pathParameters){let i=t?.[r];if(typeof i!="string"&&typeof i!="number")throw new Error(`integration endpoint path parameter required: ${r}`);n=n.replace(`{${r}}`,encodeURIComponent(String(i)))}return n}function Yw(e){let t=[];for(let n of e.matchAll(/\{([^}]+)\}/g))n[1]&&t.push(n[1]);return t}function Su(e,t){if(!dn(e)||!dn(e[t]))throw new Error(`invalid integration OpenAPI schema: ${t} must be object`);return e[t]}function hi(e,t){if(!dn(e)||e[t]===void 0||e[t]===null)return null;if(!dn(e[t]))throw new Error(`invalid integration OpenAPI schema: ${t} must be object`);return e[t]}function ka(e,t){if(typeof e[t]!="string")throw new Error(`invalid integration OpenAPI schema: ${t} must be string`);return e[t]}function Qw(e,t){if(e[t]===void 0||e[t]===null)return null;if(typeof e[t]!="string")throw new Error(`invalid integration OpenAPI schema: ${t} must be string`);return e[t]}function dn(e){return!!e&&typeof e=="object"&&!Array.isArray(e)}var m0="For Beepflow tasks, call status first and follow the instructions field returned in the status response. Treat client-saved tool outputs as historical logs; verify resource ids with live MCP queries.",Ss=`
|