corsair 0.1.147 → 0.1.148
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/{chunk-WFRHTGJD.js → chunk-TOBWTWQR.js} +10 -10
- package/dist/{connect-AS4S25YD.js → connect-4AJ2WF6T.js} +1 -1
- package/dist/core.js +1 -1
- package/dist/hub.d.ts +1 -0
- package/dist/hub.js +1 -1
- package/dist/index.js +1 -1
- package/dist/{loop-2MTTRZ2K.js → loop-HHZM2Z4J.js} +1 -1
- package/dist/oauth.js +1 -1
- package/dist/{setup-7TLWIUSW.js → setup-6TOKKM27.js} +1 -1
- package/dist/{setup-introspect-QD6GY2I5.js → setup-introspect-ZISM2BO7.js} +1 -1
- package/dist/setup.js +1 -1
- package/dist/tunnel.js +1 -1
- package/package.json +4 -4
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{a as Se,b as _r,c as Er}from"./chunk-6IURNA4L.js";import{a as Ri,b as Ai,c as xi,d as Fn}from"./chunk-XCTHEKDP.js";import{a as _i,b as _e,c as Ei,d as P,e as J,f as Oi,g as ne,h as K,i as O,j as Mi,k as lt,l as Di,m as ln,n as Sr,o as Hi}from"./chunk-BRUFMVTV.js";import{b as Ii,c as Si}from"./chunk-XPXWKPFZ.js";import{ZodBoolean as xp,ZodDate as Ip,ZodEnum as Sp,ZodNullable as _p,ZodNumber as Ep,ZodObject as Op,ZodOptional as Mp,ZodRecord as Dp,ZodString as Hp,ZodType as Bp}from"zod";var dt=["ably","abstract","abuseipdb","abyssale","accrediblecertificates","activecampaign","activetrail","addresszen","aeroleads","affinda","agencyzoom","agentmail","agentql","agenty","agiled","agilitycms","ahrefs","aimlapi","airtable","aivoov","alchemy","algolia","allimagesai","alphavantage","altoviz","alttextai","amara","ambee","ambientweather","amcards","amplitude","anchorbrowser","anonyflow","anthropicadministrator","apaleo","api2pdf","apibible","apify","apilabz","apininjas","apipie","apisports","appointo","aryn","asana","ascora","ashby","asindataapi","asticaai","asyncinterview","attio","autom","ayrshare","backendless","bannerbear","bart","basecamp","baselinker","basin","beaconstac","beamer","beeminder","benchmarkemail","bestbuy","bettercontact","betterproposals","betterstack","bigdatacloud","bigmailer","bigml","bigpictureio","bitbucket","bitwarden","blazemeter","blocknative","bluesky","boldsign","boloforms","boltiot","bonsai","bookingmood","booqable","borneo","botbaba","botpress","botsonic","bouncer","box","boxhero","brandfetch","breathehr","brevo","brex","brightdata","browseai","browserless","browsertool","bubble","bugsnag","buildkite","bunnycdn","byteforms","cal","calendly","campaigncleaner","campayn","canny","canva","canvas","capsulecrm","carbone","castingwords","cdrplatform","certifier","chaser","chatbotkit","chatfai","chmeetings","cincopa","circleci","classmarker","clickhouse","clickmeeting","clientary","clockify","cloudcart","cloudflare","cloudflareapikey","cloudinary","cody","coinbase","collegefootballdata","confluence","connecteam","contentfulgraphql","contextsevenmcp","convoloai","cosmic","countdownapi","crowterminal","currentsapi","cursor","customerio","customgpt","dadataru","databricks","datadog","datarobot","deepseek","devinmcp","diffbot","digitalocean","discord","dockerhub","docupost","dodopayments","doppler","dovetail","dreamstudio","dripcel","dropbox","dropboxsign","dynapictures","emelia","epicgames","everhour","exa","exist","extractaai","facebook","faraday","figma","filevine","filloutforms","firecrawl","fireflies","flexisign","flutterwave","formbricks","gemini","giphy","github","gitlab","gladia","gmail","googleaddressvalidation","googleanalytics","googlebigquery","googlecalendar","googlecloudvision","googledocs","googledrive","googlemaps","googlemeet","googlesheets","grafana","griptape","groqcloud","habitica","hackernews","harvest","hashnode","here","heygen","hookdeck","htmltoimage","hubspot","huggingface","imagior","humanitix","imejisio","imgbb","insightoai","instagram","intercom","jigsawstack","jira","kaggle","kibana","leexi","linear","linkedin","loyverse","mailboxlayer","mailcheck","mailchimp","mailtrap","marketstack","merriamwebsterdict","monday","neon","nextdns","northflank","notion","ocrspace","ocrwebservice","ollama","onedrive","onepassword","openai","openrouter","openweathermap","oura","outlook","pagerduty","parseur","pdfco","pdfmonkey","perplexityai","phantombuster","pinecone","plain","posthog","postman","prisma","pushbullet","razorpay","reddit","reducto","replicate","removebg","replyio","resend","retailed","rootly","runpod","salesforce","sapsuccessfactors","scaleai","scrapegraphai","securitytrails","semanticscholar","sendgrid","sentry","serpapi","sharepoint","slack","snapchat","slackbot","sourcegraph","spoki","spotify","strava","streamtime","stripe","studiobyai21labs","supabase","supadata","synthflowai","tally","tavily","tavilymcp","teams","telegram","textrazor","ticktick","timecamp","timelink","tinyurl","tisane","todoist","toggl","tokenmetrics","tpscheck","trello","tripadvisor","twentyonerisk","twilio","twitter","twitterapiio","twochat","typeform","unione","uniswapapi","uploadcare","vapi","vercel","veriphone","vestaboard","waboxapp","wakatime","webflow","webscrapingai","webvizio","whatsapp","whoisfreaks","whautomate","winstonai","witai","wix","wiza","workday","workiom","worldnewsapi","xero","writer","xquik","youcom","youtube","zendesk","zenserp","zohobigin","zohoinventory","zohomail","zoom","zoominfo"],Bi={ably:"Ably",abstract:"Abstract",abuseipdb:"AbuseIPDB",abyssale:"Abyssale",accrediblecertificates:"Accredible Certificates",activecampaign:"ActiveCampaign",activetrail:"Active Trail",addresszen:"Addresszen",aeroleads:"Aeroleads",affinda:"Affinda",agencyzoom:"AgencyZoom",agentmail:"AgentMail",agentql:"AgentQL",agenty:"Agenty",agiled:"Agiled",agilitycms:"Agility CMS",ahrefs:"Ahrefs",aimlapi:"AI/ML API",airtable:"Airtable",aivoov:"AiVOOV",alchemy:"Alchemy",algolia:"Algolia",allimagesai:"All Images AI",alphavantage:"Alpha Vantage",altoviz:"Altoviz",alttextai:"AltText.ai",amara:"Amara",ambee:"Ambee",ambientweather:"Ambient Weather",amcards:"AMcards",amplitude:"Amplitude",anchorbrowser:"Anchor Browser",anonyflow:"Anonyflow",anthropicadministrator:"Anthropic Administrator",apaleo:"Apaleo",api2pdf:"API2PDF",apibible:"API.Bible",apify:"Apify",apilabz:"API Labz",apininjas:"API Ninjas",apipie:"APIpie AI",apisports:"API-Sports",appointo:"Appointo",aryn:"Aryn",asana:"Asana",ascora:"Ascora",ashby:"Ashby",asindataapi:"ASIN Data API",asticaai:"Astica AI",asyncinterview:"Async Interview",attio:"Attio",autom:"Autom",ayrshare:"Ayrshare",backendless:"Backendless",bannerbear:"Bannerbear",bart:"BART",basecamp:"Basecamp",baselinker:"BaseLinker",basin:"Basin",beaconstac:"Beaconstac",beamer:"Beamer",beeminder:"Beeminder",benchmarkemail:"BenchmarkEmail",bestbuy:"Best Buy",bettercontact:"BetterContact",betterproposals:"Better Proposals",betterstack:"Better Stack",bigdatacloud:"BigDataCloud",bigmailer:"BigMailer",bigml:"BigML",bigpictureio:"BigPicture.io",bitbucket:"Bitbucket",bitwarden:"Bitwarden",blazemeter:"BlazeMeter",blocknative:"Blocknative",bluesky:"Bluesky",boldsign:"Boldsign",boloforms:"Boloforms",boltiot:"Bolt IoT",bonsai:"Bonsai",bookingmood:"Bookingmood",booqable:"Booqable",borneo:"Borneo",botbaba:"Botbaba",botpress:"Botpress",botsonic:"Botsonic",bouncer:"Bouncer",box:"Box",boxhero:"BoxHero",brandfetch:"Brandfetch",breathehr:"Breathe HR",brevo:"Brevo",brex:"Brex",brightdata:"Bright Data",browseai:"Browse AI",browserless:"Browserless",browsertool:"Browser Tool",bubble:"Bubble",bugsnag:"BugSnag",buildkite:"Buildkite",bunnycdn:"Bunnycdn",byteforms:"ByteForms",cal:"Cal",calendly:"Calendly",campaigncleaner:"Campaign Cleaner",campayn:"Campayn",canny:"Canny",canva:"Canva",canvas:"Canvas LMS",capsulecrm:"Capsule CRM",carbone:"Carbone",castingwords:"CastingWords",cdrplatform:"CDR Platform",certifier:"Certifier",chaser:"Chaser",chatbotkit:"ChatBotKit",chatfai:"ChatFAI",chmeetings:"ChMeetings",cincopa:"Cincopa",circleci:"CircleCI",classmarker:"ClassMarker",clickhouse:"Clickhouse",clickmeeting:"ClickMeeting",clientary:"Clientary",clockify:"Clockify",cloudcart:"CloudCart",cloudflare:"Cloudflare",cloudflareapikey:"Cloudflare API Key",cloudinary:"Cloudinary",cody:"Cody",coinbase:"Coinbase",collegefootballdata:"College Football Data",confluence:"Confluence",connecteam:"Connecteam",contentfulgraphql:"Contentful GraphQL",contextsevenmcp:"Context7",convoloai:"ConvoloAi",cosmic:"Cosmic",countdownapi:"Countdown API",crowterminal:"CrowTerminal",currentsapi:"CurrentsApi",cursor:"Cursor",customerio:"Customer.io",customgpt:"CustomGPT",dadataru:"Dadataru",databricks:"Databricks",datadog:"Datadog",datarobot:"DataRobot",deepseek:"DeepSeek",devinmcp:"Devin MCP",diffbot:"Diffbot",digitalocean:"DigitalOcean",discord:"Discord",dockerhub:"Docker Hub",docupost:"Docupost",dodopayments:"Dodo Payments",doppler:"Doppler",dovetail:"Dovetail",dreamstudio:"DreamStudio",dripcel:"Dripcel",dropbox:"Dropbox",dropboxsign:"Dropbox Sign",dynapictures:"Dynapictures",emelia:"Emelia",epicgames:"Epic Games",everhour:"Everhour",exa:"Exa",exist:"Exist",extractaai:"Extracta.ai",facebook:"Facebook",faraday:"Faraday",figma:"Figma",filevine:"Filevine",filloutforms:"FilloutForms",firecrawl:"Firecrawl",fireflies:"Fireflies",flexisign:"Flexisign",flutterwave:"Flutterwave",formbricks:"Formbricks",gemini:"Gemini",giphy:"Giphy",github:"GitHub",gitlab:"GitLab",gladia:"Gladia",gmail:"Gmail",googleaddressvalidation:"Google Address Validation",googleanalytics:"Google Analytics",googlebigquery:"Google BigQuery",googlecalendar:"Google Calendar",googlecloudvision:"Google Cloud Vision",googledocs:"Google Docs",googledrive:"Google Drive",googlemaps:"Google Maps",googlemeet:"Google Meet",googlesheets:"Google Sheets",grafana:"Grafana",griptape:"Griptape",groqcloud:"GroqCloud",habitica:"Habitica",hackernews:"Hacker News",harvest:"Harvest",hashnode:"Hashnode",here:"HERE",heygen:"HeyGen",hookdeck:"Hookdeck",htmltoimage:"HtmlToImage",hubspot:"HubSpot",huggingface:"Hugging Face",imagior:"Imagior",humanitix:"Humanitix",imejisio:"Imejis.io",imgbb:"ImgBB",insightoai:"Insighto.ai",instagram:"Instagram",intercom:"Intercom",jigsawstack:"JigsawStack",jira:"Jira",kaggle:"Kaggle",kibana:"Kibana",leexi:"Leexi",linear:"Linear",linkedin:"LinkedIn",loyverse:"Loyverse",mailboxlayer:"MailboxLayer",mailcheck:"Mailcheck",mailchimp:"Mailchimp",mailtrap:"Mailtrap",marketstack:"Marketstack",merriamwebsterdict:"Merriam-Webster Dictionary",monday:"Monday",neon:"Neon",nextdns:"NextDNS",northflank:"Northflank",notion:"Notion",ocrspace:"OCR.space",ocrwebservice:"OcrWebService",ollama:"Ollama",onedrive:"OneDrive",onepassword:"1Password",openai:"OpenAI",openrouter:"OpenRouter",openweathermap:"OpenWeatherMap",oura:"Oura",outlook:"Outlook",pagerduty:"PagerDuty",parseur:"Parseur",pdfco:"PDF.co",pdfmonkey:"PDFMonkey",perplexityai:"Perplexity AI",phantombuster:"PhantomBuster",pinecone:"Pinecone",plain:"Plain",posthog:"PostHog",postman:"Postman",prisma:"Prisma",pushbullet:"Pushbullet",razorpay:"Razorpay",reddit:"Reddit",reducto:"Reducto",replicate:"Replicate",removebg:"remove.bg",replyio:"Reply.io",resend:"Resend",retailed:"Retailed",rootly:"Rootly",runpod:"RunPod",salesforce:"Salesforce",sapsuccessfactors:"SAP SuccessFactors",scaleai:"Scale AI",scrapegraphai:"ScrapeGraphAI",securitytrails:"SecurityTrails",semanticscholar:"Semantic Scholar",sendgrid:"SendGrid",sentry:"Sentry",serpapi:"Serpapi",sharepoint:"SharePoint",slack:"Slack",snapchat:"Snapchat",slackbot:"Slackbot",sourcegraph:"Sourcegraph",spoki:"Spoki",spotify:"Spotify",strava:"Strava",streamtime:"Streamtime",stripe:"Stripe",studiobyai21labs:"StudioByAI21Labs",supabase:"Supabase",supadata:"Supadata",synthflowai:"Synthflow AI",tally:"Tally",tavily:"Tavily",tavilymcp:"Tavily MCP",teams:"Teams",telegram:"Telegram",textrazor:"TextRazor",ticktick:"TickTick",timecamp:"TimeCamp",timelink:"Timelink",tinyurl:"TinyURL",tisane:"Tisane",todoist:"Todoist",toggl:"Toggl",tokenmetrics:"Token Metrics",tpscheck:"TPSCheck",trello:"Trello",tripadvisor:"Tripadvisor",twentyonerisk:"TwentyOneRisk",twilio:"Twilio",twitter:"Twitter",twitterapiio:"Twitter API IO",twochat:"TwoChat",typeform:"Typeform",unione:"Unione",uniswapapi:"Uniswap",uploadcare:"Uploadcare",vapi:"Vapi",vercel:"Vercel",veriphone:"Veriphone",vestaboard:"Vestaboard",waboxapp:"Waboxapp",wakatime:"WakaTime",webflow:"Webflow",webscrapingai:"WebScraping.AI",webvizio:"Webvizio",whatsapp:"WhatsApp",whoisfreaks:"Whoisfreaks",whautomate:"Whautomate",winstonai:"Winston AI",witai:"WitAi",wix:"Wix",wiza:"Wiza",workday:"Workday",workiom:"Workiom",worldnewsapi:"World News API",xero:"Xero",writer:"Writer",xquik:"XQuik",youcom:"You.com",youtube:"YouTube",zendesk:"Zendesk",zenserp:"Zenserp",zohobigin:"Zoho Bigin",zohoinventory:"Zoho Inventory",zohomail:"Zoho Mail",zoom:"Zoom",zoominfo:"ZoomInfo"};function Ee(e){let n=Bi[e];return n||e.charAt(0).toUpperCase()+e.slice(1)}var ke=class extends Error{connectUrl;plugin;tenantId;reason;constructor(n){super(n.message??"Reconnect required"),Object.setPrototypeOf(this,new.target.prototype),this.name="ReconnectRequiredError",this.connectUrl=n.connectUrl,this.plugin=n.plugin,this.tenantId=n.tenantId,this.reason=n.reason}};function M(e){return typeof e=="string"&&e.length>0}function Fc(e){return e==="ready"||e==="partial"||e==="not_started"||e==="missing_integration"}function Nc(e){return e==="oauth_2"||e==="api_key"||e==="bot_token"||e==="managed"||e==="managed_pricing"}function pt(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty connect session");let n=e;if(!M(n.connectUrl)||!M(n.token)||!M(n.projectId))throw new Error("Hub API returned an incomplete connect session (expected connectUrl, token, and projectId)");let t={connectUrl:n.connectUrl,token:n.token,projectId:n.projectId,environmentId:M(n.environmentId)?n.environmentId:n.projectId};return M(n.expiresAt)&&(t.expiresAt=n.expiresAt),t}function gt(e){if(!Array.isArray(e))throw new Error("Hub API returned an invalid connections response (expected array)");let n=[];for(let t of e){if(!t||typeof t!="object")continue;let r=t;if(!M(r.tenantId)||!M(r.plugin)||!Fc(r.status)||!Nc(r.authType)||typeof r.connected!="boolean"||typeof r.verified!="boolean")continue;let o=Array.isArray(r.missingFields)?r.missingFields.filter(i=>typeof i=="string"):[];n.push({tenantId:r.tenantId,plugin:r.plugin,status:r.status,authType:r.authType,connected:r.connected,verified:r.verified,missingFields:o,reportedAt:M(r.reportedAt)?r.reportedAt:new Date().toISOString()})}return n}function ft(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty permission session");let n=e;if(!M(n.approvalUrl)||!M(n.token)||!M(n.projectId)||!M(n.expiresAt))throw new Error("Hub API returned an incomplete permission session (expected approvalUrl, token, projectId, and expiresAt)");return{approvalUrl:n.approvalUrl,token:n.token,projectId:n.projectId,expiresAt:n.expiresAt}}function dn(e){if(!e||typeof e!="object")throw new Error("Hub token refresh returned an empty response");let n=e;if(M(n.access_token))return{access_token:n.access_token,refresh_token:M(n.refresh_token)?n.refresh_token:void 0,expires_in:(()=>{if(typeof n.expires_in=="number")return n.expires_in;if(typeof n.expires_in=="string"&&n.expires_in.trim().length>0){let t=Number(n.expires_in);return Number.isFinite(t)?t:void 0}})(),scope:M(n.scope)?n.scope:void 0};throw new Error(M(n.error)?M(n.error_description)?n.error_description:n.error:"Hub token refresh returned no access_token")}function $c(e){return Array.isArray(e)?e.filter(n=>typeof n=="string"):[]}function Wc(e){if(!Array.isArray(e))return[];let n=[];for(let t of e){if(!t||typeof t!="object")continue;let r=t;M(r.name)&&n.push({name:r.name,level:r.level==="integration"||r.level==="account"?r.level:"account",required:r.required===!0,configured:r.configured===!0})}return n}function qc(e,n,t,r){return e==="ready"||e==="partial"||e==="not_started"||e==="missing_integration"?e:n?"ready":t.some(i=>i.level==="integration"&&i.required&&!i.configured)?"missing_integration":t.some(i=>i.level==="account"&&i.required&&i.configured)?"partial":(r.length>0,"not_started")}function Ui(e){if(!e||typeof e!="object")throw new Error("Connect status response was empty");let n=e;if(!M(n.tenantId)||!Array.isArray(n.plugins))throw new Error("Connect status response was incomplete (expected tenantId and plugins)");let t=[];for(let r of n.plugins){if(!r||typeof r!="object")continue;let o=r;if(!M(o.plugin)||typeof o.connected!="boolean")continue;let i=o.authKind==="oauth"||o.authKind==="api_key"||o.authKind==="bot_token"?o.authKind:"api_key",a=Wc(o.fields),s=$c(o.missingRequiredFields),c=qc(o.status,o.connected,a,s);t.push({plugin:o.plugin,providerName:M(o.providerName)?o.providerName:o.plugin,authKind:i,status:c,connected:o.connected,fields:a,missingRequiredFields:s})}return{tenantId:n.tenantId,plugins:t}}function yt(e){if(!e||typeof e!="object")return null;let n=e;return n.error??n.message??null}function Li(e){if(!e||typeof e!="object")return null;let n=e;if(n.errorType!=="reconnect_required")return null;let t=r=>typeof r=="string"&&r.length>0?r:null;return{message:t(n.error),connectUrl:t(n.connectUrl),plugin:t(n.plugin),tenantId:t(n.tenantId),reason:t(n.reason)}}function mt(e){return e.replace(/\/$/,"")}function Or(e){if(!e.projectApiKey.startsWith("ck_dev_"))return null;try{return Se()}catch{return null}}function Fi(e){let n=Or(e);return n?{"x-corsair-delivery-url":n}:{}}function Ni(e){let n=e.instanceKey?.trim();return n?{"x-corsair-instance-key":n}:{}}async function $i(e){let n=e.headers.get("content-type")??"",t=await e.text();if(!t)return null;if(!n.includes("application/json")&&t.trimStart().startsWith("<"))throw new Error(`Hub API returned HTML instead of JSON (HTTP ${e.status}). Check HUB_API_URL and deploy the latest hub API.`);try{return JSON.parse(t)}catch{throw new Error(`Hub API returned invalid JSON (HTTP ${e.status})`)}}function jc(e,n,t){if(n===404&&t)return t;let r=yt(e);return r||`Hub API returned HTTP ${n}`}function Wi(e,n,t){let r=Li(e);throw r?new ke({message:r.message??void 0,connectUrl:r.connectUrl,plugin:r.plugin,tenantId:r.tenantId,reason:r.reason??void 0}):new Error(jc(e,n,t))}async function _(e){let n=mt(e.hub.apiUrl),t=await fetch(`${n}${e.path}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${e.hub.projectApiKey}`,...Fi(e.hub),...Ni(e.hub),...e.extraHeaders},body:JSON.stringify(e.body)}),r=await $i(t);return t.ok||Wi(r,t.status,e.notFoundMessage),e.parseResponse(r)}async function Z(e){let n=mt(e.hub.apiUrl),t=await fetch(`${n}${e.path}`,{method:"GET",headers:{authorization:`Bearer ${e.hub.projectApiKey}`,...Fi(e.hub),...Ni(e.hub)}}),r=await $i(t);return t.ok||Wi(r,t.status,e.notFoundMessage),e.parseResponse(r)}function ht(e){return e&&typeof e=="object"?e:{}}function qi(e){let n=ht(e);return{chatId:n.threadId,message:n.message,workflowId:n.workflowId??null,action:n.action}}async function Mr(e,n){return _({hub:e,path:"/threads",body:{tenantId:n.tenantId,message:n.message},parseResponse:t=>{let r=ht(t);return{chat:r.thread,reply:qi(r.reply)}}})}async function Dr(e,n){return _({hub:e,path:`/threads/${encodeURIComponent(n.chatId)}/messages`,body:{tenantId:n.tenantId,message:n.message},notFoundMessage:`Chat "${n.chatId}" not found`,parseResponse:qi})}async function Hr(e,n){return Z({hub:e,path:`/threads?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ht(t).threads;return Array.isArray(r)?r:[]}})}async function Br(e,n){return Z({hub:e,path:`/threads/${encodeURIComponent(n.chatId)}/messages?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Chat "${n.chatId}" not found`,parseResponse:t=>{let r=ht(t).messages;return Array.isArray(r)?r:[]}})}import{randomUUID as Yc}from"crypto";var Kc="corsair:client-bridge";function Ur(e){return new URL(e).origin}function pn(e){let n=JSON.stringify({type:Kc,requestId:e.requestId,ok:e.ok,body:e.body??null,error:e.error??null}),t=JSON.stringify(Ur(e.hubOrigin));return`<!DOCTYPE html><html><head><meta charset="utf-8"></head><body><script>
|
|
1
|
+
import{a as Se,b as _r,c as Er}from"./chunk-6IURNA4L.js";import{a as Ri,b as Ai,c as xi,d as Fn}from"./chunk-XCTHEKDP.js";import{a as _i,b as _e,c as Ei,d as P,e as J,f as Oi,g as ne,h as K,i as E,j as Mi,k as lt,l as Di,m as ln,n as Sr,o as Hi}from"./chunk-BRUFMVTV.js";import{b as Ii,c as Si}from"./chunk-XPXWKPFZ.js";import{ZodBoolean as xp,ZodDate as Ip,ZodEnum as Sp,ZodNullable as _p,ZodNumber as Ep,ZodObject as Op,ZodOptional as Mp,ZodRecord as Dp,ZodString as Hp,ZodType as Bp}from"zod";var dt=["ably","abstract","abuseipdb","abyssale","accrediblecertificates","activecampaign","activetrail","addresszen","aeroleads","affinda","agencyzoom","agentmail","agentql","agenty","agiled","agilitycms","ahrefs","aimlapi","airtable","aivoov","alchemy","algolia","allimagesai","alphavantage","altoviz","alttextai","amara","ambee","ambientweather","amcards","amplitude","anchorbrowser","anonyflow","anthropicadministrator","apaleo","api2pdf","apibible","apify","apilabz","apininjas","apipie","apisports","appointo","aryn","asana","ascora","ashby","asindataapi","asticaai","asyncinterview","attio","autom","ayrshare","backendless","bannerbear","bart","basecamp","baselinker","basin","beaconstac","beamer","beeminder","benchmarkemail","bestbuy","bettercontact","betterproposals","betterstack","bigdatacloud","bigmailer","bigml","bigpictureio","bitbucket","bitwarden","blazemeter","blocknative","bluesky","boldsign","boloforms","boltiot","bonsai","bookingmood","booqable","borneo","botbaba","botpress","botsonic","bouncer","box","boxhero","brandfetch","breathehr","brevo","brex","brightdata","browseai","browserless","browsertool","bubble","bugsnag","buildkite","bunnycdn","byteforms","cal","calendly","campaigncleaner","campayn","canny","canva","canvas","capsulecrm","carbone","castingwords","cdrplatform","certifier","chaser","chatbotkit","chatfai","chmeetings","cincopa","circleci","classmarker","clickhouse","clickmeeting","clientary","clockify","cloudcart","cloudflare","cloudflareapikey","cloudinary","cody","coinbase","collegefootballdata","confluence","connecteam","contentfulgraphql","contextsevenmcp","convoloai","cosmic","countdownapi","crowterminal","currentsapi","cursor","customerio","customgpt","dadataru","databricks","datadog","datarobot","deepseek","devinmcp","diffbot","digitalocean","discord","dockerhub","docupost","dodopayments","doppler","dovetail","dreamstudio","dripcel","dropbox","dropboxsign","dynapictures","emelia","epicgames","everhour","exa","exist","extractaai","facebook","faraday","figma","filevine","filloutforms","firecrawl","fireflies","flexisign","flutterwave","formbricks","gemini","giphy","github","gitlab","gladia","gmail","googleaddressvalidation","googleanalytics","googlebigquery","googlecalendar","googlecloudvision","googledocs","googledrive","googlemaps","googlemeet","googlesheets","grafana","griptape","groqcloud","habitica","hackernews","harvest","hashnode","here","heygen","hookdeck","htmltoimage","hubspot","huggingface","imagior","humanitix","imejisio","imgbb","insightoai","instagram","intercom","jigsawstack","jira","kaggle","kibana","leexi","linear","linkedin","loyverse","mailboxlayer","mailcheck","mailchimp","mailtrap","marketstack","merriamwebsterdict","monday","neon","nextdns","northflank","notion","ocrspace","ocrwebservice","ollama","onedrive","onepassword","openai","openrouter","openweathermap","oura","outlook","pagerduty","parseur","pdfco","pdfmonkey","perplexityai","phantombuster","pinecone","plain","posthog","postman","prisma","pushbullet","razorpay","reddit","reducto","replicate","removebg","replyio","resend","retailed","rootly","runpod","salesforce","sapsuccessfactors","scaleai","scrapegraphai","securitytrails","semanticscholar","sendgrid","sentry","serpapi","sharepoint","slack","snapchat","slackbot","sourcegraph","spoki","spotify","strava","streamtime","stripe","studiobyai21labs","supabase","supadata","synthflowai","tally","tavily","tavilymcp","teams","telegram","textrazor","ticktick","timecamp","timelink","tinyurl","tisane","todoist","toggl","tokenmetrics","tpscheck","trello","tripadvisor","twentyonerisk","twilio","twitter","twitterapiio","twochat","typeform","unione","uniswapapi","uploadcare","vapi","vercel","veriphone","vestaboard","waboxapp","wakatime","webflow","webscrapingai","webvizio","whatsapp","whoisfreaks","whautomate","winstonai","witai","wix","wiza","workday","workiom","worldnewsapi","xero","writer","xquik","youcom","youtube","zendesk","zenserp","zohobigin","zohoinventory","zohomail","zoom","zoominfo"],Bi={ably:"Ably",abstract:"Abstract",abuseipdb:"AbuseIPDB",abyssale:"Abyssale",accrediblecertificates:"Accredible Certificates",activecampaign:"ActiveCampaign",activetrail:"Active Trail",addresszen:"Addresszen",aeroleads:"Aeroleads",affinda:"Affinda",agencyzoom:"AgencyZoom",agentmail:"AgentMail",agentql:"AgentQL",agenty:"Agenty",agiled:"Agiled",agilitycms:"Agility CMS",ahrefs:"Ahrefs",aimlapi:"AI/ML API",airtable:"Airtable",aivoov:"AiVOOV",alchemy:"Alchemy",algolia:"Algolia",allimagesai:"All Images AI",alphavantage:"Alpha Vantage",altoviz:"Altoviz",alttextai:"AltText.ai",amara:"Amara",ambee:"Ambee",ambientweather:"Ambient Weather",amcards:"AMcards",amplitude:"Amplitude",anchorbrowser:"Anchor Browser",anonyflow:"Anonyflow",anthropicadministrator:"Anthropic Administrator",apaleo:"Apaleo",api2pdf:"API2PDF",apibible:"API.Bible",apify:"Apify",apilabz:"API Labz",apininjas:"API Ninjas",apipie:"APIpie AI",apisports:"API-Sports",appointo:"Appointo",aryn:"Aryn",asana:"Asana",ascora:"Ascora",ashby:"Ashby",asindataapi:"ASIN Data API",asticaai:"Astica AI",asyncinterview:"Async Interview",attio:"Attio",autom:"Autom",ayrshare:"Ayrshare",backendless:"Backendless",bannerbear:"Bannerbear",bart:"BART",basecamp:"Basecamp",baselinker:"BaseLinker",basin:"Basin",beaconstac:"Beaconstac",beamer:"Beamer",beeminder:"Beeminder",benchmarkemail:"BenchmarkEmail",bestbuy:"Best Buy",bettercontact:"BetterContact",betterproposals:"Better Proposals",betterstack:"Better Stack",bigdatacloud:"BigDataCloud",bigmailer:"BigMailer",bigml:"BigML",bigpictureio:"BigPicture.io",bitbucket:"Bitbucket",bitwarden:"Bitwarden",blazemeter:"BlazeMeter",blocknative:"Blocknative",bluesky:"Bluesky",boldsign:"Boldsign",boloforms:"Boloforms",boltiot:"Bolt IoT",bonsai:"Bonsai",bookingmood:"Bookingmood",booqable:"Booqable",borneo:"Borneo",botbaba:"Botbaba",botpress:"Botpress",botsonic:"Botsonic",bouncer:"Bouncer",box:"Box",boxhero:"BoxHero",brandfetch:"Brandfetch",breathehr:"Breathe HR",brevo:"Brevo",brex:"Brex",brightdata:"Bright Data",browseai:"Browse AI",browserless:"Browserless",browsertool:"Browser Tool",bubble:"Bubble",bugsnag:"BugSnag",buildkite:"Buildkite",bunnycdn:"Bunnycdn",byteforms:"ByteForms",cal:"Cal",calendly:"Calendly",campaigncleaner:"Campaign Cleaner",campayn:"Campayn",canny:"Canny",canva:"Canva",canvas:"Canvas LMS",capsulecrm:"Capsule CRM",carbone:"Carbone",castingwords:"CastingWords",cdrplatform:"CDR Platform",certifier:"Certifier",chaser:"Chaser",chatbotkit:"ChatBotKit",chatfai:"ChatFAI",chmeetings:"ChMeetings",cincopa:"Cincopa",circleci:"CircleCI",classmarker:"ClassMarker",clickhouse:"Clickhouse",clickmeeting:"ClickMeeting",clientary:"Clientary",clockify:"Clockify",cloudcart:"CloudCart",cloudflare:"Cloudflare",cloudflareapikey:"Cloudflare API Key",cloudinary:"Cloudinary",cody:"Cody",coinbase:"Coinbase",collegefootballdata:"College Football Data",confluence:"Confluence",connecteam:"Connecteam",contentfulgraphql:"Contentful GraphQL",contextsevenmcp:"Context7",convoloai:"ConvoloAi",cosmic:"Cosmic",countdownapi:"Countdown API",crowterminal:"CrowTerminal",currentsapi:"CurrentsApi",cursor:"Cursor",customerio:"Customer.io",customgpt:"CustomGPT",dadataru:"Dadataru",databricks:"Databricks",datadog:"Datadog",datarobot:"DataRobot",deepseek:"DeepSeek",devinmcp:"Devin MCP",diffbot:"Diffbot",digitalocean:"DigitalOcean",discord:"Discord",dockerhub:"Docker Hub",docupost:"Docupost",dodopayments:"Dodo Payments",doppler:"Doppler",dovetail:"Dovetail",dreamstudio:"DreamStudio",dripcel:"Dripcel",dropbox:"Dropbox",dropboxsign:"Dropbox Sign",dynapictures:"Dynapictures",emelia:"Emelia",epicgames:"Epic Games",everhour:"Everhour",exa:"Exa",exist:"Exist",extractaai:"Extracta.ai",facebook:"Facebook",faraday:"Faraday",figma:"Figma",filevine:"Filevine",filloutforms:"FilloutForms",firecrawl:"Firecrawl",fireflies:"Fireflies",flexisign:"Flexisign",flutterwave:"Flutterwave",formbricks:"Formbricks",gemini:"Gemini",giphy:"Giphy",github:"GitHub",gitlab:"GitLab",gladia:"Gladia",gmail:"Gmail",googleaddressvalidation:"Google Address Validation",googleanalytics:"Google Analytics",googlebigquery:"Google BigQuery",googlecalendar:"Google Calendar",googlecloudvision:"Google Cloud Vision",googledocs:"Google Docs",googledrive:"Google Drive",googlemaps:"Google Maps",googlemeet:"Google Meet",googlesheets:"Google Sheets",grafana:"Grafana",griptape:"Griptape",groqcloud:"GroqCloud",habitica:"Habitica",hackernews:"Hacker News",harvest:"Harvest",hashnode:"Hashnode",here:"HERE",heygen:"HeyGen",hookdeck:"Hookdeck",htmltoimage:"HtmlToImage",hubspot:"HubSpot",huggingface:"Hugging Face",imagior:"Imagior",humanitix:"Humanitix",imejisio:"Imejis.io",imgbb:"ImgBB",insightoai:"Insighto.ai",instagram:"Instagram",intercom:"Intercom",jigsawstack:"JigsawStack",jira:"Jira",kaggle:"Kaggle",kibana:"Kibana",leexi:"Leexi",linear:"Linear",linkedin:"LinkedIn",loyverse:"Loyverse",mailboxlayer:"MailboxLayer",mailcheck:"Mailcheck",mailchimp:"Mailchimp",mailtrap:"Mailtrap",marketstack:"Marketstack",merriamwebsterdict:"Merriam-Webster Dictionary",monday:"Monday",neon:"Neon",nextdns:"NextDNS",northflank:"Northflank",notion:"Notion",ocrspace:"OCR.space",ocrwebservice:"OcrWebService",ollama:"Ollama",onedrive:"OneDrive",onepassword:"1Password",openai:"OpenAI",openrouter:"OpenRouter",openweathermap:"OpenWeatherMap",oura:"Oura",outlook:"Outlook",pagerduty:"PagerDuty",parseur:"Parseur",pdfco:"PDF.co",pdfmonkey:"PDFMonkey",perplexityai:"Perplexity AI",phantombuster:"PhantomBuster",pinecone:"Pinecone",plain:"Plain",posthog:"PostHog",postman:"Postman",prisma:"Prisma",pushbullet:"Pushbullet",razorpay:"Razorpay",reddit:"Reddit",reducto:"Reducto",replicate:"Replicate",removebg:"remove.bg",replyio:"Reply.io",resend:"Resend",retailed:"Retailed",rootly:"Rootly",runpod:"RunPod",salesforce:"Salesforce",sapsuccessfactors:"SAP SuccessFactors",scaleai:"Scale AI",scrapegraphai:"ScrapeGraphAI",securitytrails:"SecurityTrails",semanticscholar:"Semantic Scholar",sendgrid:"SendGrid",sentry:"Sentry",serpapi:"Serpapi",sharepoint:"SharePoint",slack:"Slack",snapchat:"Snapchat",slackbot:"Slackbot",sourcegraph:"Sourcegraph",spoki:"Spoki",spotify:"Spotify",strava:"Strava",streamtime:"Streamtime",stripe:"Stripe",studiobyai21labs:"StudioByAI21Labs",supabase:"Supabase",supadata:"Supadata",synthflowai:"Synthflow AI",tally:"Tally",tavily:"Tavily",tavilymcp:"Tavily MCP",teams:"Teams",telegram:"Telegram",textrazor:"TextRazor",ticktick:"TickTick",timecamp:"TimeCamp",timelink:"Timelink",tinyurl:"TinyURL",tisane:"Tisane",todoist:"Todoist",toggl:"Toggl",tokenmetrics:"Token Metrics",tpscheck:"TPSCheck",trello:"Trello",tripadvisor:"Tripadvisor",twentyonerisk:"TwentyOneRisk",twilio:"Twilio",twitter:"Twitter",twitterapiio:"Twitter API IO",twochat:"TwoChat",typeform:"Typeform",unione:"Unione",uniswapapi:"Uniswap",uploadcare:"Uploadcare",vapi:"Vapi",vercel:"Vercel",veriphone:"Veriphone",vestaboard:"Vestaboard",waboxapp:"Waboxapp",wakatime:"WakaTime",webflow:"Webflow",webscrapingai:"WebScraping.AI",webvizio:"Webvizio",whatsapp:"WhatsApp",whoisfreaks:"Whoisfreaks",whautomate:"Whautomate",winstonai:"Winston AI",witai:"WitAi",wix:"Wix",wiza:"Wiza",workday:"Workday",workiom:"Workiom",worldnewsapi:"World News API",xero:"Xero",writer:"Writer",xquik:"XQuik",youcom:"You.com",youtube:"YouTube",zendesk:"Zendesk",zenserp:"Zenserp",zohobigin:"Zoho Bigin",zohoinventory:"Zoho Inventory",zohomail:"Zoho Mail",zoom:"Zoom",zoominfo:"ZoomInfo"};function Ee(e){let n=Bi[e];return n||e.charAt(0).toUpperCase()+e.slice(1)}var ke=class extends Error{connectUrl;plugin;tenantId;reason;constructor(n){super(n.message??"Reconnect required"),Object.setPrototypeOf(this,new.target.prototype),this.name="ReconnectRequiredError",this.connectUrl=n.connectUrl,this.plugin=n.plugin,this.tenantId=n.tenantId,this.reason=n.reason}};function M(e){return typeof e=="string"&&e.length>0}function Fc(e){return e==="ready"||e==="partial"||e==="not_started"||e==="missing_integration"}function Nc(e){return e==="oauth_2"||e==="api_key"||e==="bot_token"||e==="managed"||e==="managed_pricing"}function pt(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty connect session");let n=e;if(!M(n.connectUrl)||!M(n.token)||!M(n.projectId))throw new Error("Hub API returned an incomplete connect session (expected connectUrl, token, and projectId)");let t={connectUrl:n.connectUrl,token:n.token,projectId:n.projectId,environmentId:M(n.environmentId)?n.environmentId:n.projectId};return M(n.expiresAt)&&(t.expiresAt=n.expiresAt),t}function gt(e){if(!Array.isArray(e))throw new Error("Hub API returned an invalid connections response (expected array)");let n=[];for(let t of e){if(!t||typeof t!="object")continue;let r=t;if(!M(r.tenantId)||!M(r.plugin)||!Fc(r.status)||!Nc(r.authType)||typeof r.connected!="boolean"||typeof r.verified!="boolean")continue;let o=Array.isArray(r.missingFields)?r.missingFields.filter(i=>typeof i=="string"):[];n.push({tenantId:r.tenantId,plugin:r.plugin,status:r.status,authType:r.authType,connected:r.connected,verified:r.verified,missingFields:o,reportedAt:M(r.reportedAt)?r.reportedAt:new Date().toISOString()})}return n}function ft(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty permission session");let n=e;if(!M(n.approvalUrl)||!M(n.token)||!M(n.projectId)||!M(n.expiresAt))throw new Error("Hub API returned an incomplete permission session (expected approvalUrl, token, projectId, and expiresAt)");return{approvalUrl:n.approvalUrl,token:n.token,projectId:n.projectId,expiresAt:n.expiresAt}}function dn(e){if(!e||typeof e!="object")throw new Error("Hub token refresh returned an empty response");let n=e;if(M(n.access_token))return{access_token:n.access_token,refresh_token:M(n.refresh_token)?n.refresh_token:void 0,expires_in:(()=>{if(typeof n.expires_in=="number")return n.expires_in;if(typeof n.expires_in=="string"&&n.expires_in.trim().length>0){let t=Number(n.expires_in);return Number.isFinite(t)?t:void 0}})(),scope:M(n.scope)?n.scope:void 0};throw new Error(M(n.error)?M(n.error_description)?n.error_description:n.error:"Hub token refresh returned no access_token")}function $c(e){return Array.isArray(e)?e.filter(n=>typeof n=="string"):[]}function Wc(e){if(!Array.isArray(e))return[];let n=[];for(let t of e){if(!t||typeof t!="object")continue;let r=t;M(r.name)&&n.push({name:r.name,level:r.level==="integration"||r.level==="account"?r.level:"account",required:r.required===!0,configured:r.configured===!0})}return n}function qc(e,n,t,r){return e==="ready"||e==="partial"||e==="not_started"||e==="missing_integration"?e:n?"ready":t.some(i=>i.level==="integration"&&i.required&&!i.configured)?"missing_integration":t.some(i=>i.level==="account"&&i.required&&i.configured)?"partial":(r.length>0,"not_started")}function Ui(e){if(!e||typeof e!="object")throw new Error("Connect status response was empty");let n=e;if(!M(n.tenantId)||!Array.isArray(n.plugins))throw new Error("Connect status response was incomplete (expected tenantId and plugins)");let t=[];for(let r of n.plugins){if(!r||typeof r!="object")continue;let o=r;if(!M(o.plugin)||typeof o.connected!="boolean")continue;let i=o.authKind==="oauth"||o.authKind==="api_key"||o.authKind==="bot_token"?o.authKind:"api_key",a=Wc(o.fields),s=$c(o.missingRequiredFields),c=qc(o.status,o.connected,a,s);t.push({plugin:o.plugin,providerName:M(o.providerName)?o.providerName:o.plugin,authKind:i,status:c,connected:o.connected,fields:a,missingRequiredFields:s})}return{tenantId:n.tenantId,plugins:t}}function yt(e){if(!e||typeof e!="object")return null;let n=e;return n.error??n.message??null}function Li(e){if(!e||typeof e!="object")return null;let n=e;if(n.errorType!=="reconnect_required")return null;let t=r=>typeof r=="string"&&r.length>0?r:null;return{message:t(n.error),connectUrl:t(n.connectUrl),plugin:t(n.plugin),tenantId:t(n.tenantId),reason:t(n.reason)}}function mt(e){return e.replace(/\/$/,"")}function Or(e){if(!e.projectApiKey.startsWith("ck_dev_"))return null;try{return Se()}catch{return null}}function Fi(e){let n=Or(e);return n?{"x-corsair-delivery-url":n}:{}}function Ni(e){let n=e.instanceKey?.trim();return n?{"x-corsair-instance-key":n}:{}}async function $i(e){let n=e.headers.get("content-type")??"",t=await e.text();if(!t)return null;if(!n.includes("application/json")&&t.trimStart().startsWith("<"))throw new Error(`Hub API returned HTML instead of JSON (HTTP ${e.status}). Check HUB_API_URL and deploy the latest hub API.`);try{return JSON.parse(t)}catch{throw new Error(`Hub API returned invalid JSON (HTTP ${e.status})`)}}function jc(e,n,t){if(n===404&&t)return t;let r=yt(e);return r||`Hub API returned HTTP ${n}`}function Wi(e,n,t){let r=Li(e);throw r?new ke({message:r.message??void 0,connectUrl:r.connectUrl,plugin:r.plugin,tenantId:r.tenantId,reason:r.reason??void 0}):new Error(jc(e,n,t))}async function _(e){let n=mt(e.hub.apiUrl),t=await fetch(`${n}${e.path}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${e.hub.projectApiKey}`,...Fi(e.hub),...Ni(e.hub),...e.extraHeaders},body:JSON.stringify(e.body)}),r=await $i(t);return t.ok||Wi(r,t.status,e.notFoundMessage),e.parseResponse(r)}async function Z(e){let n=mt(e.hub.apiUrl),t=await fetch(`${n}${e.path}`,{method:"GET",headers:{authorization:`Bearer ${e.hub.projectApiKey}`,...Fi(e.hub),...Ni(e.hub)}}),r=await $i(t);return t.ok||Wi(r,t.status,e.notFoundMessage),e.parseResponse(r)}function ht(e){return e&&typeof e=="object"?e:{}}function qi(e){let n=ht(e);return{chatId:n.threadId,message:n.message,workflowId:n.workflowId??null,action:n.action}}async function Mr(e,n){return _({hub:e,path:"/threads",body:{tenantId:n.tenantId,message:n.message},parseResponse:t=>{let r=ht(t);return{chat:r.thread,reply:qi(r.reply)}}})}async function Dr(e,n){return _({hub:e,path:`/threads/${encodeURIComponent(n.chatId)}/messages`,body:{tenantId:n.tenantId,message:n.message},notFoundMessage:`Chat "${n.chatId}" not found`,parseResponse:qi})}async function Hr(e,n){return Z({hub:e,path:`/threads?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ht(t).threads;return Array.isArray(r)?r:[]}})}async function Br(e,n){return Z({hub:e,path:`/threads/${encodeURIComponent(n.chatId)}/messages?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Chat "${n.chatId}" not found`,parseResponse:t=>{let r=ht(t).messages;return Array.isArray(r)?r:[]}})}import{randomUUID as Yc}from"crypto";var Kc="corsair:client-bridge";function Ur(e){return new URL(e).origin}function pn(e){let n=JSON.stringify({type:Kc,requestId:e.requestId,ok:e.ok,body:e.body??null,error:e.error??null}),t=JSON.stringify(Ur(e.hubOrigin));return`<!DOCTYPE html><html><head><meta charset="utf-8"></head><body><script>
|
|
2
2
|
(function () {
|
|
3
3
|
var message = ${n};
|
|
4
4
|
var targetOrigin = ${t};
|
|
@@ -6,7 +6,7 @@ import{a as Se,b as _r,c as Er}from"./chunk-6IURNA4L.js";import{a as Ri,b as Ai,
|
|
|
6
6
|
window.parent.postMessage(message, targetOrigin);
|
|
7
7
|
}
|
|
8
8
|
})();
|
|
9
|
-
</script></body></html>`}var Zc=new Set(["localhost","127.0.0.1","[::1]","::1"]);function Lr(e){try{let{hostname:n,protocol:t}=new URL(e);return t!=="http:"&&t!=="https:"?!1:Zc.has(n)}catch{return!1}}function Nn(e){return e==="development"?"browser":"server"}function ji(e){return Nn(e)==="browser"}function Ki(e){return Lr(e)?"Production delivery URL must be a public URL, not localhost":null}import{randomBytes as Vc}from"crypto";var Oe=60*1e3,We=300*1e3;import{createHmac as Gc,randomBytes as zc,timingSafeEqual as Jc}from"crypto";function we(){return zc(16).toString("base64url")}function $n(e,n){let t=n.trim();if(!t)throw new Error("Signing secret is required");return Gc("sha256",t).update(e).digest("base64url")}function ue(e,n){let t=n.trim();if(!t)return null;let r=e.split(".");if(r.length!==2)return null;let[o,i]=r;if(!o||!i)return null;let a=$n(o,t);try{if(!Jc(Buffer.from(i,"utf8"),Buffer.from(a,"utf8")))return null}catch{return null}let s;try{s=JSON.parse(Buffer.from(o,"base64url").toString("utf8"))}catch{return null}return s.exp*1e3<Date.now()?null:s}function bt(e,n,t){let r=Math.floor(Date.now()/1e3),o={...e,iat:r,exp:t},i=Buffer.from(JSON.stringify(o)).toString("base64url"),a=$n(i,n);return`${i}.${a}`}function Wn(e,n,t){let r=Math.floor(Date.now()/1e3);return bt(e,n,r+Math.floor(t/1e3))}function qe(e){return decodeURIComponent(e)}function Fr(e){return encodeURIComponent(e).replace(/\./g,"%2E")}function Zi(e){let n=e.trim();return n.length>0?n:null}function gn(e,n){let t=new URL(e);return t.searchParams.set("d",n),t.toString()}function fn(e,n){if(!Zi(n))throw new Error("Signing secret is required for browser delivery tokens");let t=Math.floor(Date.now()/1e3),r={...e,jti:e.jti??Vc(16).toString("base64url"),iat:t,exp:t+Math.floor(Oe/1e3)},o=Buffer.from(JSON.stringify(r)).toString("base64url"),i=$n(o,n);return`${o}.${i}`}function Me(e,n){return Zi(n)?ue(e,n):null}function Qc(e){let n=Ur(e.hubOrigin),t={connectJti:e.requestId,projectId:e.projectId,hubSuccessUrl:e.hubOrigin,deliveryMode:e.deliveryMode,hubOrigin:n,requestId:e.requestId};switch(e.deliveryMode){case"connections.sync":return{...t,plugin:"connections.sync",tenantId:"*"};case"connect.create_link":return{...t,plugin:"connect.create_link",tenantId:e.tenantId,connectLinkPlugins:e.plugins}}}function Nr(e){let n=fn(Qc(e),e.signingSecret);return gn(e.deliveryUrl,n)}function Gi(e){if(Nn(e.environmentSlug)==="server")return{transport:"server"};if(!e.hubOrigin)throw new Error(`hubOrigin is required for development ${e.deliveryMode} delivery`);let t=Yc(),r={...e,hubOrigin:e.hubOrigin,requestId:t};return{transport:"browser",requestId:t,deliveryUrl:Nr(r)}}var qn="https://auth.corsair.dev";var Ce=class extends Error{constructor(){super("Hub is not configured. Pass hub: { projectApiKey, signingSecret } to createCorsair()."),this.name="HubNotConfiguredError"}},jn=class extends Error{constructor(){super("Hub credentials are missing. Pass hub: { projectApiKey, signingSecret } to createCorsair() with non-empty values, or omit `hub` entirely if you are not using Corsair Hub."),this.name="HubCredentialsMissingError"}};function $r(e){let n=(e.apiUrl?.trim()||qn).replace(/\/$/,""),t=e.projectApiKey?.trim()??"",r=e.signingSecret?.trim()??"",o=t.startsWith("ck_cloud_");if(!t||!r&&!o)throw new jn;return{apiUrl:n,projectApiKey:t,signingSecret:r,instanceKey:e.instanceKey?.trim()||void 0,oauthCallbackUrl:e.oauthCallbackUrl?.trim().replace(/\/$/,""),redirectURL:e.redirectURL?.trim()||void 0,allowWorkflowExecution:e.allowWorkflowExecution??!1,tunnel:e.tunnel}}function kt(e){return $r(e)}function Xc(e){let n=e.projectApiKey.startsWith("ck_cloud_");return e.apiUrl.trim().length>0&&e.projectApiKey.trim().length>0&&(n||e.signingSecret.trim().length>0)}function N(e){let n=P(e).hub;if(!n||!Xc(n))throw new Ce;return n}function zi(e){return e.replace(/\/$/,"")}function wt(e){return e.oauthCallbackUrl?zi(e.oauthCallbackUrl.trim()):`${zi(e.apiUrl)}/oauth/callback`}function yn(e){if(e.startsWith("ck_dev_"))return"development";if(e.startsWith("ck_prod_"))return"production";if(e.startsWith("ck_cloud_"))return"cloud";throw new Error("Hub API key must start with ck_dev_ (development), ck_prod_ (production), or ck_cloud_ (cloud)")}import{createCipheriv as Ji,createDecipheriv as Vi,randomBytes as Ct,scrypt as eu}from"crypto";import{promisify as nu}from"util";var Yi=nu(eu),Tt="aes-256-gcm",Qi=12,Pt=16,tu=16,je=32;function Te(){return Ct(je).toString("base64")}async function Pe(e,n){let t=Ct(tu),r=await Yi(n,t,je),o=Ct(Qi),i=Ji(Tt,r,o,{authTagLength:Pt}),a=Buffer.concat([i.update(e,"utf8"),i.final()]),s=i.getAuthTag();return[t.toString("base64"),o.toString("base64"),s.toString("base64"),a.toString("base64")].join(":")}async function te(e,n){let[t,r,o,i]=e.split(":");if(!t||!r||!o||!i)throw new Error("Invalid encrypted DEK format");let a=Buffer.from(t,"base64"),s=Buffer.from(r,"base64"),c=Buffer.from(o,"base64"),l=Buffer.from(i,"base64"),u=await Yi(n,a,je),d=Vi(Tt,u,s,{authTagLength:Pt});return d.setAuthTag(c),Buffer.concat([d.update(l),d.final()]).toString("utf8")}function Wr(e,n){let t=Buffer.from(n,"base64"),r=Ct(Qi),o=Ji(Tt,t,r,{authTagLength:Pt}),i=Buffer.concat([o.update(e,"utf8"),o.final()]),a=o.getAuthTag();return[r.toString("base64"),a.toString("base64"),i.toString("base64")].join(":")}function Kn(e,n){let[t,r,o]=e.split(":");if(!t||!r||!o)throw new Error("Invalid encrypted data format");let i=Buffer.from(n,"base64"),a=Buffer.from(t,"base64"),s=Buffer.from(r,"base64"),c=Buffer.from(o,"base64"),l=Vi(Tt,i,a,{authTagLength:Pt});return l.setAuthTag(s),Buffer.concat([l.update(c),l.final()]).toString("utf8")}function De(e,n){let t={};for(let[r,o]of Object.entries(e))t[r]=Wr(o,n);return t}function le(e,n){let t={};for(let[r,o]of Object.entries(e))t[r]=Kn(o,n);return t}function Zn(e,n,t){let r=le(e,n);return De(r,t)}function Xi(e,n,t){let r={};for(let o of t)r[`get_${o}`]=async()=>(await e())[o]??null,r[`set_${o}`]=async i=>{let a=[null,void 0,""].includes(i)?null:i;await n({[o]:a})};return r}var qr=e=>{if(!e)return{};if(typeof e=="string")try{return JSON.parse(e)}catch{return{}}return e};function $(e){let{authType:n,integrationName:t,kek:r,database:o,extraIntegrationFields:i=[]}=e,a=[...K[n].integration,...i],s=null,c={kek:r,integrationName:t,getIntegration:async()=>{if(s)return s;let b=await o.db.selectFrom("corsair_integrations").selectAll().where("name","=",t).executeTakeFirst();if(!b)throw new Error(`Integration "${t}" not found. Make sure to create the integration first.`);return s={id:b.id,config:qr(b.config),dek:b.dek??null},s},updateIntegration:async b=>{let k=await c.getIntegration();await o.db.updateTable("corsair_integrations").set({...b.config!==void 0?{config:b.config}:{},...b.dek!==void 0?{dek:b.dek}:{},updated_at:new Date}).where("id","=",k.id).execute(),s=null}},l=null,u=async()=>{if(l)return l;let b=await c.getIntegration();if(!b.dek)throw new Error(`No DEK found for integration "${t}". Initialize the integration first.`);return l=await te(b.dek,r),l},d=async()=>{let b=await c.getIntegration(),k=await u(),T=b.config;return!T||Object.keys(T).length===0?{}:le(T,k)},p=Promise.resolve(),g=b=>{let k=p.then(()=>f(b));return p=k.catch(()=>{}),k},f=async b=>{let k=await u(),T;try{T=await d()}catch(D){console.error(`[corsair] Failed to decrypt config for integration "${t}", starting fresh:`,D),T={}}let v={...T};for(let[D,B]of Object.entries(b))B===null?delete v[D]:v[D]=B;let H=De(v,k);await c.updateIntegration({config:H})};return{get_dek:u,issue_new_dek:async()=>{let b=await c.getIntegration(),k=Te(),T={};if(b.dek){let H=await te(b.dek,r),D=b.config;D&&Object.keys(D).length>0&&(T=Zn(D,H,k))}let v=await Pe(k,r);return await c.updateIntegration({config:T,dek:v}),l=k,k},...Xi(d,g,a)}}function U(e){let{authType:n,integrationName:t,tenantId:r,kek:o,database:i,extraAccountFields:a=[],ensureProvisioned:s}=e,c=[...K[n].account,...a],l=null,u=async()=>{if(l)return l;let C=!1;for(;;){let R=await i.db.selectFrom("corsair_integrations").selectAll().where("name","=",t).executeTakeFirst();if(!R){if(!C&&s){C=!0,await s();continue}throw new Error(`Integration "${t}" not found. Make sure to create the integration first.`)}return l={id:R.id,config:qr(R.config),dek:R.dek??null},l}},d={kek:o,integrationName:t,tenantId:r,getIntegration:u,getAccount:async()=>{let C=!1;for(;;){let R=await u(),x=await i.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",r).where("integration_id","=",R.id).executeTakeFirst();if(!x){if(!C&&s){C=!0,await s();continue}throw new Error(`Account not found for tenant "${r}" and integration "${t}". Make sure to create the account first.`)}return{id:x.id,config:qr(x.config),dek:x.dek??null}}},updateAccount:async C=>{let R=await d.getAccount();await i.db.updateTable("corsair_accounts").set({...C.config!==void 0?{config:C.config}:{},...C.dek!==void 0?{dek:C.dek}:{},updated_at:new Date}).where("id","=",R.id).execute()}},p=null,g=null,f=null,h=async()=>{let C=await d.getAccount();if(!C.dek)throw new Error(`No DEK found for account (tenant: "${r}", integration: "${t}"). Initialize the account first.`);return p&&g===C.dek||(p=await te(C.dek,o),g=C.dek),p},b=async()=>{if(f)return f;let C=await d.getIntegration();if(!C.dek)throw new Error(`No DEK found for integration "${t}". Initialize the integration first.`);return f=await te(C.dek,o),f},k=async()=>{let C=await d.getAccount(),R=await h(),x=C.config;return!x||Object.keys(x).length===0?{}:le(x,R)},T=async()=>{let C=await d.getIntegration(),R=await b(),x=C.config;return!x||Object.keys(x).length===0?{}:le(x,R)},v=Promise.resolve(),H=C=>{let R=v.then(()=>D(C));return v=R.catch(()=>{}),R},D=async C=>{let R=await d.getAccount();if(!R.dek)throw new Error(`No DEK found for account (tenant: "${r}", integration: "${t}"). Initialize the account first.`);let x=await te(R.dek,o),ee;try{let q=R.config;ee=!q||Object.keys(q).length===0?{}:le(q,x)}catch(q){console.error(`[corsair] Failed to decrypt config for account (tenant: "${r}", integration: "${t}"), starting fresh:`,q),ee={}}let re={...ee};for(let[q,he]of Object.entries(C))he===null?delete re[q]:re[q]=he;let E=De(re,x);await d.updateAccount({config:E})},B={get_dek:h,issue_new_dek:async()=>{let C=await d.getAccount(),R=Te(),x={};if(C.dek){let re=await te(C.dek,o),E=C.config;E&&Object.keys(E).length>0&&(x=Zn(E,re,R))}let ee=await Pe(R,o);return await d.updateAccount({config:x,dek:ee}),p=R,g=ee,R},...Xi(k,H,c)};return n==="oauth_2"&&(B.get_integration_credentials=async()=>{let C=await T();return{...C,client_id:C.client_id||null,client_secret:C.client_secret||null,redirect_url:C.redirect_url??null}}),B}async function es(e,n,t){let r=await e.db.selectFrom("corsair_integrations").selectAll().where("name","=",n).executeTakeFirst();if(!r)throw new Error(`Integration "${n}" not found.`);let o=Te(),i=await Pe(o,t);return await e.db.updateTable("corsair_integrations").set({dek:i,updated_at:new Date}).where("id","=",r.id).execute(),o}async function ns(e,n,t,r){let o=await e.db.selectFrom("corsair_integrations").selectAll().where("name","=",n).executeTakeFirst();if(!o)throw new Error(`Integration "${n}" not found.`);let i=await e.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",t).where("integration_id","=",o.id).executeTakeFirst();if(!i)throw new Error(`Account not found for tenant "${t}" and integration "${n}".`);let a=Te(),s=await Pe(a,r);return await e.db.updateTable("corsair_accounts").set({dek:s,updated_at:new Date}).where("id","=",i.id).execute(),a}var ru=new Set(["webhook_signature","expires_at","scope","redirect_url","refresh_token"]);function He(e){return ru.has(e)}function ou(e,n){return He(n)?!1:e==="oauth_2"?n==="client_id"||n==="client_secret":!0}function iu(e){return!He(e)}function su(e){switch(e){case"oauth_2":case"managed":return["access_token"];case"api_key":return["api_key"];case"bot_token":return["bot_token"];case"managed_pricing":return[]}}function au(e,n){return e!=="oauth_2"&&e!=="managed"?!1:n.some(t=>t.level==="account"&&t.name==="expires_at"&&t.configured)}function cu(e,n){let t=i=>n.find(a=>a.level==="account"&&a.name===i);if(!su(e).every(i=>t(i)?.configured))return!1;let o=t("refresh_token");return o?.required?!!o.configured:!0}async function ts(e,n){if(!e)return!1;let t=ne(e,`get_${n}`);if(!t)return!1;try{let r=await t();return typeof r=="string"&&r.length>0}catch{return!1}}function uu(e,n){let r=e.authConfig?.[n]?.integration??[];return[...K[n].integration,...r]}function lu(e,n){let r=e.authConfig?.[n]?.account??[];return[...K[n].account,...r]}function du(e,n,t){let r=t.filter(s=>s.required&&!s.configured).map(s=>s.name),o=t.filter(s=>s.level==="integration"&&s.required&&!s.configured).map(s=>s.name),i=t.filter(s=>s.level==="account"&&s.required&&s.configured),a;return o.length>0?a="missing_integration":r.length===0?a="ready":i.length>0?a="partial":a="not_started",{plugin:e,authType:n,status:a,connected:cu(n,t),fields:t,missingRequiredFields:r}}async function Ke(e,n,t){let r=O(n);if(!r||!e.database||!e.kek)return null;let o=t.trim()||"default",i=n.authConfig,a=i?.[r]?.integration??[],s=i?.[r]?.account??[],c=$({authType:r,integrationName:n.id,kek:e.kek,database:e.database,extraIntegrationFields:a}),l=U({authType:r,integrationName:n.id,tenantId:o,kek:e.kek,database:e.database,extraAccountFields:s}),u=uu(n,r),d=lu(n,r),p=[];for(let g of u)p.push({name:g,level:"integration",required:ou(r,g),configured:await ts(c,g)});for(let g of d)p.push({name:g,level:"account",required:iu(g),configured:await ts(l,g)});if(au(r,p)){let g=p.find(f=>f.level==="account"&&f.name==="refresh_token");g&&(g.required=!0)}return du(n.id,r,p)}async function Gn(e,n,t={}){let r=n.trim()||"default",o=t.pluginIds?.length?new Set(t.pluginIds):null,i=[];for(let a of e.plugins){if(o&&!o.has(a.id))continue;let s=await Ke(e,a,r);s&&i.push(s)}return i}function vt(e){return e.connected?"connected":e.status==="missing_integration"?"missing_credentials":"not_connected"}var rs=Symbol.for("corsair:internal"),os=new WeakMap,is=new WeakMap;function pu(e,n){let t=n.map(r=>r.id).sort().join("\0");return`${e}\0${t}`}function gu(e){if(e.database){let t=os.get(e.database);return t||(t=new Map,os.set(e.database,t)),t}let n=is.get(e);return n||(n=new Map,is.set(e,n)),n}function fu(e){return e.multiTenancy?{withTenant:()=>({}),[rs]:e}:{[rs]:e}}async function mn(e,n){if(!e.database)return;let t=n.trim()||"default",r=gu(e),o=pu(t,e.plugins),i=r.get(o);if(i){await i;return}let a=(async()=>{let{setupCorsair:s}=await import("./setup-7TLWIUSW.js");await s(fu(e),{tenantId:e.multiTenancy?t:void 0,silent:!0})})().finally(()=>{r.delete(o)});r.set(o,a),await a}import*as zn from"crypto";function Be(e,n){return Buffer.from(JSON.stringify({plugin:e,tenantId:n,iat:Date.now()})).toString("base64url")}function jr(e,{maxAgeMs:n}={}){try{let t=e.includes(".")?e.split(".")[0]:e,r=JSON.parse(Buffer.from(t,"base64url").toString("utf-8"));if(r!==null&&typeof r=="object"&&"plugin"in r&&"tenantId"in r&&typeof r.plugin=="string"&&typeof r.tenantId=="string"){let o=r;return n!==void 0&&typeof o.iat=="number"&&Date.now()-o.iat>n?null:o}return null}catch{return null}}function hn(e,n){if(!n)throw new Error("OAuth state signing requires a configured kek. Pass kek to createCorsair().");let t=zn.createHmac("sha256",n).update(e).digest("base64url");return`${e}.${t}`}var Kr=600*1e3;function Rt(e,n){if(!n)return null;let t=e.lastIndexOf(".");if(t===-1)return null;let r=e.slice(0,t),o=e.slice(t+1),i=zn.createHmac("sha256",n).update(r).digest("base64url"),a=Buffer.from(o,"base64url"),s=Buffer.from(i,"base64url");return a.length!==s.length||!zn.timingSafeEqual(a,s)?null:jr(r,{maxAgeMs:Kr})}function ss(e){return{tenantId:e.tenantId,plugin:e.plugin,authType:e.authType??"oauth_2",status:"ready",connected:!0,verified:!0,webhookLink:e.link}}function as(e){return{tenantId:e.tenantId,plugin:e.plugin,authType:e.authType,status:e.status,connected:e.connected,verified:e.verified,missingFields:e.missingFields,webhookLink:e.webhookLink,webhookSecret:e.webhookSecret}}async function bn(e,n){await _({hub:e,path:"/connections/report",body:ss(n),parseResponse:()=>({ok:!0})}).catch(()=>{})}function yu(e,n){try{let t=N(e);_({hub:t,path:"/connections/report",body:n,parseResponse:()=>({ok:!0})}).catch(()=>{})}catch(t){if(t instanceof Ce)return}}async function mu(e){if(!e.hub||!e.database||!e.kek)return;let n={database:e.database,kek:e.kek,plugins:e.plugins};if(!O(e.plugin))return;let r=e.tenantId?.trim()||"default",o=await Ke(n,e.plugin,r);o&&us(e.hub,as({tenantId:r,plugin:e.plugin.id,authType:o.authType,status:o.status,connected:o.connected,verified:e.verified??o.connected,missingFields:o.missingRequiredFields}))}function cs(e,n){yu(e,n)}function us(e,n){_({hub:e,path:"/connections/report",body:n,parseResponse:()=>({ok:!0})}).catch(()=>{})}function kn(e){mu(e).catch(()=>{})}async function ve(e,n){let t=P(e);if(!O(n.plugin))return;let o=await Ke(t,n.plugin,n.tenantId);o&&cs(e,as({tenantId:n.tenantId.trim()||"default",plugin:n.plugin.id,authType:o.authType,status:o.status,connected:o.connected,verified:n.verified??o.connected,missingFields:o.missingRequiredFields,webhookLink:n.webhookLink,webhookSecret:n.webhookSecret}))}async function At(e,n,t){for(let r of e){if(r.id!==n)continue;let o=r.oauthWebhookTenantLinkResolver;return o?o(t):null}return null}var ls=e=>{if(!e)return{};if(typeof e=="string")try{return JSON.parse(e)}catch{return{}}return e};async function hu(e){let n=await e.database.db.selectFrom("corsair_integrations").selectAll().where("name","=",e.pluginId).executeTakeFirst();if(!n)throw new Error(`Integration '${e.pluginId}' not found. Run setupCorsair before registering webhook tenant links.`);let t=await e.database.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",e.tenantId).where("integration_id","=",n.id).executeTakeFirst();if(!t)throw new Error(`Account not found for tenant '${e.tenantId}' and integration '${e.pluginId}'.`);return{integrationId:n.id,accountId:t.id}}async function bu(e){let n=await e.database.db.selectFrom("corsair_accounts").selectAll().where("id","=",e.accountId).executeTakeFirst();if(!n?.dek)throw new Error(`Account '${e.accountId}' has no DEK.`);let t=await te(n.dek,e.kek),r=ls(n.config),o={};Object.keys(r).length>0&&(o=le(r,t)),o[e.link.linkType]=e.link.externalId;let i=De(o,t);await e.database.db.updateTable("corsair_accounts").set({config:i,updated_at:new Date}).where("id","=",n.id).execute()}async function wn(e){let{database:n,kek:t,pluginId:r,tenantId:o,link:i,authType:a,extraAccountFields:s=[]}=e,{accountId:c}=await hu({database:n,pluginId:r,tenantId:o}),l=!1;if(a){let u=U({authType:a,integrationName:r,tenantId:o,kek:t,database:n,extraAccountFields:s}),d=`set_${i.linkType}`,p=u[d];typeof p=="function"&&(await p(i.externalId),l=!0)}l||await bu({database:n,kek:t,accountId:c,link:i})}async function Zr(e){let{database:n,kek:t,pluginId:r,linkType:o,externalId:i}=e,a=await n.db.selectFrom("corsair_accounts as accounts").innerJoin("corsair_integrations as integrations","integrations.id","accounts.integration_id").selectAll("accounts").where("integrations.name","=",r).execute();for(let s of a)if(s.dek)try{let c=await te(s.dek,t),u=ls(s.config)[o];if(!u)continue;if(Kn(u,c)===i)return s}catch{continue}return null}async function xt(e){return(await Zr(e))?.tenant_id??null}async function ds(e){return xt({database:e.database,kek:e.kek,pluginId:e.pluginId,linkType:e.match.linkType,externalId:e.match.externalId})}import*as ps from"querystring";function Ze(e){let{oauthConfig:n,clientId:t,redirectUri:r,state:o}=e,i={...n.authParams,client_id:t,redirect_uri:r,response_type:"code",scope:n.scopes.join(" "),state:o};return`${n.authUrl}?${ps.stringify(i)}`}async function gs(e,n){try{return await Z({hub:e,path:`/webhooks/endpoint?plugin=${encodeURIComponent(n)}`,parseResponse:t=>t?.url??null})}catch{return null}}async function Cn(e,n,t,r){if(!n.subscribe)return;let o=N(e),i=await gs(o,n.id);if(!i)return;let a=await n.subscribe({keys:r},{webhookUrl:i});a&&await ve(e,{plugin:n,tenantId:t,verified:!0,webhookLink:a.webhookLink,webhookSecret:a.webhookSecret})}var V=class extends Error{code;constructor(n,t){super(t),this.name="OAuthCallbackError",this.code=n}};function fs(e){let n=e.oauthConfig;if(!n)throw new V("plugin_has_no_oauth_config",`Plugin '${e.id}' has no oauthConfig`);return n}async function ku(e,n,t,r){await e.db.transaction().execute(async o=>{let i=o.selectFrom("corsair_integrations").select(["id"]).where("name","=",n);e.isPg===!0&&(i=i.forUpdate());let a=await i.executeTakeFirst();if(!a)throw new Error(`Integration '${n}' not found. Run setupCorsair first.`);if(await o.selectFrom("corsair_accounts").select("id").where("tenant_id","=",t).where("integration_id","=",a.id).executeTakeFirst())return;let c=Te(),l=await Pe(c,r),u=new Date;await o.insertInto("corsair_accounts").values({id:ln(),created_at:u,updated_at:u,tenant_id:t,integration_id:a.id,config:{},dek:l}).execute()})}async function Gr(e,n,t){let{tenantId:r,redirectUri:o,hubConnect:i=!1}=t,a=P(e,()=>new V("invalid_corsair_instance","Invalid corsair instance"));if(!a.database)throw new Error("No database configured on corsair instance");let s=J(a,n,p=>new V("plugin_not_found",p)),c=fs(s),u=await $({authType:"oauth_2",integrationName:n,kek:a.kek,database:a.database}).get_client_id();if(!u)throw new Error(`client_id not configured for '${n}'`);if(i){let p=new URL(Ze({oauthConfig:c,clientId:u,redirectUri:o,state:""}));return p.searchParams.delete("state"),{url:p.toString(),state:""}}let d=hn(Be(n,r),a.kek);return{url:Ze({oauthConfig:c,clientId:u,redirectUri:o,state:d}),state:d}}function wu(e,n){return{...n??{},...e}}async function Jn(e,n){let{code:t,state:r,redirectUri:o}=n,i=P(e,()=>new V("invalid_corsair_instance","Invalid corsair instance")),a,s;if(n.trusted){if(!n.plugin||!n.tenantId)throw new V("invalid_state","trusted callback requires plugin and tenantId");a=n.plugin,s=n.tenantId}else{let h=Rt(r,i.kek);if(!h)throw new V("invalid_state","Invalid or tampered state parameter");a=h.plugin,s=h.tenantId}if(!i.database)throw new V("no_database","No database configured on corsair instance");let c=J(i,a,h=>new V("plugin_not_found",h)),l=fs(c),u=$({authType:"oauth_2",integrationName:a,kek:i.kek,database:i.database}),d=await u.get_client_id(),p=await u.get_client_secret();if(!d||!p)throw new V("credentials_not_configured",`Credentials not configured for '${a}'`);await ku(i.database,a,s,i.kek);let g=await It(t,d,p,l,o);if(!g.access_token)throw new V("no_access_token",`No access_token returned from ${l.providerName}`);let f=U({authType:"oauth_2",integrationName:a,tenantId:s,kek:i.kek,database:i.database,extraAccountFields:[...c.authConfig?.oauth_2?.account??[]]});await f.set_access_token(g.access_token),g.refresh_token&&await f.set_refresh_token(g.refresh_token),g.expires_in&&await f.set_expires_at(String(Math.floor(Date.now()/1e3)+g.expires_in)),await ve(e,{plugin:c,tenantId:s}).catch(()=>{});try{let h=wu(g,n.callbackParams),b=await At(i.plugins,a,h);if(b){try{let k=c.authConfig?.oauth_2?.account??[];await wn({database:i.database,kek:i.kek,pluginId:a,tenantId:s,link:b,authType:"oauth_2",extraAccountFields:k})}catch(k){console.warn(`[corsair:oauth] Failed to persist webhook tenant link for '${a}' tenant '${s}':`,k)}i.hub&&bn(i.hub,{plugin:a,tenantId:s,link:b,authType:"oauth_2"})}}catch(h){console.warn(`[corsair:oauth] Failed to resolve webhook tenant link for '${a}' tenant '${s}':`,h)}if(c.subscribe)try{await Cn(e,c,s,f)}catch(h){console.warn(`[corsair:oauth] BYO subscribe failed for '${a}' tenant '${s}':`,h)}return{plugin:a,tenantId:s}}async function Cu(e){let{corsair:n,internal:t,rows:r}=e,o=e.subscribeAndReport??Cn,i=[],a=[];if(!t.database)return{renewed:i,failed:a};for(let s of r){let c=t.plugins.find(u=>u.id===s.integrationName);if(!c?.subscribe)continue;let l=`${c.id}/${s.tenantId}`;try{let u=O(c)??"oauth_2",d=U({authType:u,integrationName:c.id,tenantId:s.tenantId,kek:t.kek,database:t.database,extraAccountFields:[...c.authConfig?.[u]?.account??[]]}),p=c.keyBuilder;if(p){let g=Object.create(d,{get_expires_at:{value:async()=>"0"}});await p({authType:u,keys:g,hub:t.hub},"endpoint")}await o(n,c,s.tenantId,d),i.push(l)}catch(u){console.warn(`[corsair:renewal] re-subscribe failed for '${l}':`,u),a.push(l)}}return{renewed:i,failed:a}}async function ys(e){let n=P(e);if(!n.database)return{renewed:[],failed:[]};let t=await n.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.tenant_id as tenantId","i.name as integrationName"]).where("a.dek","is not",null).execute();return Cu({corsair:e,internal:n,rows:t.filter(r=>!!r.tenantId)})}function Tu(e,n={}){let t=!1,r=()=>{t||(t=!0,ys(e).catch(i=>console.warn("[corsair:renewal] renewal pass failed:",i)).finally(()=>{t=!1}))};r();let o=setInterval(r,(n.intervalMinutes??45)*6e4);return o.unref?.(),()=>clearInterval(o)}async function ms(e){if(!P(e).database)throw new Error("A database must be configured to provision Corsair integrations");await St(e,{silent:!0})}async function Tn(e,n){let t=P(e);if(!t.database)throw new Error("A database must be configured to provision Corsair for connect");await mn(t,n)}var Pu=Symbol.for("corsair:internal"),vu=new Set(["access_token","refresh_token","expires_at","scope"]);function Ru(e){return e==="oauth_2"||e==="managed"?"oauth":e==="bot_token"?"bot_token":"api_key"}function Au(e,n){return e==="oauth_2"||e==="managed"?n.filter(t=>!He(t)&&!vu.has(t)):n.filter(t=>!He(t))}function hs(e){return{plugins:e.plugins,database:e.database,kek:e.kek,multiTenancy:e.multiTenancy??!1}}function xu(e){return{plugins:e.plugins,database:e.database,kek:e.kek,multiTenancy:e.multiTenancy??!1}}function Iu(e){return{[Pu]:hs(e)}}async function _t(e,n,t={}){let r=wt(e.hub),o=[],i=t.pluginIds?new Set(t.pluginIds):null,a=hs(e),s=Iu(e);for(let c of e.plugins){if(i&&!i.has(c.id))continue;let l=O(c);if(!l)continue;let u=Ru(l),d=t.providerNameOverrides?.[c.id]??Ee(c.id),p=await Ke(a,c,n),g=lt(c,l),f=Au(l,g),h={plugin:c.id,providerName:d,authKind:u,alreadyConfigured:p?.connected??!1};if(f.length>0&&(h.credentialFields=f),u==="oauth"){let k=t.oauthModeOverrides?.[c.id]??(l==="managed"?"managed":"byo");if(h.oauthMode=k,!t.skipOAuthUrlGeneration&&k!=="managed")try{let T=await Gr(s,c.id,{tenantId:n,redirectUri:r,hubConnect:!0});h.oauthUrl=T.url}catch(T){T instanceof Error&&/client_id not configured/i.test(T.message)||(h.setupError=T instanceof Error?T.message:`Could not prepare OAuth for ${c.id}`)}}o.push(h)}return o}async function uy(e,n,t={}){let r=P(e),o=r.hub;if(!o)throw new Error("Hub is not configured");return _t({plugins:r.plugins,database:r.database,kek:r.kek,hub:o},n,t)}async function bs(e,n){if(!e.database)throw new Error("A database must be configured to provision Corsair for connect");await mn(e.internalConfig??xu(e),n)}async function ks(e,n){await Tn(e,n)}async function ws(e,n){let t=yn(e.projectApiKey),r={tenantId:n.tenantId,plugins:n.plugins};return e.redirectURL&&(r.redirectUri=e.redirectURL),t==="development"&&(r.deliveryUrl=Se({deliveryUrl:n.deliveryUrl})),_({hub:e,path:"/connect/sessions",notFoundMessage:"Hub REST API not found at /connect/sessions. Check HUB_API_URL and ensure the Hub API is deployed.",body:r,parseResponse:pt})}async function Cs(e,n){let t={plugins:n.plugins,database:n.database,kek:n.kek,hub:e,multiTenancy:n.multiTenancy};await bs(t,n.tenantId);let r=await _t(t,n.tenantId,{pluginIds:[n.plugin.id]});if(r.length===0)throw new Error(`Plugin '${n.plugin.id}' is not configured on this Corsair instance`);return ws(e,{tenantId:n.tenantId,plugins:r,deliveryUrl:n.deliveryUrl})}async function Et(e,n){let t=P(e),r=N(e),o={plugins:t.plugins,database:t.database,kek:t.kek,hub:r,multiTenancy:t.multiTenancy,internalConfig:t};await ks(e,n.tenantId);let i=n.plugin?[n.plugin]:void 0,a=n.plugin&&n.oauthMode?{[n.plugin]:n.oauthMode}:void 0,s=n.plugin&&n.providerName?{[n.plugin]:n.providerName}:void 0,c=await _t(o,n.tenantId,{pluginIds:i,oauthModeOverrides:a,providerNameOverrides:s});if(c.length===0)throw new Error(n.plugin?`Plugin '${n.plugin}' is not configured on this Corsair instance`:"No plugins are configured on this Corsair instance");return ws(r,{tenantId:n.tenantId,plugins:c,deliveryUrl:n.deliveryUrl})}async function Ot(e,n){let t=n.tenantId.trim();if(!t)throw new Error("tenantId is required");let r=n.plugins.map(a=>a.trim()).filter(Boolean);if(r.length===0)throw new Error("At least one plugin is required");let o=P(e);if(!o.hub)throw new Error("Hub is not configured on this Corsair instance");if(!o.database)throw new Error("Database not configured");let i=await Su(o.hub,{plugins:o.plugins,database:o.database,kek:o.kek,multiTenancy:o.multiTenancy},{tenantId:t,pluginIds:r});return{connectUrl:i.connectUrl,expiresAt:i.expiresAt}}async function Su(e,n,t){let{buildConnectPluginManifestFromContext:r,ensureConnectAccountRowsFromContext:o}=await import("./setup-introspect-QD6GY2I5.js"),{postHubConnectSession:i}=await import("./connect-AS4S25YD.js"),a={plugins:n.plugins,database:n.database,kek:n.kek,hub:e,multiTenancy:n.multiTenancy};await o(a,t.tenantId);let s=await r(a,t.tenantId,{pluginIds:t.pluginIds});if(s.length===0)throw new Error("No connectable plugins found for this tenant");let c=s.find(l=>l.setupError);if(c)throw new Error(c.setupError??`Could not prepare connect link for ${c.plugin}`);return i(e,{tenantId:t.tenantId,plugins:s})}function Pn(e){return!!(e?.baseUrl?.trim()&&e?.redirectUri?.trim())}var ie=class extends Error{code;constructor(n,t){super(t),this.name="ConnectError",this.code=n}};function _u(e){let n=e.oauthConfig;if(!n)throw new ie("plugin_has_no_oauth_config",`Plugin '${e.id}' has no oauthConfig`);return n}async function zr(e,n){let t=P(e,()=>new ie("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new ie("no_database","No database configured on corsair instance");let r=t.manual?.redirectUri;if(!r)throw new ie("no_redirect_uri","No redirectUri configured. Set manual.redirectUri in createCorsair().");let o=Rt(n,t.kek);if(!o)throw new ie("invalid_state","Invalid or tampered state parameter");let{plugin:i,tenantId:a}=o,s=J(t,i,p=>new ie("plugin_not_found",p)),c=_u(s),u=await $({authType:"oauth_2",integrationName:i,kek:t.kek,database:t.database}).get_client_id();if(!u)throw new ie("client_id_not_configured",`client_id not configured for '${i}'`);let d=Ze({oauthConfig:c,clientId:u,redirectUri:r,state:n});return{plugin:i,tenantId:a,providerName:c.providerName,oauthUrl:d,state:n}}import{AsyncLocalStorage as Ou}from"async_hooks";import{randomBytes as Mu}from"crypto";import{v4 as Du}from"uuid";var de=class extends Error{reason;constructor(n,t="pending"){super(n),Object.setPrototypeOf(this,new.target.prototype),this.name="PermissionRequiredError",this.reason=t}};async function Mt(e,n){let t=yn(e.projectApiKey),r={permissionId:n.permissionId,permissionToken:n.permissionToken,plugin:n.plugin,endpoint:n.endpoint,args:n.args,tenantId:n.tenantId,expiresAt:n.expiresAt};return e.redirectURL&&(r.redirectUri=e.redirectURL),t==="development"&&(r.deliveryUrl=Se({deliveryUrl:n.deliveryUrl})),_({hub:e,path:"/permission/sessions",notFoundMessage:"Hub REST API not found at /permission/sessions. Check HUB_API_URL and ensure the Hub API is deployed.",body:r,parseResponse:ft})}function Dt(e){return`Approval required. Visit ${e} to approve or deny, then tell the agent to retry this action.`}var Jr="Permission approval required. Set manual.approvalBaseUrl (or use hub for hosted approval) so an approval URL can be generated. Optionally set manual.onApprovalRequired to customize the agent message.";function Yr(e){return e?e.approvalBaseUrl!==void 0||e.onApprovalRequired!==void 0:!1}function Ts(e,n){return`${e.replace(/\/+$/,"")}/${n}`}function Vr(e){return Dt(e)}async function Qr(e,n){if(Yr(e.manual)){let r=e.manual?.approvalBaseUrl?.trim();return r?Ts(r,n.token):null}let t=e.hub;if(!t)return null;try{return(await Mt(t,{permissionId:n.id,permissionToken:n.token,plugin:n.plugin,endpoint:n.endpoint,args:Eu(n.args),tenantId:n.tenant_id,expiresAt:n.expires_at})).approvalUrl}catch(r){return console.warn(`[corsair/${n.plugin}] could not create an approval link for '${n.endpoint}': ${r instanceof Error?r.message:String(r)}`),null}}function Eu(e){try{return JSON.parse(e)}catch{return e}}async function Ht(e,n){if(!(n.status==="pending"||n.status==="approved"))return{...n,approvalUrl:null};let r=await Qr(e,n);return{...n,approvalUrl:r}}async function Xr(e){let{permissionsOptions:n,manual:t,hub:r,permissionId:o,permissionToken:i,plugin:a,endpoint:s,args:c,tenantId:l,expiresAt:u,operationPath:d}=e;if(n?.formatAsyncMessage)return n.formatAsyncMessage({token:i,id:o,plugin:a,endpoint:s,args:c});let g=await Qr({manual:t,hub:r},{id:o,token:i,plugin:a,endpoint:s,args:JSON.stringify(c),tenant_id:l,expires_at:u});return Yr(t)?g?t?.onApprovalRequired?t.onApprovalRequired({approvalUrl:g}):Vr(g):Jr:r?g?Vr(g):`Action '${d}' requires user approval before it can run. Could not create approval link. Check hub configuration and server logs.`:Jr}var Bt=new Ou,Ps={open:0,cautious:1,strict:2,readonly:3},vn=class extends Error{endpointPath;riskLevel;constructor(n,t){super(`Action '${n}' is a '${t}' operation and is forbidden in readonly mode. Only read operations are permitted \u2014 rewrite the script to avoid write/destructive actions.`),this.name="ReadonlyForbiddenError",this.endpointPath=n,this.riskLevel=t}};function eo(e,n){return e===void 0?n:n===void 0||Ps[e]>=Ps[n]?e:n}function Ut(e,n){return Bt.run(eo(Bt.getStore(),e)??e,n)}function Rn(){return Bt.getStore()}function no(e){return Ut("readonly",e)}function As(){return Bt.getStore()==="readonly"}function Lt(e,n){if(As()&&n!=="read")throw new vn(e,n)}function Ge(e,n){Lt(e,n);let t=Rn();if(!(t===void 0||Ft(n,t)==="allow"))throw new de(`Action '${e}' is a '${n}' operation and permission mode '${t}' does not allow it. The entity store cannot wait for approval.`,"policy")}var Hu={open:{read:"allow",write:"allow",destructive:"allow"},cautious:{read:"allow",write:"allow",destructive:"require_approval"},strict:{read:"allow",write:"require_approval",destructive:"deny"},readonly:{read:"allow",write:"deny",destructive:"deny"}},vs={allow:0,require_approval:1,deny:2};function xs(e,n){return e===void 0?n:vs[e]>=vs[n]?e:n}function Ft(e,n,t){return t!==void 0?t:Hu[n][e]}function to(e){let n=/(\d+)(d|h|m|s)/g,t=0,r;for(;(r=n.exec(e))!==null;){let o=parseInt(r[1],10);switch(r[2]){case"d":t+=o*864e5;break;case"h":t+=o*36e5;break;case"m":t+=o*6e4;break;case"s":t+=o*1e3;break}}return t>0?t:600*1e3}function Is(e){return{async find_by_permission_id(n){if(e)return e.db.selectFrom("corsair_permissions").selectAll().where("id","=",n).executeTakeFirst()},async find_by_token(n){if(e)return e.db.selectFrom("corsair_permissions").selectAll().where("token","=",n).executeTakeFirst()},async set_executing(n){e&&await e.db.updateTable("corsair_permissions").set({status:"executing",updated_at:new Date}).where("id","=",n).execute()},async set_completed(n){e&&await e.db.updateTable("corsair_permissions").set({status:"completed",updated_at:new Date}).where("id","=",n).execute()}}}async function Rs(e,n,t){let r=Date.now()+t;for(;Date.now()<r;){let o=await e.db.selectFrom("corsair_permissions").select(["id","status"]).where("id","=",n).executeTakeFirst();if(!o)return{result:"blocked",reason:"pending"};if(o.status==="approved")return{result:"allow",onComplete:async()=>{await e.db.updateTable("corsair_permissions").set({status:"completed",updated_at:new Date}).where("id","=",n).execute()}};if(o.status==="denied")return{result:"blocked",reason:"denied"};if(o.status==="expired"||o.status==="failed")return{result:"blocked",reason:"timeout"};await new Promise(i=>setTimeout(i,500))}return{result:"blocked",reason:"timeout"}}async function Ss(e){let n=Ft(e.riskLevel,e.mode,e.override);if(n==="allow")return{result:"allow"};let t=e.meta?.irreversible?" (irreversible)":"",r=e.meta?.description?`${e.meta.description}${t}`:`${e.pluginId}.${e.endpointPath}${t}`;if(n==="deny"||!e.db)return console.log(`[corsair/${e.pluginId}] '${e.endpointPath}' blocked \u2014 denied by permission mode '${e.mode}'.`,`
|
|
9
|
+
</script></body></html>`}var Zc=new Set(["localhost","127.0.0.1","[::1]","::1"]);function Lr(e){try{let{hostname:n,protocol:t}=new URL(e);return t!=="http:"&&t!=="https:"?!1:Zc.has(n)}catch{return!1}}function Nn(e){return e==="development"?"browser":"server"}function ji(e){return Nn(e)==="browser"}function Ki(e){return Lr(e)?"Production delivery URL must be a public URL, not localhost":null}import{randomBytes as Vc}from"crypto";var Oe=60*1e3,We=300*1e3;import{createHmac as Gc,randomBytes as zc,timingSafeEqual as Jc}from"crypto";function we(){return zc(16).toString("base64url")}function $n(e,n){let t=n.trim();if(!t)throw new Error("Signing secret is required");return Gc("sha256",t).update(e).digest("base64url")}function ue(e,n){let t=n.trim();if(!t)return null;let r=e.split(".");if(r.length!==2)return null;let[o,i]=r;if(!o||!i)return null;let a=$n(o,t);try{if(!Jc(Buffer.from(i,"utf8"),Buffer.from(a,"utf8")))return null}catch{return null}let s;try{s=JSON.parse(Buffer.from(o,"base64url").toString("utf8"))}catch{return null}return s.exp*1e3<Date.now()?null:s}function bt(e,n,t){let r=Math.floor(Date.now()/1e3),o={...e,iat:r,exp:t},i=Buffer.from(JSON.stringify(o)).toString("base64url"),a=$n(i,n);return`${i}.${a}`}function Wn(e,n,t){let r=Math.floor(Date.now()/1e3);return bt(e,n,r+Math.floor(t/1e3))}function qe(e){return decodeURIComponent(e)}function Fr(e){return encodeURIComponent(e).replace(/\./g,"%2E")}function Zi(e){let n=e.trim();return n.length>0?n:null}function gn(e,n){let t=new URL(e);return t.searchParams.set("d",n),t.toString()}function fn(e,n){if(!Zi(n))throw new Error("Signing secret is required for browser delivery tokens");let t=Math.floor(Date.now()/1e3),r={...e,jti:e.jti??Vc(16).toString("base64url"),iat:t,exp:t+Math.floor(Oe/1e3)},o=Buffer.from(JSON.stringify(r)).toString("base64url"),i=$n(o,n);return`${o}.${i}`}function Me(e,n){return Zi(n)?ue(e,n):null}function Qc(e){let n=Ur(e.hubOrigin),t={connectJti:e.requestId,projectId:e.projectId,hubSuccessUrl:e.hubOrigin,deliveryMode:e.deliveryMode,hubOrigin:n,requestId:e.requestId};switch(e.deliveryMode){case"connections.sync":return{...t,plugin:"connections.sync",tenantId:"*"};case"connect.create_link":return{...t,plugin:"connect.create_link",tenantId:e.tenantId,connectLinkPlugins:e.plugins}}}function Nr(e){let n=fn(Qc(e),e.signingSecret);return gn(e.deliveryUrl,n)}function Gi(e){if(Nn(e.environmentSlug)==="server")return{transport:"server"};if(!e.hubOrigin)throw new Error(`hubOrigin is required for development ${e.deliveryMode} delivery`);let t=Yc(),r={...e,hubOrigin:e.hubOrigin,requestId:t};return{transport:"browser",requestId:t,deliveryUrl:Nr(r)}}var qn="https://auth.corsair.dev";var Ce=class extends Error{constructor(){super("Hub is not configured. Pass hub: { projectApiKey, signingSecret } to createCorsair()."),this.name="HubNotConfiguredError"}},jn=class extends Error{constructor(){super("Hub credentials are missing. Pass hub: { projectApiKey, signingSecret } to createCorsair() with non-empty values, or omit `hub` entirely if you are not using Corsair Hub."),this.name="HubCredentialsMissingError"}};function $r(e){let n=(e.apiUrl?.trim()||qn).replace(/\/$/,""),t=e.projectApiKey?.trim()??"",r=e.signingSecret?.trim()??"",o=t.startsWith("ck_cloud_");if(!t||!r&&!o)throw new jn;return{apiUrl:n,projectApiKey:t,signingSecret:r,instanceKey:e.instanceKey?.trim()||void 0,oauthCallbackUrl:e.oauthCallbackUrl?.trim().replace(/\/$/,""),redirectURL:e.redirectURL?.trim()||void 0,allowWorkflowExecution:e.allowWorkflowExecution??!1,tunnel:e.tunnel}}function kt(e){return $r(e)}function Xc(e){let n=e.projectApiKey.startsWith("ck_cloud_");return e.apiUrl.trim().length>0&&e.projectApiKey.trim().length>0&&(n||e.signingSecret.trim().length>0)}function N(e){let n=P(e).hub;if(!n||!Xc(n))throw new Ce;return n}function zi(e){return e.replace(/\/$/,"")}function wt(e){return e.oauthCallbackUrl?zi(e.oauthCallbackUrl.trim()):`${zi(e.apiUrl)}/oauth/callback`}function yn(e){if(e.startsWith("ck_dev_"))return"development";if(e.startsWith("ck_prod_"))return"production";if(e.startsWith("ck_cloud_"))return"cloud";throw new Error("Hub API key must start with ck_dev_ (development), ck_prod_ (production), or ck_cloud_ (cloud)")}import{createCipheriv as Ji,createDecipheriv as Vi,randomBytes as Ct,scrypt as eu}from"crypto";import{promisify as nu}from"util";var Yi=nu(eu),Tt="aes-256-gcm",Qi=12,Pt=16,tu=16,je=32;function Te(){return Ct(je).toString("base64")}async function Pe(e,n){let t=Ct(tu),r=await Yi(n,t,je),o=Ct(Qi),i=Ji(Tt,r,o,{authTagLength:Pt}),a=Buffer.concat([i.update(e,"utf8"),i.final()]),s=i.getAuthTag();return[t.toString("base64"),o.toString("base64"),s.toString("base64"),a.toString("base64")].join(":")}async function te(e,n){let[t,r,o,i]=e.split(":");if(!t||!r||!o||!i)throw new Error("Invalid encrypted DEK format");let a=Buffer.from(t,"base64"),s=Buffer.from(r,"base64"),c=Buffer.from(o,"base64"),l=Buffer.from(i,"base64"),u=await Yi(n,a,je),d=Vi(Tt,u,s,{authTagLength:Pt});return d.setAuthTag(c),Buffer.concat([d.update(l),d.final()]).toString("utf8")}function Wr(e,n){let t=Buffer.from(n,"base64"),r=Ct(Qi),o=Ji(Tt,t,r,{authTagLength:Pt}),i=Buffer.concat([o.update(e,"utf8"),o.final()]),a=o.getAuthTag();return[r.toString("base64"),a.toString("base64"),i.toString("base64")].join(":")}function Kn(e,n){let[t,r,o]=e.split(":");if(!t||!r||!o)throw new Error("Invalid encrypted data format");let i=Buffer.from(n,"base64"),a=Buffer.from(t,"base64"),s=Buffer.from(r,"base64"),c=Buffer.from(o,"base64"),l=Vi(Tt,i,a,{authTagLength:Pt});return l.setAuthTag(s),Buffer.concat([l.update(c),l.final()]).toString("utf8")}function De(e,n){let t={};for(let[r,o]of Object.entries(e))t[r]=Wr(o,n);return t}function le(e,n){let t={};for(let[r,o]of Object.entries(e))t[r]=Kn(o,n);return t}function Zn(e,n,t){let r=le(e,n);return De(r,t)}function Xi(e,n,t){let r={};for(let o of t)r[`get_${o}`]=async()=>(await e())[o]??null,r[`set_${o}`]=async i=>{let a=[null,void 0,""].includes(i)?null:i;await n({[o]:a})};return r}var qr=e=>{if(!e)return{};if(typeof e=="string")try{return JSON.parse(e)}catch{return{}}return e};function $(e){let{authType:n,integrationName:t,kek:r,database:o,extraIntegrationFields:i=[]}=e,a=[...K[n].integration,...i],s=null,c={kek:r,integrationName:t,getIntegration:async()=>{if(s)return s;let b=await o.db.selectFrom("corsair_integrations").selectAll().where("name","=",t).executeTakeFirst();if(!b)throw new Error(`Integration "${t}" not found. Make sure to create the integration first.`);return s={id:b.id,config:qr(b.config),dek:b.dek??null},s},updateIntegration:async b=>{let k=await c.getIntegration();await o.db.updateTable("corsair_integrations").set({...b.config!==void 0?{config:b.config}:{},...b.dek!==void 0?{dek:b.dek}:{},updated_at:new Date}).where("id","=",k.id).execute(),s=null}},l=null,u=async()=>{if(l)return l;let b=await c.getIntegration();if(!b.dek)throw new Error(`No DEK found for integration "${t}". Initialize the integration first.`);return l=await te(b.dek,r),l},d=async()=>{let b=await c.getIntegration(),k=await u(),T=b.config;return!T||Object.keys(T).length===0?{}:le(T,k)},p=Promise.resolve(),g=b=>{let k=p.then(()=>f(b));return p=k.catch(()=>{}),k},f=async b=>{let k=await u(),T;try{T=await d()}catch(D){console.error(`[corsair] Failed to decrypt config for integration "${t}", starting fresh:`,D),T={}}let v={...T};for(let[D,B]of Object.entries(b))B===null?delete v[D]:v[D]=B;let H=De(v,k);await c.updateIntegration({config:H})};return{get_dek:u,issue_new_dek:async()=>{let b=await c.getIntegration(),k=Te(),T={};if(b.dek){let H=await te(b.dek,r),D=b.config;D&&Object.keys(D).length>0&&(T=Zn(D,H,k))}let v=await Pe(k,r);return await c.updateIntegration({config:T,dek:v}),l=k,k},...Xi(d,g,a)}}function U(e){let{authType:n,integrationName:t,tenantId:r,kek:o,database:i,extraAccountFields:a=[],ensureProvisioned:s}=e,c=[...K[n].account,...a],l=null,u=async()=>{if(l)return l;let C=!1;for(;;){let R=await i.db.selectFrom("corsair_integrations").selectAll().where("name","=",t).executeTakeFirst();if(!R){if(!C&&s){C=!0,await s();continue}throw new Error(`Integration "${t}" not found. Make sure to create the integration first.`)}return l={id:R.id,config:qr(R.config),dek:R.dek??null},l}},d={kek:o,integrationName:t,tenantId:r,getIntegration:u,getAccount:async()=>{let C=!1;for(;;){let R=await u(),x=await i.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",r).where("integration_id","=",R.id).executeTakeFirst();if(!x){if(!C&&s){C=!0,await s();continue}throw new Error(`Account not found for tenant "${r}" and integration "${t}". Make sure to create the account first.`)}return{id:x.id,config:qr(x.config),dek:x.dek??null}}},updateAccount:async C=>{let R=await d.getAccount();await i.db.updateTable("corsair_accounts").set({...C.config!==void 0?{config:C.config}:{},...C.dek!==void 0?{dek:C.dek}:{},updated_at:new Date}).where("id","=",R.id).execute()}},p=null,g=null,f=null,h=async()=>{let C=await d.getAccount();if(!C.dek)throw new Error(`No DEK found for account (tenant: "${r}", integration: "${t}"). Initialize the account first.`);return p&&g===C.dek||(p=await te(C.dek,o),g=C.dek),p},b=async()=>{if(f)return f;let C=await d.getIntegration();if(!C.dek)throw new Error(`No DEK found for integration "${t}". Initialize the integration first.`);return f=await te(C.dek,o),f},k=async()=>{let C=await d.getAccount(),R=await h(),x=C.config;return!x||Object.keys(x).length===0?{}:le(x,R)},T=async()=>{let C=await d.getIntegration(),R=await b(),x=C.config;return!x||Object.keys(x).length===0?{}:le(x,R)},v=Promise.resolve(),H=C=>{let R=v.then(()=>D(C));return v=R.catch(()=>{}),R},D=async C=>{let R=await d.getAccount();if(!R.dek)throw new Error(`No DEK found for account (tenant: "${r}", integration: "${t}"). Initialize the account first.`);let x=await te(R.dek,o),ee;try{let q=R.config;ee=!q||Object.keys(q).length===0?{}:le(q,x)}catch(q){console.error(`[corsair] Failed to decrypt config for account (tenant: "${r}", integration: "${t}"), starting fresh:`,q),ee={}}let re={...ee};for(let[q,he]of Object.entries(C))he===null?delete re[q]:re[q]=he;let O=De(re,x);await d.updateAccount({config:O})},B={get_dek:h,issue_new_dek:async()=>{let C=await d.getAccount(),R=Te(),x={};if(C.dek){let re=await te(C.dek,o),O=C.config;O&&Object.keys(O).length>0&&(x=Zn(O,re,R))}let ee=await Pe(R,o);return await d.updateAccount({config:x,dek:ee}),p=R,g=ee,R},...Xi(k,H,c)};return n==="oauth_2"&&(B.get_integration_credentials=async()=>{let C=await T();return{...C,client_id:C.client_id||null,client_secret:C.client_secret||null,redirect_url:C.redirect_url??null}}),B}async function es(e,n,t){let r=await e.db.selectFrom("corsair_integrations").selectAll().where("name","=",n).executeTakeFirst();if(!r)throw new Error(`Integration "${n}" not found.`);let o=Te(),i=await Pe(o,t);return await e.db.updateTable("corsair_integrations").set({dek:i,updated_at:new Date}).where("id","=",r.id).execute(),o}async function ns(e,n,t,r){let o=await e.db.selectFrom("corsair_integrations").selectAll().where("name","=",n).executeTakeFirst();if(!o)throw new Error(`Integration "${n}" not found.`);let i=await e.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",t).where("integration_id","=",o.id).executeTakeFirst();if(!i)throw new Error(`Account not found for tenant "${t}" and integration "${n}".`);let a=Te(),s=await Pe(a,r);return await e.db.updateTable("corsair_accounts").set({dek:s,updated_at:new Date}).where("id","=",i.id).execute(),a}var ru=new Set(["webhook_signature","expires_at","scope","redirect_url","refresh_token"]);function He(e){return ru.has(e)}function ou(e,n){return He(n)?!1:e==="oauth_2"?n==="client_id"||n==="client_secret":!0}function iu(e){return!He(e)}function su(e){switch(e){case"oauth_2":case"managed":return["access_token"];case"api_key":return["api_key"];case"bot_token":return["bot_token"];case"managed_pricing":return[]}}function au(e,n){return e!=="oauth_2"&&e!=="managed"?!1:n.some(t=>t.level==="account"&&t.name==="expires_at"&&t.configured)}function cu(e,n){let t=i=>n.find(a=>a.level==="account"&&a.name===i);if(!su(e).every(i=>t(i)?.configured))return!1;let o=t("refresh_token");return o?.required?!!o.configured:!0}async function ts(e,n){if(!e)return!1;let t=ne(e,`get_${n}`);if(!t)return!1;try{let r=await t();return typeof r=="string"&&r.length>0}catch{return!1}}function uu(e,n){let r=e.authConfig?.[n]?.integration??[];return[...K[n].integration,...r]}function lu(e,n){let r=e.authConfig?.[n]?.account??[];return[...K[n].account,...r]}function du(e,n,t){let r=t.filter(s=>s.required&&!s.configured).map(s=>s.name),o=t.filter(s=>s.level==="integration"&&s.required&&!s.configured).map(s=>s.name),i=t.filter(s=>s.level==="account"&&s.required&&s.configured),a;return o.length>0?a="missing_integration":r.length===0?a="ready":i.length>0?a="partial":a="not_started",{plugin:e,authType:n,status:a,connected:cu(n,t),fields:t,missingRequiredFields:r}}async function Ke(e,n,t){let r=E(n);if(!r||!e.database||!e.kek)return null;let o=t.trim()||"default",i=n.authConfig,a=i?.[r]?.integration??[],s=i?.[r]?.account??[],c=$({authType:r,integrationName:n.id,kek:e.kek,database:e.database,extraIntegrationFields:a}),l=U({authType:r,integrationName:n.id,tenantId:o,kek:e.kek,database:e.database,extraAccountFields:s}),u=uu(n,r),d=lu(n,r),p=[];for(let g of u)p.push({name:g,level:"integration",required:ou(r,g),configured:await ts(c,g)});for(let g of d)p.push({name:g,level:"account",required:iu(g),configured:await ts(l,g)});if(au(r,p)){let g=p.find(f=>f.level==="account"&&f.name==="refresh_token");g&&(g.required=!0)}return du(n.id,r,p)}async function Gn(e,n,t={}){let r=n.trim()||"default",o=t.pluginIds?.length?new Set(t.pluginIds):null,i=[];for(let a of e.plugins){if(o&&!o.has(a.id))continue;let s=await Ke(e,a,r);s&&i.push(s)}return i}function vt(e){return e.connected?"connected":e.status==="missing_integration"?"missing_credentials":"not_connected"}var rs=Symbol.for("corsair:internal"),os=new WeakMap,is=new WeakMap;function pu(e,n){let t=n.map(r=>r.id).sort().join("\0");return`${e}\0${t}`}function gu(e){if(e.database){let t=os.get(e.database);return t||(t=new Map,os.set(e.database,t)),t}let n=is.get(e);return n||(n=new Map,is.set(e,n)),n}function fu(e){return e.multiTenancy?{withTenant:()=>({}),[rs]:e}:{[rs]:e}}async function mn(e,n){if(!e.database)return;let t=n.trim()||"default",r=gu(e),o=pu(t,e.plugins),i=r.get(o);if(i){await i;return}let a=(async()=>{let{setupCorsair:s}=await import("./setup-6TOKKM27.js");await s(fu(e),{tenantId:e.multiTenancy?t:void 0,silent:!0})})().finally(()=>{r.delete(o)});r.set(o,a),await a}import*as zn from"crypto";function Be(e,n){return Buffer.from(JSON.stringify({plugin:e,tenantId:n,iat:Date.now()})).toString("base64url")}function jr(e,{maxAgeMs:n}={}){try{let t=e.includes(".")?e.split(".")[0]:e,r=JSON.parse(Buffer.from(t,"base64url").toString("utf-8"));if(r!==null&&typeof r=="object"&&"plugin"in r&&"tenantId"in r&&typeof r.plugin=="string"&&typeof r.tenantId=="string"){let o=r;return n!==void 0&&typeof o.iat=="number"&&Date.now()-o.iat>n?null:o}return null}catch{return null}}function hn(e,n){if(!n)throw new Error("OAuth state signing requires a configured kek. Pass kek to createCorsair().");let t=zn.createHmac("sha256",n).update(e).digest("base64url");return`${e}.${t}`}var Kr=600*1e3;function Rt(e,n){if(!n)return null;let t=e.lastIndexOf(".");if(t===-1)return null;let r=e.slice(0,t),o=e.slice(t+1),i=zn.createHmac("sha256",n).update(r).digest("base64url"),a=Buffer.from(o,"base64url"),s=Buffer.from(i,"base64url");return a.length!==s.length||!zn.timingSafeEqual(a,s)?null:jr(r,{maxAgeMs:Kr})}function ss(e){return{tenantId:e.tenantId,plugin:e.plugin,authType:e.authType??"oauth_2",status:"ready",connected:!0,verified:!0,webhookLink:e.link}}function as(e){return{tenantId:e.tenantId,plugin:e.plugin,authType:e.authType,status:e.status,connected:e.connected,verified:e.verified,missingFields:e.missingFields,webhookLink:e.webhookLink,webhookSecret:e.webhookSecret}}async function bn(e,n){await _({hub:e,path:"/connections/report",body:ss(n),parseResponse:()=>({ok:!0})}).catch(()=>{})}function yu(e,n){try{let t=N(e);_({hub:t,path:"/connections/report",body:n,parseResponse:()=>({ok:!0})}).catch(()=>{})}catch(t){if(t instanceof Ce)return}}async function mu(e){if(!e.hub||!e.database||!e.kek)return;let n={database:e.database,kek:e.kek,plugins:e.plugins};if(!E(e.plugin))return;let r=e.tenantId?.trim()||"default",o=await Ke(n,e.plugin,r);o&&us(e.hub,as({tenantId:r,plugin:e.plugin.id,authType:o.authType,status:o.status,connected:o.connected,verified:e.verified??o.connected,missingFields:o.missingRequiredFields}))}function cs(e,n){yu(e,n)}function us(e,n){_({hub:e,path:"/connections/report",body:n,parseResponse:()=>({ok:!0})}).catch(()=>{})}function kn(e){mu(e).catch(()=>{})}async function ve(e,n){let t=P(e);if(!E(n.plugin))return;let o=await Ke(t,n.plugin,n.tenantId);o&&cs(e,as({tenantId:n.tenantId.trim()||"default",plugin:n.plugin.id,authType:o.authType,status:o.status,connected:o.connected,verified:n.verified??o.connected,missingFields:o.missingRequiredFields,webhookLink:n.webhookLink,webhookSecret:n.webhookSecret}))}async function At(e,n,t){for(let r of e){if(r.id!==n)continue;let o=r.oauthWebhookTenantLinkResolver;return o?o(t):null}return null}var ls=e=>{if(!e)return{};if(typeof e=="string")try{return JSON.parse(e)}catch{return{}}return e};async function hu(e){let n=await e.database.db.selectFrom("corsair_integrations").selectAll().where("name","=",e.pluginId).executeTakeFirst();if(!n)throw new Error(`Integration '${e.pluginId}' not found. Run setupCorsair before registering webhook tenant links.`);let t=await e.database.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",e.tenantId).where("integration_id","=",n.id).executeTakeFirst();if(!t)throw new Error(`Account not found for tenant '${e.tenantId}' and integration '${e.pluginId}'.`);return{integrationId:n.id,accountId:t.id}}async function bu(e){let n=await e.database.db.selectFrom("corsair_accounts").selectAll().where("id","=",e.accountId).executeTakeFirst();if(!n?.dek)throw new Error(`Account '${e.accountId}' has no DEK.`);let t=await te(n.dek,e.kek),r=ls(n.config),o={};Object.keys(r).length>0&&(o=le(r,t)),o[e.link.linkType]=e.link.externalId;let i=De(o,t);await e.database.db.updateTable("corsair_accounts").set({config:i,updated_at:new Date}).where("id","=",n.id).execute()}async function wn(e){let{database:n,kek:t,pluginId:r,tenantId:o,link:i,authType:a,extraAccountFields:s=[]}=e,{accountId:c}=await hu({database:n,pluginId:r,tenantId:o}),l=!1;if(a){let u=U({authType:a,integrationName:r,tenantId:o,kek:t,database:n,extraAccountFields:s}),d=`set_${i.linkType}`,p=u[d];typeof p=="function"&&(await p(i.externalId),l=!0)}l||await bu({database:n,kek:t,accountId:c,link:i})}async function Zr(e){let{database:n,kek:t,pluginId:r,linkType:o,externalId:i}=e,a=await n.db.selectFrom("corsair_accounts as accounts").innerJoin("corsair_integrations as integrations","integrations.id","accounts.integration_id").selectAll("accounts").where("integrations.name","=",r).execute();for(let s of a)if(s.dek)try{let c=await te(s.dek,t),u=ls(s.config)[o];if(!u)continue;if(Kn(u,c)===i)return s}catch{continue}return null}async function xt(e){return(await Zr(e))?.tenant_id??null}async function ds(e){return xt({database:e.database,kek:e.kek,pluginId:e.pluginId,linkType:e.match.linkType,externalId:e.match.externalId})}import*as ps from"querystring";function Ze(e){let{oauthConfig:n,clientId:t,redirectUri:r,state:o}=e,i={...n.authParams,client_id:t,redirect_uri:r,response_type:"code",scope:n.scopes.join(" "),state:o};return`${n.authUrl}?${ps.stringify(i)}`}async function gs(e,n){try{return await Z({hub:e,path:`/webhooks/endpoint?plugin=${encodeURIComponent(n)}`,parseResponse:t=>t?.url??null})}catch{return null}}async function Cn(e,n,t,r){if(!n.subscribe)return;let o=N(e),i=await gs(o,n.id);if(!i)return;let a=await n.subscribe({keys:r},{webhookUrl:i});a&&await ve(e,{plugin:n,tenantId:t,verified:!0,webhookLink:a.webhookLink,webhookSecret:a.webhookSecret})}var V=class extends Error{code;constructor(n,t){super(t),this.name="OAuthCallbackError",this.code=n}};function fs(e){let n=e.oauthConfig;if(!n)throw new V("plugin_has_no_oauth_config",`Plugin '${e.id}' has no oauthConfig`);return n}async function ku(e,n,t,r){await e.db.transaction().execute(async o=>{let i=o.selectFrom("corsair_integrations").select(["id"]).where("name","=",n);e.isPg===!0&&(i=i.forUpdate());let a=await i.executeTakeFirst();if(!a)throw new Error(`Integration '${n}' not found. Run setupCorsair first.`);if(await o.selectFrom("corsair_accounts").select("id").where("tenant_id","=",t).where("integration_id","=",a.id).executeTakeFirst())return;let c=Te(),l=await Pe(c,r),u=new Date;await o.insertInto("corsair_accounts").values({id:ln(),created_at:u,updated_at:u,tenant_id:t,integration_id:a.id,config:{},dek:l}).execute()})}async function Gr(e,n,t){let{tenantId:r,redirectUri:o,hubConnect:i=!1}=t,a=P(e,()=>new V("invalid_corsair_instance","Invalid corsair instance"));if(!a.database)throw new Error("No database configured on corsair instance");let s=J(a,n,p=>new V("plugin_not_found",p)),c=fs(s),u=await $({authType:"oauth_2",integrationName:n,kek:a.kek,database:a.database}).get_client_id();if(!u)throw new Error(`client_id not configured for '${n}'`);if(i){let p=new URL(Ze({oauthConfig:c,clientId:u,redirectUri:o,state:""}));return p.searchParams.delete("state"),{url:p.toString(),state:""}}let d=hn(Be(n,r),a.kek);return{url:Ze({oauthConfig:c,clientId:u,redirectUri:o,state:d}),state:d}}function wu(e,n){return{...n??{},...e}}async function Jn(e,n){let{code:t,state:r,redirectUri:o}=n,i=P(e,()=>new V("invalid_corsair_instance","Invalid corsair instance")),a,s;if(n.trusted){if(!n.plugin||!n.tenantId)throw new V("invalid_state","trusted callback requires plugin and tenantId");a=n.plugin,s=n.tenantId}else{let h=Rt(r,i.kek);if(!h)throw new V("invalid_state","Invalid or tampered state parameter");a=h.plugin,s=h.tenantId}if(!i.database)throw new V("no_database","No database configured on corsair instance");let c=J(i,a,h=>new V("plugin_not_found",h)),l=fs(c),u=$({authType:"oauth_2",integrationName:a,kek:i.kek,database:i.database}),d=await u.get_client_id(),p=await u.get_client_secret();if(!d||!p)throw new V("credentials_not_configured",`Credentials not configured for '${a}'`);await ku(i.database,a,s,i.kek);let g=await It(t,d,p,l,o);if(!g.access_token)throw new V("no_access_token",`No access_token returned from ${l.providerName}`);let f=U({authType:"oauth_2",integrationName:a,tenantId:s,kek:i.kek,database:i.database,extraAccountFields:[...c.authConfig?.oauth_2?.account??[]]});await f.set_access_token(g.access_token),g.refresh_token&&await f.set_refresh_token(g.refresh_token),g.expires_in&&await f.set_expires_at(String(Math.floor(Date.now()/1e3)+g.expires_in)),await ve(e,{plugin:c,tenantId:s}).catch(()=>{});try{let h=wu(g,n.callbackParams),b=await At(i.plugins,a,h);if(b){try{let k=c.authConfig?.oauth_2?.account??[];await wn({database:i.database,kek:i.kek,pluginId:a,tenantId:s,link:b,authType:"oauth_2",extraAccountFields:k})}catch(k){console.warn(`[corsair:oauth] Failed to persist webhook tenant link for '${a}' tenant '${s}':`,k)}i.hub&&bn(i.hub,{plugin:a,tenantId:s,link:b,authType:"oauth_2"})}}catch(h){console.warn(`[corsair:oauth] Failed to resolve webhook tenant link for '${a}' tenant '${s}':`,h)}if(c.subscribe)try{await Cn(e,c,s,f)}catch(h){console.warn(`[corsair:oauth] BYO subscribe failed for '${a}' tenant '${s}':`,h)}return{plugin:a,tenantId:s}}async function Cu(e){let{corsair:n,internal:t,rows:r}=e,o=e.subscribeAndReport??Cn,i=[],a=[];if(!t.database)return{renewed:i,failed:a};for(let s of r){let c=t.plugins.find(u=>u.id===s.integrationName);if(!c?.subscribe)continue;let l=`${c.id}/${s.tenantId}`;try{let u=E(c)??"oauth_2",d=U({authType:u,integrationName:c.id,tenantId:s.tenantId,kek:t.kek,database:t.database,extraAccountFields:[...c.authConfig?.[u]?.account??[]]}),p=c.keyBuilder;if(p){let g=Object.create(d,{get_expires_at:{value:async()=>"0"}});await p({authType:u,keys:g,hub:t.hub},"endpoint")}await o(n,c,s.tenantId,d),i.push(l)}catch(u){console.warn(`[corsair:renewal] re-subscribe failed for '${l}':`,u),a.push(l)}}return{renewed:i,failed:a}}async function ys(e){let n=P(e);if(!n.database)return{renewed:[],failed:[]};let t=await n.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.tenant_id as tenantId","i.name as integrationName"]).where("a.dek","is not",null).execute();return Cu({corsair:e,internal:n,rows:t.filter(r=>!!r.tenantId)})}function Tu(e,n={}){let t=!1,r=()=>{t||(t=!0,ys(e).catch(i=>console.warn("[corsair:renewal] renewal pass failed:",i)).finally(()=>{t=!1}))};r();let o=setInterval(r,(n.intervalMinutes??45)*6e4);return o.unref?.(),()=>clearInterval(o)}async function ms(e){if(!P(e).database)throw new Error("A database must be configured to provision Corsair integrations");await St(e,{silent:!0})}async function Tn(e,n){let t=P(e);if(!t.database)throw new Error("A database must be configured to provision Corsair for connect");await mn(t,n)}var Pu=Symbol.for("corsair:internal"),vu=new Set(["access_token","refresh_token","expires_at","scope"]);function Ru(e){return e==="oauth_2"||e==="managed"?"oauth":e==="bot_token"?"bot_token":"api_key"}function Au(e,n){return e==="oauth_2"||e==="managed"?n.filter(t=>!He(t)&&!vu.has(t)):n.filter(t=>!He(t))}function hs(e){return{plugins:e.plugins,database:e.database,kek:e.kek,multiTenancy:e.multiTenancy??!1}}function xu(e){return{plugins:e.plugins,database:e.database,kek:e.kek,multiTenancy:e.multiTenancy??!1}}function Iu(e){return{[Pu]:hs(e)}}async function _t(e,n,t={}){let r=wt(e.hub),o=[],i=t.pluginIds?new Set(t.pluginIds):null,a=hs(e),s=Iu(e);for(let c of e.plugins){if(i&&!i.has(c.id))continue;let l=E(c);if(!l)continue;let u=Ru(l),d=t.providerNameOverrides?.[c.id]??Ee(c.id),p=await Ke(a,c,n),g=lt(c,l),f=Au(l,g),h={plugin:c.id,providerName:d,authKind:u,alreadyConfigured:p?.connected??!1};if(f.length>0&&(h.credentialFields=f),u==="oauth"){let k=t.oauthModeOverrides?.[c.id]??(l==="managed"?"managed":"byo");if(h.oauthMode=k,!t.skipOAuthUrlGeneration&&k!=="managed")try{let T=await Gr(s,c.id,{tenantId:n,redirectUri:r,hubConnect:!0});h.oauthUrl=T.url}catch(T){T instanceof Error&&/client_id not configured/i.test(T.message)||(h.setupError=T instanceof Error?T.message:`Could not prepare OAuth for ${c.id}`)}}o.push(h)}return o}async function uy(e,n,t={}){let r=P(e),o=r.hub;if(!o)throw new Error("Hub is not configured");return _t({plugins:r.plugins,database:r.database,kek:r.kek,hub:o},n,t)}async function bs(e,n){if(!e.database)throw new Error("A database must be configured to provision Corsair for connect");await mn(e.internalConfig??xu(e),n)}async function ks(e,n){await Tn(e,n)}async function ws(e,n){let t=yn(e.projectApiKey),r={tenantId:n.tenantId,plugins:n.plugins};return e.redirectURL&&(r.redirectUri=e.redirectURL),t==="development"&&(r.deliveryUrl=Se({deliveryUrl:n.deliveryUrl})),_({hub:e,path:"/connect/sessions",notFoundMessage:"Hub REST API not found at /connect/sessions. Check HUB_API_URL and ensure the Hub API is deployed.",body:r,parseResponse:pt})}async function Cs(e,n){let t={plugins:n.plugins,database:n.database,kek:n.kek,hub:e,multiTenancy:n.multiTenancy};await bs(t,n.tenantId);let r=await _t(t,n.tenantId,{pluginIds:[n.plugin.id]});if(r.length===0)throw new Error(`Plugin '${n.plugin.id}' is not configured on this Corsair instance`);return ws(e,{tenantId:n.tenantId,plugins:r,deliveryUrl:n.deliveryUrl})}async function Et(e,n){let t=P(e),r=N(e),o={plugins:t.plugins,database:t.database,kek:t.kek,hub:r,multiTenancy:t.multiTenancy,internalConfig:t};await ks(e,n.tenantId);let i=n.plugin?[n.plugin]:void 0,a=n.plugin&&n.oauthMode?{[n.plugin]:n.oauthMode}:void 0,s=n.plugin&&n.providerName?{[n.plugin]:n.providerName}:void 0,c=await _t(o,n.tenantId,{pluginIds:i,oauthModeOverrides:a,providerNameOverrides:s});if(c.length===0)throw new Error(n.plugin?`Plugin '${n.plugin}' is not configured on this Corsair instance`:"No plugins are configured on this Corsair instance");return ws(r,{tenantId:n.tenantId,plugins:c,deliveryUrl:n.deliveryUrl})}async function Ot(e,n){let t=n.tenantId.trim();if(!t)throw new Error("tenantId is required");let r=n.plugins.map(a=>a.trim()).filter(Boolean);if(r.length===0)throw new Error("At least one plugin is required");let o=P(e);if(!o.hub)throw new Error("Hub is not configured on this Corsair instance");if(!o.database)throw new Error("Database not configured");let i=await Su(o.hub,{plugins:o.plugins,database:o.database,kek:o.kek,multiTenancy:o.multiTenancy},{tenantId:t,pluginIds:r});return{connectUrl:i.connectUrl,expiresAt:i.expiresAt}}async function Su(e,n,t){let{buildConnectPluginManifestFromContext:r,ensureConnectAccountRowsFromContext:o}=await import("./setup-introspect-ZISM2BO7.js"),{postHubConnectSession:i}=await import("./connect-4AJ2WF6T.js"),a={plugins:n.plugins,database:n.database,kek:n.kek,hub:e,multiTenancy:n.multiTenancy};await o(a,t.tenantId);let s=await r(a,t.tenantId,{pluginIds:t.pluginIds});if(s.length===0)throw new Error("No connectable plugins found for this tenant");let c=s.find(l=>l.setupError);if(c)throw new Error(c.setupError??`Could not prepare connect link for ${c.plugin}`);return i(e,{tenantId:t.tenantId,plugins:s})}function Pn(e){return!!(e?.baseUrl?.trim()&&e?.redirectUri?.trim())}var ie=class extends Error{code;constructor(n,t){super(t),this.name="ConnectError",this.code=n}};function _u(e){let n=e.oauthConfig;if(!n)throw new ie("plugin_has_no_oauth_config",`Plugin '${e.id}' has no oauthConfig`);return n}async function zr(e,n){let t=P(e,()=>new ie("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new ie("no_database","No database configured on corsair instance");let r=t.manual?.redirectUri;if(!r)throw new ie("no_redirect_uri","No redirectUri configured. Set manual.redirectUri in createCorsair().");let o=Rt(n,t.kek);if(!o)throw new ie("invalid_state","Invalid or tampered state parameter");let{plugin:i,tenantId:a}=o,s=J(t,i,p=>new ie("plugin_not_found",p)),c=_u(s),u=await $({authType:"oauth_2",integrationName:i,kek:t.kek,database:t.database}).get_client_id();if(!u)throw new ie("client_id_not_configured",`client_id not configured for '${i}'`);let d=Ze({oauthConfig:c,clientId:u,redirectUri:r,state:n});return{plugin:i,tenantId:a,providerName:c.providerName,oauthUrl:d,state:n}}import{AsyncLocalStorage as Ou}from"async_hooks";import{randomBytes as Mu}from"crypto";import{v4 as Du}from"uuid";var de=class extends Error{reason;constructor(n,t="pending"){super(n),Object.setPrototypeOf(this,new.target.prototype),this.name="PermissionRequiredError",this.reason=t}};async function Mt(e,n){let t=yn(e.projectApiKey),r={permissionId:n.permissionId,permissionToken:n.permissionToken,plugin:n.plugin,endpoint:n.endpoint,args:n.args,tenantId:n.tenantId,expiresAt:n.expiresAt};return e.redirectURL&&(r.redirectUri=e.redirectURL),t==="development"&&(r.deliveryUrl=Se({deliveryUrl:n.deliveryUrl})),_({hub:e,path:"/permission/sessions",notFoundMessage:"Hub REST API not found at /permission/sessions. Check HUB_API_URL and ensure the Hub API is deployed.",body:r,parseResponse:ft})}function Dt(e){return`Approval required. Visit ${e} to approve or deny, then tell the agent to retry this action.`}var Jr="Permission approval required. Set manual.approvalBaseUrl (or use hub for hosted approval) so an approval URL can be generated. Optionally set manual.onApprovalRequired to customize the agent message.";function Yr(e){return e?e.approvalBaseUrl!==void 0||e.onApprovalRequired!==void 0:!1}function Ts(e,n){return`${e.replace(/\/+$/,"")}/${n}`}function Vr(e){return Dt(e)}async function Qr(e,n){if(Yr(e.manual)){let r=e.manual?.approvalBaseUrl?.trim();return r?Ts(r,n.token):null}let t=e.hub;if(!t)return null;try{return(await Mt(t,{permissionId:n.id,permissionToken:n.token,plugin:n.plugin,endpoint:n.endpoint,args:Eu(n.args),tenantId:n.tenant_id,expiresAt:n.expires_at})).approvalUrl}catch(r){return console.warn(`[corsair/${n.plugin}] could not create an approval link for '${n.endpoint}': ${r instanceof Error?r.message:String(r)}`),null}}function Eu(e){try{return JSON.parse(e)}catch{return e}}async function Ht(e,n){if(!(n.status==="pending"||n.status==="approved"))return{...n,approvalUrl:null};let r=await Qr(e,n);return{...n,approvalUrl:r}}async function Xr(e){let{permissionsOptions:n,manual:t,hub:r,permissionId:o,permissionToken:i,plugin:a,endpoint:s,args:c,tenantId:l,expiresAt:u,operationPath:d}=e;if(n?.formatAsyncMessage)return n.formatAsyncMessage({token:i,id:o,plugin:a,endpoint:s,args:c});let g=await Qr({manual:t,hub:r},{id:o,token:i,plugin:a,endpoint:s,args:JSON.stringify(c),tenant_id:l,expires_at:u});return Yr(t)?g?t?.onApprovalRequired?t.onApprovalRequired({approvalUrl:g}):Vr(g):Jr:r?g?Vr(g):`Action '${d}' requires user approval before it can run. Could not create approval link. Check hub configuration and server logs.`:Jr}var Bt=new Ou,Ps={open:0,cautious:1,strict:2,readonly:3},vn=class extends Error{endpointPath;riskLevel;constructor(n,t){super(`Action '${n}' is a '${t}' operation and is forbidden in readonly mode. Only read operations are permitted \u2014 rewrite the script to avoid write/destructive actions.`),this.name="ReadonlyForbiddenError",this.endpointPath=n,this.riskLevel=t}};function eo(e,n){return e===void 0?n:n===void 0||Ps[e]>=Ps[n]?e:n}function Ut(e,n){return Bt.run(eo(Bt.getStore(),e)??e,n)}function Rn(){return Bt.getStore()}function no(e){return Ut("readonly",e)}function As(){return Bt.getStore()==="readonly"}function Lt(e,n){if(As()&&n!=="read")throw new vn(e,n)}function Ge(e,n){Lt(e,n);let t=Rn();if(!(t===void 0||Ft(n,t)==="allow"))throw new de(`Action '${e}' is a '${n}' operation and permission mode '${t}' does not allow it. The entity store cannot wait for approval.`,"policy")}var Hu={open:{read:"allow",write:"allow",destructive:"allow"},cautious:{read:"allow",write:"allow",destructive:"require_approval"},strict:{read:"allow",write:"require_approval",destructive:"deny"},readonly:{read:"allow",write:"deny",destructive:"deny"}},vs={allow:0,require_approval:1,deny:2};function xs(e,n){return e===void 0?n:vs[e]>=vs[n]?e:n}function Ft(e,n,t){return t!==void 0?t:Hu[n][e]}function to(e){let n=/(\d+)(d|h|m|s)/g,t=0,r;for(;(r=n.exec(e))!==null;){let o=parseInt(r[1],10);switch(r[2]){case"d":t+=o*864e5;break;case"h":t+=o*36e5;break;case"m":t+=o*6e4;break;case"s":t+=o*1e3;break}}return t>0?t:600*1e3}function Is(e){return{async find_by_permission_id(n){if(e)return e.db.selectFrom("corsair_permissions").selectAll().where("id","=",n).executeTakeFirst()},async find_by_token(n){if(e)return e.db.selectFrom("corsair_permissions").selectAll().where("token","=",n).executeTakeFirst()},async set_executing(n){e&&await e.db.updateTable("corsair_permissions").set({status:"executing",updated_at:new Date}).where("id","=",n).execute()},async set_completed(n){e&&await e.db.updateTable("corsair_permissions").set({status:"completed",updated_at:new Date}).where("id","=",n).execute()}}}async function Rs(e,n,t){let r=Date.now()+t;for(;Date.now()<r;){let o=await e.db.selectFrom("corsair_permissions").select(["id","status"]).where("id","=",n).executeTakeFirst();if(!o)return{result:"blocked",reason:"pending"};if(o.status==="approved")return{result:"allow",onComplete:async()=>{await e.db.updateTable("corsair_permissions").set({status:"completed",updated_at:new Date}).where("id","=",n).execute()}};if(o.status==="denied")return{result:"blocked",reason:"denied"};if(o.status==="expired"||o.status==="failed")return{result:"blocked",reason:"timeout"};await new Promise(i=>setTimeout(i,500))}return{result:"blocked",reason:"timeout"}}async function Ss(e){let n=Ft(e.riskLevel,e.mode,e.override);if(n==="allow")return{result:"allow"};let t=e.meta?.irreversible?" (irreversible)":"",r=e.meta?.description?`${e.meta.description}${t}`:`${e.pluginId}.${e.endpointPath}${t}`;if(n==="deny"||!e.db)return console.log(`[corsair/${e.pluginId}] '${e.endpointPath}' blocked \u2014 denied by permission mode '${e.mode}'.`,`
|
|
10
10
|
Action: ${r}`,`
|
|
11
11
|
To allow this, widen the permission mode in force for this call.`),{result:"blocked",reason:"policy"};let o=JSON.stringify(e.args),i=new Date().toISOString(),a=e.tenantId??"default",s=await e.db.db.selectFrom("corsair_permissions").selectAll().where("plugin","=",e.pluginId).where("endpoint","=",e.endpointPath).where("args","=",o).where("tenant_id","=",a).where("expires_at",">",i).where("status","in",["pending","approved","executing"]).orderBy("created_at","desc").limit(1).executeTakeFirst();if(s){if(s.status==="approved"){let f=e.db,h=s.id;return{result:"allow",onComplete:async()=>{await f.db.updateTable("corsair_permissions").set({status:"completed",updated_at:new Date}).where("id","=",h).execute()}}}return s.status==="executing"?{result:"allow"}:(console.log(`[corsair/${e.pluginId}] '${e.endpointPath}' blocked \u2014 approval already pending.`,`
|
|
12
12
|
Action: ${r}`,`
|
|
@@ -16,7 +16,7 @@ import{a as Se,b as _r,c as Er}from"./chunk-6IURNA4L.js";import{a as Ri,b as Ai,
|
|
|
16
16
|
Permission ID: ${c}`,`
|
|
17
17
|
Permission token: ${l}`,`
|
|
18
18
|
Expires at: ${d}`,`
|
|
19
|
-
Use the token to approve or deny this request.`),(typeof e.approvalMode=="function"?e.approvalMode():e.approvalMode)==="synchronous"?Rs(e.db,c,u):{result:"blocked",reason:"pending",id:c,token:l,expiresAt:d}}var w=class extends Error{status;code;extra;constructor(n,t,r,o={}){super(r??t),this.name="ManagementApiError",this.status=n,this.code=t,this.extra=o}};function I(e,n,t){return new Response(JSON.stringify(n),{status:e,headers:{"content-type":"application/json",...t}})}function pe(e){let n={error:e.code,message:e.message,...e.extra};return I(e.status,n)}function Ue(e){return new w(404,"not_found",e)}function L(e,n={}){return new w(400,"bad_request",e,n)}function ro(e,n){return J(e,n,t=>Ue(t))}async function _s(e,n){let t=e.options?.authType;if(!t||!n.database||!n.kek)return{configured:!1,missingFields:[]};let r=$({authType:t,integrationName:e.id,kek:n.kek,database:n.database}),o=K[t].integration,i=r,a;try{a=await Promise.all(o.map(l=>i[`get_${l}`]()))}catch{a=o.map(()=>null)}let s=o.filter((l,u)=>a[u]==null),c;return t==="oauth_2"?c=!s.includes("client_id")&&!s.includes("client_secret"):c=s.length===0,{configured:c,missingFields:s}}async function Es(e,n){let t=e.options?.authType??null,r=e.oauthConfig,{configured:o,missingFields:i}=await _s(e,n);return{id:e.id,authType:t,configured:o,missingFields:i,oauth:r?{providerName:r.providerName,scopes:r.scopes,requiresRegisteredRedirect:!!r.requiresRegisteredRedirect}:null}}function Nt(){return{ok:!0}}async function An(e){return Promise.all(e.plugins.map(n=>Es(n,e)))}async function $t(e,n){let t=ro(e,n);return Es(t,e)}async function Bu(e,n){return e.database?(await e.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.id as accountId","a.dek as dek","i.name as integrationName"]).where("a.tenant_id","=",n).execute()).map(r=>({integrationName:r.integrationName,hasCredentials:!!r.dek})):[]}async function Os(e,n){let t=await Bu(e,n),r=t.filter(o=>o.hasCredentials).map(o=>o.integrationName);return{id:n,accounts:t,connectedPlugins:r}}async function xn(e){let n=new Map;if(n.set("default",{id:"default",accounts:[],connectedPlugins:[]}),e.database){let t=await e.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.tenant_id","a.dek as dek","i.name as integrationName"]).execute();for(let r of t){let o=r.tenant_id;if(!o)continue;let i=n.get(o);i||(i={id:o,accounts:[],connectedPlugins:[]},n.set(o,i));let a=!!r.dek;i.accounts.push({integrationName:r.integrationName,hasCredentials:a}),a&&i.connectedPlugins.push(r.integrationName)}}return[...n.values()]}async function Wt(e,n){if(!n)throw L("Tenant id must be a non-empty string");return Os(e,n)}async function qt(e,n){let t=n?.id?.trim();if(!t)throw L("Tenant id is required",{missingFields:["id"]});return Os(e,t)}async function jt(e,n){let t=n?.trim()||"default",r={},o=await Gn(e,t);for(let i of o)r[i.plugin]=vt(i);for(let i of e.plugins)i.id in r||(!i.options?.authType||!e.database||!e.kek?r[i.id]="missing_credentials":r[i.id]="not_connected");return r}async function Kt(e,n){let t=n?.plugin;if(typeof t!="string"||!t.trim())throw L("plugin is required",{missingFields:["plugin"]});let r=t.trim();ro(e,r);let o=n?.tenantId;if(o!=null&&typeof o!="string")throw L("tenantId must be a string");let i=o?.trim()||"default";if(!e.database)return{ok:!0,disconnected:!1};let a=e.database.db,s=await a.selectFrom("corsair_integrations").select(["id"]).where("name","=",r).executeTakeFirst();if(!s)return{ok:!0,disconnected:!1};let c=!1;return await a.transaction().execute(async l=>{e.database?.isPg===!0&&await l.selectFrom("corsair_integrations").select("id").where("name","=",r).forUpdate().execute();let u=l.selectFrom("corsair_accounts").select("id").where("tenant_id","=",i).where("integration_id","=",s.id);await l.deleteFrom("corsair_events").where("account_id","in",u).execute(),await l.deleteFrom("corsair_entities").where("account_id","in",u).execute(),c=((await l.deleteFrom("corsair_accounts").where("tenant_id","=",i).where("integration_id","=",s.id).executeTakeFirst()).numDeletedRows??0n)>0n}),{ok:!0,disconnected:c}}async function oo(e,n){if(!e.database)throw Ue(`Permission '${n}' not found`);let t=await e.database.db.selectFrom("corsair_permissions").selectAll().where("id","=",n).executeTakeFirst();if(!t)throw Ue(`Permission '${n}' not found`);return Ht(e,t)}function Uu(e){if(!e.oauthConfig)throw L(`Plugin '${e.id}' has no oauthConfig`)}function Lu(e){if(!e.manual)throw new w(500,"connect_not_configured","createCorsair was not given manual config. Set { manual: { baseUrl, redirectUri } } to enable manual connect routes.");return e.manual}function io(e){let n=Lu(e);if(!n.baseUrl?.trim()||!n.redirectUri?.trim())throw new w(500,"connect_not_configured","Manual connect requires manual.baseUrl and manual.redirectUri. Use hub for hosted connect, or set both URLs for manual OAuth.");return n}function Fu(e){let n=!!e.hub,t=Pn(e.manual);if(!n&&!t)throw new w(500,"connect_not_configured","createCorsair was not given connect config. Set hub: { ... } for Hub mode, or manual: { baseUrl, redirectUri } for manual connect.")}function Ms(e){if(!e.database||!e.kek)throw new w(500,"database_not_configured","A database and kek are required to issue connect links.")}async function Nu(e,n){let t=n?.plugin?.trim();if(!t)throw L("Plugin id is required",{missingFields:["plugin"]});let r=n.tenantId?.trim()||"default",o=ro(e,t);Uu(o);let i=io(e);Ms(e);let a=await _s(o,e);if(!a.configured)throw new w(400,"missing_credentials",`Plugin '${t}' is missing OAuth client credentials`,{missingFields:a.missingFields});let s=hn(Be(t,r),e.kek),c;try{c=new URL(i.baseUrl)}catch{throw new w(500,"connect_misconfigured","manual.baseUrl is not a valid URL. Set a full URL including protocol (e.g. https://app.example.com/connect).")}return c.searchParams.set("state",s),{connectUrl:c.toString(),expiresAt:new Date(Date.now()+Kr).toISOString(),tenantId:r}}async function $u(e,n,t){Ms(n);let r=t.tenantId?.trim()||"default",o={tenantId:r,oauthMode:t.oauthMode},i=t.plugin?.trim();i&&(o.plugin=i);let a=t.providerName?.trim();a&&(o.providerName=a);let s=await Et(e,o);return{connectUrl:s.connectUrl,expiresAt:s.expiresAt,tenantId:r}}async function Zt(e,n,t){return Fu(n),n.hub?$u(e,n,t):Nu(n,t)}async function Gt(e,n,t){if(n.hub&&!Pn(n.manual))throw new w(400,"hub_mode","resolve is not used with hub config. Redirect users to connectUrl from createLink.");let r=t?.trim();if(!r)throw L("state is required",{missingFields:["state"]});io(n);try{return await zr(e,r)}catch(o){if(o instanceof ie)switch(o.code){case"invalid_state":throw L("Invalid or expired state");case"client_id_not_configured":throw new w(400,"missing_credentials","OAuth client_id is not configured for this plugin",{missingFields:["client_id"]});case"no_redirect_uri":break}throw new w(500,"resolve_failed","Could not resolve connect link. Check server logs for details.")}}async function zt(e,n,t){if(n.hub&&!Pn(n.manual))throw new w(400,"hub_mode","oauthCallback is not used with hub config. Hub delivers tokens to your deliveryUrl.");let r=t?.code?.trim(),o=t?.state?.trim(),i=[];if(r||i.push("code"),o||i.push("state"),i.length)throw L("Missing required fields",{missingFields:i});let a=io(n),{processOAuthCallback:s}=await import("./oauth.js");try{return await s(e,{code:r,state:o,redirectUri:a.redirectUri,callbackParams:t.callbackParams})}catch(c){if(c instanceof Error&&c.name==="OAuthCallbackError")switch(c.code){case"invalid_state":throw L("Invalid or expired state");case"credentials_not_configured":throw new w(400,"missing_credentials","OAuth client credentials are not configured for this plugin",{missingFields:["client_id","client_secret"]})}throw new w(502,"oauth_callback_failed","OAuth callback did not complete. Check server logs for details.")}}async function so(e,n){if(!e.database)throw Ue("Permission not found");let t=await e.database.db.selectFrom("corsair_permissions").selectAll().where("token","=",n).executeTakeFirst();if(!t)throw Ue("Permission not found");return Ht(e,t)}async function Ds(e,n){return"id"in n?oo(e,n.id):so(e,n.token)}import{createCipheriv as Ju,createDecipheriv as ym,randomBytes as Ls,scryptSync as Vu}from"crypto";import{createHmac as ao,randomUUID as Wu,timingSafeEqual as Bs}from"crypto";function co(e){return e.run??null}function uo(e){return e.probe??null}function Us(e){if(e)return e.startsWith("sha256=")?e.slice(7):e}function Jt(e){let n=JSON.stringify({type:e.type,payload:e.payload}),t=Math.floor(Date.now()/1e3).toString(),r=ao("sha256",e.signingSecret.trim()).update(n).digest("hex");return{body:n,headers:{"content-type":"application/json","x-corsair-signature":`sha256=${r}`,"x-corsair-timestamp":t,"x-corsair-project":e.projectId,"x-corsair-nonce":Wu()}}}function lo(e){let n=e.signingSecret.trim();if(!n)return!1;let t=Us(e.signatureHeader);if(!t)return!1;let r=Number(e.timestampHeader);if(!Number.isFinite(r)||Math.abs(Date.now()-r*1e3)>We)return!1;let i=ao("sha256",n).update(e.body).digest("hex");try{return Bs(Buffer.from(i,"utf8"),Buffer.from(t,"utf8"))}catch{return!1}}function In(e){let n=e.signingSecret.trim();if(!n)return{ok:!1,error:"Tunnel signing secret is required"};let t=Us(e.signatureHeader);if(!t)return{ok:!1,error:"Invalid tunnel signature"};let r=Number(e.timestampHeader);if(!Number.isFinite(r))return{ok:!1,error:"Invalid or missing tunnel timestamp"};if(Math.abs(Date.now()-r*1e3)>We)return{ok:!1,error:"Tunnel request timestamp is outside the allowed window"};let i=ao("sha256",n).update(e.body).digest("hex");try{if(!Bs(Buffer.from(i,"utf8"),Buffer.from(t,"utf8")))return{ok:!1,error:"Invalid tunnel signature"}}catch{return{ok:!1,error:"Invalid tunnel signature"}}return{ok:!0}}function Sn(e){if(!e)return{};try{return JSON.parse(e)}catch{return{}}}function Vt(e){return e.httpOk&&(e.status===204||e.body.status==="ok"||e.body.ok===!0)}function Yt(e){let n=e.sync?.encrypted;return typeof n!="string"||!n.trim()?null:{encrypted:n.trim()}}function Vn(e){let n=e.connectUrl?.trim();return n?{connectUrl:n,expiresAt:e.expiresAt}:null}function po(e){return Vn(Sn(e))}async function go(e){let n=await er({deliveryUrl:e.deliveryUrl,projectId:e.projectId,signingSecret:e.signingSecret,type:"connect.create_link",payload:{tenantId:e.tenantId,plugins:e.plugins}}),t=Sn(n.body),r=Vt({httpOk:n.ok,status:n.status,body:t}),o=Vn(t);if(!r||!o)throw new Error(Xt({deliveryUrl:e.deliveryUrl,status:n.status,body:n.body,ack:t}));return o}function Qt(e){return Yt(Sn(e))}function qu(e){let n=e;for(;n;){if(n instanceof Error){let t=n.code;if(typeof t=="string")return t;n=n.cause;continue}if(typeof n=="object"&&n!==null&&"code"in n){let t=n.code;if(typeof t=="string")return t}break}}function Hs(e,n=200){let t=e.trim();return t.length<=n?t:`${t.slice(0,n)}\u2026`}var ju="Verify hub.signingSecret in your app matches the signing secret shown in Hub project settings.",Ku="Check the delivery URL configured for this environment.";function Zu(e){return`${e.ack.error?`${e.ack.error} (HTTP ${e.status} from ${e.deliveryUrl})`:`App rejected the signed delivery (HTTP ${e.status} from ${e.deliveryUrl})`}. ${ju}`}function Gu(e){return`${e.ack.error?`${e.ack.error} (HTTP 404 from ${e.deliveryUrl})`:`Delivery endpoint not found at ${e.deliveryUrl} (HTTP 404)`}. ${Ku}`}function Yn(e,n){let t=qu(n),r=n instanceof Error?n.message:"Delivery request failed",o;switch(t){case"ECONNREFUSED":o="connection refused \u2014 nothing accepted a TCP connection on that host and port";break;case"ENOTFOUND":o="host not found \u2014 DNS could not resolve the hostname";break;case"ETIMEDOUT":case"UND_ERR_CONNECT_TIMEOUT":o="connection timed out before the app responded";break;case"ECONNRESET":o="connection reset while talking to the app";break;case"CERT_HAS_EXPIRED":case"UNABLE_TO_VERIFY_LEAF_SIGNATURE":case"DEPTH_ZERO_SELF_SIGNED_CERT":o=`TLS certificate error (${t})`;break;default:o=r==="fetch failed"&&t?`${r} (${t})`:r}return[`Could not reach ${e}`,o].join(". ")}function Xt(e){if(e.status===0)return e.ack.error?e.ack.error:e.body.startsWith("Could not reach")?e.body:Yn(e.deliveryUrl,new Error(e.body||"Delivery request failed"));if(e.status===401||e.status===403)return Zu(e);if(e.status===404)return Gu(e);if(e.ack.error)return`${e.ack.error} (HTTP ${e.status} from ${e.deliveryUrl})`;if(e.status>=500){let t=e.body.trim();return t?`App failed while processing the delivery (HTTP ${e.status} from ${e.deliveryUrl}): ${Hs(t)}`:`App failed while processing the delivery (HTTP ${e.status} from ${e.deliveryUrl})`}let n=e.body.trim();return n?`${Hs(n)} (HTTP ${e.status} from ${e.deliveryUrl})`:`Delivery failed with HTTP ${e.status} from ${e.deliveryUrl}`}var zu=15e3;async function er(e){let{body:n,headers:t}=Jt(e);try{let r=await fetch(e.deliveryUrl,{method:"POST",headers:t,body:n,signal:AbortSignal.timeout(zu)}),o=await r.text();return{ok:r.ok,status:r.status,body:o}}catch(r){return{ok:!1,status:0,body:Yn(e.deliveryUrl,r)}}}var Yu="aes-256-gcm",Qu=12,Xu=16,el=16,nl=32;function tl(e,n){return Vu(e.trim(),n,nl)}function fo(e,n){let t=n.trim();if(!t)throw new Error("Signing secret is required to encrypt sync manifest");let r=Ls(el),o=tl(t,r),i=Ls(Qu),a=Ju(Yu,o,i,{authTagLength:Xu}),s=JSON.stringify(e),c=Buffer.concat([a.update(s,"utf8"),a.final()]),l=a.getAuthTag();return[r.toString("base64"),i.toString("base64"),l.toString("base64"),c.toString("base64")].join(":")}var rl=["invalid corsair instance","a database must be configured to sync connections from the app","a database must be configured on the corsair instance","signing secret is required to encrypt sync manifest"];function yo(e){if(e instanceof _i)return!1;if(!(e instanceof Error))return!0;let n=e.message.toLowerCase();return!rl.some(t=>n.includes(t))}function ol(e){if(!e)return[];let n=O(e);return n?(e.authConfig?.[n]?.integration??[]).filter(r=>!He(r)):[]}async function Qn(e,n){let t=P(e);if(!t.database)throw new Error("A database must be configured to sync connections from the app");await St(e,{silent:!0});let[r,o]=await Promise.all([xn(t),An(t)]),i={tenants:r.map(a=>({id:a.id})),plugins:o.map(a=>{let s=ol(t.plugins.find(c=>c.id===a.id));return{id:a.id,authType:a.authType,configured:a.configured,missingFields:a.missingFields,...s.length>0?{integrationCredentialFields:s}:{}}}),syncedAt:new Date().toISOString()};return fo(i,n)}var ge=class extends Error{code;constructor(n,t){super(t),this.name="AuthCredentialsDeliveryError",this.code=n}};async function nr(e,n){let t=P(e,()=>new ge("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new ge("no_database","Database not configured");let r=J(t,n.plugin,u=>new ge("plugin_not_found",u)),o=O(r);if(!o)throw new ge("invalid_credentials",`Plugin '${r.id}' has no authType configured`);if(o==="oauth_2"||o==="managed")throw new ge("invalid_credentials","OAuth plugins must be connected via sign-in, not credentials delivery");await Tn(e,n.tenantId);let i=new Set(lt(r,o)),s=r.authConfig?.[o]?.account??[],c=U({authType:o,integrationName:n.plugin,tenantId:n.tenantId,kek:t.kek,database:t.database,extraAccountFields:s}),l=0;for(let[u,d]of Object.entries(n.credentials)){if(!d.trim())continue;if(!i.has(u))throw new ge("invalid_credentials",`Unknown credential field '${u}' for plugin '${n.plugin}'`);let p=ne(c,`set_${u}`);if(!p)throw new ge("invalid_credentials",`Cannot set credential field '${u}' for plugin '${n.plugin}'`);await p(d.trim()),l+=1}if(l===0)throw new ge("invalid_credentials","Provide at least one credential field to save");return await ve(e,{plugin:r,tenantId:n.tenantId}).catch(()=>{}),{plugin:n.plugin,tenantId:n.tenantId}}var fe=class extends Error{code;constructor(n,t){super(t),this.name="IntegrationCredentialsDeliveryError",this.code=n}};async function mo(e,n){let t=P(e,()=>new fe("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new fe("no_database","Database not configured");let r=J(t,n.plugin,u=>new fe("plugin_not_found",u)),o=O(r);if(!o)throw new fe("invalid_credentials",`Plugin '${r.id}' has no authType configured`);await ms(e);let i=new Set(Di(r,o)),s=r.authConfig?.[o]?.integration??[],c=$({authType:o,integrationName:n.plugin,kek:t.kek,database:t.database,extraIntegrationFields:s}),l=0;for(let[u,d]of Object.entries(n.credentials)){if(!d.trim())continue;if(!i.has(u))throw new fe("invalid_credentials",`Unknown integration credential field '${u}' for plugin '${n.plugin}'`);let p=ne(c,`set_${u}`);if(!p)throw new fe("invalid_credentials",`Cannot set integration field '${u}' for plugin '${n.plugin}'`);await p(d.trim()),l+=1}if(l===0)throw new fe("invalid_credentials","Provide at least one integration credential field to save");return{plugin:n.plugin}}var tr=new Map;function il(e){for(let[n,t]of tr)t<=e&&tr.delete(n)}function rr(e,n){let t=e.trim();if(!t)return{ok:!1,error:"Delivery replay key is required"};if(!Number.isFinite(n)||n<=0)return{ok:!1,error:"Delivery replay TTL must be a positive number"};let r=Date.now();il(r);let o=tr.get(t);return o!==void 0&&o>r?{ok:!1,error:"Delivery request already consumed"}:(tr.set(t,r+n),{ok:!0})}var Le=class extends Error{code;constructor(n,t){super(t),this.name="ManagedOAuthDeliveryError",this.code=n}};async function _n(e,n){let{plugin:t,tenantId:r,accessToken:o,refreshToken:i,expiresIn:a,scope:s,authType:c="managed",providerData:l}=n;if(!o.trim())throw new Le("no_access_token","Managed OAuth delivery missing access_token");let u=P(e,()=>new Le("invalid_corsair_instance","Invalid corsair instance"));if(!u.database)throw new Le("no_database","No database configured on corsair instance");let d=J(u,t,g=>new Le("plugin_not_found",g));await Tn(e,r);let p=U({authType:c,integrationName:t,tenantId:r,kek:u.kek,database:u.database});await p.set_access_token(o),i&&await p.set_refresh_token(i),a&&await p.set_expires_at(String(Math.floor(Date.now()/1e3)+a)),s&&await p.set_scope(s),await ve(e,{plugin:d,tenantId:r}).catch(()=>{});try{let g=await At(u.plugins,t,{access_token:o,refresh_token:i,scope:s,...l});if(g){try{let f=d.authConfig?.[c]?.account??[];await wn({database:u.database,kek:u.kek,pluginId:t,tenantId:r,link:g,authType:c,extraAccountFields:f})}catch(f){console.warn(`[corsair:managed-oauth] Failed to persist webhook tenant link for '${t}' tenant '${r}':`,f)}u.hub&&bn(u.hub,{plugin:t,tenantId:r,link:g,authType:c})}}catch(g){console.warn(`[corsair:managed-oauth] Failed to resolve webhook tenant link for '${t}' tenant '${r}':`,g)}return await Cn(e,d,r,p).catch(g=>{console.warn(`[corsair:managed-oauth] subscribe failed for '${t}' tenant '${r}':`,g)}),{plugin:t,tenantId:r}}function sl(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function Fs(e,n,t=[]){for(let[r,o]of Object.entries(e))if(sl(o)){if(o.match(n))return{webhook:o,path:[...t,r]}}else if(o&&typeof o=="object"){let i=Fs(o,n,[...t,r]);if(i)return i}return null}function al(e){let n={};for(let[t,r]of Object.entries(e))n[t.toLowerCase()]=Array.isArray(r)?r[0]:r;return n}function cl(e){let n=e["x-goog-resource-uri"],t=e["x-goog-channel-id"];if(!n||!t)return null;let r={resourceId:e["x-goog-resource-id"]||"",resourceState:e["x-goog-resource-state"]||"",resourceUri:n,channelId:t,channelExpiration:e["x-goog-channel-expiration"]||""};return n.includes("/drive/")&&(r.kind="drive#change"),{message:{data:Buffer.from(JSON.stringify(r)).toString("base64"),messageId:e["x-goog-message-number"]||""}}}async function Ns(e,n,t,r,o){let i=al(n),a=typeof t=="string"?JSON.parse(t):t;(!a||typeof a=="object"&&Object.keys(a).length===0)&&i["x-goog-resource-uri"]&&(a=cl(i)||a);let c={headers:i,body:a,...r?{query:r}:{}},l=r?.tenantId||"default",u=e.withTenant?e.withTenant(l):e,d=o?.plugin,p=d?[d]:dt;for(let g of p){let f=u[g];if(!f||!f.webhooks||!d&&f.pluginWebhookMatcher&&!f.pluginWebhookMatcher(c))continue;let h=Fs(f.webhooks,c);if(!h)continue;let b=h.path.join("."),k={payload:a,headers:i,rawBody:typeof t=="string"?t:JSON.stringify(t),...r?{query:r}:{},...o?.hubVerified?{hubVerified:!0}:{}};try{let T=await h.webhook.handler(k),v=!!Object.keys(T.returnToSender||{})?.length;return{plugin:g,action:b,body:a,response:v?{...T?.returnToSender,success:!0}:{success:!0},...T.responseHeaders&&{responseHeaders:T.responseHeaders}}}catch(T){return console.error(`Error executing webhook handler for ${g}.${b}:`,T),{plugin:g,action:b,body:a,response:{success:!1,error:T instanceof Error?T.message:"Unknown error"}}}}return{plugin:null,action:null,body:null}}import{createHash as ul}from"crypto";import*as ze from"vm";var $s="__corsairFailedStep",ll=3e4,ho=class{constructor(n,t){this.wakeAt=n;this.stepName=t}__corsairSleep=!0};function Ws(e){return typeof e=="object"&&e!==null&&e.__corsairSleep===!0}function qs(e,n){return`st_${ul("sha256").update(`${n} ${e}`).digest("hex").slice(0,16)}`}function or(e){if(e instanceof Error)return e.message;if(e!==null&&typeof e=="object"&&"message"in e){let n=e.message;if(typeof n=="string")return n}return String(e)}var js=new Set(["constructor","prototype","__proto__"]);function Re(e,n){if(e===null)return null;let t=typeof e;return t==="function"?pl(e,n):t==="object"?dl(e):e}function dl(e){return new Proxy(e,{get(n,t){if(!js.has(t))return Re(Reflect.get(n,t,n),n)},getPrototypeOf:()=>null,setPrototypeOf:()=>!1,defineProperty:()=>!1,set:()=>!1,deleteProperty:()=>!1})}function pl(e,n){return new Proxy(e,{apply:(t,r,o)=>gl(Reflect.apply(t,n,o)),construct(){throw new Error("Workflow code may not construct host objects")},get(t,r){if(!js.has(r))return Re(Reflect.get(t,r,t),t)},getPrototypeOf:()=>null,setPrototypeOf:()=>!1,defineProperty:()=>!1,set:()=>!1,deleteProperty:()=>!1})}function gl(e){return e!==null&&typeof e=="object"&&typeof e.then=="function"?Promise.resolve(e).then(n=>Re(n,void 0),n=>{throw Re(n,void 0)}):Re(e,void 0)}function fl(e){let n=Object.create(null),t=ze.createContext(n,{name:"corsair-workflow",codeGeneration:{strings:!1,wasm:!1}}),o=ze.runInContext("(s) => JSON.parse(s)",t,{filename:"corsair:sandbox:json"})(JSON.stringify(e.payload??null)),a=ze.runInContext(`(function (hostRun, hostSleep) {
|
|
19
|
+
Use the token to approve or deny this request.`),(typeof e.approvalMode=="function"?e.approvalMode():e.approvalMode)==="synchronous"?Rs(e.db,c,u):{result:"blocked",reason:"pending",id:c,token:l,expiresAt:d}}var w=class extends Error{status;code;extra;constructor(n,t,r,o={}){super(r??t),this.name="ManagementApiError",this.status=n,this.code=t,this.extra=o}};function I(e,n,t){return new Response(JSON.stringify(n),{status:e,headers:{"content-type":"application/json",...t}})}function pe(e){let n={error:e.code,message:e.message,...e.extra};return I(e.status,n)}function Ue(e){return new w(404,"not_found",e)}function L(e,n={}){return new w(400,"bad_request",e,n)}function ro(e,n){return J(e,n,t=>Ue(t))}async function _s(e,n){let t=e.options?.authType;if(!t||!n.database||!n.kek)return{configured:!1,missingFields:[]};let r=$({authType:t,integrationName:e.id,kek:n.kek,database:n.database}),o=K[t].integration,i=r,a;try{a=await Promise.all(o.map(l=>i[`get_${l}`]()))}catch{a=o.map(()=>null)}let s=o.filter((l,u)=>a[u]==null),c;return t==="oauth_2"?c=!s.includes("client_id")&&!s.includes("client_secret"):c=s.length===0,{configured:c,missingFields:s}}async function Es(e,n){let t=e.options?.authType??null,r=e.oauthConfig,{configured:o,missingFields:i}=await _s(e,n);return{id:e.id,authType:t,configured:o,missingFields:i,oauth:r?{providerName:r.providerName,scopes:r.scopes,requiresRegisteredRedirect:!!r.requiresRegisteredRedirect}:null}}function Nt(){return{ok:!0}}async function An(e){return Promise.all(e.plugins.map(n=>Es(n,e)))}async function $t(e,n){let t=ro(e,n);return Es(t,e)}async function Bu(e,n){return e.database?(await e.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.id as accountId","a.dek as dek","i.name as integrationName"]).where("a.tenant_id","=",n).execute()).map(r=>({integrationName:r.integrationName,hasCredentials:!!r.dek})):[]}async function Os(e,n){let t=await Bu(e,n),r=t.filter(o=>o.hasCredentials).map(o=>o.integrationName);return{id:n,accounts:t,connectedPlugins:r}}async function xn(e){let n=new Map;if(n.set("default",{id:"default",accounts:[],connectedPlugins:[]}),e.database){let t=await e.database.db.selectFrom("corsair_accounts as a").innerJoin("corsair_integrations as i","i.id","a.integration_id").select(["a.tenant_id","a.dek as dek","i.name as integrationName"]).execute();for(let r of t){let o=r.tenant_id;if(!o)continue;let i=n.get(o);i||(i={id:o,accounts:[],connectedPlugins:[]},n.set(o,i));let a=!!r.dek;i.accounts.push({integrationName:r.integrationName,hasCredentials:a}),a&&i.connectedPlugins.push(r.integrationName)}}return[...n.values()]}async function Wt(e,n){if(!n)throw L("Tenant id must be a non-empty string");return Os(e,n)}async function qt(e,n){let t=n?.id?.trim();if(!t)throw L("Tenant id is required",{missingFields:["id"]});return Os(e,t)}async function jt(e,n){let t=n?.trim()||"default",r={},o=await Gn(e,t);for(let i of o)r[i.plugin]=vt(i);for(let i of e.plugins)i.id in r||(!i.options?.authType||!e.database||!e.kek?r[i.id]="missing_credentials":r[i.id]="not_connected");return r}async function Kt(e,n){let t=n?.plugin;if(typeof t!="string"||!t.trim())throw L("plugin is required",{missingFields:["plugin"]});let r=t.trim();ro(e,r);let o=n?.tenantId;if(o!=null&&typeof o!="string")throw L("tenantId must be a string");let i=o?.trim()||"default";if(!e.database)return{ok:!0,disconnected:!1};let a=e.database.db,s=await a.selectFrom("corsair_integrations").select(["id"]).where("name","=",r).executeTakeFirst();if(!s)return{ok:!0,disconnected:!1};let c=!1;return await a.transaction().execute(async l=>{e.database?.isPg===!0&&await l.selectFrom("corsair_integrations").select("id").where("name","=",r).forUpdate().execute();let u=l.selectFrom("corsair_accounts").select("id").where("tenant_id","=",i).where("integration_id","=",s.id);await l.deleteFrom("corsair_events").where("account_id","in",u).execute(),await l.deleteFrom("corsair_entities").where("account_id","in",u).execute(),c=((await l.deleteFrom("corsair_accounts").where("tenant_id","=",i).where("integration_id","=",s.id).executeTakeFirst()).numDeletedRows??0n)>0n}),{ok:!0,disconnected:c}}async function oo(e,n){if(!e.database)throw Ue(`Permission '${n}' not found`);let t=await e.database.db.selectFrom("corsair_permissions").selectAll().where("id","=",n).executeTakeFirst();if(!t)throw Ue(`Permission '${n}' not found`);return Ht(e,t)}function Uu(e){if(!e.oauthConfig)throw L(`Plugin '${e.id}' has no oauthConfig`)}function Lu(e){if(!e.manual)throw new w(500,"connect_not_configured","createCorsair was not given manual config. Set { manual: { baseUrl, redirectUri } } to enable manual connect routes.");return e.manual}function io(e){let n=Lu(e);if(!n.baseUrl?.trim()||!n.redirectUri?.trim())throw new w(500,"connect_not_configured","Manual connect requires manual.baseUrl and manual.redirectUri. Use hub for hosted connect, or set both URLs for manual OAuth.");return n}function Fu(e){let n=!!e.hub,t=Pn(e.manual);if(!n&&!t)throw new w(500,"connect_not_configured","createCorsair was not given connect config. Set hub: { ... } for Hub mode, or manual: { baseUrl, redirectUri } for manual connect.")}function Ms(e){if(!e.database||!e.kek)throw new w(500,"database_not_configured","A database and kek are required to issue connect links.")}async function Nu(e,n){let t=n?.plugin?.trim();if(!t)throw L("Plugin id is required",{missingFields:["plugin"]});let r=n.tenantId?.trim()||"default",o=ro(e,t);Uu(o);let i=io(e);Ms(e);let a=await _s(o,e);if(!a.configured)throw new w(400,"missing_credentials",`Plugin '${t}' is missing OAuth client credentials`,{missingFields:a.missingFields});let s=hn(Be(t,r),e.kek),c;try{c=new URL(i.baseUrl)}catch{throw new w(500,"connect_misconfigured","manual.baseUrl is not a valid URL. Set a full URL including protocol (e.g. https://app.example.com/connect).")}return c.searchParams.set("state",s),{connectUrl:c.toString(),expiresAt:new Date(Date.now()+Kr).toISOString(),tenantId:r}}async function $u(e,n,t){Ms(n);let r=t.tenantId?.trim()||"default",o={tenantId:r,oauthMode:t.oauthMode},i=t.plugin?.trim();i&&(o.plugin=i);let a=t.providerName?.trim();a&&(o.providerName=a);let s=await Et(e,o);return{connectUrl:s.connectUrl,expiresAt:s.expiresAt,tenantId:r}}async function Zt(e,n,t){return Fu(n),n.hub?$u(e,n,t):Nu(n,t)}async function Gt(e,n,t){if(n.hub&&!Pn(n.manual))throw new w(400,"hub_mode","resolve is not used with hub config. Redirect users to connectUrl from createLink.");let r=t?.trim();if(!r)throw L("state is required",{missingFields:["state"]});io(n);try{return await zr(e,r)}catch(o){if(o instanceof ie)switch(o.code){case"invalid_state":throw L("Invalid or expired state");case"client_id_not_configured":throw new w(400,"missing_credentials","OAuth client_id is not configured for this plugin",{missingFields:["client_id"]});case"no_redirect_uri":break}throw new w(500,"resolve_failed","Could not resolve connect link. Check server logs for details.")}}async function zt(e,n,t){if(n.hub&&!Pn(n.manual))throw new w(400,"hub_mode","oauthCallback is not used with hub config. Hub delivers tokens to your deliveryUrl.");let r=t?.code?.trim(),o=t?.state?.trim(),i=[];if(r||i.push("code"),o||i.push("state"),i.length)throw L("Missing required fields",{missingFields:i});let a=io(n),{processOAuthCallback:s}=await import("./oauth.js");try{return await s(e,{code:r,state:o,redirectUri:a.redirectUri,callbackParams:t.callbackParams})}catch(c){if(c instanceof Error&&c.name==="OAuthCallbackError")switch(c.code){case"invalid_state":throw L("Invalid or expired state");case"credentials_not_configured":throw new w(400,"missing_credentials","OAuth client credentials are not configured for this plugin",{missingFields:["client_id","client_secret"]})}throw new w(502,"oauth_callback_failed","OAuth callback did not complete. Check server logs for details.")}}async function so(e,n){if(!e.database)throw Ue("Permission not found");let t=await e.database.db.selectFrom("corsair_permissions").selectAll().where("token","=",n).executeTakeFirst();if(!t)throw Ue("Permission not found");return Ht(e,t)}async function Ds(e,n){return"id"in n?oo(e,n.id):so(e,n.token)}import{createCipheriv as Ju,createDecipheriv as ym,randomBytes as Ls,scryptSync as Vu}from"crypto";import{createHmac as ao,randomUUID as Wu,timingSafeEqual as Bs}from"crypto";function co(e){return e.run??null}function uo(e){return e.probe??null}function Us(e){if(e)return e.startsWith("sha256=")?e.slice(7):e}function Jt(e){let n=JSON.stringify({type:e.type,payload:e.payload}),t=Math.floor(Date.now()/1e3).toString(),r=ao("sha256",e.signingSecret.trim()).update(n).digest("hex");return{body:n,headers:{"content-type":"application/json","x-corsair-signature":`sha256=${r}`,"x-corsair-timestamp":t,"x-corsair-project":e.projectId,"x-corsair-nonce":Wu()}}}function lo(e){let n=e.signingSecret.trim();if(!n)return!1;let t=Us(e.signatureHeader);if(!t)return!1;let r=Number(e.timestampHeader);if(!Number.isFinite(r)||Math.abs(Date.now()-r*1e3)>We)return!1;let i=ao("sha256",n).update(e.body).digest("hex");try{return Bs(Buffer.from(i,"utf8"),Buffer.from(t,"utf8"))}catch{return!1}}function In(e){let n=e.signingSecret.trim();if(!n)return{ok:!1,error:"Tunnel signing secret is required"};let t=Us(e.signatureHeader);if(!t)return{ok:!1,error:"Invalid tunnel signature"};let r=Number(e.timestampHeader);if(!Number.isFinite(r))return{ok:!1,error:"Invalid or missing tunnel timestamp"};if(Math.abs(Date.now()-r*1e3)>We)return{ok:!1,error:"Tunnel request timestamp is outside the allowed window"};let i=ao("sha256",n).update(e.body).digest("hex");try{if(!Bs(Buffer.from(i,"utf8"),Buffer.from(t,"utf8")))return{ok:!1,error:"Invalid tunnel signature"}}catch{return{ok:!1,error:"Invalid tunnel signature"}}return{ok:!0}}function Sn(e){if(!e)return{};try{return JSON.parse(e)}catch{return{}}}function Vt(e){return e.httpOk&&(e.status===204||e.body.status==="ok"||e.body.ok===!0)}function Yt(e){let n=e.sync?.encrypted;return typeof n!="string"||!n.trim()?null:{encrypted:n.trim()}}function Vn(e){let n=e.connectUrl?.trim();return n?{connectUrl:n,expiresAt:e.expiresAt}:null}function po(e){return Vn(Sn(e))}async function go(e){let n=await er({deliveryUrl:e.deliveryUrl,projectId:e.projectId,signingSecret:e.signingSecret,type:"connect.create_link",payload:{tenantId:e.tenantId,plugins:e.plugins}}),t=Sn(n.body),r=Vt({httpOk:n.ok,status:n.status,body:t}),o=Vn(t);if(!r||!o)throw new Error(Xt({deliveryUrl:e.deliveryUrl,status:n.status,body:n.body,ack:t}));return o}function Qt(e){return Yt(Sn(e))}function qu(e){let n=e;for(;n;){if(n instanceof Error){let t=n.code;if(typeof t=="string")return t;n=n.cause;continue}if(typeof n=="object"&&n!==null&&"code"in n){let t=n.code;if(typeof t=="string")return t}break}}function Hs(e,n=200){let t=e.trim();return t.length<=n?t:`${t.slice(0,n)}\u2026`}var ju="Verify hub.signingSecret in your app matches the signing secret shown in Hub project settings.",Ku="Check the delivery URL configured for this environment.";function Zu(e){return`${e.ack.error?`${e.ack.error} (HTTP ${e.status} from ${e.deliveryUrl})`:`App rejected the signed delivery (HTTP ${e.status} from ${e.deliveryUrl})`}. ${ju}`}function Gu(e){return`${e.ack.error?`${e.ack.error} (HTTP 404 from ${e.deliveryUrl})`:`Delivery endpoint not found at ${e.deliveryUrl} (HTTP 404)`}. ${Ku}`}function Yn(e,n){let t=qu(n),r=n instanceof Error?n.message:"Delivery request failed",o;switch(t){case"ECONNREFUSED":o="connection refused \u2014 nothing accepted a TCP connection on that host and port";break;case"ENOTFOUND":o="host not found \u2014 DNS could not resolve the hostname";break;case"ETIMEDOUT":case"UND_ERR_CONNECT_TIMEOUT":o="connection timed out before the app responded";break;case"ECONNRESET":o="connection reset while talking to the app";break;case"CERT_HAS_EXPIRED":case"UNABLE_TO_VERIFY_LEAF_SIGNATURE":case"DEPTH_ZERO_SELF_SIGNED_CERT":o=`TLS certificate error (${t})`;break;default:o=r==="fetch failed"&&t?`${r} (${t})`:r}return[`Could not reach ${e}`,o].join(". ")}function Xt(e){if(e.status===0)return e.ack.error?e.ack.error:e.body.startsWith("Could not reach")?e.body:Yn(e.deliveryUrl,new Error(e.body||"Delivery request failed"));if(e.status===401||e.status===403)return Zu(e);if(e.status===404)return Gu(e);if(e.ack.error)return`${e.ack.error} (HTTP ${e.status} from ${e.deliveryUrl})`;if(e.status>=500){let t=e.body.trim();return t?`App failed while processing the delivery (HTTP ${e.status} from ${e.deliveryUrl}): ${Hs(t)}`:`App failed while processing the delivery (HTTP ${e.status} from ${e.deliveryUrl})`}let n=e.body.trim();return n?`${Hs(n)} (HTTP ${e.status} from ${e.deliveryUrl})`:`Delivery failed with HTTP ${e.status} from ${e.deliveryUrl}`}var zu=15e3;async function er(e){let{body:n,headers:t}=Jt(e);try{let r=await fetch(e.deliveryUrl,{method:"POST",headers:t,body:n,signal:AbortSignal.timeout(zu)}),o=await r.text();return{ok:r.ok,status:r.status,body:o}}catch(r){return{ok:!1,status:0,body:Yn(e.deliveryUrl,r)}}}var Yu="aes-256-gcm",Qu=12,Xu=16,el=16,nl=32;function tl(e,n){return Vu(e.trim(),n,nl)}function fo(e,n){let t=n.trim();if(!t)throw new Error("Signing secret is required to encrypt sync manifest");let r=Ls(el),o=tl(t,r),i=Ls(Qu),a=Ju(Yu,o,i,{authTagLength:Xu}),s=JSON.stringify(e),c=Buffer.concat([a.update(s,"utf8"),a.final()]),l=a.getAuthTag();return[r.toString("base64"),i.toString("base64"),l.toString("base64"),c.toString("base64")].join(":")}var rl=["invalid corsair instance","a database must be configured to sync connections from the app","a database must be configured on the corsair instance","signing secret is required to encrypt sync manifest"];function yo(e){if(e instanceof _i)return!1;if(!(e instanceof Error))return!0;let n=e.message.toLowerCase();return!rl.some(t=>n.includes(t))}function ol(e){if(!e)return[];let n=E(e);return n?(e.authConfig?.[n]?.integration??[]).filter(r=>!He(r)):[]}async function Qn(e,n){let t=P(e);if(!t.database)throw new Error("A database must be configured to sync connections from the app");await St(e,{silent:!0});let[r,o]=await Promise.all([xn(t),An(t)]),i={tenants:r.map(a=>({id:a.id})),plugins:o.map(a=>{let s=ol(t.plugins.find(c=>c.id===a.id));return{id:a.id,authType:a.authType,configured:a.configured,missingFields:a.missingFields,...s.length>0?{integrationCredentialFields:s}:{}}}),syncedAt:new Date().toISOString()};return fo(i,n)}var ge=class extends Error{code;constructor(n,t){super(t),this.name="AuthCredentialsDeliveryError",this.code=n}};async function nr(e,n){let t=P(e,()=>new ge("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new ge("no_database","Database not configured");let r=J(t,n.plugin,u=>new ge("plugin_not_found",u)),o=E(r);if(!o)throw new ge("invalid_credentials",`Plugin '${r.id}' has no authType configured`);if(o==="oauth_2"||o==="managed")throw new ge("invalid_credentials","OAuth plugins must be connected via sign-in, not credentials delivery");await Tn(e,n.tenantId);let i=new Set(lt(r,o)),s=r.authConfig?.[o]?.account??[],c=U({authType:o,integrationName:n.plugin,tenantId:n.tenantId,kek:t.kek,database:t.database,extraAccountFields:s}),l=0;for(let[u,d]of Object.entries(n.credentials)){if(!d.trim())continue;if(!i.has(u))throw new ge("invalid_credentials",`Unknown credential field '${u}' for plugin '${n.plugin}'`);let p=ne(c,`set_${u}`);if(!p)throw new ge("invalid_credentials",`Cannot set credential field '${u}' for plugin '${n.plugin}'`);await p(d.trim()),l+=1}if(l===0)throw new ge("invalid_credentials","Provide at least one credential field to save");return await ve(e,{plugin:r,tenantId:n.tenantId}).catch(()=>{}),{plugin:n.plugin,tenantId:n.tenantId}}var fe=class extends Error{code;constructor(n,t){super(t),this.name="IntegrationCredentialsDeliveryError",this.code=n}};async function mo(e,n){let t=P(e,()=>new fe("invalid_corsair_instance","Invalid corsair instance"));if(!t.database)throw new fe("no_database","Database not configured");let r=J(t,n.plugin,u=>new fe("plugin_not_found",u)),o=E(r);if(!o)throw new fe("invalid_credentials",`Plugin '${r.id}' has no authType configured`);await ms(e);let i=new Set(Di(r,o)),s=r.authConfig?.[o]?.integration??[],c=$({authType:o,integrationName:n.plugin,kek:t.kek,database:t.database,extraIntegrationFields:s}),l=0;for(let[u,d]of Object.entries(n.credentials)){if(!d.trim())continue;if(!i.has(u))throw new fe("invalid_credentials",`Unknown integration credential field '${u}' for plugin '${n.plugin}'`);let p=ne(c,`set_${u}`);if(!p)throw new fe("invalid_credentials",`Cannot set integration field '${u}' for plugin '${n.plugin}'`);await p(d.trim()),l+=1}if(l===0)throw new fe("invalid_credentials","Provide at least one integration credential field to save");return{plugin:n.plugin}}var tr=new Map;function il(e){for(let[n,t]of tr)t<=e&&tr.delete(n)}function rr(e,n){let t=e.trim();if(!t)return{ok:!1,error:"Delivery replay key is required"};if(!Number.isFinite(n)||n<=0)return{ok:!1,error:"Delivery replay TTL must be a positive number"};let r=Date.now();il(r);let o=tr.get(t);return o!==void 0&&o>r?{ok:!1,error:"Delivery request already consumed"}:(tr.set(t,r+n),{ok:!0})}var Le=class extends Error{code;constructor(n,t){super(t),this.name="ManagedOAuthDeliveryError",this.code=n}};async function _n(e,n){let{plugin:t,tenantId:r,accessToken:o,refreshToken:i,expiresIn:a,scope:s,authType:c="managed",providerData:l}=n;if(!o.trim())throw new Le("no_access_token","Managed OAuth delivery missing access_token");let u=P(e,()=>new Le("invalid_corsair_instance","Invalid corsair instance"));if(!u.database)throw new Le("no_database","No database configured on corsair instance");let d=J(u,t,g=>new Le("plugin_not_found",g));await Tn(e,r);let p=U({authType:c,integrationName:t,tenantId:r,kek:u.kek,database:u.database});await p.set_access_token(o),i&&await p.set_refresh_token(i),a&&await p.set_expires_at(String(Math.floor(Date.now()/1e3)+a)),s&&await p.set_scope(s),await ve(e,{plugin:d,tenantId:r}).catch(()=>{});try{let g=await At(u.plugins,t,{access_token:o,refresh_token:i,scope:s,...l});if(g){try{let f=d.authConfig?.[c]?.account??[];await wn({database:u.database,kek:u.kek,pluginId:t,tenantId:r,link:g,authType:c,extraAccountFields:f})}catch(f){console.warn(`[corsair:managed-oauth] Failed to persist webhook tenant link for '${t}' tenant '${r}':`,f)}u.hub&&bn(u.hub,{plugin:t,tenantId:r,link:g,authType:c})}}catch(g){console.warn(`[corsair:managed-oauth] Failed to resolve webhook tenant link for '${t}' tenant '${r}':`,g)}return await Cn(e,d,r,p).catch(g=>{console.warn(`[corsair:managed-oauth] subscribe failed for '${t}' tenant '${r}':`,g)}),{plugin:t,tenantId:r}}function sl(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function Fs(e,n,t=[]){for(let[r,o]of Object.entries(e))if(sl(o)){if(o.match(n))return{webhook:o,path:[...t,r]}}else if(o&&typeof o=="object"){let i=Fs(o,n,[...t,r]);if(i)return i}return null}function al(e){let n={};for(let[t,r]of Object.entries(e))n[t.toLowerCase()]=Array.isArray(r)?r[0]:r;return n}function cl(e){let n=e["x-goog-resource-uri"],t=e["x-goog-channel-id"];if(!n||!t)return null;let r={resourceId:e["x-goog-resource-id"]||"",resourceState:e["x-goog-resource-state"]||"",resourceUri:n,channelId:t,channelExpiration:e["x-goog-channel-expiration"]||""};return n.includes("/drive/")&&(r.kind="drive#change"),{message:{data:Buffer.from(JSON.stringify(r)).toString("base64"),messageId:e["x-goog-message-number"]||""}}}async function Ns(e,n,t,r,o){let i=al(n),a=typeof t=="string"?JSON.parse(t):t;(!a||typeof a=="object"&&Object.keys(a).length===0)&&i["x-goog-resource-uri"]&&(a=cl(i)||a);let c={headers:i,body:a,...r?{query:r}:{}},l=r?.tenantId||"default",u=e.withTenant?e.withTenant(l):e,d=o?.plugin,p=d?[d]:dt;for(let g of p){let f=u[g];if(!f||!f.webhooks||!d&&f.pluginWebhookMatcher&&!f.pluginWebhookMatcher(c))continue;let h=Fs(f.webhooks,c);if(!h)continue;let b=h.path.join("."),k={payload:a,headers:i,rawBody:typeof t=="string"?t:JSON.stringify(t),...r?{query:r}:{},...o?.hubVerified?{hubVerified:!0}:{}};try{let T=await h.webhook.handler(k),v=!!Object.keys(T.returnToSender||{})?.length;return{plugin:g,action:b,body:a,response:v?{...T?.returnToSender,success:!0}:{success:!0},...T.responseHeaders&&{responseHeaders:T.responseHeaders}}}catch(T){return console.error(`Error executing webhook handler for ${g}.${b}:`,T),{plugin:g,action:b,body:a,response:{success:!1,error:T instanceof Error?T.message:"Unknown error"}}}}return{plugin:null,action:null,body:null}}import{createHash as ul}from"crypto";import*as ze from"vm";var $s="__corsairFailedStep",ll=3e4,ho=class{constructor(n,t){this.wakeAt=n;this.stepName=t}__corsairSleep=!0};function Ws(e){return typeof e=="object"&&e!==null&&e.__corsairSleep===!0}function qs(e,n){return`st_${ul("sha256").update(`${n} ${e}`).digest("hex").slice(0,16)}`}function or(e){if(e instanceof Error)return e.message;if(e!==null&&typeof e=="object"&&"message"in e){let n=e.message;if(typeof n=="string")return n}return String(e)}var js=new Set(["constructor","prototype","__proto__"]);function Re(e,n){if(e===null)return null;let t=typeof e;return t==="function"?pl(e,n):t==="object"?dl(e):e}function dl(e){return new Proxy(e,{get(n,t){if(!js.has(t))return Re(Reflect.get(n,t,n),n)},getPrototypeOf:()=>null,setPrototypeOf:()=>!1,defineProperty:()=>!1,set:()=>!1,deleteProperty:()=>!1})}function pl(e,n){return new Proxy(e,{apply:(t,r,o)=>gl(Reflect.apply(t,n,o)),construct(){throw new Error("Workflow code may not construct host objects")},get(t,r){if(!js.has(r))return Re(Reflect.get(t,r,t),t)},getPrototypeOf:()=>null,setPrototypeOf:()=>!1,defineProperty:()=>!1,set:()=>!1,deleteProperty:()=>!1})}function gl(e){return e!==null&&typeof e=="object"&&typeof e.then=="function"?Promise.resolve(e).then(n=>Re(n,void 0),n=>{throw Re(n,void 0)}):Re(e,void 0)}function fl(e){let n=Object.create(null),t=ze.createContext(n,{name:"corsair-workflow",codeGeneration:{strings:!1,wasm:!1}}),o=ze.runInContext("(s) => JSON.parse(s)",t,{filename:"corsair:sandbox:json"})(JSON.stringify(e.payload??null)),a=ze.runInContext(`(function (hostRun, hostSleep) {
|
|
20
20
|
const step = function step(name, fn) { return hostRun(name, fn); };
|
|
21
21
|
step.sleep = function sleep(name, ms) { return hostSleep(name, ms); };
|
|
22
22
|
return step;
|
|
@@ -44,13 +44,13 @@ const __result = await (async () => {
|
|
|
44
44
|
${e.code}
|
|
45
45
|
})();
|
|
46
46
|
return JSON.stringify(__result) ?? 'null';
|
|
47
|
-
})()`;try{let i=await no(()=>{let a=ir.runInContext(o,t,{filename:"corsair:probe",timeout:r});a.catch(()=>{});let s,c=new Promise((l,u)=>{s=setTimeout(()=>u(new Error(`Probe exceeded ${r}ms time limit`)),r)});return Promise.race([a,c]).finally(()=>clearTimeout(s))});return{status:"ok",value:yl(i)}}catch(i){return{status:"error",error:or(i)}}}function yl(e){if(typeof e!="string")throw new Error(`Probe returned a non-string result (${typeof e})`);return JSON.parse(e)}function ml(e){return typeof e!="number"||!Number.isFinite(e)||e<=0?Ks:Math.min(e,Ks)}function Je(e){return e.deliveryMode==="auth.credentials"}function Xn(e){return e.deliveryMode==="connections.sync"}function sr(e){return e.deliveryMode==="connect.create_link"}function et(e){return e.deliveryMode==="permission.approve"||e.deliveryMode==="permission.deny"}function nt(e){return e.deliveryMode==="oauth.tokens"}function ar(e){return e.deliveryMode==="oauth.callback"||e.deliveryMode===void 0&&!Je(e)&&!Xn(e)&&!sr(e)&&!et(e)&&!nt(e)}function hl(e){return{status:"ok",connectLink:{connectUrl:e.connectUrl,expiresAt:e.expiresAt},webhookResponse:{status:200,body:{status:"ok",connectUrl:e.connectUrl,expiresAt:e.expiresAt}}}}async function bl(e,n){try{return{status:"ok",webhookResponse:{status:200,body:{status:"ok",sync:{encrypted:await Qn(e,n)}}}}}catch(t){return{status:"failed",retryable:yo(t),error:t instanceof Error?t.message:"Connections sync delivery failed"}}}async function kl(e,n){try{let t=await Ot(e,n);return hl(t)}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Connect link delivery failed"}}}function wo(e,n){if(e instanceof Headers)return e.get(n)??void 0;let t=e[n]??e[n.toLowerCase()];return Array.isArray(t)?t[0]:typeof t=="string"?t:void 0}async function wl(e,n,t){let r=typeof t.tenantId=="string"?t.tenantId:typeof t.query?.tenantId=="string"?t.query.tenantId:void 0;return r||(!n.database||!t.plugin||!t.linkType||!t.externalId?void 0:await xt({database:n.database,kek:n.kek,pluginId:t.plugin,linkType:t.linkType,externalId:t.externalId})??void 0)}async function Cl(e,n,t,r){let o=await wl(e,n,t),i={...t.query??{},...o?{tenantId:o}:{}},a=await Ns(e,t.headers,t.body,i,{plugin:t.plugin,hubVerified:r&&t.hubVerified===!0});if(!a.plugin)return{status:"failed",retryable:!1,error:"No matching webhook handler found"};if(a.response&&a.response.success===!1)return{status:"failed",retryable:!1,error:typeof a.response.error=="string"?a.response.error:"Webhook handler failed"};let s=a.response?.returnToSender,c=s&&typeof s=="object"&&typeof s.validationToken=="string"&&Object.keys(s).length===1?s.validationToken:s||(a.response?.data??a.response);return{status:"ok",webhookResponse:{status:a.response?.statusCode??200,body:c,headers:a.responseHeaders}}}async function Tl(e,n){return await Jn(e,{code:n.code,state:n.state,redirectUri:n.redirectUri,callbackParams:n.callbackParams,...n.plugin&&n.tenantId?{trusted:!0,plugin:n.plugin,tenantId:n.tenantId}:{}}),{status:"ok"}}async function Pl(e,n){return await _n(e,{plugin:n.plugin,tenantId:n.tenantId,accessToken:n.accessToken,refreshToken:n.refreshToken,expiresIn:n.expiresIn,scope:n.scope,authType:n.authType,providerData:n.providerData}),{status:"ok"}}async function To(e,n,t){let r=await Co(e,{token:n},t);if(r.status!=="ok")throw new Error(r.error??"Permission decision failed")}async function Co(e,n,t){let r=P(e),o=n.token?.trim();if(!o)return{status:"failed",retryable:!1,error:"Permission token is required"};if(!r.database)return{status:"failed",retryable:!1,error:"Database not configured"};let i=new Date().toISOString(),a=await r.database.db.selectFrom("corsair_permissions").selectAll().where("token","=",o).executeTakeFirst();return a?a.status!=="pending"?{status:"ok"}:a.expires_at<i?(await r.database.db.updateTable("corsair_permissions").set({status:"expired",updated_at:new Date}).where("id","=",a.id).execute(),{status:"failed",retryable:!1,error:"Permission has expired"}):(await r.database.db.updateTable("corsair_permissions").set({status:t,updated_at:new Date}).where("id","=",a.id).execute(),{status:"ok"}):{status:"failed",retryable:!1,error:"Permission not found"}}async function vl(e,n){try{return await nr(e,n),{status:"ok"}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Credential delivery failed"}}}async function Rl(e,n){try{return await mo(e,n),{status:"ok"}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Integration credential delivery failed"}}}function Zs(e,n){let t=e;return n&&typeof t?.withTenant=="function"?t.withTenant(n):e}async function Al(e,n){try{let t=Zs(e,n.tenantId);return{status:"ok",webhookResponse:{status:200,body:{status:"ok",run:await bo({corsair:t,code:n.code,payload:n.trigger?.payload??null,memoizedSteps:n.memoizedSteps})}}}}catch(t){return{status:"failed",retryable:!0,error:t instanceof Error?t.message:"Workflow run failed"}}}async function xl(e,n){try{let t=Zs(e,n.tenantId);return{status:"ok",webhookResponse:{status:200,body:{status:"ok",probe:await ko({corsair:t,code:n.code,timeoutMs:n.timeoutMs})}}}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Probe failed"}}}async function tt(e,n,t={}){let r=P(e),o=wo(n.headers,"x-corsair-signature"),i=wo(n.headers,"x-corsair-timestamp"),a=wo(n.headers,"x-corsair-nonce"),s=!1;if(t.signingSecret?.trim()){let l=In({body:n.body,signatureHeader:o,timestampHeader:i,signingSecret:t.signingSecret});if(!l.ok)return{status:"failed",retryable:!1,error:l.error};if(!a?.trim())return{status:"failed",retryable:!1,error:"Missing tunnel nonce"};let u=rr(`nonce:${a.trim()}`,We);if(!u.ok)return{status:"failed",retryable:!1,error:u.error};s=!0}else if(!t.allowUnsignedTunnel)return{status:"failed",retryable:!1,error:"Tunnel signing secret is required"};let c;try{c=JSON.parse(n.body)}catch{return{status:"failed",retryable:!1,error:"Invalid tunnel envelope JSON"}}if(c.type==="connect.status")return{status:"failed",retryable:!1,error:"connect.status is deprecated; use connections.sync signed delivery instead"};switch(c.type){case"webhook":return Cl(e,r,c.payload,s);case"oauth.callback":return Tl(e,c.payload);case"oauth.tokens":return Pl(e,c.payload);case"permission.approve":return Co(e,c.payload,"approved");case"permission.deny":return Co(e,c.payload,"denied");case"auth.credentials":return vl(e,c.payload);case"integration.credentials":return Rl(e,c.payload);case"connect.create_link":return kl(e,c.payload);case"connections.sync":{let l=t.signingSecret?.trim();return l?bl(e,l):{status:"failed",retryable:!1,error:"Tunnel signing secret is required for connections.sync"}}case"run":return t.allowWorkflowExecution?Al(e,c.payload):{status:"failed",retryable:!1,error:"Workflow execution is not enabled (set allowWorkflowExecution: true)"};case"probe":return t.allowWorkflowExecution?xl(e,c.payload):{status:"failed",retryable:!1,error:"Workflow execution is not enabled (set allowWorkflowExecution: true)"};default:return{status:"failed",retryable:!1,error:`Unsupported tunnel type: ${String(c.type)}`}}}function Il(e){let n=e.webhookResponse;return e.status==="ok"?{status:n?.status??200,body:n?.body??{status:"ok"}}:{status:n?.status??502,body:n?.body??{status:"error",error:e.error??"delivery failed"}}}var Po=3,Sl=250;function _l(e){return e?.name==="AbortError"}async function El(e){try{return(await e.json())?.ok!==!1}catch{return!0}}async function Ol(e,n,t,r,o){for(let i=1;i<=Po;i++){try{let a=await n.fetch(`${e.apiUrl}/api/dev/ack`,{method:"POST",headers:{...t,"content-type":"application/json"},body:JSON.stringify(r),signal:o});if(a.ok)return await El(a)||console.warn(`[corsair] hub did not record delivery ${r.deliveryId} (already timed out); the run may be retried`),!0}catch(a){if(_l(a))throw a}i<Po&&await zs(Sl)}return console.warn(`[corsair] failed to acknowledge delivery ${r.deliveryId} after ${Po} attempts; the run may be retried`),!1}async function Ml(e,n,t,r){let o={authorization:`Bearer ${n.projectApiKey}`},i=await t.fetch(`${n.apiUrl}/api/dev/pull`,{headers:o,signal:r});if(i.status===204)return"idle";if(!i.ok)return"error";let{deliveryId:a,body:s,headers:c}=await i.json(),l=await t.process(e,{headers:c,body:s},{signingSecret:n.signingSecret,allowWorkflowExecution:n.allowWorkflowExecution}),{status:u,body:d}=Il(l);return await Ol(n,t,o,{deliveryId:a,status:u,body:d},r)?"handled":"error"}var Gs=1e3,Dl=5e3,Hl=3e4;function zs(e){return new Promise(n=>setTimeout(n,e))}var cr=globalThis.__corsairConnectLoops??=new Map;function Bl(e,n={fetch,process:tt}){let t;try{t=N(e)}catch{return{stop:()=>{}}}if(!t.projectApiKey.startsWith("ck_dev_"))return{stop:()=>{}};if(!t.allowWorkflowExecution)return console.warn("[corsair] workflow executions not enabled. Please set hub: { ..., allowWorkflowExecution: true }"),{stop:()=>{}};let r=t.projectApiKey;if(cr.has(r))return{stop:()=>{}};let o=Symbol("corsair-connect-loop");cr.set(r,o);let i=()=>{cr.get(r)===o&&cr.delete(r)},a=!1,s=null;return(async()=>{let l=Gs,u=!1,d=async p=>{u||(console.warn("[corsair] connect loop error; retrying",p),u=!0),a||await zs(l),l=Math.min(l*2,Dl)};try{for(;!a;){s=new AbortController;let p=setTimeout(()=>s?.abort(),Hl);try{await Ml(e,t,n,s.signal)==="error"?await d("pull or ack failed"):(u=!1,l=Gs)}catch(g){if(a)break;await d(g instanceof Error?g.message:g)}finally{clearTimeout(p)}}}finally{i()}})(),{stop:()=>{a=!0,s?.abort(),i()}}}function Js(e){return e==="oauth_2"||e==="managed"?"oauth":e==="bot_token"?"bot_token":"api_key"}function Ul(e,n){return n&&!n.has(e.id)?!1:O(e)!==null}async function Vs(e,n,t={}){let r=P(e),o=n.trim()||"default",i=t.pluginIds?.length?new Set(t.pluginIds):null,a=await Gn(r,o,{pluginIds:t.pluginIds}),s=new Map(a.map(l=>[l.plugin,l])),c=r.plugins.filter(l=>Ul(l,i)).map(l=>{let u=O(l),d=s.get(l.id);return d?{plugin:l.id,providerName:Ee(l.id),authKind:Js(u),status:d.status,connected:d.connected,fields:d.fields.map(p=>({name:p.name,level:p.level,required:p.required,configured:p.configured})),missingRequiredFields:d.missingRequiredFields}:{plugin:l.id,providerName:Ee(l.id),authKind:Js(u),status:"not_started",connected:!1,fields:[],missingRequiredFields:[]}});return{tenantId:o,plugins:c}}async function Ys(e,n){let t=N(e);return Z({hub:t,path:`/projects/${encodeURIComponent(n.projectId)}/connections`,notFoundMessage:"Hub REST API not found at /projects/:id/connections. Check HUB_API_URL and ensure the Hub API is deployed.",parseResponse:gt})}function Ll(e){return typeof e=="string"&&e.length>0}function ur(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty managed pricing credentials payload");let n=e;if(!Ll(n.api_key))throw new Error("Hub API returned incomplete managed pricing credentials (expected api_key)");let t={api_key:n.api_key};return n.expires_in!==void 0&&typeof n.expires_in=="number"&&Number.isFinite(n.expires_in)&&n.expires_in>0&&(t.expires_in=n.expires_in),t}var Qs=1024*1024,Xs=3e4;function Ve(e){return e!==void 0&&Number.isFinite(e)&&e>0?e:Qs}function Ye(e){return e!==void 0&&Number.isFinite(e)&&e>=0?e:Xs}function En(e){return new w(413,"payload_too_large",`Request body exceeds the ${e}-byte limit`)}function Fl(e){return new w(408,"request_timeout",`Request body stalled: no bytes received for ${e}ms`)}async function lr(e,n){if(!(n>0))return e();let t;try{return await Promise.race([e(),new Promise((r,o)=>{t=setTimeout(()=>o(Fl(n)),n)})])}finally{clearTimeout(t)}}async function dr(e,n){if(e.body===null)return"";let t=e.body.getReader();try{let r=[],o=0;for(;;){let{done:s,value:c}=await lr(()=>t.read(),n.bodyStallTimeoutMs);if(s)break;if(o+=c.byteLength,o>n.maxBodyBytes)throw En(n.maxBodyBytes);r.push(c)}let i=new Uint8Array(o),a=0;for(let s of r)i.set(s,a),a+=s.byteLength;return new TextDecoder().decode(i)}catch(r){throw t.cancel().catch(()=>{}),r}}var vo=new Map;function ea(e){let n;try{n=N(e)}catch{return}let t=Or(n);t&&vo.get(n.projectApiKey)!==t&&(vo.set(n.projectApiKey,t),_({hub:n,path:"/apps/announce",body:{deliveryUrl:t},parseResponse:()=>({ok:!0})}).catch(()=>{vo.delete(n.projectApiKey)}))}var Nl=[".corsair.dev"];function $l(e){return e==="localhost"||e==="127.0.0.1"||e==="[::1]"||e==="::1"}function Wl(e){try{let{hostname:n,protocol:t}=new URL(e);return t!=="http:"&&t!=="https:"?!1:$l(n)?!0:Nl.some(r=>n===r.slice(1)||n.endsWith(r))}catch{return!1}}function na(e){return!e||!Wl(e)?null:{"Access-Control-Allow-Origin":e,"Access-Control-Allow-Methods":"GET, POST, OPTIONS","Access-Control-Allow-Headers":"content-type, x-corsair-signature, x-corsair-timestamp, x-corsair-project, x-corsair-nonce, access-control-request-private-network","Access-Control-Allow-Private-Network":"true","Access-Control-Max-Age":"0",Vary:"Origin"}}function ta(e,n){if(!n)return e;let t=new Headers(e.headers);for(let[r,o]of Object.entries(n))t.set(r,o);return new Response(e.body,{status:e.status,statusText:e.statusText,headers:t})}function Ro(e,n){let t=new URL(e);return n.error?(t.searchParams.set("error",n.error),t.toString()):n.connectedPlugin?(t.searchParams.set("connected",n.connectedPlugin),t.toString()):(n.status!==void 0&&t.searchParams.set("status",Buffer.from(JSON.stringify(n.status)).toString("base64url")),t.toString())}async function Ao(e,n){let t=N(e),o=new URL(n).searchParams.get("d");if(!o)return{type:"json",status:200,body:{status:"ok",message:"Corsair tunnel endpoint is active",timestamp:new Date().toISOString()}};let i=Me(o,t.signingSecret);if(!i)return{type:"json",status:400,body:{error:"Invalid or expired delivery token"}};let a=rr(`browser:${i.jti}`,Oe);if(!a.ok)return{type:"json",status:400,body:{error:a.error}};try{if(Xn(i)){if(!i.hubOrigin||!i.requestId)return{type:"json",status:400,body:{error:"Connections sync delivery requires hubOrigin and requestId for client bridge"}};let s=await Qn(e,t.signingSecret);return{type:"text",status:200,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!0,body:{status:"ok",sync:{encrypted:s}}})}}if(sr(i)){if(!i.hubOrigin||!i.requestId)return{type:"json",status:400,body:{error:"Connect link delivery requires hubOrigin and requestId for client bridge"}};let s=i.connectLinkPlugins?.filter(Boolean)??[];if(s.length===0)return{type:"json",status:400,body:{error:"Connect link delivery requires at least one plugin in connectLinkPlugins"}};let c=await Ot(e,{tenantId:i.tenantId,plugins:s});return{type:"text",status:200,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!0,body:{status:"ok",connectUrl:c.connectUrl,expiresAt:c.expiresAt}})}}if(Je(i))return i.hubSuccessUrl?i.credentials?(await nr(e,{plugin:i.plugin,tenantId:i.tenantId,credentials:i.credentials}),{type:"redirect",url:Ro(i.hubSuccessUrl,{connectedPlugin:i.plugin})}):{type:"redirect",url:Ro(i.hubSuccessUrl,{error:"Credential delivery missing credentials"})}:{type:"json",status:400,body:{error:"Credential delivery missing hubSuccessUrl"}};if(et(i)){if(!i.permissionToken)return{type:"json",status:400,body:{error:"Permission delivery missing permission token"}};await To(e,i.permissionToken,i.deliveryMode==="permission.approve"?"approved":"denied")}else if(nt(i)){if(!i.accessToken)return{type:"json",status:400,body:{error:"Managed OAuth delivery missing access_token"}};await _n(e,{plugin:i.plugin,tenantId:i.tenantId,accessToken:i.accessToken,refreshToken:i.refreshToken,expiresIn:i.expiresIn,scope:i.scope,authType:i.authType,providerData:i.providerData})}else{if(!ar(i)||!i.code||!i.state||!i.redirectUri)return{type:"json",status:400,body:{error:"Invalid BYO OAuth delivery token"}};await Jn(e,{code:i.code,state:i.state,redirectUri:i.redirectUri,trusted:!0,plugin:i.plugin,tenantId:i.tenantId})}}catch(s){let c=s instanceof Error?s.message:"Hub delivery failed";return Xn(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:sr(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:Je(i)&&i.hubSuccessUrl?{type:"redirect",url:Ro(i.hubSuccessUrl,{error:c})}:Je(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:{type:"json",status:400,body:{error:c}}}return{type:"redirect",url:i.hubSuccessUrl}}async function xo(e,n){let t=N(e),r=await tt(e,n,{signingSecret:t.signingSecret,allowWorkflowExecution:t.allowWorkflowExecution});if(r.status!=="ok")return{type:"json",status:r.retryable===!1?400:502,body:{error:r.error??"Tunnel processing failed"}};let o=r.webhookResponse;if(!o)return{type:"json",status:200,body:{status:"ok"}};let i=o.status??200,a=o.headers;return o.body&&typeof o.body=="object"&&!(o.body instanceof ArrayBuffer)?{type:"json",status:i,body:o.body,headers:a}:{type:"text",status:i,body:typeof o.body=="string"?o.body:o.body?JSON.stringify(o.body):null,headers:a}}function Io(e){if(e.type==="redirect")return Response.redirect(e.url,302);let n=new Headers;for(let[t,r]of Object.entries(e.headers??{}))typeof r=="string"&&n.set(t,r);return e.type==="json"?Response.json(e.body,{status:e.status,headers:n}):new Response(e.body,{status:e.status,headers:n})}async function So(e,n){return n.method==="GET"?Ao(e,n.url):xo(e,{headers:n.headers,body:n.body??""})}async function _o(e,n){try{let t=await So(e,n);return Io(t)}catch(t){if(t instanceof Ce)return Response.json({error:t.message},{status:503});throw t}}async function Qe(e,n,t){ea(e);let r=n.method.toUpperCase(),o=na(n.headers.get("origin"));if(r==="OPTIONS")return o?new Response(null,{status:204,headers:o}):Response.json({error:"Method not allowed"},{status:405});if(r!=="GET"&&r!=="POST")return Response.json({error:"Method not allowed"},{status:405});let i=await _o(e,{method:r,url:n.url,headers:n.headers,body:r==="POST"?await dr(n,{maxBodyBytes:Ve(t?.maxBodyBytes),bodyStallTimeoutMs:Ye(t?.bodyStallTimeoutMs)}):void 0});return ta(i,o)}var S=class extends Error{pluginId;authType;connectUrl;tenantId;constructor(n,t,r,o){super(r??`[auth-missing:${n}:${t}]`),Object.setPrototypeOf(this,new.target.prototype),this.name="AuthMissingError",this.pluginId=n,this.authType=t,this.connectUrl=o?.connectUrl??null,this.tenantId=o?.tenantId??null}};function On(e){if(e.forceRefresh||!e.accessToken)return!1;if(!e.expiresAt)return!0;let n=e.now??Math.floor(Date.now()/1e3);return Number(e.expiresAt)>n+300}async function Mn(e,n,t){let r=Math.floor(Date.now()/1e3),o=t?Number(t):Number.NaN,i=typeof n.expires_in=="number"?r+n.expires_in:Number.isFinite(o)&&o>r?o:r+3600;return await e.set_access_token(n.access_token),await e.set_expires_at(String(i)),n.refresh_token&&await e.set_refresh_token(n.refresh_token),n.scope&&await e.set_scope(n.scope),i}var ra=new WeakMap;function Xe(e,n,t){let r=ra.get(e);r||(r=new Map,ra.set(e,r));let o=r.get(n);if(o!==void 0)return o;let i=t().finally(()=>{r.delete(n)});return r.set(n,i),i}var oa=300;async function Eo(e,n){let{keys:t,hub:r,plugin:o,tenantId:i}=e,a=n?.forceRefresh??!1,s=`managed:${o}:${i}`;return Xe(t,s,async()=>{let[c,l,u]=await Promise.all([t.get_access_token(),t.get_expires_at(),t.get_refresh_token()]);if(!c&&!u)throw new S(o,"managed");let d=Math.floor(Date.now()/1e3);if(!a&&c&&l&&Number(l)>d+oa)return{accessToken:c,expiresAt:Number(l),refreshed:!1};if(!u&&c&&!a){let f=l?Number(l):null;if(f===null||f>d+oa)return{accessToken:c,expiresAt:f??d+3600,refreshed:!1}}if(!u)throw new S(o,"managed");let p=await jl(r,o,i,u),g=await Mn(t,p,l);return{accessToken:p.access_token,expiresAt:g,refreshed:!0}})}function ql(e){return e.includes("Managed OAuth connection not found")||e.includes("Managed OAuth connection has no tokens")}async function jl(e,n,t,r){try{return await _({hub:e,path:"/oauth/refresh",body:{plugin:n,tenantId:t,refresh_token:r},parseResponse:dn})}catch(o){let i=o instanceof Error?o.message:"";throw ql(i)?new S(n,"managed"):o}}async function ia(e,n){e._refreshAuth=async()=>(await Eo(n,{forceRefresh:!0})).accessToken}var Kl="",Zl=60,Oo=new WeakMap;function sa(e){let n=mt(e.apiUrl),t=e.instanceKey?.trim()??"";return[encodeURIComponent(n),encodeURIComponent(e.projectApiKey),encodeURIComponent(t)].join(Kl)}function Gl(e,n,t,r){let i=`${sa(e)}:${n}:${t}`;return r?`${i}:${r}`:i}function zl(e,n){return Oo.get(e)?.get(n)}function Jl(e,n,t){let r=Oo.get(e);r||(r=new Map,Oo.set(e,r)),r.set(n,t)}function Vl(e,n){return e.expiresAt===null?!1:e.expiresAt>n+Zl}function pr(e,n){if(!n)throw new S(e,"managed_pricing",`[auth-missing:${e}:managed_pricing]: Hub config is required. Pass hub: { ... } to createCorsair().`)}async function Mo(e,n){pr(e.plugin,e.hub);let t=n.operation.trim();if(!t)throw new S(e.plugin,"managed_pricing",`[auth-missing:${e.plugin}:managed_pricing]: Operation id is required for Hub metering.`);let r=n.forceRefresh??!1,o=Gl(e.hub,e.plugin,e.tenantId,t),a=`managed_pricing:${r?"force":"routine"}:${o}`;return Xe(e.cache,a,async()=>{let s=Math.floor(Date.now()/1e3);if(!r){let u=zl(e.cache,o);if(u&&Vl(u,s))return{apiKey:u.apiKey,expiresAt:u.expiresAt,fromCache:!0}}let c=await _({hub:e.hub,path:"/managed-pricing/credentials",body:{plugin:e.plugin,tenantId:e.tenantId,operation:t},extraHeaders:{"x-corsair-metered-operation":t},notFoundMessage:"Managed pricing is not configured for this project",parseResponse:ur}),l=c.expires_in!==void 0?s+c.expires_in:null;return Jl(e.cache,o,{apiKey:c.api_key,expiresAt:l}),{apiKey:c.api_key,expiresAt:l,fromCache:!1}})}function gr(){return{}}async function fr(e,n){pr(n.plugin,e.hub);let t=e.tenantId?.trim();if(!t)throw new S(n.plugin,"managed_pricing",`[auth-missing:${n.plugin}:managed_pricing]: tenantId is required for metered credentials.`);let r=e.meteredOperationId?.trim();if(!r)throw new S(n.plugin,"managed_pricing",`[auth-missing:${n.plugin}:managed_pricing]: Endpoint operation id missing \u2014 cannot meter usage.`);return(await Mo({hub:e.hub,plugin:n.plugin,tenantId:t,cache:n.cache},{operation:r})).apiKey}function aa(e){return{delivery:n=>Qe(e,n),deliveryOptions:n=>Qe(e,n)}}var ca=1200*1e3;function Do(){return we()}function Ho(){return ca}function Bo(e,n){return Wn(e,n,ca)}function Uo(e,n){return ue(e,n)}function Lo(e){return qe(e)}var ua=600*1e3;function Fo(){return we()}function No(){return ua}function $o(e,n){return Wn(e,n,ua)}function Wo(e,n){return ue(e,n)}function qo(e){return Fr(e)}function jo(e){return qe(e)}function Ko(){return we()}function Zo(e,n,t){return bt(e,n,Math.floor(t.getTime()/1e3))}function Go(e,n){return ue(e,n)}function zo(e){return qe(e)}var en=class extends Error{constructor(){super(`Corsair KEK is missing. Pass \`kek\` to createCorsair() or set CORSAIR_KEK in your environment. Generate one with: openssl rand -base64 ${je}`),this.name="CorsairKekMissingError"}};function yr(e,n){let t=[];e||t.push("database"),n||t.push("kek");let r={};return new Proxy(r,{get(o,i){if(e&&!n)throw new en;let a=t.length>1;throw new Error(`corsair.keys.${String(i)}: Cannot access keys because ${t.join(" and ")} ${a?"are":"is"} not configured. Provide both 'database' and 'kek' in createCorsair() to enable key management.
|
|
47
|
+
})()`;try{let i=await no(()=>{let a=ir.runInContext(o,t,{filename:"corsair:probe",timeout:r});a.catch(()=>{});let s,c=new Promise((l,u)=>{s=setTimeout(()=>u(new Error(`Probe exceeded ${r}ms time limit`)),r)});return Promise.race([a,c]).finally(()=>clearTimeout(s))});return{status:"ok",value:yl(i)}}catch(i){return{status:"error",error:or(i)}}}function yl(e){if(typeof e!="string")throw new Error(`Probe returned a non-string result (${typeof e})`);return JSON.parse(e)}function ml(e){return typeof e!="number"||!Number.isFinite(e)||e<=0?Ks:Math.min(e,Ks)}function Je(e){return e.deliveryMode==="auth.credentials"}function Xn(e){return e.deliveryMode==="connections.sync"}function sr(e){return e.deliveryMode==="connect.create_link"}function et(e){return e.deliveryMode==="permission.approve"||e.deliveryMode==="permission.deny"}function nt(e){return e.deliveryMode==="oauth.tokens"}function ar(e){return e.deliveryMode==="oauth.callback"||e.deliveryMode===void 0&&!Je(e)&&!Xn(e)&&!sr(e)&&!et(e)&&!nt(e)}function hl(e){return{status:"ok",connectLink:{connectUrl:e.connectUrl,expiresAt:e.expiresAt},webhookResponse:{status:200,body:{status:"ok",connectUrl:e.connectUrl,expiresAt:e.expiresAt}}}}async function bl(e,n){try{return{status:"ok",webhookResponse:{status:200,body:{status:"ok",sync:{encrypted:await Qn(e,n)}}}}}catch(t){return{status:"failed",retryable:yo(t),error:t instanceof Error?t.message:"Connections sync delivery failed"}}}async function kl(e,n){try{let t=await Ot(e,n);return hl(t)}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Connect link delivery failed"}}}function wo(e,n){if(e instanceof Headers)return e.get(n)??void 0;let t=e[n]??e[n.toLowerCase()];return Array.isArray(t)?t[0]:typeof t=="string"?t:void 0}async function wl(e,n,t){let r=typeof t.tenantId=="string"?t.tenantId:typeof t.query?.tenantId=="string"?t.query.tenantId:void 0;return r||(!n.database||!t.plugin||!t.linkType||!t.externalId?void 0:await xt({database:n.database,kek:n.kek,pluginId:t.plugin,linkType:t.linkType,externalId:t.externalId})??void 0)}async function Cl(e,n,t,r){let o=await wl(e,n,t),i={...t.query??{},...o?{tenantId:o}:{}},a=await Ns(e,t.headers,t.body,i,{plugin:t.plugin,hubVerified:r&&t.hubVerified===!0});if(!a.plugin)return{status:"failed",retryable:!1,error:"No matching webhook handler found"};if(a.response&&a.response.success===!1)return{status:"failed",retryable:!1,error:typeof a.response.error=="string"?a.response.error:"Webhook handler failed"};let s=a.response?.returnToSender,c=s&&typeof s=="object"&&typeof s.validationToken=="string"&&Object.keys(s).length===1?s.validationToken:s||(a.response?.data??a.response);return{status:"ok",webhookResponse:{status:a.response?.statusCode??200,body:c,headers:a.responseHeaders}}}async function Tl(e,n){return await Jn(e,{code:n.code,state:n.state,redirectUri:n.redirectUri,callbackParams:n.callbackParams,...n.plugin&&n.tenantId?{trusted:!0,plugin:n.plugin,tenantId:n.tenantId}:{}}),{status:"ok"}}async function Pl(e,n){return await _n(e,{plugin:n.plugin,tenantId:n.tenantId,accessToken:n.accessToken,refreshToken:n.refreshToken,expiresIn:n.expiresIn,scope:n.scope,authType:n.authType,providerData:n.providerData}),{status:"ok"}}async function To(e,n,t){let r=await Co(e,{token:n},t);if(r.status!=="ok")throw new Error(r.error??"Permission decision failed")}async function Co(e,n,t){let r=P(e),o=n.token?.trim();if(!o)return{status:"failed",retryable:!1,error:"Permission token is required"};if(!r.database)return{status:"failed",retryable:!1,error:"Database not configured"};let i=new Date().toISOString(),a=await r.database.db.selectFrom("corsair_permissions").selectAll().where("token","=",o).executeTakeFirst();return a?a.status!=="pending"?{status:"ok"}:a.expires_at<i?(await r.database.db.updateTable("corsair_permissions").set({status:"expired",updated_at:new Date}).where("id","=",a.id).execute(),{status:"failed",retryable:!1,error:"Permission has expired"}):(await r.database.db.updateTable("corsair_permissions").set({status:t,updated_at:new Date}).where("id","=",a.id).execute(),{status:"ok"}):{status:"failed",retryable:!1,error:"Permission not found"}}async function vl(e,n){try{return await nr(e,n),{status:"ok"}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Credential delivery failed"}}}async function Rl(e,n){try{return await mo(e,n),{status:"ok"}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Integration credential delivery failed"}}}function Zs(e,n){let t=e;return n&&typeof t?.withTenant=="function"?t.withTenant(n):e}async function Al(e,n){try{let t=Zs(e,n.tenantId);return{status:"ok",webhookResponse:{status:200,body:{status:"ok",run:await bo({corsair:t,code:n.code,payload:n.trigger?.payload??null,memoizedSteps:n.memoizedSteps})}}}}catch(t){return{status:"failed",retryable:!0,error:t instanceof Error?t.message:"Workflow run failed"}}}async function xl(e,n){try{let t=Zs(e,n.tenantId);return{status:"ok",webhookResponse:{status:200,body:{status:"ok",probe:await ko({corsair:t,code:n.code,timeoutMs:n.timeoutMs})}}}}catch(t){return{status:"failed",retryable:!1,error:t instanceof Error?t.message:"Probe failed"}}}async function tt(e,n,t={}){let r=P(e),o=wo(n.headers,"x-corsair-signature"),i=wo(n.headers,"x-corsair-timestamp"),a=wo(n.headers,"x-corsair-nonce"),s=!1;if(t.signingSecret?.trim()){let l=In({body:n.body,signatureHeader:o,timestampHeader:i,signingSecret:t.signingSecret});if(!l.ok)return{status:"failed",retryable:!1,error:l.error};if(!a?.trim())return{status:"failed",retryable:!1,error:"Missing tunnel nonce"};let u=rr(`nonce:${a.trim()}`,We);if(!u.ok)return{status:"failed",retryable:!1,error:u.error};s=!0}else if(!t.allowUnsignedTunnel)return{status:"failed",retryable:!1,error:"Tunnel signing secret is required"};let c;try{c=JSON.parse(n.body)}catch{return{status:"failed",retryable:!1,error:"Invalid tunnel envelope JSON"}}if(c.type==="connect.status")return{status:"failed",retryable:!1,error:"connect.status is deprecated; use connections.sync signed delivery instead"};switch(c.type){case"webhook":return Cl(e,r,c.payload,s);case"oauth.callback":return Tl(e,c.payload);case"oauth.tokens":return Pl(e,c.payload);case"permission.approve":return Co(e,c.payload,"approved");case"permission.deny":return Co(e,c.payload,"denied");case"auth.credentials":return vl(e,c.payload);case"integration.credentials":return Rl(e,c.payload);case"connect.create_link":return kl(e,c.payload);case"connections.sync":{let l=t.signingSecret?.trim();return l?bl(e,l):{status:"failed",retryable:!1,error:"Tunnel signing secret is required for connections.sync"}}case"run":return t.allowWorkflowExecution?Al(e,c.payload):{status:"failed",retryable:!1,error:"Workflow execution is not enabled (set allowWorkflowExecution: true)"};case"probe":return t.allowWorkflowExecution?xl(e,c.payload):{status:"failed",retryable:!1,error:"Workflow execution is not enabled (set allowWorkflowExecution: true)"};default:return{status:"failed",retryable:!1,error:`Unsupported tunnel type: ${String(c.type)}`}}}function Il(e){let n=e.webhookResponse;return e.status==="ok"?{status:n?.status??200,body:n?.body??{status:"ok"}}:{status:n?.status??502,body:n?.body??{status:"error",error:e.error??"delivery failed"}}}var Po=3,Sl=250;function _l(e){return e?.name==="AbortError"}async function El(e){try{return(await e.json())?.ok!==!1}catch{return!0}}async function Ol(e,n,t,r,o){for(let i=1;i<=Po;i++){try{let a=await n.fetch(`${e.apiUrl}/api/dev/ack`,{method:"POST",headers:{...t,"content-type":"application/json"},body:JSON.stringify(r),signal:o});if(a.ok)return await El(a)||console.warn(`[corsair] hub did not record delivery ${r.deliveryId} (already timed out); the run may be retried`),!0}catch(a){if(_l(a))throw a}i<Po&&await zs(Sl)}return console.warn(`[corsair] failed to acknowledge delivery ${r.deliveryId} after ${Po} attempts; the run may be retried`),!1}async function Ml(e,n,t,r){let o={authorization:`Bearer ${n.projectApiKey}`},i=await t.fetch(`${n.apiUrl}/api/dev/pull`,{headers:o,signal:r});if(i.status===204)return"idle";if(!i.ok)return"error";let{deliveryId:a,body:s,headers:c}=await i.json(),l=await t.process(e,{headers:c,body:s},{signingSecret:n.signingSecret,allowWorkflowExecution:n.allowWorkflowExecution}),{status:u,body:d}=Il(l);return await Ol(n,t,o,{deliveryId:a,status:u,body:d},r)?"handled":"error"}var Gs=1e3,Dl=5e3,Hl=3e4;function zs(e){return new Promise(n=>setTimeout(n,e))}var cr=globalThis.__corsairConnectLoops??=new Map;function Bl(e,n={fetch,process:tt}){let t;try{t=N(e)}catch{return{stop:()=>{}}}if(!t.projectApiKey.startsWith("ck_dev_"))return{stop:()=>{}};if(!t.allowWorkflowExecution)return console.warn("[corsair] workflow executions not enabled. Please set hub: { ..., allowWorkflowExecution: true }"),{stop:()=>{}};let r=t.projectApiKey;if(cr.has(r))return{stop:()=>{}};let o=Symbol("corsair-connect-loop");cr.set(r,o);let i=()=>{cr.get(r)===o&&cr.delete(r)},a=!1,s=null;return(async()=>{let l=Gs,u=!1,d=async p=>{u||(console.warn("[corsair] connect loop error; retrying",p),u=!0),a||await zs(l),l=Math.min(l*2,Dl)};try{for(;!a;){s=new AbortController;let p=setTimeout(()=>s?.abort(),Hl);try{await Ml(e,t,n,s.signal)==="error"?await d("pull or ack failed"):(u=!1,l=Gs)}catch(g){if(a)break;await d(g instanceof Error?g.message:g)}finally{clearTimeout(p)}}}finally{i()}})(),{stop:()=>{a=!0,s?.abort(),i()}}}function Js(e){return e==="oauth_2"||e==="managed"?"oauth":e==="bot_token"?"bot_token":"api_key"}function Ul(e,n){return n&&!n.has(e.id)?!1:E(e)!==null}async function Vs(e,n,t={}){let r=P(e),o=n.trim()||"default",i=t.pluginIds?.length?new Set(t.pluginIds):null,a=await Gn(r,o,{pluginIds:t.pluginIds}),s=new Map(a.map(l=>[l.plugin,l])),c=r.plugins.filter(l=>Ul(l,i)).map(l=>{let u=E(l),d=s.get(l.id);return d?{plugin:l.id,providerName:Ee(l.id),authKind:Js(u),status:d.status,connected:d.connected,fields:d.fields.map(p=>({name:p.name,level:p.level,required:p.required,configured:p.configured})),missingRequiredFields:d.missingRequiredFields}:{plugin:l.id,providerName:Ee(l.id),authKind:Js(u),status:"not_started",connected:!1,fields:[],missingRequiredFields:[]}});return{tenantId:o,plugins:c}}async function Ys(e,n){let t=N(e);return Z({hub:t,path:`/projects/${encodeURIComponent(n.projectId)}/connections`,notFoundMessage:"Hub REST API not found at /projects/:id/connections. Check HUB_API_URL and ensure the Hub API is deployed.",parseResponse:gt})}function Ll(e){return typeof e=="string"&&e.length>0}function ur(e){if(!e||typeof e!="object")throw new Error("Hub API returned an empty managed pricing credentials payload");let n=e;if(!Ll(n.api_key))throw new Error("Hub API returned incomplete managed pricing credentials (expected api_key)");let t={api_key:n.api_key};return n.expires_in!==void 0&&typeof n.expires_in=="number"&&Number.isFinite(n.expires_in)&&n.expires_in>0&&(t.expires_in=n.expires_in),t}var Qs=1024*1024,Xs=3e4;function Ve(e){return e!==void 0&&Number.isFinite(e)&&e>0?e:Qs}function Ye(e){return e!==void 0&&Number.isFinite(e)&&e>=0?e:Xs}function En(e){return new w(413,"payload_too_large",`Request body exceeds the ${e}-byte limit`)}function Fl(e){return new w(408,"request_timeout",`Request body stalled: no bytes received for ${e}ms`)}async function lr(e,n){if(!(n>0))return e();let t;try{return await Promise.race([e(),new Promise((r,o)=>{t=setTimeout(()=>o(Fl(n)),n)})])}finally{clearTimeout(t)}}async function dr(e,n){if(e.body===null)return"";let t=e.body.getReader();try{let r=[],o=0;for(;;){let{done:s,value:c}=await lr(()=>t.read(),n.bodyStallTimeoutMs);if(s)break;if(o+=c.byteLength,o>n.maxBodyBytes)throw En(n.maxBodyBytes);r.push(c)}let i=new Uint8Array(o),a=0;for(let s of r)i.set(s,a),a+=s.byteLength;return new TextDecoder().decode(i)}catch(r){throw t.cancel().catch(()=>{}),r}}var vo=new Map;function ea(e){let n;try{n=N(e)}catch{return}let t=Or(n);t&&vo.get(n.projectApiKey)!==t&&(vo.set(n.projectApiKey,t),_({hub:n,path:"/apps/announce",body:{deliveryUrl:t},parseResponse:()=>({ok:!0})}).catch(()=>{vo.delete(n.projectApiKey)}))}var Nl=[".corsair.dev"];function $l(e){return e==="localhost"||e==="127.0.0.1"||e==="[::1]"||e==="::1"}function Wl(e){try{let{hostname:n,protocol:t}=new URL(e);return t!=="http:"&&t!=="https:"?!1:$l(n)?!0:Nl.some(r=>n===r.slice(1)||n.endsWith(r))}catch{return!1}}function na(e){return!e||!Wl(e)?null:{"Access-Control-Allow-Origin":e,"Access-Control-Allow-Methods":"GET, POST, OPTIONS","Access-Control-Allow-Headers":"content-type, x-corsair-signature, x-corsair-timestamp, x-corsair-project, x-corsair-nonce, access-control-request-private-network","Access-Control-Allow-Private-Network":"true","Access-Control-Max-Age":"0",Vary:"Origin"}}function ta(e,n){if(!n)return e;let t=new Headers(e.headers);for(let[r,o]of Object.entries(n))t.set(r,o);return new Response(e.body,{status:e.status,statusText:e.statusText,headers:t})}function Ro(e,n){let t=new URL(e);return n.error?(t.searchParams.set("error",n.error),t.toString()):n.connectedPlugin?(t.searchParams.set("connected",n.connectedPlugin),t.toString()):(n.status!==void 0&&t.searchParams.set("status",Buffer.from(JSON.stringify(n.status)).toString("base64url")),t.toString())}async function Ao(e,n){let t=N(e),o=new URL(n).searchParams.get("d");if(!o)return{type:"json",status:200,body:{status:"ok",message:"Corsair tunnel endpoint is active",timestamp:new Date().toISOString()}};let i=Me(o,t.signingSecret);if(!i)return{type:"json",status:400,body:{error:"Invalid or expired delivery token"}};let a=rr(`browser:${i.jti}`,Oe);if(!a.ok)return{type:"json",status:400,body:{error:a.error}};try{if(Xn(i)){if(!i.hubOrigin||!i.requestId)return{type:"json",status:400,body:{error:"Connections sync delivery requires hubOrigin and requestId for client bridge"}};let s=await Qn(e,t.signingSecret);return{type:"text",status:200,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!0,body:{status:"ok",sync:{encrypted:s}}})}}if(sr(i)){if(!i.hubOrigin||!i.requestId)return{type:"json",status:400,body:{error:"Connect link delivery requires hubOrigin and requestId for client bridge"}};let s=i.connectLinkPlugins?.filter(Boolean)??[];if(s.length===0)return{type:"json",status:400,body:{error:"Connect link delivery requires at least one plugin in connectLinkPlugins"}};let c=await Ot(e,{tenantId:i.tenantId,plugins:s});return{type:"text",status:200,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!0,body:{status:"ok",connectUrl:c.connectUrl,expiresAt:c.expiresAt}})}}if(Je(i))return i.hubSuccessUrl?i.credentials?(await nr(e,{plugin:i.plugin,tenantId:i.tenantId,credentials:i.credentials}),{type:"redirect",url:Ro(i.hubSuccessUrl,{connectedPlugin:i.plugin})}):{type:"redirect",url:Ro(i.hubSuccessUrl,{error:"Credential delivery missing credentials"})}:{type:"json",status:400,body:{error:"Credential delivery missing hubSuccessUrl"}};if(et(i)){if(!i.permissionToken)return{type:"json",status:400,body:{error:"Permission delivery missing permission token"}};await To(e,i.permissionToken,i.deliveryMode==="permission.approve"?"approved":"denied")}else if(nt(i)){if(!i.accessToken)return{type:"json",status:400,body:{error:"Managed OAuth delivery missing access_token"}};await _n(e,{plugin:i.plugin,tenantId:i.tenantId,accessToken:i.accessToken,refreshToken:i.refreshToken,expiresIn:i.expiresIn,scope:i.scope,authType:i.authType,providerData:i.providerData})}else{if(!ar(i)||!i.code||!i.state||!i.redirectUri)return{type:"json",status:400,body:{error:"Invalid BYO OAuth delivery token"}};await Jn(e,{code:i.code,state:i.state,redirectUri:i.redirectUri,trusted:!0,plugin:i.plugin,tenantId:i.tenantId})}}catch(s){let c=s instanceof Error?s.message:"Hub delivery failed";return Xn(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:sr(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:Je(i)&&i.hubSuccessUrl?{type:"redirect",url:Ro(i.hubSuccessUrl,{error:c})}:Je(i)&&i.hubOrigin&&i.requestId?{type:"text",status:400,headers:{"Content-Type":"text/html; charset=utf-8"},body:pn({hubOrigin:i.hubOrigin,requestId:i.requestId,ok:!1,error:c})}:{type:"json",status:400,body:{error:c}}}return{type:"redirect",url:i.hubSuccessUrl}}async function xo(e,n){let t=N(e),r=await tt(e,n,{signingSecret:t.signingSecret,allowWorkflowExecution:t.allowWorkflowExecution});if(r.status!=="ok")return{type:"json",status:r.retryable===!1?400:502,body:{error:r.error??"Tunnel processing failed"}};let o=r.webhookResponse;if(!o)return{type:"json",status:200,body:{status:"ok"}};let i=o.status??200,a=o.headers;return o.body&&typeof o.body=="object"&&!(o.body instanceof ArrayBuffer)?{type:"json",status:i,body:o.body,headers:a}:{type:"text",status:i,body:typeof o.body=="string"?o.body:o.body?JSON.stringify(o.body):null,headers:a}}function Io(e){if(e.type==="redirect")return Response.redirect(e.url,302);let n=new Headers;for(let[t,r]of Object.entries(e.headers??{}))typeof r=="string"&&n.set(t,r);return e.type==="json"?Response.json(e.body,{status:e.status,headers:n}):new Response(e.body,{status:e.status,headers:n})}async function So(e,n){return n.method==="GET"?Ao(e,n.url):xo(e,{headers:n.headers,body:n.body??""})}async function _o(e,n){try{let t=await So(e,n);return Io(t)}catch(t){if(t instanceof Ce)return Response.json({error:t.message},{status:503});throw t}}async function Qe(e,n,t){ea(e);let r=n.method.toUpperCase(),o=na(n.headers.get("origin"));if(r==="OPTIONS")return o?new Response(null,{status:204,headers:o}):Response.json({error:"Method not allowed"},{status:405});if(r!=="GET"&&r!=="POST")return Response.json({error:"Method not allowed"},{status:405});let i=await _o(e,{method:r,url:n.url,headers:n.headers,body:r==="POST"?await dr(n,{maxBodyBytes:Ve(t?.maxBodyBytes),bodyStallTimeoutMs:Ye(t?.bodyStallTimeoutMs)}):void 0});return ta(i,o)}var S=class extends Error{pluginId;authType;connectUrl;tenantId;constructor(n,t,r,o){super(r??`[auth-missing:${n}:${t}]`),Object.setPrototypeOf(this,new.target.prototype),this.name="AuthMissingError",this.pluginId=n,this.authType=t,this.connectUrl=o?.connectUrl??null,this.tenantId=o?.tenantId??null}};function On(e){if(e.forceRefresh||!e.accessToken)return!1;if(!e.expiresAt)return!0;let n=e.now??Math.floor(Date.now()/1e3);return Number(e.expiresAt)>n+300}async function Mn(e,n,t){let r=Math.floor(Date.now()/1e3),o=t?Number(t):Number.NaN,i=typeof n.expires_in=="number"?r+n.expires_in:Number.isFinite(o)&&o>r?o:r+3600;return await e.set_access_token(n.access_token),await e.set_expires_at(String(i)),n.refresh_token&&await e.set_refresh_token(n.refresh_token),n.scope&&await e.set_scope(n.scope),i}var ra=new WeakMap;function Xe(e,n,t){let r=ra.get(e);r||(r=new Map,ra.set(e,r));let o=r.get(n);if(o!==void 0)return o;let i=t().finally(()=>{r.delete(n)});return r.set(n,i),i}var oa=300;async function Eo(e,n){let{keys:t,hub:r,plugin:o,tenantId:i}=e,a=n?.forceRefresh??!1,s=`managed:${o}:${i}`;return Xe(t,s,async()=>{let[c,l,u]=await Promise.all([t.get_access_token(),t.get_expires_at(),t.get_refresh_token()]);if(!c&&!u)throw new S(o,"managed");let d=Math.floor(Date.now()/1e3);if(!a&&c&&l&&Number(l)>d+oa)return{accessToken:c,expiresAt:Number(l),refreshed:!1};if(!u&&c&&!a){let f=l?Number(l):null;if(f===null||f>d+oa)return{accessToken:c,expiresAt:f??d+3600,refreshed:!1}}if(!u)throw new S(o,"managed");let p=await jl(r,o,i,u),g=await Mn(t,p,l);return{accessToken:p.access_token,expiresAt:g,refreshed:!0}})}function ql(e){return e.includes("Managed OAuth connection not found")||e.includes("Managed OAuth connection has no tokens")}async function jl(e,n,t,r){try{return await _({hub:e,path:"/oauth/refresh",body:{plugin:n,tenantId:t,refresh_token:r},parseResponse:dn})}catch(o){let i=o instanceof Error?o.message:"";throw ql(i)?new S(n,"managed"):o}}async function ia(e,n){e._refreshAuth=async()=>(await Eo(n,{forceRefresh:!0})).accessToken}var Kl="",Zl=60,Oo=new WeakMap;function sa(e){let n=mt(e.apiUrl),t=e.instanceKey?.trim()??"";return[encodeURIComponent(n),encodeURIComponent(e.projectApiKey),encodeURIComponent(t)].join(Kl)}function Gl(e,n,t,r){let i=`${sa(e)}:${n}:${t}`;return r?`${i}:${r}`:i}function zl(e,n){return Oo.get(e)?.get(n)}function Jl(e,n,t){let r=Oo.get(e);r||(r=new Map,Oo.set(e,r)),r.set(n,t)}function Vl(e,n){return e.expiresAt===null?!1:e.expiresAt>n+Zl}function pr(e,n){if(!n)throw new S(e,"managed_pricing",`[auth-missing:${e}:managed_pricing]: Hub config is required. Pass hub: { ... } to createCorsair().`)}async function Mo(e,n){pr(e.plugin,e.hub);let t=n.operation.trim();if(!t)throw new S(e.plugin,"managed_pricing",`[auth-missing:${e.plugin}:managed_pricing]: Operation id is required for Hub metering.`);let r=n.forceRefresh??!1,o=Gl(e.hub,e.plugin,e.tenantId,t),a=`managed_pricing:${r?"force":"routine"}:${o}`;return Xe(e.cache,a,async()=>{let s=Math.floor(Date.now()/1e3);if(!r){let u=zl(e.cache,o);if(u&&Vl(u,s))return{apiKey:u.apiKey,expiresAt:u.expiresAt,fromCache:!0}}let c=await _({hub:e.hub,path:"/managed-pricing/credentials",body:{plugin:e.plugin,tenantId:e.tenantId,operation:t},extraHeaders:{"x-corsair-metered-operation":t},notFoundMessage:"Managed pricing is not configured for this project",parseResponse:ur}),l=c.expires_in!==void 0?s+c.expires_in:null;return Jl(e.cache,o,{apiKey:c.api_key,expiresAt:l}),{apiKey:c.api_key,expiresAt:l,fromCache:!1}})}function gr(){return{}}async function fr(e,n){pr(n.plugin,e.hub);let t=e.tenantId?.trim();if(!t)throw new S(n.plugin,"managed_pricing",`[auth-missing:${n.plugin}:managed_pricing]: tenantId is required for metered credentials.`);let r=(n.operation??e.meteredOperationId)?.trim();if(!r)throw new S(n.plugin,"managed_pricing",`[auth-missing:${n.plugin}:managed_pricing]: Endpoint operation id missing \u2014 cannot meter usage.`);return(await Mo({hub:e.hub,plugin:n.plugin,tenantId:t,cache:n.cache},{operation:r})).apiKey}function aa(e){return{delivery:n=>Qe(e,n),deliveryOptions:n=>Qe(e,n)}}var ca=1200*1e3;function Do(){return we()}function Ho(){return ca}function Bo(e,n){return Wn(e,n,ca)}function Uo(e,n){return ue(e,n)}function Lo(e){return qe(e)}var ua=600*1e3;function Fo(){return we()}function No(){return ua}function $o(e,n){return Wn(e,n,ua)}function Wo(e,n){return ue(e,n)}function qo(e){return Fr(e)}function jo(e){return qe(e)}function Ko(){return we()}function Zo(e,n,t){return bt(e,n,Math.floor(t.getTime()/1e3))}function Go(e,n){return ue(e,n)}function zo(e){return qe(e)}var en=class extends Error{constructor(){super(`Corsair KEK is missing. Pass \`kek\` to createCorsair() or set CORSAIR_KEK in your environment. Generate one with: openssl rand -base64 ${je}`),this.name="CorsairKekMissingError"}};function yr(e,n){let t=[];e||t.push("database"),n||t.push("kek");let r={};return new Proxy(r,{get(o,i){if(e&&!n)throw new en;let a=t.length>1;throw new Error(`corsair.keys.${String(i)}: Cannot access keys because ${t.join(" and ")} ${a?"are":"is"} not configured. Provide both 'database' and 'kek' in createCorsair() to enable key management.
|
|
48
48
|
|
|
49
|
-
To generate a KEK, run: openssl rand -base64 ${je}`)}})}async function Yl(e){let n=!1;for(;;){let t=await e.database.db.selectFrom("corsair_integrations").selectAll().where("name","=",e.integrationName).executeTakeFirst();if(!t){if(!n&&e.ensureProvisioned){n=!0,await e.ensureProvisioned();continue}throw new Error(`Integration "${e.integrationName}" not found. Make sure to create the integration first.`)}let r=await e.database.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",e.tenantId).where("integration_id","=",t.id).executeTakeFirst();if(!r){if(!n&&e.ensureProvisioned){n=!0,await e.ensureProvisioned();continue}throw new Error(`Account not found for tenant "${e.tenantId}" and integration "${e.integrationName}". Make sure to create the account first.`)}return{integrationId:t.id,accountId:r.id,integration:{id:t.id,config:t.config,dek:t.dek??null},account:{id:r.id,config:r.config,dek:r.dek??null}}}}async function la(e){let{integrationId:n,accountId:t}=await Yl(e);return{integrationId:n,accountId:t}}function da(e,n){let t=()=>{if(!e)throw new Error("corsair.chats requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e};return{create:r=>Mr(t(),{tenantId:n,message:r}),list:()=>Hr(t(),{tenantId:n}),get:r=>({message:o=>Dr(t(),{chatId:r,tenantId:n,message:o}),listMessages:()=>Br(t(),{chatId:r,tenantId:n})})}}function pa(e,n){return`[auth-missing:${e}] Authentication required. Direct the user to connect their account: ${n}`}async function Ql(e){let n=e.hub;if(n&&e.database&&e.kek)try{let t=await Cs(n,{tenantId:e.tenantId,plugin:e.plugin,database:e.database,kek:e.kek,plugins:e.plugins,multiTenancy:e.multiTenancy});return{message:e.manual?.onAuthMissing?e.manual.onAuthMissing({plugin:e.pluginId,connectUrl:t.connectUrl,state:t.token}):pa(e.pluginId,t.connectUrl),connectUrl:t.connectUrl}}catch{return{message:`[auth-missing:${e.pluginId}:${e.authType}] Authentication required. Could not create connect link. Check hub configuration and server logs.`,connectUrl:null}}return{message:`[auth-missing:${e.pluginId}:${e.authType}]`,connectUrl:null}}function Xl(e,n,t){let r=hn(Be(e,n.tenantId??t??"default"),n.kek),o=new URL(n.baseUrl);o.searchParams.set("state",r);let i=o.toString();return{message:n.onAuthMissing?n.onAuthMissing({plugin:e,connectUrl:i,state:r}):pa(e,i),connectUrl:i}}async function ed(e){let n=e.tenantId??"default",t=e.error.pluginId;return e.error.authType==="managed_pricing"?{message:e.error.message,connectUrl:null}:e.manual&&Pn(e.manual)&&e.manual.oauthConfig&&e.manual.kek&&e.error.authType==="oauth_2"?Xl(t,{...e.manual,baseUrl:e.manual.baseUrl,kek:e.manual.kek},e.tenantId):e.hub&&e.plugin&&e.kek&&e.database&&e.plugins?Ql({manual:e.manual,hub:e.hub,plugin:e.plugin,pluginId:t,tenantId:n,authType:e.error.authType,database:e.database,kek:e.kek,plugins:e.plugins,multiTenancy:e.multiTenancy}):{message:e.error.message,connectUrl:null}}async function ga(e){let{message:n,connectUrl:t}=await ed(e);throw new S(e.error.pluginId,e.error.authType,n,{connectUrl:t,tenantId:e.tenantId??"default"})}var mr="connect.request",Vo="connect.cleared",nd=600*1e3;async function Jo(e,n,t){let r=await e.db.selectFrom("corsair_integrations").select("id").where("name","=",t).executeTakeFirst();return r?(await e.db.selectFrom("corsair_accounts").select("id").where("tenant_id","=",n).where("integration_id","=",r.id).executeTakeFirst())?.id??null:null}async function td(e,n){return(await e.db.selectFrom("corsair_accounts").select("id").where("tenant_id","=",n).execute()).map(r=>r.id)}async function rd(e,n,t){let r=await e.db.selectFrom("corsair_events").select("created_at").where("account_id","=",n).where("event_type","in",[mr,Vo]).orderBy("created_at","desc").limit(1).executeTakeFirst();if(!r)return t;let o=r.created_at instanceof Date?r.created_at.getTime():Date.parse(String(r.created_at));return Math.max(t,o+1)}async function fa(e,n,t,r,o){let i=await rd(e,n,o),a=new Date(i);await e.db.insertInto("corsair_events").values({id:ln(),created_at:a,updated_at:a,account_id:n,event_type:t,payload:r}).execute()}async function od(e,n,t=Date.now()){let r=await Jo(e,n.tenantId,n.plugin);r&&await fa(e,r,mr,{plugin:n.plugin,connectUrl:n.connectUrl},t)}function id(e){let n=e;if(typeof e=="string")try{n=JSON.parse(e)}catch{return null}return!n||typeof n!="object"||Array.isArray(n)?null:n}async function sd(e,n,t,r,o){let i=await e.db.selectFrom("corsair_events").select(["event_type","payload","created_at"]).where("account_id","=",n).where("event_type","in",[mr,Vo]).orderBy("created_at","desc").limit(1).executeTakeFirst();if(!i||i.event_type!==mr)return null;let a=i.created_at instanceof Date?i.created_at.getTime():Date.parse(String(i.created_at));if(r-a>o)return null;let s=id(i.payload);if(!s)return null;let c=s.plugin,l=s.connectUrl;return typeof c!="string"||typeof l!="string"?null:{plugin:c,connectUrl:l,requestedAt:new Date(a).toISOString(),tenantId:t,requestedAtMs:a,accountId:n}}async function Yo(e,n,t=Date.now(),r=nd){let o=await td(e,n);if(o.length===0)return null;let i=(await Promise.all(o.map(l=>sd(e,l,n,t,r)))).filter(l=>l!==null);if(i.length===0)return null;i.sort((l,u)=>l.requestedAtMs-u.requestedAtMs||l.accountId.localeCompare(u.accountId));let{requestedAtMs:a,accountId:s,...c}=i[0];return c}async function ya(e,n,t=Date.now(),r){let o;if(r)o=await Jo(e,n,r);else{let i=await Yo(e,n,t);o=i?await Jo(e,n,i.plugin):null}o&&await fa(e,o,Vo,{},t)}async function Qo(e,n){if(!(!e||!n.plugin||!n.connectUrl))try{await od(e,{tenantId:n.tenantId??"default",plugin:n.plugin,connectUrl:n.connectUrl})}catch{}}var ad=async(e,n)=>(console.error(`[corsair:${n.pluginId}:${n.operation}]`,{error:e.message,input:n.input}),{maxRetries:0});async function ma(e,n,t,r,o){let i={pluginId:n,operation:t,input:r,originalError:e},a=Object.keys(o).find(l=>o[l]?.match(e,i));return await(o[a||"DEFAULT"]?.handler||ad)(e,i)}var ha=new Map;function cd(e){let n=ha.get(e);return n||(n=gr(),ha.set(e,n)),n}function ud(e){return typeof e=="function"}function Xo({endpoints:e,hooks:n,ctx:t,tree:r,pluginId:o,errorHandlers:i,currentPath:a=[],keyBuilder:s,permissionsConfig:c,endpointMeta:l,database:u,permissionsOptions:d,tenantId:p,manualConfig:g,hubConfig:f,plugin:h,kek:b,allPlugins:k,multiTenancy:T}){for(let[v,H]of Object.entries(e)){let D=n?.[v];if(ud(H)){let B=D,C=[...a,v].join("."),R=async(x={})=>{let ee=l?.[C];Lt(C,ee?.riskLevel??"write");let re,E=Rn(),q=c?.mode,he=eo(E,q);if(he){let W=ee,oe=W?.riskLevel??"write",be=c?.overrides?.[C],$e=E!==void 0&&E!==q&&he===E?xs(be,Ft(oe,E)):be,{result:cn,reason:F,onComplete:Ln,token:ut,id:vi,expiresAt:Uc}=await Ss({pluginId:o,endpointPath:C,args:x,mode:he,override:$e,riskLevel:oe,meta:W,db:u,timeoutMs:d?to(d.timeout):void 0,tenantId:p,approvalMode:d?.mode});if(cn==="blocked"){let un;F==="denied"?un=`Action '${C}' was denied by the user. Await further instructions before proceeding.`:F==="policy"?un=E?`Action '${C}' is blocked by permission mode '${E}'.`:`Action '${C}' is blocked by the permission policy. Update the corsair config to allow it.`:F==="timeout"?un=`Action '${C}' timed out waiting for approval.`:ut&&vi?un=await Xr({permissionsOptions:d,manual:g,hub:f,permissionId:vi,permissionToken:ut,plugin:o,endpoint:C,args:x,tenantId:p??"default",expiresAt:Uc??new Date(Date.now()+(d?to(d.timeout):600*1e3)).toISOString(),operationPath:C}):un=`Action '${C}' requires user approval before it can run.`;let Lc=F==="denied"||F==="policy"||F==="timeout"?F:"pending";throw new de(un,Lc)}re=Ln}let Bn=async(W,oe,be)=>{try{return await H(oe,be)}catch(ct){if(ct instanceof Error){let $e=await ma(ct,o,C,typeof be=="object"&&be!==null?be:{args:be},i);if(W<($e.maxRetries||0)){let cn=W+1;console.log(`Retrying (${cn} / ${$e.maxRetries})...`);let F;if($e.headersRetryAfterMs)F=$e.headersRetryAfterMs;else switch($e.retryStrategy){case"exponential_backoff":F=Math.pow(2,cn-1)*1e3;break;case"exponential_backoff_jitter":let Ln=Math.pow(2,cn-1)*1e3,ut=(Math.random()-.5)*1e3;F=Math.max(0,Ln+ut);break;case"linear_1s":F=1e3;break;case"linear_2s":F=2e3;break;case"linear_3s":F=3e3;break;case"linear_4s":F=4e3;break;default:F=1e3;break}return await new Promise(Ln=>setTimeout(Ln,F)),await Bn(cn,oe,be)}}throw ct}},at,Dc={...t,meteredOperationId:C},Hc=typeof t.authType=="string"?t.authType:void 0,Bc=typeof t.tenantId=="string"?t.tenantId:void 0;try{Hc==="managed_pricing"&&f?at=await fr({hub:f,tenantId:Bc??p,meteredOperationId:C},{plugin:o,cache:cd(o)}):s&&(at=await s(Dc,"endpoint"))}catch(W){if(W instanceof ke)throw h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!1}),await Qo(u,{tenantId:W.tenantId??p,plugin:W.plugin,connectUrl:W.connectUrl}),W;if(W instanceof S){h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!1});try{await ga({error:W,manual:g,hub:f,plugin:h,tenantId:p,database:u,kek:b,plugins:k,multiTenancy:T})}catch(oe){throw oe instanceof S&&await Qo(u,{tenantId:oe.tenantId??p,plugin:oe.pluginId,connectUrl:oe.connectUrl}),oe}}throw W}if(!B?.before&&!B?.after){let W=await Bn(0,{...t,key:at},x);return await re?.(),h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!0}),W}let Ti={...t,key:at},Un=B.before?await B.before(Ti,x):{ctx:Ti,args:x,continue:!0,passToAfter:void 0};if(Un.continue===!1)return;let Pi=await Bn(0,Un.ctx,Un.args);return await B.after?.(Un.ctx,Pi,Un.passToAfter),await re?.(),h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!0}),Pi};r[v]=R}else if(H&&typeof H=="object"){let B={};Xo({endpoints:H,hooks:D,ctx:t,tree:B,pluginId:o,errorHandlers:i,currentPath:[...a,v],keyBuilder:s,permissionsConfig:c,endpointMeta:l,database:u,permissionsOptions:d,tenantId:p,manualConfig:g,hubConfig:f,plugin:h,kek:b,allPlugins:k,multiTenancy:T}),r[v]=B}}}var ye={findByEntityId:"read",existsByEntityId:"read",findIdByEntityId:"read",findById:"read",findManyByEntityIds:"read",list:"read",search:"read",count:"read",upsertByEntityId:"write",deleteById:"destructive",deleteByEntityId:"destructive"},ld=/^\$+date$/;function ba(e){if(typeof e!="object"||e===null||Array.isArray(e))return null;let n=Object.keys(e),t=n[0];return n.length!==1||!t||!ld.test(t)?null:typeof e[t]=="string"?t:null}function nn(e){if(e instanceof Date)return{$date:e.toISOString()};if(Array.isArray(e))return e.map(nn);let n=ba(e);return n?{[`$${n}`]:e[n]}:e&&typeof e=="object"?Object.fromEntries(Object.entries(e).map(([t,r])=>[t,nn(r)])):e}function tn(e){let n=ba(e);if(n){let t=e[n];if(n!=="$date")return{[n.slice(1)]:t};let r=new Date(t);if(Number.isNaN(r.getTime()))throw L(`Invalid $date value "${t}" \u2014 expected an ISO 8601 timestamp`);return r}return Array.isArray(e)?e.map(tn):e&&typeof e=="object"?Object.fromEntries(Object.entries(e).map(([t,r])=>[t,tn(r)])):e}async function ei(e,n,t){let r=Object.hasOwn(ye,n.method)?ye[n.method]:void 0;if(!r)throw new w(404,"unknown_db_method",`Unknown db method "${n.method}" \u2014 expected one of ${Object.keys(ye).join(", ")}`);Ge(`${n.plugin}.db.${n.entityType}.${n.method}`,r);let i=e?.[n.plugin]?.db;if(!i)throw new w(404,"unknown_plugin",`Plugin "${n.plugin}" has no entity store`);let a=Object.hasOwn(i,n.entityType)?i[n.entityType]:void 0,s=a?.[n.method];if(typeof s!="function")throw new w(404,"unknown_entity_type",`Plugin "${n.plugin}" has no entity type "${n.entityType}"`);return s.apply(a,t)}function dd(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function ni({webhooks:e,hooks:n,ctx:t,webhooksTree:r,keyBuilder:o}){for(let[i,a]of Object.entries(e)){let s=n?.[i];if(dd(a)){let c=s,l=async u=>{let d=(g,f)=>a.handler(g,f),p=o&&u?.hubVerified!==!0?await o(t,"webhook"):void 0;return!c?.before&&!c?.after?d({...t,key:p},u):(async()=>{let g={...t,key:p},f=c.before?await c.before(g,u):{ctx:g,args:u,continue:!0,passToAfter:void 0};if(f.continue===!1)return;let h=await d(f.ctx,f.args);return h?.success===!0&&await c.after?.(f.ctx,h,f.passToAfter),h})()};r[i]={match:a.match,handler:l}}else if(a&&typeof a=="object"){let c={};ni({webhooks:a,hooks:s,ctx:t,webhooksTree:c,keyBuilder:o}),r[i]=c}}}function ka(e){return e&&typeof e=="object"?e:{}}async function wa(e,n){return Z({hub:e,path:`/workflows?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ka(t).workflows;return Array.isArray(r)?r:[]}})}async function Ca(e,n){return Z({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>ka(t).workflow})}async function Ta(e,n){await _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/status?tenantId=${encodeURIComponent(n.tenantId)}`,body:{status:n.status},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}async function Pa(e,n){await _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/rename?tenantId=${encodeURIComponent(n.tenantId)}`,body:{name:n.name},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}async function va(e,n){return _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/run?tenantId=${encodeURIComponent(n.tenantId)}`,body:{payload:n.payload,idempotencyKey:n.idempotencyKey},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}function ti(e){return e&&typeof e=="object"?e:{}}async function Ra(e,n){return Z({hub:e,path:`/runs?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ti(t).runs;return Array.isArray(r)?r:[]}})}async function Aa(e,n){return Z({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/runs?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>{let r=ti(t).runs;return Array.isArray(r)?r:[]}})}async function xa(e,n){return Z({hub:e,path:`/runs/${encodeURIComponent(n.runId)}?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Run "${n.runId}" not found`,parseResponse:t=>ti(t).run})}async function ri(e,n,t){await _({hub:e,path:`/runs/${encodeURIComponent(t.runId)}/${n}?tenantId=${encodeURIComponent(t.tenantId)}`,body:{},notFoundMessage:`Run "${t.runId}" cannot be ${n==="cancel"?"canceled":`${n}d`} in its current state`,parseResponse:r=>r})}var Ia=(e,n)=>ri(e,"approve",n),Sa=(e,n)=>ri(e,"deny",n),_a=(e,n)=>ri(e,"cancel",n);function Ea(e,n){let t=()=>{if(!e)throw new Error("corsair.workflows.runs requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e};return{list:r=>r?.workflowId?Aa(t(),{workflowId:r.workflowId,tenantId:n}):Ra(t(),{tenantId:n}),get:r=>xa(t(),{runId:r,tenantId:n}),approve:r=>Ia(t(),{runId:r,tenantId:n}),deny:r=>Sa(t(),{runId:r,tenantId:n}),cancel:r=>_a(t(),{runId:r,tenantId:n})}}function Oa(e,n){let t=()=>{if(!e)throw new Error("corsair.workflows requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e},r=(o,i)=>Ta(t(),{workflowId:o,tenantId:n,status:i});return{list:()=>wa(t(),{tenantId:n}),get:o=>Ca(t(),{workflowId:o,tenantId:n}),run:(o,i)=>va(t(),{workflowId:o,tenantId:n,payload:i?.payload,idempotencyKey:i?.idempotencyKey}),runs:Ea(e,n),disable:o=>r(o,"inactive"),enable:o=>r(o,"active"),archive:o=>r(o,"archived"),unarchive:o=>r(o,"inactive"),rename:(o,i)=>Pa(t(),{workflowId:o,tenantId:n,name:i})}}function pd(e,n,t,r){let o=null;return async()=>{if(o)return o;if(!e)throw new Error("Database not configured");let{accountId:i}=await la({database:e,integrationName:n,tenantId:t,ensureProvisioned:r});return o=i,o}}function gd(e,n){let t={};for(let[r,o]of Object.entries(n))t[r]=new Proxy(o,{get(i,a){let s=i[a];if(typeof a!="string"||typeof s!="function")return s;let c=Object.hasOwn(ye,a)?ye[a]:void 0;if(!c)return s;let l=s;return async(...u)=>(Ge(`${e}.db.${r}.${a}`,c),l.apply(i,u))}});return t}function fd(e,n,t,r,o){return e?Sr(e.db,n,t,r,o):{findByEntityId:async()=>null,existsByEntityId:async()=>!1,findIdByEntityId:async()=>null,findById:async()=>null,findManyByEntityIds:async()=>[],list:async()=>[],search:async()=>[],upsertByEntityId:async()=>{throw new Error("Database not configured")},deleteById:async()=>!1,deleteByEntityId:async()=>!1,count:async()=>0}}function oi(e,n){let{database:t,tenantId:r,kek:o,rootErrorHandlers:i,permissionsOptions:a,manualConfig:s,hubConfig:c,internalConfig:l}=n,u=r??"default",d=l&&t?()=>mn(l,u):void 0,p={},g={};for(let f of e)p[f.id]={},g[f.id]={};for(let f of e){let h=f.schema,b=pd(t,f.id,u,d);if(h?.entities){let E={};for(let[q,he]of Object.entries(h.entities)){let Bn=t?Sr(t.db,b,q,h.version,he):fd(void 0,b,q,h.version,he);E[q]=Bn}g[f.id].db=E,p[f.id].db=gd(f.id,E)}let k=f.options,T=f.authConfig,v;if(t&&o&&k?.authType){let E=T?.[k.authType]?.account??[];v=U({authType:k.authType,integrationName:f.id,tenantId:u,kek:o,database:t,extraAccountFields:E,ensureProvisioned:d}),p[f.id].keys=v}let H={database:t,db:g[f.id]?.db??{},$getAccountId:b,...f.options?{options:f.options}:{},...v?{keys:v,authType:k?.authType}:{},tenantId:u,...c?{hub:c}:{}},D=f.endpoints??{},B=f.hooks,C={...i,...f.errorHandlers},R={},x=f.options?.permissions;Xo({endpoints:D,hooks:B,ctx:H,tree:R,pluginId:f.id,errorHandlers:C,currentPath:[],keyBuilder:f.keyBuilder,permissionsConfig:x,endpointMeta:f.endpointMeta,database:t,permissionsOptions:a,tenantId:r,manualConfig:s?{...s,oauthConfig:f.oauthConfig,kek:o,tenantId:u}:void 0,hubConfig:c,plugin:f,kek:o,allPlugins:e,multiTenancy:l?.multiTenancy}),Object.keys(R).length>0&&(p[f.id].api=R),H.endpoints=R;let ee=f.webhooks??{},re=f.webhookHooks;if(Object.keys(ee).length>0&&!Mi(k?.authType)){let E={};ni({webhooks:ee,hooks:re,ctx:H,webhooksTree:E,keyBuilder:f.keyBuilder}),p[f.id].webhooks=E,f.pluginWebhookMatcher&&(p[f.id].pluginWebhookMatcher=f.pluginWebhookMatcher),f.pluginTenantWebhookMatcher&&(p[f.id].pluginTenantWebhookMatcher=f.pluginTenantWebhookMatcher)}}return p.chats=da(c,u),p.workflows=Oa(c,u),p}function Ma(e,n,t){let r={};for(let o of e){let i=o.options,a=o.authConfig;if(i?.authType){let s=a?.[i.authType]?.integration??[],c=$({authType:i.authType,integrationName:o.id,kek:t,database:n,extraIntegrationFields:s});r[o.id]=c}}return r}var yd=3e4;function hr(e){let n=e.length;for(;n>0&&e[n-1]==="/";)n--;return e.slice(0,n)}function md(e){let n=0;for(;n<e.length&&e[n]==="/";)n++;return e.slice(n)}function hd(e,n){return`${hr(e)}/${md(n)}`}function bd(e,n){let t=n??{},{error:r,message:o,...i}=t;return typeof r!="string"?new w(e,"internal_error","Internal error"):new w(e,r,o,i)}var ii=Symbol("cloudRequestTimeout");async function G(e,n,t,r){let o=Rn(),i=e.fetch??globalThis.fetch,a=e.timeoutMs??yd,s=new AbortController,c,l=new Promise(g=>{c=setTimeout(()=>{s.abort(),g(ii)},a)}),u;try{let g=i(hd(e.baseUrl,t),{method:n,headers:{authorization:`Bearer ${e.apiKey}`,"content-type":"application/json",...o?{"x-corsair-mode":o}:{}},body:r===void 0?void 0:JSON.stringify(r),signal:s.signal}).catch(h=>{if(s.signal.aborted)return ii;throw h}),f=await Promise.race([g,l]);if(f===ii)throw new w(0,"internal_error","Cloud request timed out");u=f}finally{clearTimeout(c)}let d=await u.text(),p;try{p=d?JSON.parse(d):void 0}catch{p=void 0}if(!u.ok)throw bd(u.status,p);if(p===void 0)throw new w(u.status,"internal_error","Invalid or empty response body from runtime");return p}var z={invoke:"/:tenant/:plugin/call/:op",entityDb:"/:tenant/:plugin/db/:entity/:method",instances:"/instances",connectLinks:"/connect/links",tenants:"/tenants",tenant:"/tenants/:id",connectionStatus:"/connection-status",disconnect:"/disconnect",permission:"/permissions/:id",permissionLookup:"/permissions/lookup-by-token"};var kd=new Set(["keys","webhooks"]),wd=new Set(["chats","workflows"]),si=new Set(["then","catch","finally"]);function me(e){return typeof e=="function"?e():Promise.resolve(e)}function Da(e,n,t,r){let o=async(...i)=>{let a=await me(e);return(await G(a,"POST",z.invoke.replace(":tenant",encodeURIComponent(n)).replace(":plugin",encodeURIComponent(t)).replace(":op",r.map(encodeURIComponent).join(".")),{args:i[0]})).data};return new Proxy(o,{get(i,a){if(!(typeof a!="string"||si.has(a)))return Da(e,n,t,[...r,a])}})}function Cd(e,n,t){return new Proxy({},{get(r,o){if(!(typeof o!="string"||si.has(o)))return new Proxy({},{get(i,a){if(typeof a!="string")return;let s=Object.hasOwn(ye,a)?ye[a]:void 0;if(s)return async(...c)=>{Ge(`${t}.db.${o}.${a}`,s);let l=await me(e),u=await G(l,"POST",z.entityDb.replace(":tenant",encodeURIComponent(n)).replace(":plugin",encodeURIComponent(t)).replace(":entity",encodeURIComponent(o)).replace(":method",encodeURIComponent(a)),{args:nn(c)});return tn(u.data)}}})}})}function br(e,n){let t=e?new Set(e.map(r=>r.id)):null;return new Proxy({},{get(r,o){if(!(typeof o!="string"||si.has(o))){if(wd.has(o))throw new Error(`"${o}" is not available in cloud mode (deferred)`);if(t&&!t.has(o))throw new Error(`Unknown plugin "${o}"`);return new Proxy({},{get(i,a){if(a==="api")return Da(n.transport,n.tenantId,o,[]);if(a==="db")return Cd(n.transport,n.tenantId,o);if(typeof a=="string"&&kd.has(a))throw new Error(`"${a}" is not available in cloud mode (deferred)`)}})}}})}function kr(e){return{connect:{createLink:n=>{if(!n.plugin||!n.tenantId)throw new Error('connect.createLink requires both "plugin" and "tenantId" in cloud mode');return me(e).then(t=>G(t,"POST",z.connectLinks,n))}},tenants:{create:n=>me(e).then(t=>G(t,"POST",z.tenants,n)),list:()=>me(e).then(n=>G(n,"GET",z.tenants)),get:n=>me(e).then(t=>G(t,"GET",z.tenant.replace(":id",encodeURIComponent(n))))},connectionStatus:{get:n=>me(e).then(t=>G(t,"GET",`${z.connectionStatus}?tenantId=${encodeURIComponent(n.tenantId)}`))},disconnect:n=>me(e).then(t=>G(t,"POST",z.disconnect,n)),permissions:{get:n=>me(e).then(t=>"id"in n?G(t,"GET",z.permission.replace(":id",encodeURIComponent(n.id))):G(t,"POST",z.permissionLookup,{token:n.token}))}}}var Ae=class extends w{type;retryable;param;docUrl;requestId;constructor(n,t){super(n,t.code,t.message,{...t}),this.name="CloudApiError",this.type=t.type??"api_error",this.retryable=t.retryable??(n===0||n===429||n>=500),this.param=t.param,this.docUrl=t.doc_url,this.requestId=t.request_id}};function rt(e,n,t){let r=t?.get("request-id")?.trim()||void 0,i=(n??{}).error;if(typeof i=="string"){let a=n.message;return new Ae(e,{code:i,message:typeof a=="string"?a:void 0,request_id:r})}return i&&typeof i=="object"&&typeof i.code=="string"?new Ae(e,{request_id:r,...i}):new Ae(e,{code:e===0?"request_failed":"internal_error",message:`Corsair Cloud returned ${e} with no error body`,request_id:r})}var Td=3e4,Pd=new Set(["GET","HEAD","PUT","DELETE"]),vd=/^[a-z][a-z0-9-]{0,31}$/;function rn(e,n){if(!vd.test(e))throw new Error(`${n}: "${e}" is not a valid instance key. Lowercase letter first, then letters, digits or hyphens, up to 32 characters.`)}function on(e){let n=new URLSearchParams;for(let[r,o]of Object.entries(e))o!==void 0&&n.set(r,String(o));let t=n.toString();return t?`?${t}`:""}function A(e,n){return`${e}/${encodeURIComponent(n)}`}async function wr(e,n,t,r,o={}){let i=e.fetch??globalThis.fetch,a=new AbortController;o.signal?.aborted&&a.abort();let s=()=>a.abort();o.signal?.addEventListener("abort",s,{once:!0});let c=setTimeout(()=>a.abort(),e.timeoutMs??Td),l={authorization:`Bearer ${e.apiKey}`,"content-type":"application/json"};e.apiVersion&&(l["corsair-version"]=e.apiVersion),o.idempotencyKey&&(l["idempotency-key"]=o.idempotencyKey),o.requestId&&(l["x-corsair-request-id"]=o.requestId);let u;try{u=await i(`${e.baseUrl}${t}`,{method:n,headers:l,body:r===void 0?void 0:JSON.stringify(r),signal:a.signal});let d=await u.text(),p;try{p=d?JSON.parse(d):void 0}catch{p=void 0}if(!u.ok)throw rt(u.status,p,u.headers);if(p===void 0&&u.status!==204)throw rt(u.status,void 0,u.headers);return p}catch(d){if(o.signal?.aborted||d instanceof Ae)throw d;let p=Pd.has(n),g=u?p?!0:void 0:p||!!o.idempotencyKey;throw rt(u?.status??0,{error:{code:"request_failed",message:d instanceof Error?d.message:String(d),retryable:g}},u?.headers)}finally{clearTimeout(c),o.signal?.removeEventListener("abort",s)}}function ai(e,n){rn(n,"withInstance");let t=(s,c,l,u)=>wr(e,s,c,l,u),r=(...s)=>[n,...s].join(":"),o=s=>on({...s,instance:n}),i=s=>`${A("/instances",n)}${s}`,a=s=>`${A("/webhooks",r(s))}/deliveries`;return{instanceKey:n,tenants:{list:(s={},c)=>t("GET",`/tenants${o(s)}`,void 0,c),create:(s,c)=>t("POST","/tenants",{...s,instance:n},c),get:(s,c)=>t("GET",A("/tenants",r(s)),void 0,c),update:(s,c,l)=>t("PATCH",A("/tenants",r(s)),c,l),delete:(s,c)=>t("DELETE",A("/tenants",r(s)),void 0,c)},access:{list:(s={},c)=>t("GET",`/access${o(s)}`,void 0,c),get:(s,c)=>t("GET",A("/access",r(s)),void 0,c),set:(s,c,l)=>t("PUT",A("/access",r(s)),c,l),revoke:(s,c)=>t("DELETE",A("/access",r(s)),void 0,c)},connections:{list:(s={},c)=>t("GET",`/connections${o(s)}`,void 0,c),get:(s,c,l)=>t("GET",A("/connections",r(s,c)),void 0,l),delete:(s,c,l)=>t("DELETE",A("/connections",r(s,c)),void 0,l)},connect:{createSession:(s,c)=>t("POST","/connect/sessions",{...s,instance:n},c)},integrations:{list:(s={},c)=>t("GET",`/integrations${o(s)}`,void 0,c),get:(s,c)=>t("GET",A("/integrations",r(s)),void 0,c),put:(s,c,l)=>t("PUT",A("/integrations",r(s)),c,l),delete:(s,c)=>t("DELETE",A("/integrations",r(s)),void 0,c),operations:(s,c)=>t("GET",`${A("/integrations",r(s))}/operations`,void 0,c),oauthApp:{get:(s,c)=>t("GET",`${A("/integrations",r(s))}/oauth-app`,void 0,c),put:(s,c,l)=>t("PUT",`${A("/integrations",r(s))}/oauth-app`,c,l),delete:(s,c)=>t("DELETE",`${A("/integrations",r(s))}/oauth-app`,void 0,c)}},webhooks:{list:(s={},c)=>t("GET",`/webhooks${o(s)}`,void 0,c),create:(s,c)=>t("POST","/webhooks",{...s,instance:n},c),get:(s,c)=>t("GET",A("/webhooks",r(s)),void 0,c),delete:(s,c)=>t("DELETE",A("/webhooks",r(s)),void 0,c),rotateSecret:(s,c,l)=>t("POST",`${A("/webhooks",r(s))}/rotate-secret`,c,l),deliveries:{list:(s,c={},l)=>t("GET",`${a(s)}${on(c)}`,void 0,l),get:(s,c,l)=>t("GET",A(a(s),c),void 0,l),retry:(s,c,l)=>t("POST",`${A(a(s),c)}/retry`,void 0,l)}},signingSecret:{get:s=>t("GET",i("/signing-secret"),void 0,s),rotate:s=>t("POST",i("/signing-secret/rotate"),void 0,s)},apply:s=>t("POST",i("/apply"),void 0,s),removeFromRuntime:s=>t("POST",i("/remove"),void 0,s),reconcile:s=>t("POST",i("/reconcile"),void 0,s)}}function ci(e){let n=(t,r,o,i)=>wr(e,t,r,o,i);return{project:{get:t=>n("GET","/project",void 0,t)},keys:{get:t=>n("GET","/keys",void 0,t),rotate:t=>n("POST","/keys/rotate",void 0,t)},instances:{list:(t={},r)=>n("GET",`/instances${on(t)}`,void 0,r),create:(t,r)=>(rn(t.instance_key,"instances.create"),n("POST","/instances",t,r)),get:(t,r)=>(rn(t,"instances.get"),n("GET",A("/instances",t),void 0,r)),update:(t,r,o)=>(rn(t,"instances.update"),n("PATCH",A("/instances",t),r,o)),delete:(t,r)=>(rn(t,"instances.delete"),n("DELETE",A("/instances",t),void 0,r))},integrations:{catalog:(t={},r)=>n("GET",`/integrations/catalog${on(t)}`,void 0,r)},mcp:{links:{list:(t={},r)=>n("GET",`/mcp/links${on(t)}`,void 0,r),mint:(t,r)=>n("POST","/mcp/links",t,r),get:(t,r)=>n("GET",A("/mcp/links",t),void 0,r),update:(t,r,o)=>n("PATCH",A("/mcp/links",t),r,o),delete:(t,r)=>n("DELETE",A("/mcp/links",t),void 0,r),rotate:(t,r)=>n("POST",`${A("/mcp/links",t)}/rotate`,void 0,r)},tokens:{mint:(t,r)=>n("POST","/mcp/tokens",t,r)}}}}var Ha="default",Rd="corsairCloud: the management API needs a ck_cloud_<slug>.<secret> key, or an explicit `managementUrl`.",Ad=new Set(["then","catch","finally","toString","toJSON","valueOf","constructor","inspect",Symbol.toPrimitive,Symbol.toStringTag,Symbol.iterator,Symbol.asyncIterator]);function ui(e={}){return new Proxy(e,{get(n,t,r){if(Reflect.has(n,t))return Reflect.get(n,t,r);if(!Ad.has(t))throw new Error(Rd)}})}function xe(e){throw new Error(`"${e}" is not available in cloud mode (deferred)`)}function xd(e){let n=e?.baseUrl?.trim()||process.env.CORSAIR_CLOUD_URL?.trim();if(!n)throw new Error("Cloud mode (ck_cloud_ key) requires a base URL \u2014 set hub.baseUrl or CORSAIR_CLOUD_URL.");return Fn(n),n}function Ba(e){return!!(e?.baseUrl?.trim()||process.env.CORSAIR_CLOUD_URL?.trim())}function Id(e,n){let t=kr(e);return{ok:()=>xe("manage.ok"),tenants:t.tenants,plugins:{list:()=>xe("manage.plugins.list"),get:()=>xe("manage.plugins.get")},connectionStatus:{get:r=>{let o=r?.tenantId||void 0;if(!o&&n)throw new Error("connectionStatus.get requires a tenantId in multi-tenant mode");return t.connectionStatus.get({tenantId:o??Ha})}},permissions:t.permissions,connect:{createLink:t.connect.createLink,resolve:()=>xe("manage.connect.resolve"),oauthCallback:()=>xe("manage.connect.oauthCallback")},disconnect:t.disconnect}}function Sd(e,n){let t=Id(e,n.multiTenancy);if(n.multiTenancy)return{withTenant:a=>{if(!a)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");return br(n.plugins,{transport:e,tenantId:a})},get keys(){return xe("keys")},get permissions(){return xe("permissions")},manage:t};let r=br(n.plugins,{transport:e,tenantId:Ha}),o={manage:t,get keys(){return xe("keys")},get permissions(){return xe("permissions")}};return new Proxy(r,{get(a,s,c){return typeof s=="string"&&s in o?Reflect.get(o,s,c):Reflect.get(a,s,c)}})}function Ua(e){return Sd({baseUrl:xd(e.hub),apiKey:e.hub.projectApiKey},{multiTenancy:!!e.multiTenancy,plugins:e.plugins})}function _d(e){let n=hr(e),t="/api/corsair";return n.endsWith(t)?n.slice(0,-t.length):n}async function Ed(e){let n=await G({...e,baseUrl:_d(e.baseUrl)},"GET",z.instances),t=new Map;for(let r of n.instances)Fn(r.url,`Instance "${r.instanceKey}" URL`),t.set(r.instanceKey,r.url);return t}function Od(e){let n=e.apiKey?.trim();if(!n)throw new Error("corsairCloud: apiKey is required");let t=Ri(n),r=e.url?.trim()||Ai(n);if(!r)throw new Error("corsairCloud: could not resolve a URL from apiKey \u2014 pass a ck_cloud_<slug>.<secret> key, or set `url` explicitly.");Fn(r);let o={baseUrl:r,apiKey:n,fetch:e.fetch,timeoutMs:e.timeoutMs},a=(hr(e.managementUrl?.trim()??"")||void 0)??(t?xi(r,t):null);a&&Fn(a,"Management base URL");let s=a?{baseUrl:a,apiKey:n,fetch:e.fetch,timeoutMs:e.timeoutMs,apiVersion:e.apiVersion}:null,c=null;function l(g){return g&&c===g&&(c=null),c||(c=Ed(o).catch(f=>{throw c=null,f})),c}async function u(g){let f=l(),b=(await f).get(g)??(await l(f)).get(g);if(b)return b;let k=[...(await l()).keys()].join(", ");throw new Error(`corsairCloud.withInstance("${g}"): no such instance \u2014 available: ${k||"(none)"}`)}let d=kr(o),p={tenants:d.tenants,permissions:d.permissions};return{manage:s?{...ci(s),...p}:ui(p),withInstance:g=>{let f=s?ai(s,g):ui(),h=async()=>({...o,baseUrl:await u(g)}),b=kr(h),k={withTenant(T){if(!T)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");return br(void 0,{transport:h,tenantId:T})},connectionStatus:b.connectionStatus,disconnect:b.disconnect,createConnectLink:b.connect.createLink};return s?{...f,...k}:ui(k)}}}var Md="createCorsair({ approval: ... }) is deprecated. Rename to permissions: { timeout, onTimeout, mode }.";function La(e){let{permissions:n,approval:t}=e;if(n&&t)throw new Error("createCorsair was given both permissions and approval config. Use permissions only \u2014 approval is deprecated.");return t?(console.warn(`[corsair] ${Md}`),t):n}var Dd=e=>new w(404,"unknown_plugin",`Plugin '${e}' is not registered.`),Hd=(e,n)=>new w(404,"unknown_op",`Operation '${n}' not found on plugin '${e}'.`),Cr=(e="/call")=>new w(403,"call_disabled",`The ${e} route is disabled. Construct managementHandler with { unsafeAllowUnauthenticated: true } to enable it \u2014 only when your own backend fronts the handler.`),Bd=e=>new w(401,"not_connected",`Tenant is not connected for plugin '${e}'. Reconnect and retry.`),Fa=e=>new w(403,"permission_denied",`The call was blocked (${e}).`,{reason:e}),Ud=()=>new w(403,"approval_required","This action needs human approval before it can run. Approval is not resumable over HTTP in this version.",{reason:"pending"}),Ld=(e,n)=>new w(502,"provider_error","The provider returned an error.",{providerStatus:e,body:n});function Fd(e,n){if(e instanceof w)return e;if(e instanceof S)return Bd(e.pluginId||n);if(e instanceof vn)return Fa("readonly");if(e instanceof de)return e.reason==="pending"?Ud():Fa(e.reason);if(e instanceof Error&&e.name==="ApiError"){let t=e;return Ld(typeof t.status=="number"?t.status:502,t.body)}return console.error("[corsair] unhandled error in call operation",e),new w(500,"internal_error","Internal error")}var Nd=new WeakMap,Na=new WeakMap,$d=512;function $a(e,n){let t=e.get(n);return t||(t=new Map,e.set(n,t)),t}function Wd(e,n,t){if(n.size<=$d)return;let r=Na.get(e);for(let o of n.keys())if(o!==t&&(r?.get(o)??0)===0){n.delete(o);return}}function qd(e,n,t){if(!n.multiTenancy)return{client:e};let r=typeof t=="string"?t.trim():"";if(!r)throw L("tenant is required for a multi-tenant runtime",{missingFields:["tenant"]});let o=$a(Nd,e),i=o.get(r);if(i)return o.delete(r),o.set(r,i),{client:i,tenantId:r};let a=e.withTenant(r);return o.set(r,a),Wd(e,o,r),{client:a,tenantId:r}}function jd(e,n){let t=e;for(let r of n.split(".")){if(t==null||typeof t!="object"||!Object.prototype.hasOwnProperty.call(t,r))return null;t=t[r]}return typeof t=="function"?t:null}function Wa(e,n=[]){let t=[];for(let[r,o]of Object.entries(e??{}))typeof o=="function"?t.push([...n,r].join(".")):o&&typeof o=="object"&&t.push(...Wa(o,[...n,r]));return t}function qa(e){let n={};for(let t of e.plugins)n[t.id]=Wa(t.endpoints??{});return n}async function li(e,n,t,r){if(!n.plugins.some(s=>s.id===t.plugin))throw Dd(t.plugin);let{client:o,tenantId:i}=qd(e,n,t.tenant),a=i?$a(Na,e):null;a&&i&&a.set(i,(a.get(i)??0)+1);try{return await r(o)}catch(s){throw Fd(s,t.plugin)}finally{if(a&&i){let s=(a.get(i)??1)-1;s<=0?a.delete(i):a.set(i,s)}}}async function ja(e,n,{plugin:t,op:r,tenant:o,args:i}){return li(e,n,{plugin:t,tenant:o},a=>{let s=a[t],c=jd(s?.api,r);if(!c)throw Hd(t,r);return c(i??{})})}function sn(e,n){if(e===void 0)return n;if(e===null)throw new w(401,"unauthenticated","Could not determine the tenant for this request. Sign in and retry.");return e}function ot(e){if(e!==void 0)throw new w(403,"forbidden","This route is disabled when resolveTenant is configured (end-user mode). Use a handler without resolveTenant, behind your own admin auth.")}var Ga=[{method:"GET",pattern:"/ok",public:!0,handler:async()=>I(200,Nt())},{method:"GET",pattern:"/tenants",handler:async({internal:e,scopedTenant:n})=>(ot(n),I(200,await xn(e)))},{method:"POST",pattern:"/tenants",handler:async({internal:e,body:n,scopedTenant:t})=>(ot(t),I(201,await qt(e,n)))},{method:"GET",pattern:"/tenants/:id",handler:async({internal:e,params:n,scopedTenant:t})=>(ot(t),I(200,await Wt(e,n.id)))},{method:"GET",pattern:"/plugins",handler:async({internal:e})=>I(200,await An(e))},{method:"GET",pattern:"/plugins/:id",handler:async({internal:e,params:n})=>I(200,await $t(e,n.id))},{method:"GET",pattern:"/connection-status",handler:async({internal:e,query:n,scopedTenant:t})=>I(200,await jt(e,sn(t,n.tenantId)))},{method:"GET",pattern:"/permissions/:id",handler:async({internal:e,params:n,scopedTenant:t})=>(ot(t),I(200,await oo(e,n.id)))},{method:"POST",pattern:"/permissions/lookup-by-token",public:!0,handler:async({internal:e,body:n})=>{let t=n?.token?.trim();return t?I(200,await so(e,t)):I(400,{error:"bad_request",message:"token is required",missingFields:["token"]})}},{method:"POST",pattern:"/connect/links",handler:async({corsair:e,internal:n,body:t,scopedTenant:r})=>{let o=t,i=sn(r,o.tenantId);return I(200,await Zt(e,n,{...o,tenantId:i}))}},{method:"GET",pattern:"/connect/resolve",public:!0,handler:async({corsair:e,internal:n,query:t})=>I(200,await Gt(e,n,t.state??""))},{method:"POST",pattern:"/connect/oauth/callback",public:!0,handler:async({corsair:e,internal:n,body:t})=>I(200,await zt(e,n,t))},{method:"GET",pattern:"/connect/request",handler:async({internal:e,query:n,scopedTenant:t})=>{let r=sn(t,n.tenantId)??"default",o=e.database?await Yo(e.database,r):null;return I(200,{request:o},{"cache-control":"no-store"})}},{method:"POST",pattern:"/connect/request/clear",handler:async({internal:e,body:n,scopedTenant:t})=>{let r=n,o=sn(t,r?.tenantId)??"default";return e.database&&await ya(e.database,o,void 0,r?.plugin),I(200,{ok:!0})}},{method:"POST",pattern:"/disconnect",handler:async({internal:e,body:n,scopedTenant:t})=>{let r=n??{},o=sn(t,r.tenantId);return I(200,await Kt(e,{...r,tenantId:o}))}},{method:"GET",pattern:"/call",handler:async({internal:e,allowCall:n})=>{if(!n)throw Cr();return I(200,{plugins:qa(e)})}},{method:"POST",pattern:"/:tenant/:plugin/db/:entityType/:method",handler:async({corsair:e,internal:n,req:t,params:r,body:o,scopedTenant:i,allowCall:a})=>{if(!a)throw Cr("/db");ot(i);let s=o??{};if(s.args!==void 0&&!Array.isArray(s.args))throw L("args must be an array");let c=sn(i,r.tenant),l=tn(s.args??[]),u=await li(e,n,{plugin:r.plugin,tenant:c},d=>Za(t,()=>ei(d,{plugin:r.plugin,entityType:r.entityType,method:r.method},l)));return I(200,{data:nn(u)})}},{method:"POST",pattern:"/:tenant/:plugin/call/:op",handler:async({corsair:e,internal:n,req:t,params:r,body:o,scopedTenant:i,allowCall:a})=>{if(!a)throw Cr();let s=o??{},c=sn(i,r.tenant),l=await Za(t,()=>ja(e,n,{plugin:r.plugin,op:r.op,tenant:c,args:s.args}));return I(200,{data:l})}}];(()=>{let e=new Set;for(let n of Ga){let t=`${n.method} ${n.pattern}`;if(e.has(t))throw new Error(`Duplicate management route registered: ${t}`);e.add(t)}})();function Kd(e,n){let t=e.split("/").filter(Boolean),r=n.split("/").filter(Boolean);if(t.length!==r.length)return null;let o={};for(let i=0;i<t.length;i++){let a=t[i],s=r[i];if(a.startsWith(":"))o[a.slice(1)]=decodeURIComponent(s);else if(a!==s)return null}return o}function Zd(e,n){if(!n)return e;let t=n.endsWith("/")?n.slice(0,-1):n;return e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length):e}async function Gd(e,n){if(e.method==="GET"||e.method==="HEAD"||!(e.headers.get("content-type")??"").includes("application/json"))return;let r=await dr(e,n).catch(o=>{throw o instanceof w?o:new w(400,"invalid_json","Request body is not valid JSON")});if(r)try{return JSON.parse(r)}catch{throw new w(400,"invalid_json","Request body is not valid JSON")}}var zd="/api/corsair",Ka=new Set(["open","cautious","strict","readonly"]);function Za(e,n){let t=e.headers.get("x-corsair-mode");if(t===null)return n();if(!Ka.has(t))throw L(`Unknown permission mode "${t}" \u2014 expected one of ${[...Ka].join(", ")}`);return Ut(t,n)}function j(e,n={}){let t=n.basePath??zd,r=Ve(n.maxBodyBytes),o=Ye(n.bodyStallTimeoutMs),i={maxBodyBytes:r,bodyStallTimeoutMs:o},a=P(e,()=>new Error("managementHandler: invalid corsair instance (missing internal config)"));return async s=>{try{let c=s.headers.get("content-length");if(c!==null&&Number(c)>r)throw En(r);let l=new URL(s.url),u=Zd(l.pathname,t),d=s.method.toUpperCase();if(d==="OPTIONS"||u==="/"||u==="")return await Qe(e,s,{maxBodyBytes:r,bodyStallTimeoutMs:o});if(d!=="GET"&&d!=="POST")return I(405,{error:"method_not_allowed",message:`Method ${d} not allowed`});let p=Object.fromEntries(l.searchParams);for(let g of Ga){if(g.method!==d)continue;let f=Kd(g.pattern,u);if(!f)continue;if(!g.public&&n.authenticate&&!await n.authenticate(s))return I(401,{error:"unauthorized",message:"invalid or missing credentials"});let h=await Gd(s,i),b=n.resolveTenant?await n.resolveTenant(s):void 0;return await g.handler({corsair:e,internal:a,req:s,params:f,query:p,body:h,scopedTenant:b,allowCall:(n.unsafeAllowUnauthenticated??!1)||!!n.authenticate})}throw Ue(`No route for ${d} ${u}`)}catch(c){if(n.onError){let u=await n.onError(c,s);if(u)return u}if(c instanceof w)return pe(c);let l=c instanceof Error?c.message:"Internal server error";return I(500,{error:"internal_error",message:l})}}}function Jd(e,n){if(e.get)return e.get(n);let t=e.headers[n]??e.headers[n.toLowerCase()];return Array.isArray(t)?t[0]:t}function Vd(e){if(Buffer.isBuffer(e))return e;if(e instanceof Uint8Array)return Buffer.from(e);if(typeof e=="string")return Buffer.from(e,"utf8");throw new TypeError(`corsair adapter: unsupported stream chunk type ${typeof e}`)}async function Yd(e,n,t){let r=[],o=0,i=e();try{let a=await lr(()=>i.next(),t);for(;a.done!==!0;){let s=Vd(a.value);if(o+=s.byteLength,o>n)throw En(n);r.push(s),a=await lr(()=>i.next(),t)}return Buffer.concat(r)}catch(a){try{Promise.resolve(i.return?.()).catch(()=>{})}catch{}throw a}}var za=!1;function Qd(){za||(za=!0,console.warn("[corsair] A JSON body parser consumed this request before the corsair adapter.","Re-serializing the parsed object is lossy and will likely fail Hub signature",'verification ("Invalid tunnel signature"). Fix on the corsair route only:',"Express \u2192 mount express.raw({ type: 'application/json' }) before the handler,","or capture raw bytes via express.json({ verify: (req, _res, buf) => { req.rawBody = buf; } }).","Fastify \u2192 call registerCorsairRawBodyParser(app) before listen()."))}async function Xd(e,n){let t=(e.method??"GET").toUpperCase();if(t==="GET"||t==="HEAD")return;let r=Ve(n.maxBodyBytes),o=Ye(n.bodyStallTimeoutMs),i;if(typeof e.rawBody=="string")i=e.rawBody;else if(e.rawBody instanceof Uint8Array)i=e.rawBody;else if(e.body!==void 0&&e.body!==null)typeof e.body=="string"||e.body instanceof Uint8Array?i=e.body:(Qd(),i=JSON.stringify(e.body));else{let s=e[Symbol.asyncIterator];if(typeof s!="function")return;let c=await Yd(s.bind(e),r,o);c.length>0&&(i=c)}if(i===void 0)return;if((typeof i=="string"?Buffer.byteLength(i,"utf8"):i.byteLength)>r)throw En(r);return typeof i=="string"?i:i}function Y(e){e.resume?.()}async function Fe(e,n={}){let t=Jd(e,"host")??"localhost",r=e.protocol??"http",o=e.originalUrl??e.url??"/",i=`${r}://${t}${o}`,a=new Headers;for(let[l,u]of Object.entries(e.headers))if(u!=null&&!ep.has(l.toLowerCase()))if(Array.isArray(u))for(let d of u)a.append(l,d);else a.set(l,u);let s={method:(e.method??"GET").toUpperCase(),headers:a},c=await Xd(e,n);return c!==void 0&&(s.body=c,a.has("content-type")||a.set("content-type","application/json")),new Request(i,s)}async function Q(e,n){typeof e.status=="function"?e.status(n.status):e.statusCode=n.status;let t=n.headers.getSetCookie();n.headers.forEach((o,i)=>{i!=="set-cookie"&&e.setHeader(i,o)}),t.length>0&&e.setHeader("set-cookie",t);let r=Buffer.from(await n.arrayBuffer());e.send?e.send(r):e.end?.(r)}var ep=new Set(["connection","keep-alive","proxy-authenticate","proxy-authorization","te","trailer","transfer-encoding","upgrade","content-length"]);function Ja(e,n){let t=j(e,n);return async(r,o,i)=>{try{let a=await t(await Fe(r,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(o,a)}catch(a){if(a instanceof w&&o.headersSent!==!0){await Q(o,pe(a)),Y(r);return}Y(r),i(a)}}}function np(e,n){let t=e[n];return Array.isArray(t)?t[0]:t}function tp(e){let n=(e.method??"GET").toUpperCase();if(n==="GET"||n==="HEAD"||e.body!==void 0||e.rawBody!==void 0)return;let t=np(e.headers,"content-type");if(!(!t||!t.includes("application/json"))&&!(e.raw.readableEnded!==!0&&e.raw.complete!==!0))throw new Error("corsair: Fastify consumed this JSON body before the corsair adapter could read it. Call registerCorsairRawBodyParser(app) before listen() so the original bytes reach the adapter verbatim (Hub signs deliveries over the exact bytes it sent).")}function Va(e){e.addContentTypeParser("application/json",{parseAs:"buffer"},(n,t,r)=>{n.rawBody=t;try{r(null,JSON.parse(t.toString("utf8")))}catch{r(Object.assign(new Error("Invalid JSON body"),{statusCode:400}))}})}function Ya(e,n){let t=j(e,n);return async(r,o)=>{tp(r);let i={method:r.method??r.raw.method,url:r.url??r.raw.url,headers:r.headers,protocol:r.protocol,body:r.body,rawBody:r.rawBody,resume:r.raw.resume?.bind(r.raw),[Symbol.asyncIterator]:r.raw[Symbol.asyncIterator]?.bind(r.raw)};try{let a=await t(await Fe(i,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));o.hijack?.(),await Q(o.raw,a)}catch(a){if(a instanceof w&&o.raw.headersSent!==!0&&o.hijack){o.hijack(),await Q(o.raw,pe(a)),Y(i);return}throw Y(i),a}}}function Qa(e,n){let t=j(e,n);return r=>t(r.req.raw)}function Xa(e,n){let t=j(e,n);return{GET:t,POST:t,OPTIONS:t}}function ec(e,n){let t=j(e,n);return async(r,o)=>{try{let i=await t(await Fe(r,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(o,i)}catch(i){if(o.headersSent===!0){console.error("[corsair] management response failed after headers were sent:",i),o.end?.(),Y(r);return}if(i instanceof w){await Q(o,pe(i)),Y(r);return}console.error("[corsair] management handler failed:",i),await Q(o,I(500,{error:"internal_error"})),Y(r)}}}function Tr(e,n){let t=j(e,n);return r=>t(r.request)}function nc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function tc(e,n){let t=Tr(e,n);return{loader:t,action:t}}function rc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function oc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function ic(e,n){let t=j(e,n);return async r=>{let o={method:r.node.req.method,url:r.node.req.url,headers:r.node.req.headers,protocol:r.node.req.protocol,body:r._body,rawBody:r.node.req.rawBody??r._rawBody,resume:r.node.req.resume?.bind(r.node.req),[Symbol.asyncIterator]:r.node.req[Symbol.asyncIterator]?.bind(r.node.req)};try{let i=await t(await Fe(o,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(r.node.res,i)}catch(i){if(i instanceof w&&r.node.res.headersSent!==!0){await Q(r.node.res,pe(i)),Y(o);return}throw Y(o),i}}}function sc(e,n){return j(e,n)}function ac(e){let n={[it]:e};return{ok:Nt,tenants:{list:()=>xn(e),create:t=>qt(e,t),get:t=>Wt(e,t)},plugins:{list:()=>An(e),get:t=>$t(e,t)},connectionStatus:{get:t=>jt(e,t?.tenantId)},permissions:{get:t=>Ds(e,t)},connect:{createLink:t=>Zt(n,e,t),resolve:t=>Gt(n,e,t),oauthCallback:t=>zt(n,e,t)},disconnect:t=>Kt(e,t)}}async function cc(e,n,t,r,o="pending"){if(!e)return null;try{let i=ln(),a=new Date;return await e.db.insertInto("corsair_events").values({id:i,created_at:a,updated_at:a,account_id:n,event_type:t,payload:r,status:o}).execute(),i}catch(i){return console.warn("Failed to log event:",i),null}}async function rp(e,n,t,r="pending"){try{let o=await e.$getAccountId();return cc(e.database,o,n,t,r)}catch(o){return console.warn("Failed to log event:",o),null}}import*as lc from"https";import*as Pr from"querystring";var op=["expires_in","refresh_token_expires_in"];function uc(e){let n={...e};for(let t of op){let r=e[t];if(typeof r=="string"){let o=Number(r);n[t]=Number.isFinite(o)?o:void 0}}return n}function ip(e){try{return uc(JSON.parse(e))}catch{}if(!e.includes("="))return null;let n=Pr.parse(e);return!n.access_token&&!n.error?null:uc({...n})}function It(e,n,t,r,o){let i=new URL(r.tokenUrl),a=r.tokenAuthMethod==="basic";return new Promise((s,c)=>{let l={code:e.trim(),redirect_uri:o,grant_type:"authorization_code"};a||(l.client_id=n,l.client_secret=t);let u=Pr.stringify(l),d={"Content-Type":"application/x-www-form-urlencoded",Accept:"application/json","Content-Length":Buffer.byteLength(u).toString()};a&&(d.Authorization=`Basic ${Buffer.from(`${n}:${t}`).toString("base64")}`);let p=lc.request({hostname:i.hostname,...i.port?{port:Number(i.port)}:{},path:i.pathname+i.search,method:"POST",headers:d},g=>{let f="";g.on("data",h=>{f+=h}),g.on("end",()=>{if(g.statusCode!==200){c(new Error(`Token exchange failed (${g.statusCode}): ${f}`));return}let h=ip(f);h?s(h):c(new Error(`Token endpoint returned non-JSON response: ${f}`))})});p.on("error",g=>c(new Error(`Request failed: ${g.message}`))),p.write(u),p.end()})}async function dc(e,n){let{keys:t,hub:r,plugin:o,tenantId:i}=e,[a,s,c]=await Promise.all([t.get_access_token(),t.get_expires_at(),t.get_refresh_token()]);if(On({accessToken:a,expiresAt:s,forceRefresh:n?.forceRefresh}))return{accessToken:a,expiresAt:Number(s),refreshed:!1};if(!c)throw new S(o,"oauth_2");let l=await _({hub:r,path:"/oauth/refresh",body:{plugin:o,tenantId:i,refresh_token:c},parseResponse:dn}),u=await Mn(t,l,s);return{accessToken:l.access_token,expiresAt:u,refreshed:!0}}async function pc(e){let{tokenUrl:n,refreshToken:t,clientSecret:r,clientId:o,tokenAuthMethod:i="body",bodyFormat:a="form",extraParams:s}=e,c={grant_type:"refresh_token",refresh_token:t,...s},l={Accept:"application/json"};i==="basic"?l.Authorization=`Basic ${Buffer.from(`${o??""}:${r}`).toString("base64")}`:i==="basic_secret_only"?l.Authorization=`Basic ${Buffer.from(`${r}:`).toString("base64")}`:(o&&(c.client_id=o),c.client_secret=r),a==="json"?l["Content-Type"]="application/json":l["Content-Type"]="application/x-www-form-urlencoded";let u=await fetch(n,{method:"POST",headers:l,body:a==="json"?JSON.stringify(c):new URLSearchParams(c)});if(!u.ok)throw new Error(`OAuth token refresh failed (${u.status}): ${await u.text()}`);let d=JSON.parse(await u.text());if(typeof d.access_token!="string"||d.access_token.length===0)throw new Error("OAuth token refresh returned no access_token");return{access_token:d.access_token,...typeof d.refresh_token=="string"&&d.refresh_token.length>0?{refresh_token:d.refresh_token}:{},...typeof d.expires_in=="number"?{expires_in:d.expires_in}:{},...typeof d.scope=="string"&&d.scope.length>0?{scope:d.scope}:{}}}async function gc(e,n){let t=await e.keys.get_integration_credentials(),r=`${n.plugin}:${e.tenantId}`;if(!t.client_secret){if(!e.hub)throw new S(n.plugin,"oauth_2");let l={keys:e.keys,hub:e.hub,plugin:n.plugin,tenantId:e.tenantId},u=g=>Xe(e.keys,r,async()=>(await dc(l,{forceRefresh:g})).accessToken);e._refreshAuth=()=>u(!0);let[d,p]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at()]);return On({accessToken:d,expiresAt:p})?d:u(!1)}let o=t.client_secret,i=t.client_id,a=l=>Xe(e.keys,r,async()=>{let[u,d,p]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at(),e.keys.get_refresh_token()]);if(!l&&On({accessToken:u,expiresAt:d}))return u;if(!p)throw new S(n.plugin,"oauth_2");let g=await pc({tokenUrl:n.tokenUrl,tokenAuthMethod:n.tokenAuthMethod,bodyFormat:n.bodyFormat,extraParams:n.extraParams,clientId:i,clientSecret:o,refreshToken:p});return await Mn(e.keys,g,d),g.access_token});e._refreshAuth=()=>a(!0);let[s,c]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at()]);return On({accessToken:s,expiresAt:c})?s:a(!1)}var fc=" ";function ae(e){let n=e;return n._def??n.def??{}}function ce(e){let n=e.typeName;if(n)return n;let t=e.type;if(t)return`Zod${t.split("_").map(r=>r.charAt(0).toUpperCase()+r.slice(1)).join("")}`}function se(e){return e.innerType??e.schema??e.out??e.in}function mc(e,n){switch(n){case"ZodPipe":return e.in??e.innerType;case"ZodEffects":return e.schema??e.innerType;case"ZodTransform":return e.schema??e.innerType??e.in;default:return se(e)}}function hc(e){let n=e.type;return e.element??(typeof n=="string"?void 0:n)}function Rr(e,n){let t=n.shape??e.shape;return typeof t=="function"?t():t}function Dn(e){return Array.isArray(e.options)?e.options:Array.isArray(e.values)?e.values:e.entries!==null&&typeof e.entries=="object"&&!Array.isArray(e.entries)?Object.values(e.entries):[]}function bc(e,n){return e.description??n.description}function sp(e){let n=e;for(;n;){let t=ae(n),r=bc(n,t);if(r)return r;let o=ce(t);if(yi(o)||o==="ZodPipe"||o==="ZodEffects"||o==="ZodTransform"){n=mc(t,o);continue}break}}function yi(e){return e==="ZodOptional"||e==="ZodNullable"||e==="ZodDefault"||e==="ZodCatch"}function X(e){let n=ae(e),t=ce(n);switch(t){case"ZodString":return"string";case"ZodNumber":return"number";case"ZodBoolean":return"boolean";case"ZodDate":return"Date";case"ZodNull":return"null";case"ZodUnknown":case"ZodAny":return"any";case"ZodLiteral":return String(n.value??Dn(n)[0]??"unknown");case"ZodEnum":return Dn(n).map(r=>String(r)).join(" | ");case"ZodOptional":{let r=se(n);return r?X(r):"unknown"}case"ZodNullable":{let r=se(n);return`${r?X(r):"unknown"} | null`}case"ZodDefault":case"ZodCatch":{let r=se(n);return r?X(r):"unknown"}case"ZodArray":{let r=hc(n);if(!r)return"unknown[]";let o=ae(r),i=ce(o)==="ZodUnion",a=X(r);return`${i?`(${a})`:a}[]`}case"ZodRecord":return"{}";case"ZodObject":{let r=Rr(e,n),o=Object.entries(r);return o.length===0?"{}":`{ ${o.map(([a,s])=>{let c=ce(ae(s));return`${c==="ZodOptional"||c==="ZodNullable"?a+"?":a}: ${X(s)}`}).join(", ")} }`}case"ZodUnion":return Dn(n).map(r=>X(r)).join(" | ");case"ZodIntersection":return`${X(n.left)} & ${X(n.right)}`;case"ZodPipe":case"ZodTransform":case"ZodEffects":{let r=mc(n,t);return r?X(r):"unknown"}default:return(t??"unknown").replace("Zod","").toLowerCase()}}function Ie(e){let n=ae(e),t=ce(n),r=bc(e,n);switch(t){case"ZodString":return{kind:"string",optional:!1,description:r};case"ZodNumber":return{kind:"number",optional:!1,description:r};case"ZodBoolean":return{kind:"boolean",optional:!1,description:r};case"ZodLiteral":{let o=n.value??Dn(n)[0],i=typeof o=="string"||typeof o=="number"||typeof o=="boolean"?o:String(o??"");return{kind:"literal",optional:!1,description:r,value:i}}case"ZodEnum":{let o=Dn(n).map(i=>String(i));return{kind:"string",optional:!1,description:r,enum:o}}case"ZodOptional":{let o=se(n),i=o?Ie(o):{kind:"unknown",optional:!1};return{...i,optional:!0,description:r??i.description}}case"ZodNullable":{let o=se(n),i=o?Ie(o):{kind:"unknown",optional:!1};return{...i,optional:!0,description:r??i.description}}case"ZodDefault":case"ZodCatch":{let o=se(n);return o?{...Ie(o),description:r}:{kind:"unknown",optional:!1,description:r}}case"ZodArray":{let o=hc(n);return{kind:"array",optional:!1,description:r,items:o?Ie(o):{kind:"unknown",optional:!1}}}case"ZodObject":{let o=Rr(e,n),i={};for(let[a,s]of Object.entries(o))i[a]=Ie(s);return{kind:"object",optional:!1,description:r,fields:i}}case"ZodRecord":return{kind:"unknown",optional:!1,description:r};case"ZodUnion":{let o=Dn(n);for(let i of o){let a=ae(i);if(ce(a)==="ZodObject")return{...Ie(i),description:r}}return{kind:"unknown",optional:!1,description:r}}case"ZodIntersection":case"ZodPipe":case"ZodTransform":case"ZodEffects":{let o=se(n);return o?{...Ie(o),description:r}:{kind:"unknown",optional:!1,description:r}}default:return{kind:"unknown",optional:!1,description:r}}}function LP(e,n){let t=n.toLowerCase(),r=t.indexOf(".");if(r===-1)return null;let o=t.slice(0,r),i=t.slice(r+1),a=e.find(u=>u.id===o);if(!a)return null;let s=i;s.startsWith("api.")&&(s=s.slice(4));let c=Ne(a.endpointMeta,s),l=Ne(a.endpointSchemas,s);return!c&&!l?null:{input:l?.input?Ie(l.input):null,output:l?.output?Ie(l.output):null,description:c?.description}}var mi=["equals","contains","startsWith","endsWith","in"],ap=["equals","gt","gte","lt","lte","in"],cp=["equals"],up=["equals","before","after","between"];function kc(e){let n=ae(e);switch(ce(n)){case"ZodOptional":case"ZodNullable":case"ZodDefault":case"ZodCatch":{let r=se(n);return r?kc(r):null}case"ZodString":return"string";case"ZodNumber":return"number";case"ZodBoolean":return"boolean";case"ZodDate":return"date";default:return null}}function hi(e){let n=ae(e),t=ce(n);if(yi(t)){let i=se(n);return i?hi(i):{}}if(t!=="ZodObject")return{};let r=Rr(e,n),o={};for(let[i,a]of Object.entries(r)){let s=kc(a);s==="string"?o[i]={type:"string",operators:mi}:s==="number"?o[i]={type:"number",operators:ap}:s==="boolean"?o[i]={type:"boolean",operators:cp}:s==="date"&&(o[i]={type:"date",operators:up})}return o}function wc(e,n){for(let[t,r]of Object.entries(e))if(t.toLowerCase()===n)return[t,r]}function pi(e,n,t){for(let[r,o]of Object.entries(e)){let i=[...n,r];typeof o=="function"?t.push(i.join(".")):o!==null&&typeof o=="object"&&pi(o,i,t)}}function gi(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function fi(e,n,t){for(let[r,o]of Object.entries(e)){let i=[...n,r];gi(o)?t.push(i.join(".")):o!==null&&typeof o=="object"&&fi(o,i,t)}}function bi(e,n){if(n.length===0)return null;let[t,...r]=n,o=Object.entries(e).find(([s])=>s.toLowerCase()===t);if(!o)return null;let[i,a]=o;if(r.length===0)return gi(a)?[i]:null;if(a!==null&&typeof a=="object"&&!gi(a)){let s=bi(a,r);if(s!==null)return[i,...s]}return null}function Cc(e,n){let t=[];t.push(`${e}({`),t.push(" webhookHooks: {");for(let i=0;i<n.length;i++){let a=" ".repeat(i+2);t.push(`${a}${n[i]}: {`)}let r=" ".repeat(n.length+2),o=r+" ";t.push(`${r}before(ctx, args) {`),t.push(`${o}return { ctx, args };`),t.push(`${r}},`),t.push(`${r}after(ctx, response) {`),t.push(`${r}},`);for(let i=n.length-1;i>=0;i--){let a=" ".repeat(i+2);t.push(`${a}},`)}return t.push(" },"),t.push("})"),t.join(`
|
|
49
|
+
To generate a KEK, run: openssl rand -base64 ${je}`)}})}async function Yl(e){let n=!1;for(;;){let t=await e.database.db.selectFrom("corsair_integrations").selectAll().where("name","=",e.integrationName).executeTakeFirst();if(!t){if(!n&&e.ensureProvisioned){n=!0,await e.ensureProvisioned();continue}throw new Error(`Integration "${e.integrationName}" not found. Make sure to create the integration first.`)}let r=await e.database.db.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",e.tenantId).where("integration_id","=",t.id).executeTakeFirst();if(!r){if(!n&&e.ensureProvisioned){n=!0,await e.ensureProvisioned();continue}throw new Error(`Account not found for tenant "${e.tenantId}" and integration "${e.integrationName}". Make sure to create the account first.`)}return{integrationId:t.id,accountId:r.id,integration:{id:t.id,config:t.config,dek:t.dek??null},account:{id:r.id,config:r.config,dek:r.dek??null}}}}async function la(e){let{integrationId:n,accountId:t}=await Yl(e);return{integrationId:n,accountId:t}}function da(e,n){let t=()=>{if(!e)throw new Error("corsair.chats requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e};return{create:r=>Mr(t(),{tenantId:n,message:r}),list:()=>Hr(t(),{tenantId:n}),get:r=>({message:o=>Dr(t(),{chatId:r,tenantId:n,message:o}),listMessages:()=>Br(t(),{chatId:r,tenantId:n})})}}function pa(e,n){return`[auth-missing:${e}] Authentication required. Direct the user to connect their account: ${n}`}async function Ql(e){let n=e.hub;if(n&&e.database&&e.kek)try{let t=await Cs(n,{tenantId:e.tenantId,plugin:e.plugin,database:e.database,kek:e.kek,plugins:e.plugins,multiTenancy:e.multiTenancy});return{message:e.manual?.onAuthMissing?e.manual.onAuthMissing({plugin:e.pluginId,connectUrl:t.connectUrl,state:t.token}):pa(e.pluginId,t.connectUrl),connectUrl:t.connectUrl}}catch{return{message:`[auth-missing:${e.pluginId}:${e.authType}] Authentication required. Could not create connect link. Check hub configuration and server logs.`,connectUrl:null}}return{message:`[auth-missing:${e.pluginId}:${e.authType}]`,connectUrl:null}}function Xl(e,n,t){let r=hn(Be(e,n.tenantId??t??"default"),n.kek),o=new URL(n.baseUrl);o.searchParams.set("state",r);let i=o.toString();return{message:n.onAuthMissing?n.onAuthMissing({plugin:e,connectUrl:i,state:r}):pa(e,i),connectUrl:i}}async function ed(e){let n=e.tenantId??"default",t=e.error.pluginId;return e.error.authType==="managed_pricing"?{message:e.error.message,connectUrl:null}:e.manual&&Pn(e.manual)&&e.manual.oauthConfig&&e.manual.kek&&e.error.authType==="oauth_2"?Xl(t,{...e.manual,baseUrl:e.manual.baseUrl,kek:e.manual.kek},e.tenantId):e.hub&&e.plugin&&e.kek&&e.database&&e.plugins?Ql({manual:e.manual,hub:e.hub,plugin:e.plugin,pluginId:t,tenantId:n,authType:e.error.authType,database:e.database,kek:e.kek,plugins:e.plugins,multiTenancy:e.multiTenancy}):{message:e.error.message,connectUrl:null}}async function ga(e){let{message:n,connectUrl:t}=await ed(e);throw new S(e.error.pluginId,e.error.authType,n,{connectUrl:t,tenantId:e.tenantId??"default"})}var mr="connect.request",Vo="connect.cleared",nd=600*1e3;async function Jo(e,n,t){let r=await e.db.selectFrom("corsair_integrations").select("id").where("name","=",t).executeTakeFirst();return r?(await e.db.selectFrom("corsair_accounts").select("id").where("tenant_id","=",n).where("integration_id","=",r.id).executeTakeFirst())?.id??null:null}async function td(e,n){return(await e.db.selectFrom("corsair_accounts").select("id").where("tenant_id","=",n).execute()).map(r=>r.id)}async function rd(e,n,t){let r=await e.db.selectFrom("corsair_events").select("created_at").where("account_id","=",n).where("event_type","in",[mr,Vo]).orderBy("created_at","desc").limit(1).executeTakeFirst();if(!r)return t;let o=r.created_at instanceof Date?r.created_at.getTime():Date.parse(String(r.created_at));return Math.max(t,o+1)}async function fa(e,n,t,r,o){let i=await rd(e,n,o),a=new Date(i);await e.db.insertInto("corsair_events").values({id:ln(),created_at:a,updated_at:a,account_id:n,event_type:t,payload:r}).execute()}async function od(e,n,t=Date.now()){let r=await Jo(e,n.tenantId,n.plugin);r&&await fa(e,r,mr,{plugin:n.plugin,connectUrl:n.connectUrl},t)}function id(e){let n=e;if(typeof e=="string")try{n=JSON.parse(e)}catch{return null}return!n||typeof n!="object"||Array.isArray(n)?null:n}async function sd(e,n,t,r,o){let i=await e.db.selectFrom("corsair_events").select(["event_type","payload","created_at"]).where("account_id","=",n).where("event_type","in",[mr,Vo]).orderBy("created_at","desc").limit(1).executeTakeFirst();if(!i||i.event_type!==mr)return null;let a=i.created_at instanceof Date?i.created_at.getTime():Date.parse(String(i.created_at));if(r-a>o)return null;let s=id(i.payload);if(!s)return null;let c=s.plugin,l=s.connectUrl;return typeof c!="string"||typeof l!="string"?null:{plugin:c,connectUrl:l,requestedAt:new Date(a).toISOString(),tenantId:t,requestedAtMs:a,accountId:n}}async function Yo(e,n,t=Date.now(),r=nd){let o=await td(e,n);if(o.length===0)return null;let i=(await Promise.all(o.map(l=>sd(e,l,n,t,r)))).filter(l=>l!==null);if(i.length===0)return null;i.sort((l,u)=>l.requestedAtMs-u.requestedAtMs||l.accountId.localeCompare(u.accountId));let{requestedAtMs:a,accountId:s,...c}=i[0];return c}async function ya(e,n,t=Date.now(),r){let o;if(r)o=await Jo(e,n,r);else{let i=await Yo(e,n,t);o=i?await Jo(e,n,i.plugin):null}o&&await fa(e,o,Vo,{},t)}async function Qo(e,n){if(!(!e||!n.plugin||!n.connectUrl))try{await od(e,{tenantId:n.tenantId??"default",plugin:n.plugin,connectUrl:n.connectUrl})}catch{}}var ad=async(e,n)=>(console.error(`[corsair:${n.pluginId}:${n.operation}]`,{error:e.message,input:n.input}),{maxRetries:0});async function ma(e,n,t,r,o){let i={pluginId:n,operation:t,input:r,originalError:e},a=Object.keys(o).find(l=>o[l]?.match(e,i));return await(o[a||"DEFAULT"]?.handler||ad)(e,i)}var ha=new Map;function cd(e){let n=ha.get(e);return n||(n=gr(),ha.set(e,n)),n}function ud(e){return typeof e=="function"}function Xo({endpoints:e,hooks:n,ctx:t,tree:r,pluginId:o,errorHandlers:i,currentPath:a=[],keyBuilder:s,permissionsConfig:c,endpointMeta:l,database:u,permissionsOptions:d,tenantId:p,manualConfig:g,hubConfig:f,plugin:h,kek:b,allPlugins:k,multiTenancy:T}){for(let[v,H]of Object.entries(e)){let D=n?.[v];if(ud(H)){let B=D,C=[...a,v].join("."),R=async(x={})=>{let ee=l?.[C];Lt(C,ee?.riskLevel??"write");let re,O=Rn(),q=c?.mode,he=eo(O,q);if(he){let W=ee,oe=W?.riskLevel??"write",be=c?.overrides?.[C],$e=O!==void 0&&O!==q&&he===O?xs(be,Ft(oe,O)):be,{result:cn,reason:F,onComplete:Ln,token:ut,id:vi,expiresAt:Uc}=await Ss({pluginId:o,endpointPath:C,args:x,mode:he,override:$e,riskLevel:oe,meta:W,db:u,timeoutMs:d?to(d.timeout):void 0,tenantId:p,approvalMode:d?.mode});if(cn==="blocked"){let un;F==="denied"?un=`Action '${C}' was denied by the user. Await further instructions before proceeding.`:F==="policy"?un=O?`Action '${C}' is blocked by permission mode '${O}'.`:`Action '${C}' is blocked by the permission policy. Update the corsair config to allow it.`:F==="timeout"?un=`Action '${C}' timed out waiting for approval.`:ut&&vi?un=await Xr({permissionsOptions:d,manual:g,hub:f,permissionId:vi,permissionToken:ut,plugin:o,endpoint:C,args:x,tenantId:p??"default",expiresAt:Uc??new Date(Date.now()+(d?to(d.timeout):600*1e3)).toISOString(),operationPath:C}):un=`Action '${C}' requires user approval before it can run.`;let Lc=F==="denied"||F==="policy"||F==="timeout"?F:"pending";throw new de(un,Lc)}re=Ln}let Bn=async(W,oe,be)=>{try{return await H(oe,be)}catch(ct){if(ct instanceof Error){let $e=await ma(ct,o,C,typeof be=="object"&&be!==null?be:{args:be},i);if(W<($e.maxRetries||0)){let cn=W+1;console.log(`Retrying (${cn} / ${$e.maxRetries})...`);let F;if($e.headersRetryAfterMs)F=$e.headersRetryAfterMs;else switch($e.retryStrategy){case"exponential_backoff":F=Math.pow(2,cn-1)*1e3;break;case"exponential_backoff_jitter":let Ln=Math.pow(2,cn-1)*1e3,ut=(Math.random()-.5)*1e3;F=Math.max(0,Ln+ut);break;case"linear_1s":F=1e3;break;case"linear_2s":F=2e3;break;case"linear_3s":F=3e3;break;case"linear_4s":F=4e3;break;default:F=1e3;break}return await new Promise(Ln=>setTimeout(Ln,F)),await Bn(cn,oe,be)}}throw ct}},at,Dc={...t,meteredOperationId:C},Hc=typeof t.tenantId=="string"?t.tenantId:void 0,Bc=h?E(h):void 0;try{Bc==="managed_pricing"&&f?at=await fr({hub:f,tenantId:Hc??p,meteredOperationId:C},{plugin:o,cache:cd(o),operation:C}):s&&(at=await s(Dc,"endpoint"))}catch(W){if(W instanceof ke)throw h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!1}),await Qo(u,{tenantId:W.tenantId??p,plugin:W.plugin,connectUrl:W.connectUrl}),W;if(W instanceof S){h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!1});try{await ga({error:W,manual:g,hub:f,plugin:h,tenantId:p,database:u,kek:b,plugins:k,multiTenancy:T})}catch(oe){throw oe instanceof S&&await Qo(u,{tenantId:oe.tenantId??p,plugin:oe.pluginId,connectUrl:oe.connectUrl}),oe}}throw W}if(!B?.before&&!B?.after){let W=await Bn(0,{...t,key:at},x);return await re?.(),h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!0}),W}let Ti={...t,key:at},Un=B.before?await B.before(Ti,x):{ctx:Ti,args:x,continue:!0,passToAfter:void 0};if(Un.continue===!1)return;let Pi=await Bn(0,Un.ctx,Un.args);return await B.after?.(Un.ctx,Pi,Un.passToAfter),await re?.(),h&&f&&kn({hub:f,database:u,kek:b,plugins:k??[],plugin:h,tenantId:p,verified:!0}),Pi};r[v]=R}else if(H&&typeof H=="object"){let B={};Xo({endpoints:H,hooks:D,ctx:t,tree:B,pluginId:o,errorHandlers:i,currentPath:[...a,v],keyBuilder:s,permissionsConfig:c,endpointMeta:l,database:u,permissionsOptions:d,tenantId:p,manualConfig:g,hubConfig:f,plugin:h,kek:b,allPlugins:k,multiTenancy:T}),r[v]=B}}}var ye={findByEntityId:"read",existsByEntityId:"read",findIdByEntityId:"read",findById:"read",findManyByEntityIds:"read",list:"read",search:"read",count:"read",upsertByEntityId:"write",deleteById:"destructive",deleteByEntityId:"destructive"},ld=/^\$+date$/;function ba(e){if(typeof e!="object"||e===null||Array.isArray(e))return null;let n=Object.keys(e),t=n[0];return n.length!==1||!t||!ld.test(t)?null:typeof e[t]=="string"?t:null}function nn(e){if(e instanceof Date)return{$date:e.toISOString()};if(Array.isArray(e))return e.map(nn);let n=ba(e);return n?{[`$${n}`]:e[n]}:e&&typeof e=="object"?Object.fromEntries(Object.entries(e).map(([t,r])=>[t,nn(r)])):e}function tn(e){let n=ba(e);if(n){let t=e[n];if(n!=="$date")return{[n.slice(1)]:t};let r=new Date(t);if(Number.isNaN(r.getTime()))throw L(`Invalid $date value "${t}" \u2014 expected an ISO 8601 timestamp`);return r}return Array.isArray(e)?e.map(tn):e&&typeof e=="object"?Object.fromEntries(Object.entries(e).map(([t,r])=>[t,tn(r)])):e}async function ei(e,n,t){let r=Object.hasOwn(ye,n.method)?ye[n.method]:void 0;if(!r)throw new w(404,"unknown_db_method",`Unknown db method "${n.method}" \u2014 expected one of ${Object.keys(ye).join(", ")}`);Ge(`${n.plugin}.db.${n.entityType}.${n.method}`,r);let i=e?.[n.plugin]?.db;if(!i)throw new w(404,"unknown_plugin",`Plugin "${n.plugin}" has no entity store`);let a=Object.hasOwn(i,n.entityType)?i[n.entityType]:void 0,s=a?.[n.method];if(typeof s!="function")throw new w(404,"unknown_entity_type",`Plugin "${n.plugin}" has no entity type "${n.entityType}"`);return s.apply(a,t)}function dd(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function ni({webhooks:e,hooks:n,ctx:t,webhooksTree:r,keyBuilder:o}){for(let[i,a]of Object.entries(e)){let s=n?.[i];if(dd(a)){let c=s,l=async u=>{let d=(g,f)=>a.handler(g,f),p=o&&u?.hubVerified!==!0?await o(t,"webhook"):void 0;return!c?.before&&!c?.after?d({...t,key:p},u):(async()=>{let g={...t,key:p},f=c.before?await c.before(g,u):{ctx:g,args:u,continue:!0,passToAfter:void 0};if(f.continue===!1)return;let h=await d(f.ctx,f.args);return h?.success===!0&&await c.after?.(f.ctx,h,f.passToAfter),h})()};r[i]={match:a.match,handler:l}}else if(a&&typeof a=="object"){let c={};ni({webhooks:a,hooks:s,ctx:t,webhooksTree:c,keyBuilder:o}),r[i]=c}}}function ka(e){return e&&typeof e=="object"?e:{}}async function wa(e,n){return Z({hub:e,path:`/workflows?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ka(t).workflows;return Array.isArray(r)?r:[]}})}async function Ca(e,n){return Z({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>ka(t).workflow})}async function Ta(e,n){await _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/status?tenantId=${encodeURIComponent(n.tenantId)}`,body:{status:n.status},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}async function Pa(e,n){await _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/rename?tenantId=${encodeURIComponent(n.tenantId)}`,body:{name:n.name},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}async function va(e,n){return _({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/run?tenantId=${encodeURIComponent(n.tenantId)}`,body:{payload:n.payload,idempotencyKey:n.idempotencyKey},notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>t})}function ti(e){return e&&typeof e=="object"?e:{}}async function Ra(e,n){return Z({hub:e,path:`/runs?tenantId=${encodeURIComponent(n.tenantId)}`,parseResponse:t=>{let r=ti(t).runs;return Array.isArray(r)?r:[]}})}async function Aa(e,n){return Z({hub:e,path:`/workflows/${encodeURIComponent(n.workflowId)}/runs?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Workflow "${n.workflowId}" not found`,parseResponse:t=>{let r=ti(t).runs;return Array.isArray(r)?r:[]}})}async function xa(e,n){return Z({hub:e,path:`/runs/${encodeURIComponent(n.runId)}?tenantId=${encodeURIComponent(n.tenantId)}`,notFoundMessage:`Run "${n.runId}" not found`,parseResponse:t=>ti(t).run})}async function ri(e,n,t){await _({hub:e,path:`/runs/${encodeURIComponent(t.runId)}/${n}?tenantId=${encodeURIComponent(t.tenantId)}`,body:{},notFoundMessage:`Run "${t.runId}" cannot be ${n==="cancel"?"canceled":`${n}d`} in its current state`,parseResponse:r=>r})}var Ia=(e,n)=>ri(e,"approve",n),Sa=(e,n)=>ri(e,"deny",n),_a=(e,n)=>ri(e,"cancel",n);function Ea(e,n){let t=()=>{if(!e)throw new Error("corsair.workflows.runs requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e};return{list:r=>r?.workflowId?Aa(t(),{workflowId:r.workflowId,tenantId:n}):Ra(t(),{tenantId:n}),get:r=>xa(t(),{runId:r,tenantId:n}),approve:r=>Ia(t(),{runId:r,tenantId:n}),deny:r=>Sa(t(),{runId:r,tenantId:n}),cancel:r=>_a(t(),{runId:r,tenantId:n})}}function Oa(e,n){let t=()=>{if(!e)throw new Error("corsair.workflows requires Hub to be configured. Pass `hub` to createCorsair({ hub: { projectApiKey, ... } }).");return e},r=(o,i)=>Ta(t(),{workflowId:o,tenantId:n,status:i});return{list:()=>wa(t(),{tenantId:n}),get:o=>Ca(t(),{workflowId:o,tenantId:n}),run:(o,i)=>va(t(),{workflowId:o,tenantId:n,payload:i?.payload,idempotencyKey:i?.idempotencyKey}),runs:Ea(e,n),disable:o=>r(o,"inactive"),enable:o=>r(o,"active"),archive:o=>r(o,"archived"),unarchive:o=>r(o,"inactive"),rename:(o,i)=>Pa(t(),{workflowId:o,tenantId:n,name:i})}}function pd(e,n,t,r){let o=null;return async()=>{if(o)return o;if(!e)throw new Error("Database not configured");let{accountId:i}=await la({database:e,integrationName:n,tenantId:t,ensureProvisioned:r});return o=i,o}}function gd(e,n){let t={};for(let[r,o]of Object.entries(n))t[r]=new Proxy(o,{get(i,a){let s=i[a];if(typeof a!="string"||typeof s!="function")return s;let c=Object.hasOwn(ye,a)?ye[a]:void 0;if(!c)return s;let l=s;return async(...u)=>(Ge(`${e}.db.${r}.${a}`,c),l.apply(i,u))}});return t}function fd(e,n,t,r,o){return e?Sr(e.db,n,t,r,o):{findByEntityId:async()=>null,existsByEntityId:async()=>!1,findIdByEntityId:async()=>null,findById:async()=>null,findManyByEntityIds:async()=>[],list:async()=>[],search:async()=>[],upsertByEntityId:async()=>{throw new Error("Database not configured")},deleteById:async()=>!1,deleteByEntityId:async()=>!1,count:async()=>0}}function oi(e,n){let{database:t,tenantId:r,kek:o,rootErrorHandlers:i,permissionsOptions:a,manualConfig:s,hubConfig:c,internalConfig:l}=n,u=r??"default",d=l&&t?()=>mn(l,u):void 0,p={},g={};for(let f of e)p[f.id]={},g[f.id]={};for(let f of e){let h=f.schema,b=pd(t,f.id,u,d);if(h?.entities){let O={};for(let[q,he]of Object.entries(h.entities)){let Bn=t?Sr(t.db,b,q,h.version,he):fd(void 0,b,q,h.version,he);O[q]=Bn}g[f.id].db=O,p[f.id].db=gd(f.id,O)}let k=f.options,T=f.authConfig,v;if(t&&o&&k?.authType){let O=T?.[k.authType]?.account??[];v=U({authType:k.authType,integrationName:f.id,tenantId:u,kek:o,database:t,extraAccountFields:O,ensureProvisioned:d}),p[f.id].keys=v}let H={database:t,db:g[f.id]?.db??{},$getAccountId:b,...f.options?{options:f.options}:{},...v?{keys:v,authType:k?.authType}:{},tenantId:u,...c?{hub:c}:{}},D=f.endpoints??{},B=f.hooks,C={...i,...f.errorHandlers},R={},x=f.options?.permissions;Xo({endpoints:D,hooks:B,ctx:H,tree:R,pluginId:f.id,errorHandlers:C,currentPath:[],keyBuilder:f.keyBuilder,permissionsConfig:x,endpointMeta:f.endpointMeta,database:t,permissionsOptions:a,tenantId:r,manualConfig:s?{...s,oauthConfig:f.oauthConfig,kek:o,tenantId:u}:void 0,hubConfig:c,plugin:f,kek:o,allPlugins:e,multiTenancy:l?.multiTenancy}),Object.keys(R).length>0&&(p[f.id].api=R),H.endpoints=R;let ee=f.webhooks??{},re=f.webhookHooks;if(Object.keys(ee).length>0&&!Mi(k?.authType)){let O={};ni({webhooks:ee,hooks:re,ctx:H,webhooksTree:O,keyBuilder:f.keyBuilder}),p[f.id].webhooks=O,f.pluginWebhookMatcher&&(p[f.id].pluginWebhookMatcher=f.pluginWebhookMatcher),f.pluginTenantWebhookMatcher&&(p[f.id].pluginTenantWebhookMatcher=f.pluginTenantWebhookMatcher)}}return p.chats=da(c,u),p.workflows=Oa(c,u),p}function Ma(e,n,t){let r={};for(let o of e){let i=o.options,a=o.authConfig;if(i?.authType){let s=a?.[i.authType]?.integration??[],c=$({authType:i.authType,integrationName:o.id,kek:t,database:n,extraIntegrationFields:s});r[o.id]=c}}return r}var yd=3e4;function hr(e){let n=e.length;for(;n>0&&e[n-1]==="/";)n--;return e.slice(0,n)}function md(e){let n=0;for(;n<e.length&&e[n]==="/";)n++;return e.slice(n)}function hd(e,n){return`${hr(e)}/${md(n)}`}function bd(e,n){let t=n??{},{error:r,message:o,...i}=t;return typeof r!="string"?new w(e,"internal_error","Internal error"):new w(e,r,o,i)}var ii=Symbol("cloudRequestTimeout");async function G(e,n,t,r){let o=Rn(),i=e.fetch??globalThis.fetch,a=e.timeoutMs??yd,s=new AbortController,c,l=new Promise(g=>{c=setTimeout(()=>{s.abort(),g(ii)},a)}),u;try{let g=i(hd(e.baseUrl,t),{method:n,headers:{authorization:`Bearer ${e.apiKey}`,"content-type":"application/json",...o?{"x-corsair-mode":o}:{}},body:r===void 0?void 0:JSON.stringify(r),signal:s.signal}).catch(h=>{if(s.signal.aborted)return ii;throw h}),f=await Promise.race([g,l]);if(f===ii)throw new w(0,"internal_error","Cloud request timed out");u=f}finally{clearTimeout(c)}let d=await u.text(),p;try{p=d?JSON.parse(d):void 0}catch{p=void 0}if(!u.ok)throw bd(u.status,p);if(p===void 0)throw new w(u.status,"internal_error","Invalid or empty response body from runtime");return p}var z={invoke:"/:tenant/:plugin/call/:op",entityDb:"/:tenant/:plugin/db/:entity/:method",instances:"/instances",connectLinks:"/connect/links",tenants:"/tenants",tenant:"/tenants/:id",connectionStatus:"/connection-status",disconnect:"/disconnect",permission:"/permissions/:id",permissionLookup:"/permissions/lookup-by-token"};var kd=new Set(["keys","webhooks"]),wd=new Set(["chats","workflows"]),si=new Set(["then","catch","finally"]);function me(e){return typeof e=="function"?e():Promise.resolve(e)}function Da(e,n,t,r){let o=async(...i)=>{let a=await me(e);return(await G(a,"POST",z.invoke.replace(":tenant",encodeURIComponent(n)).replace(":plugin",encodeURIComponent(t)).replace(":op",r.map(encodeURIComponent).join(".")),{args:i[0]})).data};return new Proxy(o,{get(i,a){if(!(typeof a!="string"||si.has(a)))return Da(e,n,t,[...r,a])}})}function Cd(e,n,t){return new Proxy({},{get(r,o){if(!(typeof o!="string"||si.has(o)))return new Proxy({},{get(i,a){if(typeof a!="string")return;let s=Object.hasOwn(ye,a)?ye[a]:void 0;if(s)return async(...c)=>{Ge(`${t}.db.${o}.${a}`,s);let l=await me(e),u=await G(l,"POST",z.entityDb.replace(":tenant",encodeURIComponent(n)).replace(":plugin",encodeURIComponent(t)).replace(":entity",encodeURIComponent(o)).replace(":method",encodeURIComponent(a)),{args:nn(c)});return tn(u.data)}}})}})}function br(e,n){let t=e?new Set(e.map(r=>r.id)):null;return new Proxy({},{get(r,o){if(!(typeof o!="string"||si.has(o))){if(wd.has(o))throw new Error(`"${o}" is not available in cloud mode (deferred)`);if(t&&!t.has(o))throw new Error(`Unknown plugin "${o}"`);return new Proxy({},{get(i,a){if(a==="api")return Da(n.transport,n.tenantId,o,[]);if(a==="db")return Cd(n.transport,n.tenantId,o);if(typeof a=="string"&&kd.has(a))throw new Error(`"${a}" is not available in cloud mode (deferred)`)}})}}})}function kr(e){return{connect:{createLink:n=>{if(!n.plugin||!n.tenantId)throw new Error('connect.createLink requires both "plugin" and "tenantId" in cloud mode');return me(e).then(t=>G(t,"POST",z.connectLinks,n))}},tenants:{create:n=>me(e).then(t=>G(t,"POST",z.tenants,n)),list:()=>me(e).then(n=>G(n,"GET",z.tenants)),get:n=>me(e).then(t=>G(t,"GET",z.tenant.replace(":id",encodeURIComponent(n))))},connectionStatus:{get:n=>me(e).then(t=>G(t,"GET",`${z.connectionStatus}?tenantId=${encodeURIComponent(n.tenantId)}`))},disconnect:n=>me(e).then(t=>G(t,"POST",z.disconnect,n)),permissions:{get:n=>me(e).then(t=>"id"in n?G(t,"GET",z.permission.replace(":id",encodeURIComponent(n.id))):G(t,"POST",z.permissionLookup,{token:n.token}))}}}var Ae=class extends w{type;retryable;param;docUrl;requestId;constructor(n,t){super(n,t.code,t.message,{...t}),this.name="CloudApiError",this.type=t.type??"api_error",this.retryable=t.retryable??(n===0||n===429||n>=500),this.param=t.param,this.docUrl=t.doc_url,this.requestId=t.request_id}};function rt(e,n,t){let r=t?.get("request-id")?.trim()||void 0,i=(n??{}).error;if(typeof i=="string"){let a=n.message;return new Ae(e,{code:i,message:typeof a=="string"?a:void 0,request_id:r})}return i&&typeof i=="object"&&typeof i.code=="string"?new Ae(e,{request_id:r,...i}):new Ae(e,{code:e===0?"request_failed":"internal_error",message:`Corsair Cloud returned ${e} with no error body`,request_id:r})}var Td=3e4,Pd=new Set(["GET","HEAD","PUT","DELETE"]),vd=/^[a-z][a-z0-9-]{0,31}$/;function rn(e,n){if(!vd.test(e))throw new Error(`${n}: "${e}" is not a valid instance key. Lowercase letter first, then letters, digits or hyphens, up to 32 characters.`)}function on(e){let n=new URLSearchParams;for(let[r,o]of Object.entries(e))o!==void 0&&n.set(r,String(o));let t=n.toString();return t?`?${t}`:""}function A(e,n){return`${e}/${encodeURIComponent(n)}`}async function wr(e,n,t,r,o={}){let i=e.fetch??globalThis.fetch,a=new AbortController;o.signal?.aborted&&a.abort();let s=()=>a.abort();o.signal?.addEventListener("abort",s,{once:!0});let c=setTimeout(()=>a.abort(),e.timeoutMs??Td),l={authorization:`Bearer ${e.apiKey}`,"content-type":"application/json"};e.apiVersion&&(l["corsair-version"]=e.apiVersion),o.idempotencyKey&&(l["idempotency-key"]=o.idempotencyKey),o.requestId&&(l["x-corsair-request-id"]=o.requestId);let u;try{u=await i(`${e.baseUrl}${t}`,{method:n,headers:l,body:r===void 0?void 0:JSON.stringify(r),signal:a.signal});let d=await u.text(),p;try{p=d?JSON.parse(d):void 0}catch{p=void 0}if(!u.ok)throw rt(u.status,p,u.headers);if(p===void 0&&u.status!==204)throw rt(u.status,void 0,u.headers);return p}catch(d){if(o.signal?.aborted||d instanceof Ae)throw d;let p=Pd.has(n),g=u?p?!0:void 0:p||!!o.idempotencyKey;throw rt(u?.status??0,{error:{code:"request_failed",message:d instanceof Error?d.message:String(d),retryable:g}},u?.headers)}finally{clearTimeout(c),o.signal?.removeEventListener("abort",s)}}function ai(e,n){rn(n,"withInstance");let t=(s,c,l,u)=>wr(e,s,c,l,u),r=(...s)=>[n,...s].join(":"),o=s=>on({...s,instance:n}),i=s=>`${A("/instances",n)}${s}`,a=s=>`${A("/webhooks",r(s))}/deliveries`;return{instanceKey:n,tenants:{list:(s={},c)=>t("GET",`/tenants${o(s)}`,void 0,c),create:(s,c)=>t("POST","/tenants",{...s,instance:n},c),get:(s,c)=>t("GET",A("/tenants",r(s)),void 0,c),update:(s,c,l)=>t("PATCH",A("/tenants",r(s)),c,l),delete:(s,c)=>t("DELETE",A("/tenants",r(s)),void 0,c)},access:{list:(s={},c)=>t("GET",`/access${o(s)}`,void 0,c),get:(s,c)=>t("GET",A("/access",r(s)),void 0,c),set:(s,c,l)=>t("PUT",A("/access",r(s)),c,l),revoke:(s,c)=>t("DELETE",A("/access",r(s)),void 0,c)},connections:{list:(s={},c)=>t("GET",`/connections${o(s)}`,void 0,c),get:(s,c,l)=>t("GET",A("/connections",r(s,c)),void 0,l),delete:(s,c,l)=>t("DELETE",A("/connections",r(s,c)),void 0,l)},connect:{createSession:(s,c)=>t("POST","/connect/sessions",{...s,instance:n},c)},integrations:{list:(s={},c)=>t("GET",`/integrations${o(s)}`,void 0,c),get:(s,c)=>t("GET",A("/integrations",r(s)),void 0,c),put:(s,c,l)=>t("PUT",A("/integrations",r(s)),c,l),delete:(s,c)=>t("DELETE",A("/integrations",r(s)),void 0,c),operations:(s,c)=>t("GET",`${A("/integrations",r(s))}/operations`,void 0,c),oauthApp:{get:(s,c)=>t("GET",`${A("/integrations",r(s))}/oauth-app`,void 0,c),put:(s,c,l)=>t("PUT",`${A("/integrations",r(s))}/oauth-app`,c,l),delete:(s,c)=>t("DELETE",`${A("/integrations",r(s))}/oauth-app`,void 0,c)}},webhooks:{list:(s={},c)=>t("GET",`/webhooks${o(s)}`,void 0,c),create:(s,c)=>t("POST","/webhooks",{...s,instance:n},c),get:(s,c)=>t("GET",A("/webhooks",r(s)),void 0,c),delete:(s,c)=>t("DELETE",A("/webhooks",r(s)),void 0,c),rotateSecret:(s,c,l)=>t("POST",`${A("/webhooks",r(s))}/rotate-secret`,c,l),deliveries:{list:(s,c={},l)=>t("GET",`${a(s)}${on(c)}`,void 0,l),get:(s,c,l)=>t("GET",A(a(s),c),void 0,l),retry:(s,c,l)=>t("POST",`${A(a(s),c)}/retry`,void 0,l)}},signingSecret:{get:s=>t("GET",i("/signing-secret"),void 0,s),rotate:s=>t("POST",i("/signing-secret/rotate"),void 0,s)},apply:s=>t("POST",i("/apply"),void 0,s),removeFromRuntime:s=>t("POST",i("/remove"),void 0,s),reconcile:s=>t("POST",i("/reconcile"),void 0,s)}}function ci(e){let n=(t,r,o,i)=>wr(e,t,r,o,i);return{project:{get:t=>n("GET","/project",void 0,t)},keys:{get:t=>n("GET","/keys",void 0,t),rotate:t=>n("POST","/keys/rotate",void 0,t)},instances:{list:(t={},r)=>n("GET",`/instances${on(t)}`,void 0,r),create:(t,r)=>(rn(t.instance_key,"instances.create"),n("POST","/instances",t,r)),get:(t,r)=>(rn(t,"instances.get"),n("GET",A("/instances",t),void 0,r)),update:(t,r,o)=>(rn(t,"instances.update"),n("PATCH",A("/instances",t),r,o)),delete:(t,r)=>(rn(t,"instances.delete"),n("DELETE",A("/instances",t),void 0,r))},integrations:{catalog:(t={},r)=>n("GET",`/integrations/catalog${on(t)}`,void 0,r)},mcp:{links:{list:(t={},r)=>n("GET",`/mcp/links${on(t)}`,void 0,r),mint:(t,r)=>n("POST","/mcp/links",t,r),get:(t,r)=>n("GET",A("/mcp/links",t),void 0,r),update:(t,r,o)=>n("PATCH",A("/mcp/links",t),r,o),delete:(t,r)=>n("DELETE",A("/mcp/links",t),void 0,r),rotate:(t,r)=>n("POST",`${A("/mcp/links",t)}/rotate`,void 0,r)},tokens:{mint:(t,r)=>n("POST","/mcp/tokens",t,r)}}}}var Ha="default",Rd="corsairCloud: the management API needs a ck_cloud_<slug>.<secret> key, or an explicit `managementUrl`.",Ad=new Set(["then","catch","finally","toString","toJSON","valueOf","constructor","inspect",Symbol.toPrimitive,Symbol.toStringTag,Symbol.iterator,Symbol.asyncIterator]);function ui(e={}){return new Proxy(e,{get(n,t,r){if(Reflect.has(n,t))return Reflect.get(n,t,r);if(!Ad.has(t))throw new Error(Rd)}})}function xe(e){throw new Error(`"${e}" is not available in cloud mode (deferred)`)}function xd(e){let n=e?.baseUrl?.trim()||process.env.CORSAIR_CLOUD_URL?.trim();if(!n)throw new Error("Cloud mode (ck_cloud_ key) requires a base URL \u2014 set hub.baseUrl or CORSAIR_CLOUD_URL.");return Fn(n),n}function Ba(e){return!!(e?.baseUrl?.trim()||process.env.CORSAIR_CLOUD_URL?.trim())}function Id(e,n){let t=kr(e);return{ok:()=>xe("manage.ok"),tenants:t.tenants,plugins:{list:()=>xe("manage.plugins.list"),get:()=>xe("manage.plugins.get")},connectionStatus:{get:r=>{let o=r?.tenantId||void 0;if(!o&&n)throw new Error("connectionStatus.get requires a tenantId in multi-tenant mode");return t.connectionStatus.get({tenantId:o??Ha})}},permissions:t.permissions,connect:{createLink:t.connect.createLink,resolve:()=>xe("manage.connect.resolve"),oauthCallback:()=>xe("manage.connect.oauthCallback")},disconnect:t.disconnect}}function Sd(e,n){let t=Id(e,n.multiTenancy);if(n.multiTenancy)return{withTenant:a=>{if(!a)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");return br(n.plugins,{transport:e,tenantId:a})},get keys(){return xe("keys")},get permissions(){return xe("permissions")},manage:t};let r=br(n.plugins,{transport:e,tenantId:Ha}),o={manage:t,get keys(){return xe("keys")},get permissions(){return xe("permissions")}};return new Proxy(r,{get(a,s,c){return typeof s=="string"&&s in o?Reflect.get(o,s,c):Reflect.get(a,s,c)}})}function Ua(e){return Sd({baseUrl:xd(e.hub),apiKey:e.hub.projectApiKey},{multiTenancy:!!e.multiTenancy,plugins:e.plugins})}function _d(e){let n=hr(e),t="/api/corsair";return n.endsWith(t)?n.slice(0,-t.length):n}async function Ed(e){let n=await G({...e,baseUrl:_d(e.baseUrl)},"GET",z.instances),t=new Map;for(let r of n.instances)Fn(r.url,`Instance "${r.instanceKey}" URL`),t.set(r.instanceKey,r.url);return t}function Od(e){let n=e.apiKey?.trim();if(!n)throw new Error("corsairCloud: apiKey is required");let t=Ri(n),r=e.url?.trim()||Ai(n);if(!r)throw new Error("corsairCloud: could not resolve a URL from apiKey \u2014 pass a ck_cloud_<slug>.<secret> key, or set `url` explicitly.");Fn(r);let o={baseUrl:r,apiKey:n,fetch:e.fetch,timeoutMs:e.timeoutMs},a=(hr(e.managementUrl?.trim()??"")||void 0)??(t?xi(r,t):null);a&&Fn(a,"Management base URL");let s=a?{baseUrl:a,apiKey:n,fetch:e.fetch,timeoutMs:e.timeoutMs,apiVersion:e.apiVersion}:null,c=null;function l(g){return g&&c===g&&(c=null),c||(c=Ed(o).catch(f=>{throw c=null,f})),c}async function u(g){let f=l(),b=(await f).get(g)??(await l(f)).get(g);if(b)return b;let k=[...(await l()).keys()].join(", ");throw new Error(`corsairCloud.withInstance("${g}"): no such instance \u2014 available: ${k||"(none)"}`)}let d=kr(o),p={tenants:d.tenants,permissions:d.permissions};return{manage:s?{...ci(s),...p}:ui(p),withInstance:g=>{let f=s?ai(s,g):ui(),h=async()=>({...o,baseUrl:await u(g)}),b=kr(h),k={withTenant(T){if(!T)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");return br(void 0,{transport:h,tenantId:T})},connectionStatus:b.connectionStatus,disconnect:b.disconnect,createConnectLink:b.connect.createLink};return s?{...f,...k}:ui(k)}}}var Md="createCorsair({ approval: ... }) is deprecated. Rename to permissions: { timeout, onTimeout, mode }.";function La(e){let{permissions:n,approval:t}=e;if(n&&t)throw new Error("createCorsair was given both permissions and approval config. Use permissions only \u2014 approval is deprecated.");return t?(console.warn(`[corsair] ${Md}`),t):n}var Dd=e=>new w(404,"unknown_plugin",`Plugin '${e}' is not registered.`),Hd=(e,n)=>new w(404,"unknown_op",`Operation '${n}' not found on plugin '${e}'.`),Cr=(e="/call")=>new w(403,"call_disabled",`The ${e} route is disabled. Construct managementHandler with { unsafeAllowUnauthenticated: true } to enable it \u2014 only when your own backend fronts the handler.`),Bd=e=>new w(401,"not_connected",`Tenant is not connected for plugin '${e}'. Reconnect and retry.`),Fa=e=>new w(403,"permission_denied",`The call was blocked (${e}).`,{reason:e}),Ud=()=>new w(403,"approval_required","This action needs human approval before it can run. Approval is not resumable over HTTP in this version.",{reason:"pending"}),Ld=(e,n)=>new w(502,"provider_error","The provider returned an error.",{providerStatus:e,body:n});function Fd(e,n){if(e instanceof w)return e;if(e instanceof S)return Bd(e.pluginId||n);if(e instanceof vn)return Fa("readonly");if(e instanceof de)return e.reason==="pending"?Ud():Fa(e.reason);if(e instanceof Error&&e.name==="ApiError"){let t=e;return Ld(typeof t.status=="number"?t.status:502,t.body)}return console.error("[corsair] unhandled error in call operation",e),new w(500,"internal_error","Internal error")}var Nd=new WeakMap,Na=new WeakMap,$d=512;function $a(e,n){let t=e.get(n);return t||(t=new Map,e.set(n,t)),t}function Wd(e,n,t){if(n.size<=$d)return;let r=Na.get(e);for(let o of n.keys())if(o!==t&&(r?.get(o)??0)===0){n.delete(o);return}}function qd(e,n,t){if(!n.multiTenancy)return{client:e};let r=typeof t=="string"?t.trim():"";if(!r)throw L("tenant is required for a multi-tenant runtime",{missingFields:["tenant"]});let o=$a(Nd,e),i=o.get(r);if(i)return o.delete(r),o.set(r,i),{client:i,tenantId:r};let a=e.withTenant(r);return o.set(r,a),Wd(e,o,r),{client:a,tenantId:r}}function jd(e,n){let t=e;for(let r of n.split(".")){if(t==null||typeof t!="object"||!Object.prototype.hasOwnProperty.call(t,r))return null;t=t[r]}return typeof t=="function"?t:null}function Wa(e,n=[]){let t=[];for(let[r,o]of Object.entries(e??{}))typeof o=="function"?t.push([...n,r].join(".")):o&&typeof o=="object"&&t.push(...Wa(o,[...n,r]));return t}function qa(e){let n={};for(let t of e.plugins)n[t.id]=Wa(t.endpoints??{});return n}async function li(e,n,t,r){if(!n.plugins.some(s=>s.id===t.plugin))throw Dd(t.plugin);let{client:o,tenantId:i}=qd(e,n,t.tenant),a=i?$a(Na,e):null;a&&i&&a.set(i,(a.get(i)??0)+1);try{return await r(o)}catch(s){throw Fd(s,t.plugin)}finally{if(a&&i){let s=(a.get(i)??1)-1;s<=0?a.delete(i):a.set(i,s)}}}async function ja(e,n,{plugin:t,op:r,tenant:o,args:i}){return li(e,n,{plugin:t,tenant:o},a=>{let s=a[t],c=jd(s?.api,r);if(!c)throw Hd(t,r);return c(i??{})})}function sn(e,n){if(e===void 0)return n;if(e===null)throw new w(401,"unauthenticated","Could not determine the tenant for this request. Sign in and retry.");return e}function ot(e){if(e!==void 0)throw new w(403,"forbidden","This route is disabled when resolveTenant is configured (end-user mode). Use a handler without resolveTenant, behind your own admin auth.")}var Ga=[{method:"GET",pattern:"/ok",public:!0,handler:async()=>I(200,Nt())},{method:"GET",pattern:"/tenants",handler:async({internal:e,scopedTenant:n})=>(ot(n),I(200,await xn(e)))},{method:"POST",pattern:"/tenants",handler:async({internal:e,body:n,scopedTenant:t})=>(ot(t),I(201,await qt(e,n)))},{method:"GET",pattern:"/tenants/:id",handler:async({internal:e,params:n,scopedTenant:t})=>(ot(t),I(200,await Wt(e,n.id)))},{method:"GET",pattern:"/plugins",handler:async({internal:e})=>I(200,await An(e))},{method:"GET",pattern:"/plugins/:id",handler:async({internal:e,params:n})=>I(200,await $t(e,n.id))},{method:"GET",pattern:"/connection-status",handler:async({internal:e,query:n,scopedTenant:t})=>I(200,await jt(e,sn(t,n.tenantId)))},{method:"GET",pattern:"/permissions/:id",handler:async({internal:e,params:n,scopedTenant:t})=>(ot(t),I(200,await oo(e,n.id)))},{method:"POST",pattern:"/permissions/lookup-by-token",public:!0,handler:async({internal:e,body:n})=>{let t=n?.token?.trim();return t?I(200,await so(e,t)):I(400,{error:"bad_request",message:"token is required",missingFields:["token"]})}},{method:"POST",pattern:"/connect/links",handler:async({corsair:e,internal:n,body:t,scopedTenant:r})=>{let o=t,i=sn(r,o.tenantId);return I(200,await Zt(e,n,{...o,tenantId:i}))}},{method:"GET",pattern:"/connect/resolve",public:!0,handler:async({corsair:e,internal:n,query:t})=>I(200,await Gt(e,n,t.state??""))},{method:"POST",pattern:"/connect/oauth/callback",public:!0,handler:async({corsair:e,internal:n,body:t})=>I(200,await zt(e,n,t))},{method:"GET",pattern:"/connect/request",handler:async({internal:e,query:n,scopedTenant:t})=>{let r=sn(t,n.tenantId)??"default",o=e.database?await Yo(e.database,r):null;return I(200,{request:o},{"cache-control":"no-store"})}},{method:"POST",pattern:"/connect/request/clear",handler:async({internal:e,body:n,scopedTenant:t})=>{let r=n,o=sn(t,r?.tenantId)??"default";return e.database&&await ya(e.database,o,void 0,r?.plugin),I(200,{ok:!0})}},{method:"POST",pattern:"/disconnect",handler:async({internal:e,body:n,scopedTenant:t})=>{let r=n??{},o=sn(t,r.tenantId);return I(200,await Kt(e,{...r,tenantId:o}))}},{method:"GET",pattern:"/call",handler:async({internal:e,allowCall:n})=>{if(!n)throw Cr();return I(200,{plugins:qa(e)})}},{method:"POST",pattern:"/:tenant/:plugin/db/:entityType/:method",handler:async({corsair:e,internal:n,req:t,params:r,body:o,scopedTenant:i,allowCall:a})=>{if(!a)throw Cr("/db");ot(i);let s=o??{};if(s.args!==void 0&&!Array.isArray(s.args))throw L("args must be an array");let c=sn(i,r.tenant),l=tn(s.args??[]),u=await li(e,n,{plugin:r.plugin,tenant:c},d=>Za(t,()=>ei(d,{plugin:r.plugin,entityType:r.entityType,method:r.method},l)));return I(200,{data:nn(u)})}},{method:"POST",pattern:"/:tenant/:plugin/call/:op",handler:async({corsair:e,internal:n,req:t,params:r,body:o,scopedTenant:i,allowCall:a})=>{if(!a)throw Cr();let s=o??{},c=sn(i,r.tenant),l=await Za(t,()=>ja(e,n,{plugin:r.plugin,op:r.op,tenant:c,args:s.args}));return I(200,{data:l})}}];(()=>{let e=new Set;for(let n of Ga){let t=`${n.method} ${n.pattern}`;if(e.has(t))throw new Error(`Duplicate management route registered: ${t}`);e.add(t)}})();function Kd(e,n){let t=e.split("/").filter(Boolean),r=n.split("/").filter(Boolean);if(t.length!==r.length)return null;let o={};for(let i=0;i<t.length;i++){let a=t[i],s=r[i];if(a.startsWith(":"))o[a.slice(1)]=decodeURIComponent(s);else if(a!==s)return null}return o}function Zd(e,n){if(!n)return e;let t=n.endsWith("/")?n.slice(0,-1):n;return e===t?"/":e.startsWith(`${t}/`)?e.slice(t.length):e}async function Gd(e,n){if(e.method==="GET"||e.method==="HEAD"||!(e.headers.get("content-type")??"").includes("application/json"))return;let r=await dr(e,n).catch(o=>{throw o instanceof w?o:new w(400,"invalid_json","Request body is not valid JSON")});if(r)try{return JSON.parse(r)}catch{throw new w(400,"invalid_json","Request body is not valid JSON")}}var zd="/api/corsair",Ka=new Set(["open","cautious","strict","readonly"]);function Za(e,n){let t=e.headers.get("x-corsair-mode");if(t===null)return n();if(!Ka.has(t))throw L(`Unknown permission mode "${t}" \u2014 expected one of ${[...Ka].join(", ")}`);return Ut(t,n)}function j(e,n={}){let t=n.basePath??zd,r=Ve(n.maxBodyBytes),o=Ye(n.bodyStallTimeoutMs),i={maxBodyBytes:r,bodyStallTimeoutMs:o},a=P(e,()=>new Error("managementHandler: invalid corsair instance (missing internal config)"));return async s=>{try{let c=s.headers.get("content-length");if(c!==null&&Number(c)>r)throw En(r);let l=new URL(s.url),u=Zd(l.pathname,t),d=s.method.toUpperCase();if(d==="OPTIONS"||u==="/"||u==="")return await Qe(e,s,{maxBodyBytes:r,bodyStallTimeoutMs:o});if(d!=="GET"&&d!=="POST")return I(405,{error:"method_not_allowed",message:`Method ${d} not allowed`});let p=Object.fromEntries(l.searchParams);for(let g of Ga){if(g.method!==d)continue;let f=Kd(g.pattern,u);if(!f)continue;if(!g.public&&n.authenticate&&!await n.authenticate(s))return I(401,{error:"unauthorized",message:"invalid or missing credentials"});let h=await Gd(s,i),b=n.resolveTenant?await n.resolveTenant(s):void 0;return await g.handler({corsair:e,internal:a,req:s,params:f,query:p,body:h,scopedTenant:b,allowCall:(n.unsafeAllowUnauthenticated??!1)||!!n.authenticate})}throw Ue(`No route for ${d} ${u}`)}catch(c){if(n.onError){let u=await n.onError(c,s);if(u)return u}if(c instanceof w)return pe(c);let l=c instanceof Error?c.message:"Internal server error";return I(500,{error:"internal_error",message:l})}}}function Jd(e,n){if(e.get)return e.get(n);let t=e.headers[n]??e.headers[n.toLowerCase()];return Array.isArray(t)?t[0]:t}function Vd(e){if(Buffer.isBuffer(e))return e;if(e instanceof Uint8Array)return Buffer.from(e);if(typeof e=="string")return Buffer.from(e,"utf8");throw new TypeError(`corsair adapter: unsupported stream chunk type ${typeof e}`)}async function Yd(e,n,t){let r=[],o=0,i=e();try{let a=await lr(()=>i.next(),t);for(;a.done!==!0;){let s=Vd(a.value);if(o+=s.byteLength,o>n)throw En(n);r.push(s),a=await lr(()=>i.next(),t)}return Buffer.concat(r)}catch(a){try{Promise.resolve(i.return?.()).catch(()=>{})}catch{}throw a}}var za=!1;function Qd(){za||(za=!0,console.warn("[corsair] A JSON body parser consumed this request before the corsair adapter.","Re-serializing the parsed object is lossy and will likely fail Hub signature",'verification ("Invalid tunnel signature"). Fix on the corsair route only:',"Express \u2192 mount express.raw({ type: 'application/json' }) before the handler,","or capture raw bytes via express.json({ verify: (req, _res, buf) => { req.rawBody = buf; } }).","Fastify \u2192 call registerCorsairRawBodyParser(app) before listen()."))}async function Xd(e,n){let t=(e.method??"GET").toUpperCase();if(t==="GET"||t==="HEAD")return;let r=Ve(n.maxBodyBytes),o=Ye(n.bodyStallTimeoutMs),i;if(typeof e.rawBody=="string")i=e.rawBody;else if(e.rawBody instanceof Uint8Array)i=e.rawBody;else if(e.body!==void 0&&e.body!==null)typeof e.body=="string"||e.body instanceof Uint8Array?i=e.body:(Qd(),i=JSON.stringify(e.body));else{let s=e[Symbol.asyncIterator];if(typeof s!="function")return;let c=await Yd(s.bind(e),r,o);c.length>0&&(i=c)}if(i===void 0)return;if((typeof i=="string"?Buffer.byteLength(i,"utf8"):i.byteLength)>r)throw En(r);return typeof i=="string"?i:i}function Y(e){e.resume?.()}async function Fe(e,n={}){let t=Jd(e,"host")??"localhost",r=e.protocol??"http",o=e.originalUrl??e.url??"/",i=`${r}://${t}${o}`,a=new Headers;for(let[l,u]of Object.entries(e.headers))if(u!=null&&!ep.has(l.toLowerCase()))if(Array.isArray(u))for(let d of u)a.append(l,d);else a.set(l,u);let s={method:(e.method??"GET").toUpperCase(),headers:a},c=await Xd(e,n);return c!==void 0&&(s.body=c,a.has("content-type")||a.set("content-type","application/json")),new Request(i,s)}async function Q(e,n){typeof e.status=="function"?e.status(n.status):e.statusCode=n.status;let t=n.headers.getSetCookie();n.headers.forEach((o,i)=>{i!=="set-cookie"&&e.setHeader(i,o)}),t.length>0&&e.setHeader("set-cookie",t);let r=Buffer.from(await n.arrayBuffer());e.send?e.send(r):e.end?.(r)}var ep=new Set(["connection","keep-alive","proxy-authenticate","proxy-authorization","te","trailer","transfer-encoding","upgrade","content-length"]);function Ja(e,n){let t=j(e,n);return async(r,o,i)=>{try{let a=await t(await Fe(r,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(o,a)}catch(a){if(a instanceof w&&o.headersSent!==!0){await Q(o,pe(a)),Y(r);return}Y(r),i(a)}}}function np(e,n){let t=e[n];return Array.isArray(t)?t[0]:t}function tp(e){let n=(e.method??"GET").toUpperCase();if(n==="GET"||n==="HEAD"||e.body!==void 0||e.rawBody!==void 0)return;let t=np(e.headers,"content-type");if(!(!t||!t.includes("application/json"))&&!(e.raw.readableEnded!==!0&&e.raw.complete!==!0))throw new Error("corsair: Fastify consumed this JSON body before the corsair adapter could read it. Call registerCorsairRawBodyParser(app) before listen() so the original bytes reach the adapter verbatim (Hub signs deliveries over the exact bytes it sent).")}function Va(e){e.addContentTypeParser("application/json",{parseAs:"buffer"},(n,t,r)=>{n.rawBody=t;try{r(null,JSON.parse(t.toString("utf8")))}catch{r(Object.assign(new Error("Invalid JSON body"),{statusCode:400}))}})}function Ya(e,n){let t=j(e,n);return async(r,o)=>{tp(r);let i={method:r.method??r.raw.method,url:r.url??r.raw.url,headers:r.headers,protocol:r.protocol,body:r.body,rawBody:r.rawBody,resume:r.raw.resume?.bind(r.raw),[Symbol.asyncIterator]:r.raw[Symbol.asyncIterator]?.bind(r.raw)};try{let a=await t(await Fe(i,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));o.hijack?.(),await Q(o.raw,a)}catch(a){if(a instanceof w&&o.raw.headersSent!==!0&&o.hijack){o.hijack(),await Q(o.raw,pe(a)),Y(i);return}throw Y(i),a}}}function Qa(e,n){let t=j(e,n);return r=>t(r.req.raw)}function Xa(e,n){let t=j(e,n);return{GET:t,POST:t,OPTIONS:t}}function ec(e,n){let t=j(e,n);return async(r,o)=>{try{let i=await t(await Fe(r,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(o,i)}catch(i){if(o.headersSent===!0){console.error("[corsair] management response failed after headers were sent:",i),o.end?.(),Y(r);return}if(i instanceof w){await Q(o,pe(i)),Y(r);return}console.error("[corsair] management handler failed:",i),await Q(o,I(500,{error:"internal_error"})),Y(r)}}}function Tr(e,n){let t=j(e,n);return r=>t(r.request)}function nc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function tc(e,n){let t=Tr(e,n);return{loader:t,action:t}}function rc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function oc(e,n){let t=Tr(e,n);return{GET:t,POST:t,OPTIONS:t}}function ic(e,n){let t=j(e,n);return async r=>{let o={method:r.node.req.method,url:r.node.req.url,headers:r.node.req.headers,protocol:r.node.req.protocol,body:r._body,rawBody:r.node.req.rawBody??r._rawBody,resume:r.node.req.resume?.bind(r.node.req),[Symbol.asyncIterator]:r.node.req[Symbol.asyncIterator]?.bind(r.node.req)};try{let i=await t(await Fe(o,{maxBodyBytes:n?.maxBodyBytes,bodyStallTimeoutMs:n?.bodyStallTimeoutMs}));await Q(r.node.res,i)}catch(i){if(i instanceof w&&r.node.res.headersSent!==!0){await Q(r.node.res,pe(i)),Y(o);return}throw Y(o),i}}}function sc(e,n){return j(e,n)}function ac(e){let n={[it]:e};return{ok:Nt,tenants:{list:()=>xn(e),create:t=>qt(e,t),get:t=>Wt(e,t)},plugins:{list:()=>An(e),get:t=>$t(e,t)},connectionStatus:{get:t=>jt(e,t?.tenantId)},permissions:{get:t=>Ds(e,t)},connect:{createLink:t=>Zt(n,e,t),resolve:t=>Gt(n,e,t),oauthCallback:t=>zt(n,e,t)},disconnect:t=>Kt(e,t)}}async function cc(e,n,t,r,o="pending"){if(!e)return null;try{let i=ln(),a=new Date;return await e.db.insertInto("corsair_events").values({id:i,created_at:a,updated_at:a,account_id:n,event_type:t,payload:r,status:o}).execute(),i}catch(i){return console.warn("Failed to log event:",i),null}}async function rp(e,n,t,r="pending"){try{let o=await e.$getAccountId();return cc(e.database,o,n,t,r)}catch(o){return console.warn("Failed to log event:",o),null}}import*as lc from"https";import*as Pr from"querystring";var op=["expires_in","refresh_token_expires_in"];function uc(e){let n={...e};for(let t of op){let r=e[t];if(typeof r=="string"){let o=Number(r);n[t]=Number.isFinite(o)?o:void 0}}return n}function ip(e){try{return uc(JSON.parse(e))}catch{}if(!e.includes("="))return null;let n=Pr.parse(e);return!n.access_token&&!n.error?null:uc({...n})}function It(e,n,t,r,o){let i=new URL(r.tokenUrl),a=r.tokenAuthMethod==="basic";return new Promise((s,c)=>{let l={code:e.trim(),redirect_uri:o,grant_type:"authorization_code"};a||(l.client_id=n,l.client_secret=t);let u=Pr.stringify(l),d={"Content-Type":"application/x-www-form-urlencoded",Accept:"application/json","Content-Length":Buffer.byteLength(u).toString()};a&&(d.Authorization=`Basic ${Buffer.from(`${n}:${t}`).toString("base64")}`);let p=lc.request({hostname:i.hostname,...i.port?{port:Number(i.port)}:{},path:i.pathname+i.search,method:"POST",headers:d},g=>{let f="";g.on("data",h=>{f+=h}),g.on("end",()=>{if(g.statusCode!==200){c(new Error(`Token exchange failed (${g.statusCode}): ${f}`));return}let h=ip(f);h?s(h):c(new Error(`Token endpoint returned non-JSON response: ${f}`))})});p.on("error",g=>c(new Error(`Request failed: ${g.message}`))),p.write(u),p.end()})}async function dc(e,n){let{keys:t,hub:r,plugin:o,tenantId:i}=e,[a,s,c]=await Promise.all([t.get_access_token(),t.get_expires_at(),t.get_refresh_token()]);if(On({accessToken:a,expiresAt:s,forceRefresh:n?.forceRefresh}))return{accessToken:a,expiresAt:Number(s),refreshed:!1};if(!c)throw new S(o,"oauth_2");let l=await _({hub:r,path:"/oauth/refresh",body:{plugin:o,tenantId:i,refresh_token:c},parseResponse:dn}),u=await Mn(t,l,s);return{accessToken:l.access_token,expiresAt:u,refreshed:!0}}async function pc(e){let{tokenUrl:n,refreshToken:t,clientSecret:r,clientId:o,tokenAuthMethod:i="body",bodyFormat:a="form",extraParams:s}=e,c={grant_type:"refresh_token",refresh_token:t,...s},l={Accept:"application/json"};i==="basic"?l.Authorization=`Basic ${Buffer.from(`${o??""}:${r}`).toString("base64")}`:i==="basic_secret_only"?l.Authorization=`Basic ${Buffer.from(`${r}:`).toString("base64")}`:(o&&(c.client_id=o),c.client_secret=r),a==="json"?l["Content-Type"]="application/json":l["Content-Type"]="application/x-www-form-urlencoded";let u=await fetch(n,{method:"POST",headers:l,body:a==="json"?JSON.stringify(c):new URLSearchParams(c)});if(!u.ok)throw new Error(`OAuth token refresh failed (${u.status}): ${await u.text()}`);let d=JSON.parse(await u.text());if(typeof d.access_token!="string"||d.access_token.length===0)throw new Error("OAuth token refresh returned no access_token");return{access_token:d.access_token,...typeof d.refresh_token=="string"&&d.refresh_token.length>0?{refresh_token:d.refresh_token}:{},...typeof d.expires_in=="number"?{expires_in:d.expires_in}:{},...typeof d.scope=="string"&&d.scope.length>0?{scope:d.scope}:{}}}async function gc(e,n){let t=await e.keys.get_integration_credentials(),r=`${n.plugin}:${e.tenantId}`;if(!t.client_secret){if(!e.hub)throw new S(n.plugin,"oauth_2");let l={keys:e.keys,hub:e.hub,plugin:n.plugin,tenantId:e.tenantId},u=g=>Xe(e.keys,r,async()=>(await dc(l,{forceRefresh:g})).accessToken);e._refreshAuth=()=>u(!0);let[d,p]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at()]);return On({accessToken:d,expiresAt:p})?d:u(!1)}let o=t.client_secret,i=t.client_id,a=l=>Xe(e.keys,r,async()=>{let[u,d,p]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at(),e.keys.get_refresh_token()]);if(!l&&On({accessToken:u,expiresAt:d}))return u;if(!p)throw new S(n.plugin,"oauth_2");let g=await pc({tokenUrl:n.tokenUrl,tokenAuthMethod:n.tokenAuthMethod,bodyFormat:n.bodyFormat,extraParams:n.extraParams,clientId:i,clientSecret:o,refreshToken:p});return await Mn(e.keys,g,d),g.access_token});e._refreshAuth=()=>a(!0);let[s,c]=await Promise.all([e.keys.get_access_token(),e.keys.get_expires_at()]);return On({accessToken:s,expiresAt:c})?s:a(!1)}var fc=" ";function ae(e){let n=e;return n._def??n.def??{}}function ce(e){let n=e.typeName;if(n)return n;let t=e.type;if(t)return`Zod${t.split("_").map(r=>r.charAt(0).toUpperCase()+r.slice(1)).join("")}`}function se(e){return e.innerType??e.schema??e.out??e.in}function mc(e,n){switch(n){case"ZodPipe":return e.in??e.innerType;case"ZodEffects":return e.schema??e.innerType;case"ZodTransform":return e.schema??e.innerType??e.in;default:return se(e)}}function hc(e){let n=e.type;return e.element??(typeof n=="string"?void 0:n)}function Rr(e,n){let t=n.shape??e.shape;return typeof t=="function"?t():t}function Dn(e){return Array.isArray(e.options)?e.options:Array.isArray(e.values)?e.values:e.entries!==null&&typeof e.entries=="object"&&!Array.isArray(e.entries)?Object.values(e.entries):[]}function bc(e,n){return e.description??n.description}function sp(e){let n=e;for(;n;){let t=ae(n),r=bc(n,t);if(r)return r;let o=ce(t);if(yi(o)||o==="ZodPipe"||o==="ZodEffects"||o==="ZodTransform"){n=mc(t,o);continue}break}}function yi(e){return e==="ZodOptional"||e==="ZodNullable"||e==="ZodDefault"||e==="ZodCatch"}function X(e){let n=ae(e),t=ce(n);switch(t){case"ZodString":return"string";case"ZodNumber":return"number";case"ZodBoolean":return"boolean";case"ZodDate":return"Date";case"ZodNull":return"null";case"ZodUnknown":case"ZodAny":return"any";case"ZodLiteral":return String(n.value??Dn(n)[0]??"unknown");case"ZodEnum":return Dn(n).map(r=>String(r)).join(" | ");case"ZodOptional":{let r=se(n);return r?X(r):"unknown"}case"ZodNullable":{let r=se(n);return`${r?X(r):"unknown"} | null`}case"ZodDefault":case"ZodCatch":{let r=se(n);return r?X(r):"unknown"}case"ZodArray":{let r=hc(n);if(!r)return"unknown[]";let o=ae(r),i=ce(o)==="ZodUnion",a=X(r);return`${i?`(${a})`:a}[]`}case"ZodRecord":return"{}";case"ZodObject":{let r=Rr(e,n),o=Object.entries(r);return o.length===0?"{}":`{ ${o.map(([a,s])=>{let c=ce(ae(s));return`${c==="ZodOptional"||c==="ZodNullable"?a+"?":a}: ${X(s)}`}).join(", ")} }`}case"ZodUnion":return Dn(n).map(r=>X(r)).join(" | ");case"ZodIntersection":return`${X(n.left)} & ${X(n.right)}`;case"ZodPipe":case"ZodTransform":case"ZodEffects":{let r=mc(n,t);return r?X(r):"unknown"}default:return(t??"unknown").replace("Zod","").toLowerCase()}}function Ie(e){let n=ae(e),t=ce(n),r=bc(e,n);switch(t){case"ZodString":return{kind:"string",optional:!1,description:r};case"ZodNumber":return{kind:"number",optional:!1,description:r};case"ZodBoolean":return{kind:"boolean",optional:!1,description:r};case"ZodLiteral":{let o=n.value??Dn(n)[0],i=typeof o=="string"||typeof o=="number"||typeof o=="boolean"?o:String(o??"");return{kind:"literal",optional:!1,description:r,value:i}}case"ZodEnum":{let o=Dn(n).map(i=>String(i));return{kind:"string",optional:!1,description:r,enum:o}}case"ZodOptional":{let o=se(n),i=o?Ie(o):{kind:"unknown",optional:!1};return{...i,optional:!0,description:r??i.description}}case"ZodNullable":{let o=se(n),i=o?Ie(o):{kind:"unknown",optional:!1};return{...i,optional:!0,description:r??i.description}}case"ZodDefault":case"ZodCatch":{let o=se(n);return o?{...Ie(o),description:r}:{kind:"unknown",optional:!1,description:r}}case"ZodArray":{let o=hc(n);return{kind:"array",optional:!1,description:r,items:o?Ie(o):{kind:"unknown",optional:!1}}}case"ZodObject":{let o=Rr(e,n),i={};for(let[a,s]of Object.entries(o))i[a]=Ie(s);return{kind:"object",optional:!1,description:r,fields:i}}case"ZodRecord":return{kind:"unknown",optional:!1,description:r};case"ZodUnion":{let o=Dn(n);for(let i of o){let a=ae(i);if(ce(a)==="ZodObject")return{...Ie(i),description:r}}return{kind:"unknown",optional:!1,description:r}}case"ZodIntersection":case"ZodPipe":case"ZodTransform":case"ZodEffects":{let o=se(n);return o?{...Ie(o),description:r}:{kind:"unknown",optional:!1,description:r}}default:return{kind:"unknown",optional:!1,description:r}}}function FP(e,n){let t=n.toLowerCase(),r=t.indexOf(".");if(r===-1)return null;let o=t.slice(0,r),i=t.slice(r+1),a=e.find(u=>u.id===o);if(!a)return null;let s=i;s.startsWith("api.")&&(s=s.slice(4));let c=Ne(a.endpointMeta,s),l=Ne(a.endpointSchemas,s);return!c&&!l?null:{input:l?.input?Ie(l.input):null,output:l?.output?Ie(l.output):null,description:c?.description}}var mi=["equals","contains","startsWith","endsWith","in"],ap=["equals","gt","gte","lt","lte","in"],cp=["equals"],up=["equals","before","after","between"];function kc(e){let n=ae(e);switch(ce(n)){case"ZodOptional":case"ZodNullable":case"ZodDefault":case"ZodCatch":{let r=se(n);return r?kc(r):null}case"ZodString":return"string";case"ZodNumber":return"number";case"ZodBoolean":return"boolean";case"ZodDate":return"date";default:return null}}function hi(e){let n=ae(e),t=ce(n);if(yi(t)){let i=se(n);return i?hi(i):{}}if(t!=="ZodObject")return{};let r=Rr(e,n),o={};for(let[i,a]of Object.entries(r)){let s=kc(a);s==="string"?o[i]={type:"string",operators:mi}:s==="number"?o[i]={type:"number",operators:ap}:s==="boolean"?o[i]={type:"boolean",operators:cp}:s==="date"&&(o[i]={type:"date",operators:up})}return o}function wc(e,n){for(let[t,r]of Object.entries(e))if(t.toLowerCase()===n)return[t,r]}function pi(e,n,t){for(let[r,o]of Object.entries(e)){let i=[...n,r];typeof o=="function"?t.push(i.join(".")):o!==null&&typeof o=="object"&&pi(o,i,t)}}function gi(e){return e!==null&&typeof e=="object"&&"match"in e&&"handler"in e&&typeof e.match=="function"&&typeof e.handler=="function"}function fi(e,n,t){for(let[r,o]of Object.entries(e)){let i=[...n,r];gi(o)?t.push(i.join(".")):o!==null&&typeof o=="object"&&fi(o,i,t)}}function bi(e,n){if(n.length===0)return null;let[t,...r]=n,o=Object.entries(e).find(([s])=>s.toLowerCase()===t);if(!o)return null;let[i,a]=o;if(r.length===0)return gi(a)?[i]:null;if(a!==null&&typeof a=="object"&&!gi(a)){let s=bi(a,r);if(s!==null)return[i,...s]}return null}function Cc(e,n){let t=[];t.push(`${e}({`),t.push(" webhookHooks: {");for(let i=0;i<n.length;i++){let a=" ".repeat(i+2);t.push(`${a}${n[i]}: {`)}let r=" ".repeat(n.length+2),o=r+" ";t.push(`${r}before(ctx, args) {`),t.push(`${o}return { ctx, args };`),t.push(`${r}},`),t.push(`${r}after(ctx, response) {`),t.push(`${r}},`);for(let i=n.length-1;i>=0;i--){let a=" ".repeat(i+2);t.push(`${a}},`)}return t.push(" },"),t.push("})"),t.join(`
|
|
50
50
|
`)}var lp=new Set(dt);function an(e,n){let t=n?.type??"api",r=n?.plugin;if(r!==void 0){let i=e.find(s=>s.id===r);if(!i)return lp.has(r)?`This plugin (${r}) is not configured. Please add it to the Corsair instance to see its associated methods.`:an(e);if(t==="webhooks"){if(!i.webhooks)return[];let s=[];return fi(i.webhooks,[],s),s.map(c=>`${i.id}.webhooks.${c}`)}if(t==="db"){let s=i.schema?.entities;return s?Object.keys(s).map(c=>`${i.id}.db.${c}.search`):[]}if(!i.endpoints)return[];let a=[];return pi(i.endpoints,[],a),a.map(s=>`${i.id}.api.${s}`)}let o={};if(t==="webhooks")for(let i of e){if(!i.webhooks)continue;let a=[];fi(i.webhooks,[],a),o[i.id]=a.map(s=>`${i.id}.webhooks.${s}`)}else if(t==="db")for(let i of e){let a=i.schema?.entities;a&&(o[i.id]=Object.keys(a).map(s=>`${i.id}.db.${s}.search`))}else for(let i of e){if(!i.endpoints)continue;let a=[];pi(i.endpoints,[],a),o[i.id]=a.map(s=>`${i.id}.api.${s}`)}return o}function Ne(e,n){if(e){for(let[t,r]of Object.entries(e))if(t.toLowerCase()===n)return r}}function dp(e,n){let t=e.toLowerCase(),r=n.toLowerCase();if(!t.startsWith(`${r}.`)){let i=t.slice(n.length+1),a=i.startsWith(".")?i.slice(1):i;return a.startsWith("api.")&&(a=a.slice(4)),{shortPath:a,lookupKey:a}}let o=e.slice(n.length+1);return o.toLowerCase().startsWith("api.")&&(o=o.slice(4)),{shortPath:o,lookupKey:o.toLowerCase()}}function di(e,n){return typeof e=="string"?e:Array.isArray(e)?`${n}:
|
|
51
51
|
${e.join(", ")}`:`${n}:
|
|
52
52
|
`+Object.entries(e).map(([t,r])=>` ${t}: ${r.join(", ")}`).join(`
|
|
53
|
-
`)}function
|
|
53
|
+
`)}function NP(e,n){let t=n.toLowerCase(),r=t.indexOf(".");if(r!==-1){let o=t.slice(0,r),i=t.slice(r+1),a=e.find(s=>s.id===o);if(a){if(i.startsWith("db.")){let u=i.slice(3),d=u.lastIndexOf(".");if(d!==-1){let p=u.slice(0,d),g=u.slice(d+1),f=a.schema?.entities;if(g==="search"&&f){let h=wc(f,p);if(h){let[b,k]=h,T=hi(k),v=[`Search ${o} ${b} stored in the local database.`,"Pass limit and offset as numbers for pagination.","","filters {",` entity_id: string [${mi.join(", ")}]`];for(let[H,D]of Object.entries(T))v.push(` ${H}?: ${D.type} [${D.operators.join(", ")}]`);return v.push("}"),v.join(`
|
|
54
54
|
`)}}}return di(an(e,{type:"db"}),"Path not found. Available db operations")}if(i.startsWith("webhooks.")){let u=i.slice(9);if(a.webhooks){let d=bi(a.webhooks,u.split("."));if(d!==null){let p=d.join("."),g=Ne(a.webhookSchemas,p.toLowerCase()),f=g?.response?X(g.response):null,h=[];return g?.description&&h.push(g.description),g?.payload&&h.push(`payload ${vr(Hn(g.payload))}`),f&&h.push(`response: ${f}`),h.push(`usage:
|
|
55
55
|
${Cc(o,d)}`),h.join(`
|
|
56
56
|
|
|
@@ -59,8 +59,8 @@ ${Cc(o,d)}`),h.join(`
|
|
|
59
59
|
`)}}}return di(an(e),"Path not found. Available operations")}function yc(e){let n=e;for(;;){let t=ae(n),r=ce(t);if(yi(r)){let o=se(t);if(!o)return n;n=o;continue}return n}}function Hn(e){if(e===void 0)return{kind:"inline",type:"unknown"};let n=yc(e),t=ae(n);if(ce(t)==="ZodObject"){let o=Rr(n,t),i=[];for(let[a,s]of Object.entries(o)){let c=ae(s),l=ce(c),u=l==="ZodOptional"||l==="ZodNullable",d=yc(s),p=sp(s);i.push({key:a,optional:u,type:X(d),...p!==void 0?{description:p}:{}})}return{kind:"object",fields:i}}return{kind:"inline",type:X(n)}}function vr(e,n=0){if(e===void 0)return"{}";if(e.kind==="inline")return e.type;if(e.kind==="object"){if(e.fields.length===0)return"{}";let t=fc.repeat(n+1),r=fc.repeat(n);return`{
|
|
60
60
|
${e.fields.map(i=>{let a=i.optional?`${i.key}?`:i.key,s=i.description?` // ${i.description}`:"";return`${t}${a}: ${i.type}${s}`}).join(`
|
|
61
61
|
`)}
|
|
62
|
-
${r}}`}return"unknown"}function pp(e,n){let t=an(e,{plugin:n,type:"api"});if(typeof t=="string")return{ok:!1,error:t};if(!Array.isArray(t))return{ok:!1,error:"list_operations did not return a path array \u2014 pass a configured plugin id."};let r=e.find(u=>u.id===n);if(!r)return{ok:!1,error:`Plugin "${n}" is not configured on this instance.`};let o=[];for(let u of t){let{shortPath:d,lookupKey:p}=dp(u,n),g=Ne(r.endpointMeta,p),f=Ne(r.endpointSchemas,p);!g&&!f||o.push({path:u,shortPath:d,description:g?.description,riskLevel:g?.riskLevel,irreversible:g?.irreversible,input:Hn(f?.input),output:Hn(f?.output)})}o.sort((u,d)=>u.path.localeCompare(d.path));let i=[],a=an(e,{plugin:n,type:"webhooks"});if(Array.isArray(a)&&r.webhooks)for(let u of a){let p=u.toLowerCase().slice(n.length+1),g=p.startsWith(".")?p.slice(1):p;if(!g.startsWith("webhooks."))continue;let f=g.slice(9),h=bi(r.webhooks,f.split("."));if(h===null)continue;let b=h.join("."),k=Ne(r.webhookSchemas,b.toLowerCase()),T=k?.response?X(k.response):void 0;i.push({path:u,description:k?.description,payload:Hn(k?.payload),responseType:T,usageExample:Cc(n,h)})}i.sort((u,d)=>u.path.localeCompare(d.path));let s=[],c=an(e,{plugin:n,type:"db"}),l=r.schema?.entities;if(Array.isArray(c)&&l)for(let u of c){let p=u.toLowerCase().slice(n.length+1),g=p.startsWith(".")?p.slice(1):p;if(!g.startsWith("db."))continue;let f=g.slice(3),h=f.lastIndexOf(".");if(h===-1)continue;let b=f.slice(0,h);if(f.slice(h+1)!=="search")continue;let T=wc(l,b);if(!T)continue;let[v,H]=T,D=hi(H),B=Object.entries(D).map(([C,R])=>({field:C,type:R.type,operators:R.operators}));s.push({path:u,entityName:v,filters:[{field:"entity_id",type:"string",operators:mi},...B]})}return s.sort((u,d)=>u.path.localeCompare(d.path)),{ok:!0,data:{pluginId:n,api:o,webhooks:i,db:s}}}import{randomUUID as Tc}from"crypto";async function gp(e,n){let t=await e.keys.get_access_token();if(!t)return null;let r=Tc(),o=Tc(),i=await fetch(n.watchUrl,{method:"POST",signal:AbortSignal.timeout(2e4),headers:{authorization:`Bearer ${t}`,"content-type":"application/json"},body:JSON.stringify({id:r,type:"web_hook",address:n.webhookUrl,token:o,...n.body})});if(!i.ok)throw new Error(`Google channel watch failed (${i.status}): ${await i.text()}`);return{webhookLink:{linkType:"channel_id",externalId:r},webhookSecret:o}}import{randomUUID as fp}from"crypto";var Ar="https://graph.microsoft.com/v1.0",ki=2e4,yp=60;async function mp(e,n){let t=await e.keys.get_access_token();if(!t)return null;let r={authorization:`Bearer ${t}`};try{let c=await fetch(`${Ar}/subscriptions`,{headers:r,signal:AbortSignal.timeout(ki)});if(c.ok){let{value:l}=await c.json(),u=(l??[]).filter(d=>d.notificationUrl===n.webhookUrl);await Promise.all(u.map(d=>fetch(`${Ar}/subscriptions/${d.id}`,{method:"DELETE",headers:r,signal:AbortSignal.timeout(ki)}).catch(()=>{})))}}catch{}let o=fp(),i=new Date(Date.now()+yp*6e4).toISOString(),a=await fetch(`${Ar}/subscriptions`,{method:"POST",headers:{...r,"content-type":"application/json"},signal:AbortSignal.timeout(ki),body:JSON.stringify({changeType:n.changeType,notificationUrl:n.webhookUrl,resource:n.resource,expirationDateTime:i,clientState:o})});if(!a.ok)throw new Error(`MS Graph subscribe failed (${a.status}): ${await a.text()}`);let s=await a.json();return s.id?(await e.keys.set_webhook_signature(o),{webhookLink:{linkType:"subscription_id",externalId:s.id},webhookSecret:o}):null}function Pc(e,n){for(let[t,r]of Object.entries(e))if(r?.pluginWebhookMatcher&&r.pluginWebhookMatcher(n))return t;return null}function hp(e,n){let t=Pc(e,n);if(!t)return null;let r=e[t];if(!r?.pluginTenantWebhookMatcher)return null;let o=r.pluginTenantWebhookMatcher(n);return o?{plugin:t,tenantMatch:o}:null}function bp(e){let n={};for(let t of e)!t.pluginWebhookMatcher&&!t.pluginTenantWebhookMatcher||(n[t.id]={pluginWebhookMatcher:t.pluginWebhookMatcher,pluginTenantWebhookMatcher:t.pluginTenantWebhookMatcher});return n}function vc(e,n){let t=n.toLowerCase(),r=e[t]??e[n];return Array.isArray(r)?r[0]:typeof r=="string"?r:void 0}function Rc(e){if(typeof e=="string"){let n=e.trim();return n.length>0?n:void 0}if(typeof e=="number"&&Number.isFinite(e))return String(e)}function st(e){return!e||typeof e!="object"||Array.isArray(e)?null:e}function kp(e){return st(e.body)}function Ac(e,n){let t=e.query;if(!t)return;let r=t[n]??t[n.toLowerCase()];return xr(Array.isArray(r)?r:[r])}function xc(e){let n=e.headers??{},t=[n.validationtoken,n.validationToken,n["validation-token"],n["ms-validation-token"]];for(let c of t){let l=xr(Array.isArray(c)?c:[c]);if(l)return decodeURIComponent(l)}let r=Ac({query:e.query},"validationToken");if(r)return r;let o=["x-forwarded-uri","x-original-uri","x-rewrite-url","x-envoy-original-path","referer"];for(let c of o){let l=n[c],u=Array.isArray(l)?l[0]:l;if(!(!u||typeof u!="string"))try{let p=(u.startsWith("http")?new URL(u):new URL(`https://example.invalid${u.startsWith("/")?u:`/${u}`}`)).searchParams.get("validationToken");if(p?.trim())return p.trim()}catch{continue}}let i=e.payload!==void 0?e.payload:e.body!==void 0?e.body:void 0,a=st(typeof i=="string"?(()=>{try{return JSON.parse(i)}catch{return i}})():i);return xr([a?.validationToken])??null}function wp(e){if(xc(e))return!0;let n=st(e.body??e.payload);return vc(e.headers??{},"content-type")?.includes("text/plain")?!n||Object.keys(n).length===0:!1}function xr(e){for(let n of e){let t=Rc(n);if(t)return t}}function Cp(e){let t=st(e.message)?.data;if(typeof t!="string")return null;try{return JSON.parse(Buffer.from(t,"base64").toString("utf8"))}catch{return null}}var it=Symbol.for("corsair:internal");function Ec(e){if(e.hub?.projectApiKey?.startsWith("ck_cloud_")&&Ba(e.hub))return Ua(e);let n=e.database?Si(e.database,{dbTables:e.dbTables}):void 0,t=e.kek??"",r=n&&t?Ma(e.plugins,n,t):yr(!!n,!!t),o=La(e),i={plugins:e.plugins,database:n,kek:t,multiTenancy:!!e.multiTenancy,permissions:o,manual:e.manual,hub:e.hub?kt(e.hub):void 0},a=Is(n),s=ac(i);if(e.multiTenancy){let u=Object.assign({withTenant:d=>{if(!d)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");let p=oi(e.plugins,{database:n,tenantId:d,kek:t,rootErrorHandlers:e.errorHandlers,permissionsOptions:o,manualConfig:e.manual,hubConfig:i.hub,internalConfig:i});return Object.assign(p,{[it]:i})},keys:r,permissions:a,manage:s},{[it]:i});return Ic(u,i.hub),_c(u,i.hub),u}let c=oi(e.plugins,{database:n,tenantId:void 0,kek:t,rootErrorHandlers:e.errorHandlers,permissionsOptions:o,manualConfig:e.manual,hubConfig:i.hub,internalConfig:i}),l=Object.assign({},c,{keys:r,permissions:a,manage:s,[it]:i});return Ic(l,i.hub),_c(l,i.hub),l}function Ic(e,n){n?.projectApiKey?.startsWith("ck_dev_")&&import("./loop-
|
|
63
|
-
`)}function Ci(e,n,t){let r=t==="integration"?e.authConfig?.[n]?.integration??[]:e.authConfig?.[n]?.account??[];return new Set([...K[n][t],...r])}function Up(e,n){if(!e)return!1;for(let[t,r]of Object.entries(e)){let o=n.find(s=>s.id===t);if(!o)continue;let i=
|
|
64
|
-
Schema: ${JSON.stringify(Ir(a),null,2)}`)}}}async function Wp(e,n,t,r,o){let i=new Date,a=new Map;for(let s of n.plugins){let c=s.id,l=
|
|
62
|
+
${r}}`}return"unknown"}function pp(e,n){let t=an(e,{plugin:n,type:"api"});if(typeof t=="string")return{ok:!1,error:t};if(!Array.isArray(t))return{ok:!1,error:"list_operations did not return a path array \u2014 pass a configured plugin id."};let r=e.find(u=>u.id===n);if(!r)return{ok:!1,error:`Plugin "${n}" is not configured on this instance.`};let o=[];for(let u of t){let{shortPath:d,lookupKey:p}=dp(u,n),g=Ne(r.endpointMeta,p),f=Ne(r.endpointSchemas,p);!g&&!f||o.push({path:u,shortPath:d,description:g?.description,riskLevel:g?.riskLevel,irreversible:g?.irreversible,input:Hn(f?.input),output:Hn(f?.output)})}o.sort((u,d)=>u.path.localeCompare(d.path));let i=[],a=an(e,{plugin:n,type:"webhooks"});if(Array.isArray(a)&&r.webhooks)for(let u of a){let p=u.toLowerCase().slice(n.length+1),g=p.startsWith(".")?p.slice(1):p;if(!g.startsWith("webhooks."))continue;let f=g.slice(9),h=bi(r.webhooks,f.split("."));if(h===null)continue;let b=h.join("."),k=Ne(r.webhookSchemas,b.toLowerCase()),T=k?.response?X(k.response):void 0;i.push({path:u,description:k?.description,payload:Hn(k?.payload),responseType:T,usageExample:Cc(n,h)})}i.sort((u,d)=>u.path.localeCompare(d.path));let s=[],c=an(e,{plugin:n,type:"db"}),l=r.schema?.entities;if(Array.isArray(c)&&l)for(let u of c){let p=u.toLowerCase().slice(n.length+1),g=p.startsWith(".")?p.slice(1):p;if(!g.startsWith("db."))continue;let f=g.slice(3),h=f.lastIndexOf(".");if(h===-1)continue;let b=f.slice(0,h);if(f.slice(h+1)!=="search")continue;let T=wc(l,b);if(!T)continue;let[v,H]=T,D=hi(H),B=Object.entries(D).map(([C,R])=>({field:C,type:R.type,operators:R.operators}));s.push({path:u,entityName:v,filters:[{field:"entity_id",type:"string",operators:mi},...B]})}return s.sort((u,d)=>u.path.localeCompare(d.path)),{ok:!0,data:{pluginId:n,api:o,webhooks:i,db:s}}}import{randomUUID as Tc}from"crypto";async function gp(e,n){let t=await e.keys.get_access_token();if(!t)return null;let r=Tc(),o=Tc(),i=await fetch(n.watchUrl,{method:"POST",signal:AbortSignal.timeout(2e4),headers:{authorization:`Bearer ${t}`,"content-type":"application/json"},body:JSON.stringify({id:r,type:"web_hook",address:n.webhookUrl,token:o,...n.body})});if(!i.ok)throw new Error(`Google channel watch failed (${i.status}): ${await i.text()}`);return{webhookLink:{linkType:"channel_id",externalId:r},webhookSecret:o}}import{randomUUID as fp}from"crypto";var Ar="https://graph.microsoft.com/v1.0",ki=2e4,yp=60;async function mp(e,n){let t=await e.keys.get_access_token();if(!t)return null;let r={authorization:`Bearer ${t}`};try{let c=await fetch(`${Ar}/subscriptions`,{headers:r,signal:AbortSignal.timeout(ki)});if(c.ok){let{value:l}=await c.json(),u=(l??[]).filter(d=>d.notificationUrl===n.webhookUrl);await Promise.all(u.map(d=>fetch(`${Ar}/subscriptions/${d.id}`,{method:"DELETE",headers:r,signal:AbortSignal.timeout(ki)}).catch(()=>{})))}}catch{}let o=fp(),i=new Date(Date.now()+yp*6e4).toISOString(),a=await fetch(`${Ar}/subscriptions`,{method:"POST",headers:{...r,"content-type":"application/json"},signal:AbortSignal.timeout(ki),body:JSON.stringify({changeType:n.changeType,notificationUrl:n.webhookUrl,resource:n.resource,expirationDateTime:i,clientState:o})});if(!a.ok)throw new Error(`MS Graph subscribe failed (${a.status}): ${await a.text()}`);let s=await a.json();return s.id?(await e.keys.set_webhook_signature(o),{webhookLink:{linkType:"subscription_id",externalId:s.id},webhookSecret:o}):null}function Pc(e,n){for(let[t,r]of Object.entries(e))if(r?.pluginWebhookMatcher&&r.pluginWebhookMatcher(n))return t;return null}function hp(e,n){let t=Pc(e,n);if(!t)return null;let r=e[t];if(!r?.pluginTenantWebhookMatcher)return null;let o=r.pluginTenantWebhookMatcher(n);return o?{plugin:t,tenantMatch:o}:null}function bp(e){let n={};for(let t of e)!t.pluginWebhookMatcher&&!t.pluginTenantWebhookMatcher||(n[t.id]={pluginWebhookMatcher:t.pluginWebhookMatcher,pluginTenantWebhookMatcher:t.pluginTenantWebhookMatcher});return n}function vc(e,n){let t=n.toLowerCase(),r=e[t]??e[n];return Array.isArray(r)?r[0]:typeof r=="string"?r:void 0}function Rc(e){if(typeof e=="string"){let n=e.trim();return n.length>0?n:void 0}if(typeof e=="number"&&Number.isFinite(e))return String(e)}function st(e){return!e||typeof e!="object"||Array.isArray(e)?null:e}function kp(e){return st(e.body)}function Ac(e,n){let t=e.query;if(!t)return;let r=t[n]??t[n.toLowerCase()];return xr(Array.isArray(r)?r:[r])}function xc(e){let n=e.headers??{},t=[n.validationtoken,n.validationToken,n["validation-token"],n["ms-validation-token"]];for(let c of t){let l=xr(Array.isArray(c)?c:[c]);if(l)return decodeURIComponent(l)}let r=Ac({query:e.query},"validationToken");if(r)return r;let o=["x-forwarded-uri","x-original-uri","x-rewrite-url","x-envoy-original-path","referer"];for(let c of o){let l=n[c],u=Array.isArray(l)?l[0]:l;if(!(!u||typeof u!="string"))try{let p=(u.startsWith("http")?new URL(u):new URL(`https://example.invalid${u.startsWith("/")?u:`/${u}`}`)).searchParams.get("validationToken");if(p?.trim())return p.trim()}catch{continue}}let i=e.payload!==void 0?e.payload:e.body!==void 0?e.body:void 0,a=st(typeof i=="string"?(()=>{try{return JSON.parse(i)}catch{return i}})():i);return xr([a?.validationToken])??null}function wp(e){if(xc(e))return!0;let n=st(e.body??e.payload);return vc(e.headers??{},"content-type")?.includes("text/plain")?!n||Object.keys(n).length===0:!1}function xr(e){for(let n of e){let t=Rc(n);if(t)return t}}function Cp(e){let t=st(e.message)?.data;if(typeof t!="string")return null;try{return JSON.parse(Buffer.from(t,"base64").toString("utf8"))}catch{return null}}var it=Symbol.for("corsair:internal");function Ec(e){if(e.hub?.projectApiKey?.startsWith("ck_cloud_")&&Ba(e.hub))return Ua(e);let n=e.database?Si(e.database,{dbTables:e.dbTables}):void 0,t=e.kek??"",r=n&&t?Ma(e.plugins,n,t):yr(!!n,!!t),o=La(e),i={plugins:e.plugins,database:n,kek:t,multiTenancy:!!e.multiTenancy,permissions:o,manual:e.manual,hub:e.hub?kt(e.hub):void 0},a=Is(n),s=ac(i);if(e.multiTenancy){let u=Object.assign({withTenant:d=>{if(!d)throw new Error("corsair.withTenant(tenantId): tenantId must be a non-empty string");let p=oi(e.plugins,{database:n,tenantId:d,kek:t,rootErrorHandlers:e.errorHandlers,permissionsOptions:o,manualConfig:e.manual,hubConfig:i.hub,internalConfig:i});return Object.assign(p,{[it]:i})},keys:r,permissions:a,manage:s},{[it]:i});return Ic(u,i.hub),_c(u,i.hub),u}let c=oi(e.plugins,{database:n,tenantId:void 0,kek:t,rootErrorHandlers:e.errorHandlers,permissionsOptions:o,manualConfig:e.manual,hubConfig:i.hub,internalConfig:i}),l=Object.assign({},c,{keys:r,permissions:a,manage:s,[it]:i});return Ic(l,i.hub),_c(l,i.hub),l}function Ic(e,n){n?.projectApiKey?.startsWith("ck_dev_")&&import("./loop-HHZM2Z4J.js").then(t=>t.startConnectLoop(e)).catch(()=>{})}function Tp(e){return e?.projectApiKey?.startsWith("ck_dev_")?e.tunnel!==!1&&process.env.CORSAIR_TUNNEL!=="0":!1}var Sc=globalThis.__corsairTunnels??=new Set,Pp=1e3,vp=3e4;function Rp(e){let n=e.schedule??((a,s)=>void setTimeout(a,s).unref?.()),t=e.minDelayMs??Pp,r=e.maxDelayMs??vp,o=t,i=()=>{let a=!1,s=()=>{a||(a=!0,n(i,o),o=Math.min(o*2,r))};e.start(s).then(()=>{o=t}).catch(s)};i()}function _c(e,n){if(!Tp(n))return;let t=n.projectApiKey;if(Sc.has(t))return;let r=Number(process.env.PORT);if(!Number.isInteger(r)||r<1||r>65535){console.error("[corsair] PORT is not set \u2014 dev tunnel skipped. Set PORT to your app port, or run `corsair http <port>`.");return}Sc.add(t);let o=typeof n.tunnel=="object"?n.tunnel:{},i=process.env.CORSAIR_FRP_HOST??o.shareHost??_r;Rp({start:a=>import("./hub/tunnel/run-tunnel.js").then(s=>s.runTunnel({port:r,apiUrl:n.apiUrl,apiKey:t,shareHost:i,onClose:a})).then(({url:s})=>{console.log(`[corsair] tunnel active: ${s}${Er}`)}).catch(s=>{throw console.warn(`[corsair] tunnel down: ${s instanceof Error?s.message:String(s)}. Retrying \u2014 run \`corsair setup\` if it doesn't recover.`),s})})}var Ap={slack:{channels:{list:{}},users:{list:{}}},linear:{projects:{list:{}},issues:{list:{}},users:{list:{}}},github:{issues:{list:{}},repositories:{list:{}}},discord:{guilds:{list:{}},channels:{list:{}}},hubspot:{contacts:{getMany:{}},companies:{getMany:{}},deals:{getMany:{}}},gmail:{messages:{list:{}},labels:{list:{}},drafts:{list:{}},threads:{list:{}}},googlecalendar:{events:{getMany:{}}},googlemeet:{conferenceRecords:{list:{}}},googledrive:{files:{list:{}},folders:{list:{}},sharedDrives:{list:{}}},notion:{databases:{getManyDatabases:{}},databasePages:{getManyDatabasePages:{}},users:{getManyUsers:{}}},airtable:{bases:{getMany:{}}},todoist:{projects:{getMany:{}},tasks:{getMany:{}}},cal:{bookings:{list:{}}},zohomail:{folders:{list:{}},messages:{list:{}}}},wi=Ap;async function St(e,n){let t=[],r=n?.silent??!1,o=g=>{t.push(g),r||console.log(g)},i=g=>{t.push(g),r||console.warn(g)},a=n?.caller??"script",s=Ei(e);if(!s)throw new Error("setupCorsair: invalid corsair instance");if(!s.database)throw new Error("setupCorsair: a database must be configured on the corsair instance");let c=Lp(e,s.plugins,n),l={...s,database:s.database},u=l.database.db;await $p(l.database,i);let d=await Wp(u,l,c.tenantId,c.provisionAccounts,o);n?.credentials&&Object.keys(n.credentials).length>0&&await Kp(e,c,n.credentials,l,o,i);let p=await Gp(d,c,o,a);if(n?.backfill){o("[corsair:setup] Starting backfill...");let g=Ec({plugins:s.plugins,database:u,kek:s.kek,multiTenancy:!0}).withTenant(c.tenantId);await zp(g,s.plugins,p,o,i),o("[corsair:setup] Backfill complete.")}return t.join(`
|
|
63
|
+
`)}function Ci(e,n,t){let r=t==="integration"?e.authConfig?.[n]?.integration??[]:e.authConfig?.[n]?.account??[];return new Set([...K[n][t],...r])}function Up(e,n){if(!e)return!1;for(let[t,r]of Object.entries(e)){let o=n.find(s=>s.id===t);if(!o)continue;let i=E(o);if(!i)continue;let a=Ci(o,i,"account");for(let s of Object.keys(r))if(a.has(s))return!0}return!1}function Lp(e,n,t){let r=Oi(e),o=t?.tenantId?.trim(),i=o!==void 0&&o.length>0;if(r&&t?.backfill&&!i)throw new Error("setupCorsair: tenantId is required for backfill on a multi-tenant instance");if(r&&Up(t?.credentials,n)&&!i)throw new Error("setupCorsair: tenantId is required when setting account-level credentials on a multi-tenant instance");if(i&&!o)throw new Error("setupCorsair: tenantId must be a non-empty string");return{multiTenant:r,tenantIdProvided:i,tenantId:i?o:"default",provisionAccounts:!r||i}}function Mc(e,n){return _e(e)?n===0?!0:Object.values(e).every(t=>Mc(t,n-1)):!1}function Fp(e){return Mc(e,4)}var Np=Hi;function Ir(e){if(e instanceof Op){let n={};for(let[t,r]of Object.entries(e.shape))n[t]=r instanceof Bp?Ir(r):"unknown";return n}return e instanceof _p?`${Ir(e.unwrap())} | null`:e instanceof Mp?`${Ir(e.unwrap())} | undefined`:e instanceof Sp?e.options.join(" | "):e instanceof Hp?"string":e instanceof Ep?"number":e instanceof xp?"boolean":e instanceof Ip?"date":e instanceof Dp?"jsonb":"unknown"}async function $p(e,n){let t=await e.db.introspection.getTables(),r=new Set(t.map(i=>i.name)),o=e.tableNames??Ii();for(let[i,a]of Object.entries(Np)){let s=o[i];if(!r.has(s)){let c=s!==i?` (dbTables.${i} \u2192 "${s}")`:"";n(`[corsair:setup] Table "${s}" does not exist${c}. Run your database migrations before calling setupCorsair.
|
|
64
|
+
Schema: ${JSON.stringify(Ir(a),null,2)}`)}}}async function Wp(e,n,t,r,o){let i=new Date,a=new Map;for(let s of n.plugins){let c=s.id,l=E(s),u=await e.selectFrom("corsair_integrations").selectAll().where("name","=",c).executeTakeFirst();if(!u){let h=crypto.randomUUID();await e.insertInto("corsair_integrations").values({id:h,name:c,config:{},created_at:i,updated_at:i}).execute(),u=await e.selectFrom("corsair_integrations").selectAll().where("id","=",h).executeTakeFirst(),o(`[corsair:setup] Created integration: ${c}`)}let d=l?s.authConfig?.[l]?.integration??[]:[],p=l?s.authConfig?.[l]?.account??[]:[],g=l&&u?$({authType:l,integrationName:c,kek:n.kek,database:n.database,extraIntegrationFields:d}):void 0;if(u&&!u.dek&&g&&(await g.issue_new_dek(),o(`[corsair:setup] Issued integration DEK: ${c}`)),!u||!l||!g)continue;let f;if(r){let h=await e.selectFrom("corsair_accounts").selectAll().where("tenant_id","=",t).where("integration_id","=",u.id).executeTakeFirst();if(!h){let b=crypto.randomUUID();await e.insertInto("corsair_accounts").values({id:b,tenant_id:t,integration_id:u.id,config:{},created_at:i,updated_at:i}).execute(),h=await e.selectFrom("corsair_accounts").selectAll().where("id","=",b).executeTakeFirst(),o(`[corsair:setup] Created account: ${c}`)}f=h&&U({authType:l,integrationName:c,tenantId:t,kek:n.kek,database:n.database,extraAccountFields:p}),h&&f&&!h.dek&&(await f.issue_new_dek(),o(`[corsair:setup] Issued account DEK: ${c}`))}a.set(c,{pluginId:c,authType:l,integration:g,account:f,integrationFields:[...K[l].integration,...d],accountFields:r?[...K[l].account,...p]:[]})}return a}function qp(e){if(!_e(e))return;let n=e.keys;return _e(n)?n:void 0}function jp(e,n){return"withTenant"in e&&typeof e.withTenant=="function"?e.withTenant(n):e}async function Kp(e,n,t,r,o,i){let a=qp(e),s=n.provisionAccounts?jp(e,n.tenantId):void 0;for(let[c,l]of Object.entries(t)){let u=r.plugins.find(k=>k.id===c);if(!u){i(`[corsair:setup] Unknown plugin '${c}' \u2014 skipping credentials.`);continue}let d=E(u);if(!d){i(`[corsair:setup] Plugin '${c}' has no auth type \u2014 skipping credentials.`);continue}let p=Ci(u,d,"integration"),g=Ci(u,d,"account"),f=a?.[c],h=s?.[c],b=_e(h)?h.keys:void 0;for(let[k,T]of Object.entries(l))if(T){if(p.has(k)){if(n.multiTenant&&n.tenantIdProvided)throw new Error(`[corsair:setup] '${c}.${k}' is an integration-level credential shared across all tenants. You passed tenantId="${n.tenantId}", which only scopes account-level credentials. Run setup without --tenant if you intend to change this credential globally.`);let v=ne(f,`set_${k}`);if(!v){i(`[corsair:setup] Cannot set integration field '${k}' for '${c}'.`);continue}await v(T),o(`[corsair:setup] Set ${c} integration.${k}`);continue}if(g.has(k)){if(n.multiTenant&&!n.tenantIdProvided)throw new Error(`setupCorsair: tenantId is required to set account-level credential '${c}.${k}' on a multi-tenant instance`);let v=ne(b,`set_${k}`);if(!v){i(`[corsair:setup] Cannot set account field '${k}' for '${c}'.`);continue}await v(T),o(`[corsair:setup] Set ${c} account.${k} (tenant=${n.tenantId})`);continue}i(`[corsair:setup] Unknown credential field '${k}' for plugin '${c}'.`)}}}var Oc=new Set(["webhook_signature","expires_at","scope","redirect_url"]);async function Zp(e,n,t,r,o,i,a,s,c){let l=[],u=[];for(let p of o){if(Oc.has(p))continue;let g=ne(t,`get_${p}`);if(!g)continue;let f=null;try{let h=await g();f=typeof h=="string"?h:null}catch{}f||l.push(p)}if(r&&i.length>0)for(let p of i){if(Oc.has(p))continue;let g=ne(r,`get_${p}`);if(!g)continue;let f=null;try{let h=await g();f=typeof h=="string"?h:null}catch{}f||u.push(p)}let d=l.length===0&&u.length===0;if(n==="managed_pricing")s(`[corsair:setup] '${e}' (managed_pricing) uses Corsair metered credentials via Hub \u2014 nothing to store in your database. Pass hub: { ... } to createCorsair().`);else if(d)s(`[corsair:setup] '${e}' (${n}) is configured \u2713`);else if(n==="managed")s(`[corsair:setup] '${e}' (managed) is not connected yet. Use Connect in your app \u2014 Corsair Hub delivers OAuth tokens after authorization.`);else{let p=[...l,...u];if(c==="cli"){let g=p.map(f=>`${f}=VALUE`).join(" ");s(`[corsair:setup] '${e}' (${n}) needs credentials. Run:
|
|
65
65
|
corsair setup --${e} ${g}`)}else{let g=[`[corsair:setup] '${e}' (${n}) needs credentials. Call:`];for(let f of l)g.push(` await corsair.keys.${e}.set_${f}(value)`);for(let f of u){let h=a.provisionAccounts?a.tenantId==="default"?`corsair.${e}`:`corsair.withTenant(${JSON.stringify(a.tenantId)}).${e}`:`corsair.withTenant(<tenant>).${e}`;g.push(` await ${h}.keys.set_${f}(value)`)}s(g.join(`
|
|
66
|
-
`))}}return d}async function Gp(e,n,t,r){let o=new Set;for(let i of e.values())await Zp(i.pluginId,i.authType,i.integration,i.account,i.integrationFields,i.accountFields,n,t,r)&&o.add(i.pluginId);return o}async function zp(e,n,t,r,o){if(!Fp(wi)){o("[corsair:setup] Backfill config is invalid - skipping backfill.");return}let i=wi,a=new Set(n.map(s=>s.id));for(let[s,c]of Object.entries(i)){if(!a.has(s))continue;if(!t.has(s)){r(`[corsair:setup] Skipping backfill for '${s}' \u2014 auth not configured.`);continue}let l=_e(e)?e[s]:void 0,u=_e(l)?l.api:void 0;if(u)for(let[d,p]of Object.entries(c))for(let[g,f]of Object.entries(p)){r(`[corsair:setup] Backfilling ${s} \u203A ${d}.${g}...`);try{let h=_e(u)?u[d]:void 0;await ne(h,g)?.(f)}catch(h){o(`[corsair:setup] ${s} \u203A ${d}.${g} failed: `+(h instanceof Error?h.message:String(h)))}}}}export{Bi as a,Ee as b,ke as c,pt as d,gt as e,ft as f,dn as g,Ui as h,yt as i,Lr as j,Nn as k,ji as l,Ki as m,Oe as n,We as o,we as p,gn as q,fn as r,Me as s,Nr as t,Gi as u,qn as v,Ce as w,jn as x,$r as y,kt as z,N as A,wt as B,yn as C,Te as D,Pe as E,te as F,Wr as G,Kn as H,De as I,le as J,Zn as K,$ as L,U as M,es as N,ns as O,St as P,Kp as Q,Be as R,jr as S,bn as T,wn as U,Zr as V,xt as W,ds as X,Ze as Y,V as Z,Gr as _,Jn as $,ys as aa,Tu as ba,_t as ca,uy as da,bs as ea,ks as fa,ws as ga,Cs as ha,Et as ia,zr as ja,de as ka,Mt as la,Dt as ma,vn as na,Ut as oa,Rn as pa,no as qa,As as ra,Lt as sa,Ge as ta,w as ua,co as va,uo as wa,Jt as xa,lo as ya,In as za,Sn as Aa,Vt as Ba,Yt as Ca,Vn as Da,po as Ea,go as Fa,Qt as Ga,Yn as Ha,Xt as Ia,er as Ja,Le as Ka,_n as La,Ns as Ma,bo as Na,ko as Oa,Je as Pa,et as Qa,nt as Ra,ar as Sa,To as Ta,tt as Ua,Il as Va,Ml as Wa,Bl as Xa,Vs as Ya,Ys as Za,ur as _a,Qs as $a,Xs as ab,Ve as bb,Ye as cb,Ao as db,xo as eb,Io as fb,So as gb,_o as hb,Qe as ib,S as jb,Eo as kb,ia as lb,pr as mb,Mo as nb,gr as ob,fr as pb,aa as qb,Do as rb,Ho as sb,Bo as tb,Uo as ub,Lo as vb,Fo as wb,No as xb,$o as yb,Wo as zb,qo as Ab,jo as Bb,Ko as Cb,Zo as Db,Go as Eb,zo as Fb,en as Gb,ye as Hb,nn as Ib,tn as Jb,ei as Kb,Ae as Lb,Od as Mb,j as Nb,Ja as Ob,Va as Pb,Ya as Qb,Qa as Rb,Xa as Sb,ec as Tb,nc as Ub,tc as Vb,rc as Wb,oc as Xb,ic as Yb,sc as Zb,cc as _b,rp as $b,It as ac,gc as bc,
|
|
66
|
+
`))}}return d}async function Gp(e,n,t,r){let o=new Set;for(let i of e.values())await Zp(i.pluginId,i.authType,i.integration,i.account,i.integrationFields,i.accountFields,n,t,r)&&o.add(i.pluginId);return o}async function zp(e,n,t,r,o){if(!Fp(wi)){o("[corsair:setup] Backfill config is invalid - skipping backfill.");return}let i=wi,a=new Set(n.map(s=>s.id));for(let[s,c]of Object.entries(i)){if(!a.has(s))continue;if(!t.has(s)){r(`[corsair:setup] Skipping backfill for '${s}' \u2014 auth not configured.`);continue}let l=_e(e)?e[s]:void 0,u=_e(l)?l.api:void 0;if(u)for(let[d,p]of Object.entries(c))for(let[g,f]of Object.entries(p)){r(`[corsair:setup] Backfilling ${s} \u203A ${d}.${g}...`);try{let h=_e(u)?u[d]:void 0;await ne(h,g)?.(f)}catch(h){o(`[corsair:setup] ${s} \u203A ${d}.${g} failed: `+(h instanceof Error?h.message:String(h)))}}}}export{Bi as a,Ee as b,ke as c,pt as d,gt as e,ft as f,dn as g,Ui as h,yt as i,Lr as j,Nn as k,ji as l,Ki as m,Oe as n,We as o,we as p,gn as q,fn as r,Me as s,Nr as t,Gi as u,qn as v,Ce as w,jn as x,$r as y,kt as z,N as A,wt as B,yn as C,Te as D,Pe as E,te as F,Wr as G,Kn as H,De as I,le as J,Zn as K,$ as L,U as M,es as N,ns as O,St as P,Kp as Q,Be as R,jr as S,bn as T,wn as U,Zr as V,xt as W,ds as X,Ze as Y,V as Z,Gr as _,Jn as $,ys as aa,Tu as ba,_t as ca,uy as da,bs as ea,ks as fa,ws as ga,Cs as ha,Et as ia,zr as ja,de as ka,Mt as la,Dt as ma,vn as na,Ut as oa,Rn as pa,no as qa,As as ra,Lt as sa,Ge as ta,w as ua,co as va,uo as wa,Jt as xa,lo as ya,In as za,Sn as Aa,Vt as Ba,Yt as Ca,Vn as Da,po as Ea,go as Fa,Qt as Ga,Yn as Ha,Xt as Ia,er as Ja,Le as Ka,_n as La,Ns as Ma,bo as Na,ko as Oa,Je as Pa,et as Qa,nt as Ra,ar as Sa,To as Ta,tt as Ua,Il as Va,Ml as Wa,Bl as Xa,Vs as Ya,Ys as Za,ur as _a,Qs as $a,Xs as ab,Ve as bb,Ye as cb,Ao as db,xo as eb,Io as fb,So as gb,_o as hb,Qe as ib,S as jb,Eo as kb,ia as lb,pr as mb,Mo as nb,gr as ob,fr as pb,aa as qb,Do as rb,Ho as sb,Bo as tb,Uo as ub,Lo as vb,Fo as wb,No as xb,$o as yb,Wo as zb,qo as Ab,jo as Bb,Ko as Cb,Zo as Db,Go as Eb,zo as Fb,en as Gb,ye as Hb,nn as Ib,tn as Jb,ei as Kb,Ae as Lb,Od as Mb,j as Nb,Ja as Ob,Va as Pb,Ya as Qb,Qa as Rb,Xa as Sb,ec as Tb,nc as Ub,tc as Vb,rc as Wb,oc as Xb,ic as Yb,sc as Zb,cc as _b,rp as $b,It as ac,gc as bc,FP as cc,an as dc,NP as ec,vr as fc,pp as gc,gp as hc,Ar as ic,mp as jc,Pc as kc,hp as lc,bp as mc,vc as nc,Rc as oc,st as pc,kp as qc,Ac as rc,xc as sc,wp as tc,xr as uc,Cp as vc,it as wc,Ec as xc,Tp as yc,Rp as zc};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{ga as a,ha as b,ia as c}from"./chunk-
|
|
1
|
+
import{ga as a,ha as b,ia as c}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{c as createHubConnectSession,b as createHubConnectSessionForPlugin,a as postHubConnectSession};
|
package/dist/core.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{$b as J,D as e,E as f,F as g,G as h,Gb as B,H as i,Hb as C,I as j,Ib as D,J as k,Jb as E,K as l,Kb as F,L as m,Lb as G,M as n,Mb as H,N as o,O as p,_b as I,a,ac as K,b,bc as L,c,fc as M,gc as N,hc as O,ic as P,ja as q,jb as A,jc as Q,ka as r,kc as R,lc as S,mc as T,na as s,nc as U,oa as t,oc as V,pa as u,pc as W,qa as v,qc as X,ra as w,rc as Y,sa as x,sc as Z,ta as y,tc as _,ua as z,uc as $,vc as aa,wc as ba,xc as ca,yc as da,zc as ea}from"./chunk-
|
|
1
|
+
import{$b as J,D as e,E as f,F as g,G as h,Gb as B,H as i,Hb as C,I as j,Ib as D,J as k,Jb as E,K as l,Kb as F,L as m,Lb as G,M as n,Mb as H,N as o,O as p,_b as I,a,ac as K,b,bc as L,c,fc as M,gc as N,hc as O,ic as P,ja as q,jb as A,jc as Q,ka as r,kc as R,lc as S,mc as T,na as s,nc as U,oa as t,oc as V,pa as u,pc as W,qa as v,qc as X,ra as w,rc as Y,sa as x,sc as Z,ta as y,tc as _,ua as z,uc as $,vc as aa,wc as ba,xc as ca,yc as da,zc as ea}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import{h as d}from"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{A as AuthMissingError,d as BASE_AUTH_FIELDS,ba as CORSAIR_INTERNAL,G as CloudApiError,B as CorsairKekMissingError,C as DB_METHOD_RISK,P as MS_GRAPH_API_BASE,z as ManagementApiError,r as PermissionRequiredError,a as ProviderDisplayNames,s as ReadonlyForbiddenError,c as ReconnectRequiredError,u as activeMode,W as asRecord,y as assertModeAllows,x as assertReadonlyAllowed,F as callPluginDb,T as collectPluginWebhookMatchers,H as corsairCloud,n as createAccountKeyManager,ca as createCorsair,m as createIntegrationKeyManager,E as decodeDbArgs,aa as decodePubSubData,k as decryptConfig,g as decryptDEK,i as decryptWithDEK,D as encodeDbArgs,j as encryptConfig,f as encryptDEK,h as encryptWithDEK,K as exchangeCodeForTokens,Z as extractMicrosoftGraphValidationToken,$ as firstString,M as formatDocSchemaShape,b as formatProviderDisplayName,e as generateDEK,U as getHeader,L as getOAuthAccessToken,O as googleChannelSubscribe,p as initializeAccountDEK,o as initializeIntegrationDEK,N as introspectPluginForDocs,_ as isMicrosoftGraphValidationHandshake,w as isReadonlyScopeActive,I as logEvent,J as logEventFromContext,R as matchWebhookPlugin,S as matchWebhookPluginAndTenant,Q as msGraphSubscribe,l as reEncryptConfig,X as readBodyRecord,Y as readQueryParam,q as resolveConnectLink,v as runReadonly,t as runWithMode,da as shouldStartTunnel,ea as superviseTunnel,V as toExternalId};
|
package/dist/hub.d.ts
CHANGED
|
@@ -455,6 +455,7 @@ declare function createManagedPricingCredentialCache(): object;
|
|
|
455
455
|
declare function resolveManagedPricingApiKey(ctx: ManagedPricingKeyBuilderContext, input: {
|
|
456
456
|
plugin: string;
|
|
457
457
|
cache: object;
|
|
458
|
+
operation?: string;
|
|
458
459
|
}): Promise<string>;
|
|
459
460
|
|
|
460
461
|
declare function createHubPermissionSession(hub: HubConfig, input: HubPermissionSessionInput): Promise<HubPermissionSessionResult>;
|
package/dist/hub.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{A as z,Aa as L,Ab as ua,B as A,Ba as M,Bb as va,C as B,Ca as N,Cb as wa,Da as O,Db as xa,Ea as P,Eb as ya,Fa as Q,Fb as za,Ga as R,Ha as S,Ia as T,Ja as U,Ka as V,La as W,T as C,Ya as X,Za as Y,_a as Z,b as a,d as b,db as _,e as c,eb as $,f as d,fb as aa,g as e,gb as ba,h as f,hb as ca,i as g,ia as D,ib as da,j as i,k as j,kb as ea,l as k,la as E,lb as fa,m as l,ma as F,mb as ga,n as m,nb as ha,o as n,ob as ia,p as o,pb as ja,q as p,qb as ka,r as q,rb as la,s as r,sb as ma,t as s,tb as na,u as t,ub as oa,v as u,va as G,vb as pa,w as v,wa as H,wb as qa,x as w,xa as I,xb as ra,y as x,ya as J,yb as sa,z as y,za as K,zb as ta}from"./chunk-
|
|
1
|
+
import{A as z,Aa as L,Ab as ua,B as A,Ba as M,Bb as va,C as B,Ca as N,Cb as wa,Da as O,Db as xa,Ea as P,Eb as ya,Fa as Q,Fb as za,Ga as R,Ha as S,Ia as T,Ja as U,Ka as V,La as W,T as C,Ya as X,Za as Y,_a as Z,b as a,d as b,db as _,e as c,eb as $,f as d,fb as aa,g as e,gb as ba,h as f,hb as ca,i as g,ia as D,ib as da,j as i,k as j,kb as ea,l as k,la as E,lb as fa,m as l,ma as F,mb as ga,n as m,nb as ha,o as n,ob as ia,p as o,pb as ja,q as p,qb as ka,r as q,rb as la,s as r,sb as ma,t as s,tb as na,u as t,ub as oa,v as u,va as G,vb as pa,w as v,wa as H,wb as qa,x as w,xa as I,xb as ra,y as x,ya as J,yb as sa,z as y,za as K,zb as ta}from"./chunk-TOBWTWQR.js";import{a as h,b as Aa,c as Ba,d as Ca,e as Da,f as Ea}from"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{m as BROWSER_DELIVERY_TTL_MS,Ba as CORSAIR_TUNNEL_PATH,Aa as CORSAIR_TUNNEL_ZONE,u as DEFAULT_HUB_API_URL,Ca as FRPC_VERSION,w as HubCredentialsMissingError,v as HubNotConfiguredError,V as ManagedOAuthDeliveryError,n as SIGNED_TUNNEL_REPLAY_WINDOW_MS,fa as attachManagedRefreshAuth,p as buildBrowserDeliveryRedirectUrl,s as buildClientBridgeBrowserDeliveryUrl,la as createConnectSessionJti,qa as createConnectTokenJti,D as createHubConnectSession,E as createHubPermissionSession,ka as createHubRouteHandlers,ia as createManagedPricingCredentialCache,wa as createPermissionSessionJti,o as createSignedTokenJti,pa as decodeConnectSessionTokenFromPath,va as decodeConnectTokenFromPath,za as decodePermissionTokenFromPath,Q as deliverConnectCreateLink,U as deliverSignedEnvelope,S as describeDeliveryNetworkError,ua as encodeConnectTokenForPath,O as extractConnectLinkFromDeliveryAck,H as extractProbeFromDeliveryAck,G as extractRunFromDeliveryAck,N as extractSyncFromDeliveryAck,F as formatHubApprovalMessage,a as formatProviderDisplayName,T as formatServerDeliveryError,Da as frpcPlatformKey,ma as getConnectSessionExpiryMs,X as getConnectStatusForTenant,ra as getConnectTokenExpiryMs,z as getHubConfig,ea as getManagedAccessToken,ha as getManagedPricingApiKey,_ as handleHubDeliveryGet,$ as handleHubDeliveryPost,ba as handleHubDeliveryRequest,aa as hubDeliveryToResponse,B as inferHubEnvironmentSlug,i as isLoopbackUrl,M as isServerDeliveryAckSuccessful,Y as listHubProjectConnections,x as normalizeHubConfig,P as parseConnectLinkFromDeliveryBody,b as parseConnectSessionResponse,f as parseConnectStatusResponse,g as parseHubApiErrorBody,Z as parseManagedPricingCredentialsResponse,e as parseOAuthRefreshResponse,d as parsePermissionSessionResponse,c as parseProjectConnectionsResponse,L as parseServerDeliveryAckBody,R as parseSyncFromDeliveryBody,t as prepareClientBridgeDeliveryTransport,W as processManagedOAuthDelivery,C as registerHubWebhookTenantLink,ga as requireHubForManagedPricing,j as resolveDeliveryTransport,Ea as resolveFrpcBinary,y as resolveHubConfigInput,h as resolveHubDeliveryUrl,A as resolveHubOAuthCallbackUrl,ja as resolveManagedPricingApiKey,ca as respondToHubDelivery,da as respondToHubDeliveryFromRequest,q as signBrowserDeliveryToken,na as signConnectSessionToken,sa as signConnectToken,I as signDeliveryEnvelope,xa as signPermissionToken,k as usesBrowserDelivery,l as validateProductionDeliveryUrl,r as verifyBrowserDeliveryToken,oa as verifyConnectSessionToken,ta as verifyConnectToken,J as verifyDeliveryEnvelope,ya as verifyPermissionToken,K as verifySignedTunnelDelivery};
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{$a as j,Gb as z,Lb as J,Ma as q,Mb as Y,Nb as K,Ob as G,P as O,Pb as X,Qb as Q,Rb as V,Sb as nn,Tb as en,U as A,Ua as N,Ub as tn,V as L,Vb as rn,W as E,Wb as on,X as v,Xb as sn,Yb as an,Zb as un,ab as B,bb as D,c as S,cb as U,cc as w,dc as P,ec as T,fc as x,ja as F,jb as Z,ka as M,kc as cn,lc as pn,mc as ln,na as $,nc as dn,oa as _,oc as mn,pc as gn,qa as H,qc as Cn,ua as W,uc as fn,vc as yn,wc as I,xc as kn}from"./chunk-
|
|
1
|
+
import{$a as j,Gb as z,Lb as J,Ma as q,Mb as Y,Nb as K,Ob as G,P as O,Pb as X,Qb as Q,Rb as V,Sb as nn,Tb as en,U as A,Ua as N,Ub as tn,V as L,Vb as rn,W as E,Wb as on,X as v,Xb as sn,Yb as an,Zb as un,ab as B,bb as D,c as S,cb as U,cc as w,dc as P,ec as T,fc as x,ja as F,jb as Z,ka as M,kc as cn,lc as pn,mc as ln,na as $,nc as dn,oa as _,oc as mn,pc as gn,qa as H,qc as Cn,ua as W,uc as fn,vc as yn,wc as I,xc as kn}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";import{z as p}from"zod";function C(e){let t=e[I];if(!t)throw new Error("listOperations / getSchema: invalid corsair instance. Pass the value returned by createCorsair() or corsair.withTenant().");return t.plugins}function y(e,t){let o=P(C(e),t);return typeof o=="string"?o:Array.isArray(o)?o.join(`
|
|
2
2
|
`):Object.values(o).flat().join(`
|
|
3
3
|
`)}function hn(e,t){return T(C(e),t)}function k(e,t){return w(C(e),t)}function h(e,t){let o=C(e),n=t.toLowerCase(),i=n.indexOf(".");if(i===-1)return null;let u=n.slice(0,i),r=n.slice(i+1),s=o.find(c=>c.id===u);if(!s?.endpointSchemas)return null;let a=r;a.startsWith("api.")&&(a=a.slice(4));for(let[c,l]of Object.entries(s.endpointSchemas))if(c.toLowerCase()===a)return l.input??null;return null}function f(e){let t=wn(e);return e.description&&(t=t.describe(e.description)),e.optional&&(t=t.optional()),t}function wn(e){switch(e.kind){case"string":return e.enum&&e.enum.length>0?p.enum(e.enum):p.string();case"number":return p.number();case"boolean":return p.boolean();case"literal":return p.literal(e.value);case"object":{let t={};for(let[o,n]of Object.entries(e.fields))t[o]=f(n);return p.object(t)}case"array":return p.array(f(e.items));case"unknown":return p.unknown()}}function Pn(e,t){let o=t?.tenantId?In(e,t.tenantId):e;return(t?.operations??Tn(y(o,{plugin:t?.plugin,type:"api"}))).map(i=>{let u=k(o,i),s=h(o,i)??(u?.input?f(u.input):p.object({}));return{name:xn(i),operation:i,description:u?.description??i,schema:s,execute:a=>Rn(o,i,a??{})}})}function Tn(e){return e.split(`
|
|
4
4
|
`).map(t=>t.trim()).filter(Boolean)}function xn(e){return e.replace(/[^a-zA-Z0-9_-]/g,"_")}function In(e,t){let o=e.withTenant;return typeof o=="function"?o.call(e,t):e}async function Rn(e,t,o){let n=t.split("."),i=n.pop();if(!i)throw new Error(`Invalid operation path: ${t}`);let u=e;for(let s of n)if(u=u?.[s],u==null)throw new Error(`Unknown operation path: ${t}`);let r=u[i];if(typeof r!="function")throw new Error(`Operation is not callable: ${t}`);return r.call(u,o)}var d=class extends Error{status;code;extra;constructor(t,o,n,i={}){super(n),this.name="CorsairClientError",this.status=t,this.code=o,this.extra=i}};function bn(e){return e.endsWith("/")?e.slice(0,-1):e}async function R(e){let t={};try{t=await e.json()}catch{}let o=typeof t.error=="string"?t.error:"request_failed",n=typeof t.message=="string"?t.message:`Request failed (${e.status})`,{error:i,message:u,...r}=t;return new d(e.status,o,n,r)}function Sn(e){let t=bn(e.baseURL),o=e.fetch??((...r)=>globalThis.fetch(...r));async function n(r,s){let a=s&&Object.keys(s).length?`?${new URLSearchParams(s).toString()}`:"",c=await o(`${t}${r}${a}`,{method:"GET"});if(!c.ok)throw await R(c);return await c.json()}async function i(r,s){let a=await o(`${t}${r}`,{method:"POST",headers:{"content-type":"application/json"},body:JSON.stringify(s)});if(!a.ok)throw await R(a);return await a.json()}let u=encodeURIComponent;return{ok:()=>n("/ok"),tenants:{list:()=>n("/tenants"),create:r=>i("/tenants",r),get:r=>n(`/tenants/${u(r)}`)},plugins:{list:()=>n("/plugins"),get:r=>n(`/plugins/${u(r)}`)},connectionStatus:{get:r=>{let s={};return r?.tenantId&&(s.tenantId=r.tenantId),n("/connection-status",s)}},permissions:{get:r=>"id"in r?n(`/permissions/${u(r.id)}`):i("/permissions/lookup-by-token",{token:r.token})},connect:{createLink:r=>i("/connect/links",r),resolve:r=>n("/connect/resolve",{state:r}),oauthCallback:r=>i("/connect/oauth/callback",r)},connectRequest:{get:r=>{let s={};return r?.tenantId&&(s.tenantId=r.tenantId),n("/connect/request",s)},clear:r=>i("/connect/request/clear",r??{})},call(r,s,a,c){return i(`/${u(a)}/${u(r)}/call/${u(s)}`,{args:c}).then(l=>l.data)}}}var On=Symbol.for("corsair:internal");function An(e,t){let o=e;for(let n of t){if(!o||typeof o!="object")return null;o=o[n]}return typeof o=="function"?o:null}function b(e){return e[On]?.database}async function Ln(e,t){let o=new Date().toISOString(),n=await e.permissions.find_by_token(t);if(!n)return console.error("executePermission: no permission found for token."),{error:"executePermission: no permission found for token."};if(n.status!=="approved")return console.error(`executePermission: permission '${n.id}' is '${n.status}', expected 'approved'.`),{endpoint:n.endpoint,plugin:n.plugin,result:null,error:`executePermission: permission '${n.id}' is '${n.status}', expected 'approved'.`};if(n.expires_at<o){let a=b(e);return a&&await a.db.updateTable("corsair_permissions").set({status:"expired",updated_at:new Date}).where("id","=",n.id).execute(),console.error(`executePermission: permission '${n.id}' has expired.`),{error:`executePermission: permission '${n.id}' has expired.`,endpoint:n.endpoint,plugin:n.plugin,result:null}}let i=n.tenant_id??"default",r=(e.withTenant?e.withTenant(i):e)[n.plugin];if(!r?.api)return console.error(`executePermission: plugin '${n.plugin}' not found or has no API on this corsair instance.`),{error:`executePermission: plugin '${n.plugin}' not found or has no API on this corsair instance.`,plugin:n.plugin,endpoint:n.endpoint,result:null};let s=An(r.api,n.endpoint.split("."));if(!s)return console.error(`executePermission: endpoint '${n.endpoint}' not found in plugin '${n.plugin}'.`),{endpoint:n.endpoint,plugin:n.plugin,result:null,error:`executePermission: endpoint '${n.endpoint}' not found in plugin '${n.plugin}'.`};await e.permissions.set_executing(n.id);try{let a=typeof n.args=="string"?JSON.parse(n.args):n.args,c=await s(a);return await e.permissions.set_completed(n.id),{plugin:n.plugin,endpoint:n.endpoint,result:c}}catch(a){let c=a instanceof Error?a.message:String(a),l=b(e);return l&&await l.db.updateTable("corsair_permissions").set({status:"failed",error:c,updated_at:new Date}).where("id","=",n.id).execute(),{plugin:n.plugin,endpoint:n.endpoint,result:null,error:c}}}export{Z as AuthMissingError,J as CloudApiError,d as CorsairClientError,z as CorsairKekMissingError,B as DEFAULT_BODY_STALL_TIMEOUT_MS,j as DEFAULT_MAX_BODY_BYTES,W as ManagementApiError,M as PermissionRequiredError,$ as ReadonlyForbiddenError,S as ReconnectRequiredError,gn as asRecord,Pn as buildCorsairTools,ln as collectPluginWebhookMatchers,Y as corsairCloud,kn as createCorsair,Sn as createCorsairClient,yn as decodePubSubData,Ln as executePermission,fn as firstString,f as formFieldToZod,x as formatDocSchemaShape,dn as getHeader,h as getInputSchema,hn as getSchema,k as getStructuredSchema,y as listOperations,K as managementHandler,cn as matchWebhookPlugin,pn as matchWebhookPluginAndTenant,N as processCorsair,q as processWebhook,Cn as readBodyRecord,X as registerCorsairRawBodyParser,L as resolveAccountFromWebhookLink,U as resolveBodyStallTimeoutMs,F as resolveConnectLink,D as resolveMaxBodyBytes,v as resolveTenantFromWebhookLink,E as resolveTenantIdFromWebhookLink,H as runReadonly,_ as runWithMode,A as setWebhookTenantLink,O as setupCorsair,on as toAstroHandler,G as toExpressHandler,mn as toExternalId,Q as toFastifyHandler,V as toHonoHandler,nn as toNextJsHandler,en as toNodeHandler,an as toNuxtHandler,rn as toRemixHandler,tn as toSvelteKitHandler,sn as toTanStackHandler,un as toWebHandler};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{Va as a,Wa as b,Xa as c}from"./chunk-
|
|
1
|
+
import{Va as a,Wa as b,Xa as c}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{a as deriveAck,b as pollOnce,c as startConnectLoop};
|
package/dist/oauth.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{$ as f,R as a,S as b,Y as c,Z as d,_ as e,aa as g,ba as h}from"./chunk-
|
|
1
|
+
import{$ as f,R as a,S as b,Y as c,Z as d,_ as e,aa as g,ba as h}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{d as OAuthCallbackError,c as buildOAuthAuthorizeUrl,b as decodeOAuthState,a as encodeOAuthState,e as generateOAuthUrl,f as processOAuthCallback,g as renewSubscriptions,h as startSubscriptionRenewal};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{P as a,Q as b}from"./chunk-
|
|
1
|
+
import{P as a,Q as b}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{b as applySetupCredentials,a as setupCorsair};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{ca as a,da as b,ea as c,fa as d}from"./chunk-
|
|
1
|
+
import{ca as a,da as b,ea as c,fa as d}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{b as buildConnectPluginManifest,a as buildConnectPluginManifestFromContext,d as ensureConnectAccountRows,c as ensureConnectAccountRowsFromContext};
|
package/dist/setup.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{P as a,Q as b}from"./chunk-
|
|
1
|
+
import{P as a,Q as b}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{b as applySetupCredentials,a as setupCorsair};
|
package/dist/tunnel.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
import{Na as f,Oa as g,Pa as h,Qa as i,Ra as j,Sa as k,Ta as l,U as b,Ua as m,V as c,W as d,X as e,s as a}from"./chunk-
|
|
1
|
+
import{Na as f,Oa as g,Pa as h,Qa as i,Ra as j,Sa as k,Ta as l,U as b,Ua as m,V as c,W as d,X as e,s as a}from"./chunk-TOBWTWQR.js";import"./chunk-6IURNA4L.js";import"./chunk-XCTHEKDP.js";import"./chunk-BRUFMVTV.js";import"./chunk-XPXWKPFZ.js";import"./chunk-Z2KT4F2U.js";import"./chunk-SOY77BN4.js";export{l as applyPermissionDecision,f as executeWorkflowRun,h as isAuthCredentialsBrowserDelivery,k as isByoOAuthBrowserDelivery,j as isManagedBrowserDelivery,i as isPermissionBrowserDelivery,m as processCorsair,c as resolveAccountFromWebhookLink,e as resolveTenantFromWebhookLink,d as resolveTenantIdFromWebhookLink,g as runReadonlyProbe,b as setWebhookTenantLink,a as verifyBrowserDeliveryToken};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "corsair",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.148",
|
|
4
4
|
"description": "Open-source integration layer for AI agents and apps. Managed OAuth, webhooks, and one API for 350+ integrations, with credentials that stay in your own database.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./dist/index.js",
|
|
@@ -89,11 +89,11 @@
|
|
|
89
89
|
},
|
|
90
90
|
"optionalDependencies": {
|
|
91
91
|
"@corsair-dev/frpc-darwin-arm64": "0.1.117",
|
|
92
|
-
"@corsair-dev/frpc-
|
|
92
|
+
"@corsair-dev/frpc-win32-arm64": "0.1.117",
|
|
93
|
+
"@corsair-dev/frpc-win32-x64": "0.1.117",
|
|
93
94
|
"@corsair-dev/frpc-linux-arm64": "0.1.117",
|
|
94
95
|
"@corsair-dev/frpc-linux-x64": "0.1.117",
|
|
95
|
-
"@corsair-dev/frpc-
|
|
96
|
-
"@corsair-dev/frpc-win32-x64": "0.1.117"
|
|
96
|
+
"@corsair-dev/frpc-darwin-x64": "0.1.117"
|
|
97
97
|
},
|
|
98
98
|
"devDependencies": {
|
|
99
99
|
"@testing-library/react": "^16.3.2",
|