@hailer/app-sdk 2.14.0 → 2.15.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -46,6 +46,7 @@ The `HailerApi` instance exposes these modules:
46
46
  | `hailer.metrics` | Read usage metrics: `list(options?)`, `get(metricTypes, options?)`. |
47
47
  | `hailer.http` | Authenticated proxy through the parent frame: `fetch`, `upload`, `openWebSocket`. |
48
48
  | `hailer.credential` | Securely store and retrieve personal credentials bound to your app: `create`, `list`, `get`, `update`. Supports `basic`, `apiKey`, and `custom` payloads. |
49
+ | `hailer.action` | Trigger workspace actions and read back their runs: `trigger(target, input?)`, `getRun(runId)`. |
49
50
  | `hailer.public` | Endpoints callable without a Hailer session — talks directly to the public backend (`https://api.hailer.com` by default). Sub-modules: `.app` (public app config), `.form` (public form submit/read), `.insight` (public insight viewing), `.product` (marketplace lookup). The only namespace usable in `outside` mode. |
50
51
  | `hailer.ui` | Sub-modules for commanding the host frame: `.activity`, `.discussion`, `.snackbar`, `.workflow`, `.insight`, `.files`. |
51
52
 
package/lib/app-sdk.js CHANGED
@@ -1,3 +1,3 @@
1
- var oe=Object.create;var X=Object.defineProperty;var ae=Object.getOwnPropertyDescriptor;var ce=Object.getOwnPropertyNames;var ue=Object.getPrototypeOf,le=Object.prototype.hasOwnProperty;var J=(o,e)=>()=>(e||o((e={exports:{}}).exports,e),e.exports);var pe=(o,e,t,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let i of ce(e))!le.call(o,i)&&i!==t&&X(o,i,{get:()=>e[i],enumerable:!(r=ae(e,i))||r.enumerable});return o};var de=(o,e,t)=>(t=o!=null?oe(ue(o)):{},pe(e||!o||!o.__esModule?X(t,"default",{value:o,enumerable:!0}):t,o));var Z=J(d=>{"use strict";var me=d&&d.__awaiter||function(o,e,t,r){function i(s){return s instanceof t?s:new t(function(a){a(s)})}return new(t||(t=Promise))(function(s,a){function u(c){try{p(r.next(c))}catch(K){a(K)}}function m(c){try{p(r.throw(c))}catch(K){a(K)}}function p(c){c.done?s(c.value):i(c.value).then(u,m)}p((r=r.apply(o,e||[])).next())})};Object.defineProperty(d,"__esModule",{value:!0});d.Client=void 0;var $=class{constructor(e,t){this.write=e,this.requests={},this.id=0,this.mtu=65535,t&&t.mtu&&(this.mtu=t.mtu)}destroy(){this.requests=null,this.write=null}messageReceived(e){let t=!!(e.err||e.ack||e.fin),r=e.ack||e.err||e.sig||e.fin,i=this.requests[r],s;if(i&&typeof i.cb=="function"){let a;e.fin?i.cb.call(i.context,null,null,!0):i.canceled?console.log("This request is canceled. Not calling the callback."):(a=e.err?e.data:null,s=i.cb.call(i.context,a,e.data,t))}return t&&delete this.requests[r],s}requestAsync(e,t){return me(this,void 0,void 0,function*(){return new Promise((r,i)=>{this.request(e,t,(s,a)=>{if(s)return i(a);r(a)})})})}request(e,t,r){this.id++;let i={op:e};return Array.isArray(t)&&(i.args=t),r&&(i.id=this.id,this.requests[i.id]={cb:r,context:{id:i.id,cancel:()=>{setTimeout((s=>()=>{this.requests[s]&&console.log("rpc-client.js: timeout, the request has not been removed while it was canceled",s,this.requests[s])})(i.id),1500),this.requests[i.id].canceled=!0,this.write({end:i.id})},emit:s=>this.write({sig:i.id,data:s})}}),this.write(i),i.id||null}send(e,t){this.write({push:e,data:t})}end(e){this.write({end:e})}};d.Client=$});var ee=J(y=>{"use strict";Object.defineProperty(y,"__esModule",{value:!0});y.Server=void 0;var h=console.log,G=class{constructor(e){this.modules={},this.methods={},this.requests={},this.clientIdCounter=0,this.requestId=0,this.invokeId=0,e&&this.insertMethods(e)}destroy(){for(let e in this.requests){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end();delete this.requests[e]}}insertMethods(e){this.addMethods("",e)}addMethods(e,t){let r=e?e+".":"";for(let i in t)if(i!=="_"){if(i.substring(0,1)!=="_"&&t["_"+i])if(typeof t[i]=="function"){let s=t["_"+i].name||i;t["_"+i].fullname=r+s;try{this.modules[r+s]=t["_"+i],this.methods[r+s]=t[i]}catch(a){console.log("Kaboom! ",a)}}else typeof t[i]=="object"&&this.addMethods(r+i,t[i])}}listMethods(e,t,r){let i={};function s(u,m){let p={};for(let c in u)m[c]||(p[c]=u[c]);return p}let a={fullname:!0};for(let u in this.modules)i[u]=s(this.modules[u],a);r(null,i)}clientOffline(e){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t]}closeAll(){for(let e in this.requests)for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t]}parse(e,t,r,i){if(typeof i=="number")try{if(e.push){this.requests[i]&&this.requests[i][e.push]&&this.invokeRaw(e,t,this.requests[i][e.push].context,i);return}if(e.sig){this.requests[i]&&this.requests[i][e.sig]&&this.invokeRaw(e,t,this.requests[i][e.sig].context,i);return}if(e.end){let s=e.end;if(this.requests[i]&&this.requests[i][s]){typeof this.requests[i][s].end=="function"&&this.requests[i][s].end(),t({fin:s}),delete this.requests[i][s];return}if(!this.requests[i][s])return;typeof this.requests[i][s].end=="function"&&this.requests[s].end();return}if(e.op==="methods"){this.listMethods(e.args,r,function(s,a){t({ack:e.id,data:a})});return}if(typeof this.methods[e.op]>"u"){t({err:e.id,data:{code:300,msg:"No method found: "+e.op}});return}this.invokeRaw(e,t,r,i)}catch(s){h("Dynamic RPC failed to execute ",e.op,s,s.stack);try{console.log("RPC caught error",s.stack),t({ack:e.id,err:e.id,data:"caught error in "+e.op+": "+s.toString(),debug:s.stack})}catch(a){t({err:e.id,data:"rpc",errmsg:a.toString()})}}}emit(e,t){for(let r in this.requests)if(this.requests[r]){for(let i in this.requests[r])if(this.requests[r][i].op===e){let{send:s}=this.requests[r][i];s({sig:i,data:t})}}}invokeRaw(e,t,r,i){if(++this.requestId,!this.requests[i])return console.log("Session not opened for client. Use Server.open() first");if(e.push){let s=this.requests[i][e.push];if(e.data===null){console.log("msg.data is null:",e);return}s.data(e.data);return}if(e.sig){let s=this.requests[i][e.sig];try{this.methods[s.op].call(this.requests[i][e.sig],e.data,{send:a=>{typeof s.end=="function"&&s.end(),this.requests[i][e.sig]&&delete this.requests[i][e.sig],t({ack:e.sig,data:a})},emit:a=>(this.requests[i][e.sig]||typeof s.end=="function"&&s.end(),t({sig:e.sig,data:a})),error:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.sig],t({err:e.sig,data:a})},close:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.sig],t({fin:e.sig})}},r)}catch(a){console.log("Calling the method in RPC failed:",e.op,e.args,a.stack),delete this.requests[i][e.sig],t({err:e.sig,data:{msg:"rpc failed during execution of "+e.op,code:578}})}return}if(typeof e.id>"u"){let s={};this.methods[e.op].call(s,{args:e.args},{send:()=>{h("Trying to send response to event ("+e.op+"). Dropping.")},emit:()=>{h("Trying to emit response to event ("+e.op+"). Dropping.")},error:()=>{h("Trying to respond with error to event ("+e.op+"). Dropping.")},close:()=>{h("Trying to close event ("+e.op+"). Dropping.")}},r)}else{let s={id:e.id,op:e.op,args:e.args,context:r,end:null,send:t};this.requests[i]||(this.requests[i]={}),this.requests[i][e.id]&&(console.log("Serious warning. There is already a request by that id, we'll kill it off! This session is likely not clean. clientId:",i,"msg",e,"stack trace:",new Error().stack),typeof this.requests[i][e.id].end=="function"&&this.requests[i][e.id].end(),delete this.requests[i][e.id],console.log("Removed old request by same id from same client...")),this.requests[i][e.id]=s;try{this.methods[e.op].call(s,{args:e.args},{send:a=>{typeof s.end=="function"&&s.end(),this.requests[i][e.id]&&delete this.requests[i][e.id],t({ack:e.id,data:a})},emit:a=>(this.requests[i][e.id]||typeof s.end=="function"&&s.end(),t({sig:e.id,data:a})),error:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.id],t({err:e.id,data:a})},close:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.id],t({fin:e.id})}},r)}catch(a){console.log("Calling the method in RPC failed:",e.op,e.args,a.stack),delete this.requests[i][e.id],t({err:e.id,data:{msg:"rpc failed during execution of "+e.op,code:578}})}}}close(e){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t];delete this.requests[e]}open(){let e=++this.clientIdCounter;return this.requests[e]={},e}};y.Server=G});var re=J(l=>{"use strict";var he=l&&l.__createBinding||(Object.create?(function(o,e,t,r){r===void 0&&(r=t),Object.defineProperty(o,r,{enumerable:!0,get:function(){return e[t]}})}):(function(o,e,t,r){r===void 0&&(r=t),o[r]=e[t]})),te=l&&l.__exportStar||function(o,e){for(var t in o)t!=="default"&&!Object.prototype.hasOwnProperty.call(e,t)&&he(e,o,t)};Object.defineProperty(l,"__esModule",{value:!0});te(Z(),l);te(ee(),l)});var se=de(re(),1);var z=class extends Error{constructor(e,t){super(e),this.name=this.constructor.name,this.msg=e,this.code=t,Error.captureStackTrace?.(this,this.constructor)}},n=class extends z{constructor(e){super(e.msg,e.code),this.details=e.details,this.debug=e.debug}toString(){return console.log("Going to log an error... ;-D"),`${super.toString()}
2
- Field: ${this.details}, ${this.debug}`}};var f=class{constructor(e){this.client=e}async get(e){try{return await this.client.requestAsync("user.get",[e])}catch(t){throw new n(t)}}async current(){try{return await this.client.requestAsync("user.current",[])}catch(e){throw new n(e)}}async list(){try{return await this.client.requestAsync("user.list",[])}catch(e){throw new n(e)}}};var b=class{constructor(e){this.client=e}async list(e,t){try{return await this.client.requestAsync("activity.kanban.list",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async load(e){try{return await this.client.requestAsync("activity.kanban.load",[e])}catch(t){throw new n(t)}}async updatePriority(e,t){try{return await this.client.requestAsync("activity.kanban.updatePriority",[{activityId:e,priority:t}])}catch(r){throw new n(r)}}};var w=class{constructor(e){this.client=e}async pass(e,t){try{return await this.client.requestAsync("activity.ball.pass",[e,t])}catch(r){throw new n(r)}}async take(e){try{return await this.client.requestAsync("activity.ball.take",[e])}catch(t){throw new n(t)}}async list(e){if(Array.isArray(e)&&e.length===0)return[];try{return await this.client.requestAsync("activity.ball.list",[e])}catch(t){throw new n(t)}}};var A=class{constructor(e){this.client=e;this.kanban=new b(e),this.ball=new w(e)}async list(e,t,r){try{return await this.client.requestAsync("activity.list",[e,t,r])}catch(i){throw new n(i)}}async get(e){try{return await this.client.requestAsync("activity.get",[e])}catch(t){throw new n(t)}}async create(e,t,r){try{return await this.client.requestAsync("activity.create",[e,t,...r?[r]:[]])}catch(i){throw new n(i)}}async update(e,t){try{return await this.client.requestAsync("activity.update",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("activity.remove",[e])}catch(t){throw new n(t)}}async print(e,t){try{return await this.client.requestAsync("activity.print",[e,...t?[t]:[]])}catch(r){throw new n(r)}}};var P=class{constructor(e){this.client=e;this.product={publishTemplate:this.publishTemplate.bind(this),isProductInstalled:this.isProductInstalled.bind(this),get:this.get.bind(this),install:this.install.bind(this),getManifest:this.getManifest.bind(this)}}async current(){try{return await this.client.requestAsync("workspace.current",[])}catch(e){throw new n(e)}}async list(){try{return await this.client.requestAsync("workspace.list",[])}catch(e){throw new n(e)}}async create(e){try{return await this.client.requestAsync("workspace.create",[e])}catch(t){throw new n(t)}}async publishTemplate(e){try{return await this.client.requestAsync("workspace.product.publishTemplate",[e])}catch(t){throw new n(t)}}async isProductInstalled(e,t){try{return await this.client.requestAsync("workspace.product.isProductInstalled",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("workspace.product.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("workspace.product.install",[e,t])}catch(r){throw new n(r)}}async getManifest(e){try{return await this.client.requestAsync("workspace.product.getManifest",[e])}catch(t){throw new n(t)}}};var v=class{constructor(e){this.client=e}async list(){try{return await this.client.requestAsync("team.list",[])}catch(e){throw new n(e)}}};var ge=300,ye={workspace:o=>`network_${o}`,team:o=>`team_${o}`,user:o=>`user_${o}`},k=class{constructor(e){this.client=e;this.readers=ye}async get(e){try{return await this.client.requestAsync("file.get",[e])}catch(t){throw new n(t)}}async upload(e,t,r){if(r?.isPublic&&r?.scoped)throw new n({code:400,msg:"A file cannot be both public and scoped",debug:void 0});try{let i=await this.toBase64(e);if(!r?.scoped)return await this.client.requestAsync("file.upload",[i,t,!!r?.isPublic]);let s=await this.client.requestAsync("file.upload",[i,t,!1,!0]);return await this.assertScoped(s),s}catch(i){throw i instanceof n?i:new n(i)}}async addTags(e,t){try{return await this.client.requestAsync("file.addTags",[e,t])}catch(r){throw new n(r)}}async removeTags(e,t){try{return await this.client.requestAsync("file.removeTags",[e,t])}catch(r){throw new n(r)}}async getScope(e){try{return await this.client.requestAsync("file.getScope",[e])}catch(t){throw new n(t)}}async setReaders(e,t){try{return await this.client.requestAsync("file.setReaders",[e,t])}catch(r){throw new n(r)}}async list(e){try{return await this.client.requestAsync("file.list",e?[e]:[])}catch(t){throw new n(t)}}async setOwner(e,t){try{return await this.client.requestAsync("file.setOwner",[e,t])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("file.remove",[e])}catch(t){throw new n(t)}}async assertScoped(e){let t;try{t=await this.client.requestAsync("file.getScope",[e])}catch(r){if(r?.code!==ge)throw new n(r)}if(!t?.workspaceId)throw new n({code:501,msg:`File ${e} was uploaded but not scoped: this Hailer version does not support scoped files`,debug:void 0})}toBase64(e){return new Promise((t,r)=>{let i=new FileReader;i.readAsDataURL(e),i.onload=()=>t(i.result??""),i.onerror=r})}};var x=class{constructor(e){this.client=e}async open(e,t){await this.client.requestAsync("ui.activity.open",[e,...t?[t]:[]])}async create(e,t){return this.client.requestAsync("ui.activity.create",[e,...t?[t]:[]])}async editMultiple(e){return this.client.requestAsync("ui.activity.editMultiple",[e])}};var q=class{constructor(e){this.client=e}async open(e,t){await this.client.requestAsync("ui.discussion.open",[e,...t?[t]:[]])}};var R=class{constructor(e){this.client=e}async open(e,t,r){await this.client.requestAsync("ui.snackbar.open",[e,t,r])}};var I=class{constructor(e){this.client=e}async uploadFile(e,t,r){return this.client.requestAsync("ui.file.upload",[await this.toBase64(e),t,!!r?.isPublic])}toBase64(e){return new Promise((t,r)=>{let i=new FileReader;i.readAsDataURL(e),i.onload=()=>t(i.result??""),i.onerror=r})}};var C=class{constructor(e){this.client=e;this.function={edit:async(e,t)=>{await this.client.requestAsync("ui.workflow.function.edit",[e,t])}}}};var T=class{constructor(e){this.client=e;this.activity=new x(e),this.discussion=new q(e),this.snackbar=new R(e),this.workflow=new C(e),this.insight={create:async t=>{await e.requestAsync("ui.insight.create",[t])},edit:async t=>{await e.requestAsync("ui.insight.edit",[t])},delete:async t=>{await e.requestAsync("ui.insight.delete",[t])},permission:async t=>{await e.requestAsync("ui.insight.permission",[t])}},this.files=new I(e)}};var ie=["https://app.hailer.com","https://next.hailer.com","https://testapp.hailer.biz","https://app.hailer.biz","https://app.hailer.local.gd","https://app.k8s.hailer.com","https://next.k8s.hailer.com","https://localhost:9443"],g="https://api.hailer.com",ne={"https://app.hailer.com":g,"https://next.hailer.com":g,"https://app.hailer.biz":"https://api.hailer.biz","https://testapp.hailer.biz":"https://testapi.hailer.biz","https://app.hailer.local.gd":"https://api.hailer.local.gd","https://app.k8s.hailer.com":"https://api.k8s.hailer.com","https://next.k8s.hailer.com":"https://api.k8s.hailer.com","https://localhost:9443":"http://localhost:1337"};var S=class{constructor(e){this.options=e}async config(){let e="manifest.json",t=window.location.origin+window.location.pathname,r=t+e;t.endsWith("/index.html")&&(r=t.slice(0,-10)+e);let i=await(await fetch(r)).text(),a=JSON.parse(i).appId;return(await fetch(`${this.options.publicBackendUrl}/api/v3/app/public`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([a])})).json()}};var U=class{constructor(e){this.options=e}async data(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v2/forms/process/get`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}async submit(e,t){let r=await fetch(`${this.options.publicBackendUrl}/api/v2/forms/activity/create`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e,t])});if(!r.ok)throw new n(await r.json());return r.json()}};var O=class{constructor(e){this.options=e}async data(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v3/insight/public`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}async dataAsObject(e){let r=(await this.data(e)).data,i=[];return r.rows.forEach(s=>{let a={};r.headers.forEach((u,m)=>{a[u]=s[m]}),i.push(a)}),i}};var L=class{constructor(e){this.options=e}async list(e,t){let r=await fetch(`${this.options.publicBackendUrl}/api/v3/product/list`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e,t])});if(!r.ok)throw new n(await r.json());return r.json()}async get(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v3/product/get`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}};var D=class{constructor(e){this.insight=new O(e),this.form=new U(e),this.app=new S(e),this.product=new L(e)}};var _=class{constructor(e){this.client=e}async list(){try{return await this.client.requestAsync("workflow.list",[])}catch(e){throw console.error(e.msg,e),new n(e)}}async get(e){try{return await this.client.requestAsync("workflow.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("workflow.install",[e,t])}catch(r){throw new n(r)}}};var W=class{constructor(e){this.client=e;this.config={update:async(e,t)=>{try{return await this.client.requestAsync("app.config.update",[e,...t?[t]:[]])}catch(r){throw new n(r)}}};this.product={isProductInstalled:this.isProductInstalled.bind(this),get:this.get.bind(this),install:this.install.bind(this),getInstalledVersion:this.getInstalledVersion.bind(this),getManifest:this.getManifest.bind(this)}}async isProductInstalled(e,t){try{return await this.client.requestAsync("app.product.isProductInstalled",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("app.product.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("app.product.install",[e,t])}catch(r){throw new n(r)}}async getInstalledVersion(e){try{return await this.client.requestAsync("app.product.getInstalledVersion",[e])}catch(t){throw new n(t)}}async getManifest(e){try{return await this.client.requestAsync("app.product.getManifest",[e])}catch(t){throw new n(t)}}};var E=class{constructor(e){this.client=e}async data(e,t){try{return await this.client.requestAsync("insight.data",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async list(){try{return await this.client.requestAsync("insight.list",[])}catch(e){throw new n(e)}}async update(e,t){try{return await this.client.requestAsync("insight.update",[e,t])}catch(r){throw new n(r)}}async query(e,t,r){try{return await this.client.requestAsync("insight.query",[e,{sources:t,query:r}])}catch(i){throw new n(i)}}};var F=class{constructor(e){this.client=e;this.map=async({workspaceId:e}={})=>{try{return await this.client.requestAsync("permission.map",e?[{workspaceId:e}]:[])}catch(t){throw console.log("Failed to read permissions from Hailer, error:",t),new n(t)}}}};var M=class{constructor(e){this.client=e}async list(e,t){try{return await this.client.requestAsync("product.list",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("product.get",[e])}catch(t){throw new n(t)}}async create(e){try{return await this.client.requestAsync("product.create",[e])}catch(t){throw new n(t)}}async update(e,t){try{return await this.client.requestAsync("product.update",[e,t])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("product.remove",[e])}catch(t){throw new n(t)}}async setPublic(e,t){try{return await this.client.requestAsync("product.setPublic",[e,t])}catch(r){throw new n(r)}}};var B=class{constructor(e){this.client=e}async createPricing(e){try{return await this.client.requestAsync("payment.createPricing",[e])}catch(t){throw new n(t)}}async updatePricing(e){try{return await this.client.requestAsync("payment.updatePricing",[e])}catch(t){throw new n(t)}}async getPricing(e){try{return await this.client.requestAsync("payment.getPricing",[{productId:e}])}catch(t){throw new n(t)}}async createPurchase(e){try{return await this.client.requestAsync("payment.createPurchase",[e])}catch(t){throw new n(t)}}async getPurchases(e){try{return await this.client.requestAsync("payment.getPurchases",[{workspaceId:e}])||[]}catch(t){throw new n(t)}}async calculateStripeTax(e){try{return await this.client.requestAsync("payment.calculateStripeTax",[e])}catch(t){throw new n(t)}}};var H=class{constructor(e){this.client=e;this.referral={listCodes:async e=>{try{return await this.client.requestAsync("admin.referral.listCodes",[e?.filter||null,e?.options||null])}catch(t){throw new n(t)}},listEvents:async e=>{try{return await this.client.requestAsync("admin.referral.listEvents",[e?.filter||null,e?.options||null])}catch(t){throw new n(t)}},updateCode:async(e,t)=>{try{return await this.client.requestAsync("admin.referral.updateCode",[{codeId:e,...t}])}catch(r){throw new n(r)}}}}async listWorkspaces(e){try{return await this.client.requestAsync("admin.workspace.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async getWorkspace(e){try{return await this.client.requestAsync("admin.workspace.get",[e])}catch(t){throw new n(t)}}async createStripeSession(e){try{return await this.client.requestAsync("admin.workspace.createStripeSession",[e])}catch(t){throw new n(t)}}async createInvoiceIntegration(e){try{return await this.client.requestAsync("admin.workspace.createInvoiceIntegration",[e])}catch(t){throw new n(t)}}async updateWorkspaceSubscription(e){try{return await this.client.requestAsync("admin.workspace.updateSubscription",[e])}catch(t){throw new n(t)}}async updatePurchasePrice(e){try{return await this.client.requestAsync("admin.purchase.updatePrice",[e])}catch(t){throw new n(t)}}async listWorkspaceUsers(e){try{return await this.client.requestAsync("admin.workspace.listUsers",[e.workspaceId,e.filter,e.options])}catch(t){throw new n(t)}}async updateUser(e){try{return await this.client.requestAsync("admin.user.update",[e.userId,e.updates])}catch(t){throw new n(t)}}async updateTokenBalance(e){try{return await this.client.requestAsync("admin.workspace.updateTokenBalance",[e])}catch(t){throw new n(t)}}async updateWorkspaceOverrides(e){try{return await this.client.requestAsync("admin.workspace.updateOverrides",[e])}catch(t){throw new n(t)}}async updateWorkspaceMarketplaceSettings(e){try{return await this.client.requestAsync("admin.workspace.updateMarketplaceSettings",[e])}catch(t){throw new n(t)}}async listTokenTransactions(e){try{return await this.client.requestAsync("admin.tokenTransaction.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async listInvoices(e){try{return await this.client.requestAsync("admin.invoice.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async updateInvoiceHandled(e){try{return await this.client.requestAsync("admin.invoice.updateHandled",[e.purchaseIds,e.handled])}catch(t){throw new n(t)}}async setSubscriptionActivityId(e,t){try{return await this.client.requestAsync("admin.invoice.setSubscriptionActivityId",[e,t])}catch(r){throw new n(r)}}async listMonthlyRevenue(e){try{return await this.client.requestAsync("admin.revenue.list",[e.month,e.year,e.filter,e.options])}catch(t){throw new n(t)}}async getDashboardStatistics(e){try{return await this.client.requestAsync("admin.dashboard.statistics",[e])}catch(t){throw new n(t)}}async getDashboardTrends(e,t){try{return await this.client.requestAsync("admin.dashboard.trends",[e,t])}catch(r){throw new n(r)}}};var N=class{constructor(e){this.client=e;this.admin={workspacesList:async e=>{try{return await this.client.requestAsync("metrics.workspaceSearch",[e])}catch(t){throw new n(t)}},usersList:async e=>{try{return await this.client.requestAsync("metrics.userList",[e])}catch(t){throw new n(t)}}}}async list(){try{return await this.client.requestAsync("metrics.list",[])}catch(e){throw new n(e)}}async get(e,t){try{let r=Array.isArray(e)?e:[e];return await this.client.requestAsync("metrics.get",[r,t])}catch(r){throw new n(r)}}};var Q=class{constructor(e,t){this.client=e;this.onopen=null;this.onmessage=null;this.onclose=null;this.onerror=null;this.readyState=WebSocket.CONNECTING;this.connectionId=null;this.client.request("http.ws.open",[t],(r,i)=>{if(r){this.readyState=WebSocket.CLOSED,this.onerror?.({error:r});return}if(i)switch(i.connectionId&&!this.connectionId&&(this.connectionId=i.connectionId),i.event){case"open":this.readyState=WebSocket.OPEN,this.onopen?.({});break;case"message":this.onmessage?.({data:i.data??""});break;case"close":this.readyState=WebSocket.CLOSED,this.onclose?.({code:i.code,reason:i.reason});break;case"error":this.onerror?.({error:i.data});break}})}send(e){if(this.readyState!==WebSocket.OPEN||!this.connectionId)throw new Error("WebSocket is not open");this.client.requestAsync("http.ws.send",[this.connectionId,e]).catch(t=>{this.onerror?.({error:t})})}close(e,t){this.connectionId&&this.client.requestAsync("http.ws.close",[this.connectionId,e,t]).catch(r=>{this.onerror?.({error:r})}),this.readyState=WebSocket.CLOSING}},j=class{constructor(e){this.client=e}async fetch(e,t){return this.client.requestAsync("http.fetch",[e,t]).catch(r=>{throw r})}async upload(e,t){return this.client.requestAsync("http.upload",[e,t]).catch(r=>{throw r})}openWebSocket(e){return new Q(this.client,e)}};var V=class{constructor(e){this.client=e}async create(e,t,r){try{return await this.client.requestAsync("credential.create",[{name:e,type:t,secret:r}])}catch(i){throw new n(i)}}async list(){try{return await this.client.requestAsync("credential.list",[])}catch(e){throw new n(e)}}async get(e){try{return await this.client.requestAsync("credential.get",[e])}catch(t){throw new n(t)}}async update(e,t){try{return await this.client.requestAsync("credential.update",[e,t])}catch(r){throw new n(r)}}};var Y=class{constructor(e={}){this.options=e;this.outside=null;let t=e.allowedUrls??ie;this.client=new se.Client(i=>{this.hostUrl&&parent.postMessage(JSON.stringify(i),this.hostUrl)}),this.user=new f(this.client),this.app=new W(this.client),this.activity=new A(this.client),this.insight=new E(this.client),this.workspace=new P(this.client),this.team=new v(this.client),this.file=new k(this.client),this.workflow=new _(this.client),this.permission=new F(this.client),this.public=new D(this.options),this.ui=new T(this.client),this.product=new M(this.client),this.payment=new B(this.client),this.admin=new H(this.client),this.metrics=new N(this.client),this.http=new j(this.client),this.credential=new V(this.client);let r=JSON.stringify({op:"register",args:[{appApiVersion:"2"}]});window.location===window.parent.location?(this.options.publicBackendUrl||(this.options.publicBackendUrl=g),this.public.app.config().then(i=>{this.outside=!0,this.options.outside?.(i)}).catch(i=>{this.options.error?.(i),console.error("Failed to get app configuration in Public App.",i)})):(t.forEach(i=>parent.postMessage(r,i)),this.timer=setTimeout(()=>{this.outside=!0,this.options.outside?.()},100)),this.createEventListener()}createEventListener(){window.addEventListener("message",async e=>{let t=e.data;try{let r=JSON.parse(t);if(r.op==="register"){if(this.appId){console.error("App Id is already set...! Are you using hot-reload?");return}clearTimeout(this.timer),this.appId=r.data.appId,this.workspaceId=r.data.workspaceId,this.hostUrl=e.origin,this.options.publicBackendUrl||(this.options.publicBackendUrl=ne[this.hostUrl]||g),this.client.request("ui.settings",[],(i,s,a)=>{if(i){console.log("ui.settings error:",i,s);return}this.options.settings?.(s)}),this.client.request("config",[],(i,s,a)=>{if(i){console.log("config error:",i,s);return}this.config=s,this.options.config?.(s)}),this.client.request("signal",[],(i,s,a)=>{if(i){console.log("signal error:",i,s);return}s&&(this.options.signals?.(s),typeof s.name=="string"&&s.name.startsWith("workspace.role.")&&this.options.permissions?.())}),this.outside=!1,this.options.permissions?.(),this.options.connected?.();return}if(!this.appId)return;this.client.messageReceived(r)}catch{console.log("Dropped invalid JSON message")}})}info(){return{hostUrl:this.hostUrl,config:this.config,outside:this.outside,workspaceId:this.workspaceId}}};export{k as FileApi,Y as HailerApi,n as HailerError,N as MetricsApi,ye as fileReaders};
1
+ var ae=Object.create;var Z=Object.defineProperty;var ce=Object.getOwnPropertyDescriptor;var ue=Object.getOwnPropertyNames;var le=Object.getPrototypeOf,pe=Object.prototype.hasOwnProperty;var $=(o,e)=>()=>(e||o((e={exports:{}}).exports,e),e.exports);var de=(o,e,t,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let i of ue(e))!pe.call(o,i)&&i!==t&&Z(o,i,{get:()=>e[i],enumerable:!(r=ce(e,i))||r.enumerable});return o};var me=(o,e,t)=>(t=o!=null?ae(le(o)):{},de(e||!o||!o.__esModule?Z(t,"default",{value:o,enumerable:!0}):t,o));var ee=$(d=>{"use strict";var he=d&&d.__awaiter||function(o,e,t,r){function i(s){return s instanceof t?s:new t(function(a){a(s)})}return new(t||(t=Promise))(function(s,a){function u(c){try{p(r.next(c))}catch(J){a(J)}}function m(c){try{p(r.throw(c))}catch(J){a(J)}}function p(c){c.done?s(c.value):i(c.value).then(u,m)}p((r=r.apply(o,e||[])).next())})};Object.defineProperty(d,"__esModule",{value:!0});d.Client=void 0;var G=class{constructor(e,t){this.write=e,this.requests={},this.id=0,this.mtu=65535,t&&t.mtu&&(this.mtu=t.mtu)}destroy(){this.requests=null,this.write=null}messageReceived(e){let t=!!(e.err||e.ack||e.fin),r=e.ack||e.err||e.sig||e.fin,i=this.requests[r],s;if(i&&typeof i.cb=="function"){let a;e.fin?i.cb.call(i.context,null,null,!0):i.canceled?console.log("This request is canceled. Not calling the callback."):(a=e.err?e.data:null,s=i.cb.call(i.context,a,e.data,t))}return t&&delete this.requests[r],s}requestAsync(e,t){return he(this,void 0,void 0,function*(){return new Promise((r,i)=>{this.request(e,t,(s,a)=>{if(s)return i(a);r(a)})})})}request(e,t,r){this.id++;let i={op:e};return Array.isArray(t)&&(i.args=t),r&&(i.id=this.id,this.requests[i.id]={cb:r,context:{id:i.id,cancel:()=>{setTimeout((s=>()=>{this.requests[s]&&console.log("rpc-client.js: timeout, the request has not been removed while it was canceled",s,this.requests[s])})(i.id),1500),this.requests[i.id].canceled=!0,this.write({end:i.id})},emit:s=>this.write({sig:i.id,data:s})}}),this.write(i),i.id||null}send(e,t){this.write({push:e,data:t})}end(e){this.write({end:e})}};d.Client=G});var te=$(y=>{"use strict";Object.defineProperty(y,"__esModule",{value:!0});y.Server=void 0;var h=console.log,z=class{constructor(e){this.modules={},this.methods={},this.requests={},this.clientIdCounter=0,this.requestId=0,this.invokeId=0,e&&this.insertMethods(e)}destroy(){for(let e in this.requests){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end();delete this.requests[e]}}insertMethods(e){this.addMethods("",e)}addMethods(e,t){let r=e?e+".":"";for(let i in t)if(i!=="_"){if(i.substring(0,1)!=="_"&&t["_"+i])if(typeof t[i]=="function"){let s=t["_"+i].name||i;t["_"+i].fullname=r+s;try{this.modules[r+s]=t["_"+i],this.methods[r+s]=t[i]}catch(a){console.log("Kaboom! ",a)}}else typeof t[i]=="object"&&this.addMethods(r+i,t[i])}}listMethods(e,t,r){let i={};function s(u,m){let p={};for(let c in u)m[c]||(p[c]=u[c]);return p}let a={fullname:!0};for(let u in this.modules)i[u]=s(this.modules[u],a);r(null,i)}clientOffline(e){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t]}closeAll(){for(let e in this.requests)for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t]}parse(e,t,r,i){if(typeof i=="number")try{if(e.push){this.requests[i]&&this.requests[i][e.push]&&this.invokeRaw(e,t,this.requests[i][e.push].context,i);return}if(e.sig){this.requests[i]&&this.requests[i][e.sig]&&this.invokeRaw(e,t,this.requests[i][e.sig].context,i);return}if(e.end){let s=e.end;if(this.requests[i]&&this.requests[i][s]){typeof this.requests[i][s].end=="function"&&this.requests[i][s].end(),t({fin:s}),delete this.requests[i][s];return}if(!this.requests[i][s])return;typeof this.requests[i][s].end=="function"&&this.requests[s].end();return}if(e.op==="methods"){this.listMethods(e.args,r,function(s,a){t({ack:e.id,data:a})});return}if(typeof this.methods[e.op]>"u"){t({err:e.id,data:{code:300,msg:"No method found: "+e.op}});return}this.invokeRaw(e,t,r,i)}catch(s){h("Dynamic RPC failed to execute ",e.op,s,s.stack);try{console.log("RPC caught error",s.stack),t({ack:e.id,err:e.id,data:"caught error in "+e.op+": "+s.toString(),debug:s.stack})}catch(a){t({err:e.id,data:"rpc",errmsg:a.toString()})}}}emit(e,t){for(let r in this.requests)if(this.requests[r]){for(let i in this.requests[r])if(this.requests[r][i].op===e){let{send:s}=this.requests[r][i];s({sig:i,data:t})}}}invokeRaw(e,t,r,i){if(++this.requestId,!this.requests[i])return console.log("Session not opened for client. Use Server.open() first");if(e.push){let s=this.requests[i][e.push];if(e.data===null){console.log("msg.data is null:",e);return}s.data(e.data);return}if(e.sig){let s=this.requests[i][e.sig];try{this.methods[s.op].call(this.requests[i][e.sig],e.data,{send:a=>{typeof s.end=="function"&&s.end(),this.requests[i][e.sig]&&delete this.requests[i][e.sig],t({ack:e.sig,data:a})},emit:a=>(this.requests[i][e.sig]||typeof s.end=="function"&&s.end(),t({sig:e.sig,data:a})),error:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.sig],t({err:e.sig,data:a})},close:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.sig],t({fin:e.sig})}},r)}catch(a){console.log("Calling the method in RPC failed:",e.op,e.args,a.stack),delete this.requests[i][e.sig],t({err:e.sig,data:{msg:"rpc failed during execution of "+e.op,code:578}})}return}if(typeof e.id>"u"){let s={};this.methods[e.op].call(s,{args:e.args},{send:()=>{h("Trying to send response to event ("+e.op+"). Dropping.")},emit:()=>{h("Trying to emit response to event ("+e.op+"). Dropping.")},error:()=>{h("Trying to respond with error to event ("+e.op+"). Dropping.")},close:()=>{h("Trying to close event ("+e.op+"). Dropping.")}},r)}else{let s={id:e.id,op:e.op,args:e.args,context:r,end:null,send:t};this.requests[i]||(this.requests[i]={}),this.requests[i][e.id]&&(console.log("Serious warning. There is already a request by that id, we'll kill it off! This session is likely not clean. clientId:",i,"msg",e,"stack trace:",new Error().stack),typeof this.requests[i][e.id].end=="function"&&this.requests[i][e.id].end(),delete this.requests[i][e.id],console.log("Removed old request by same id from same client...")),this.requests[i][e.id]=s;try{this.methods[e.op].call(s,{args:e.args},{send:a=>{typeof s.end=="function"&&s.end(),this.requests[i][e.id]&&delete this.requests[i][e.id],t({ack:e.id,data:a})},emit:a=>(this.requests[i][e.id]||typeof s.end=="function"&&s.end(),t({sig:e.id,data:a})),error:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.id],t({err:e.id,data:a})},close:a=>{typeof s.end=="function"&&s.end(),delete this.requests[i][e.id],t({fin:e.id})}},r)}catch(a){console.log("Calling the method in RPC failed:",e.op,e.args,a.stack),delete this.requests[i][e.id],t({err:e.id,data:{msg:"rpc failed during execution of "+e.op,code:578}})}}}close(e){for(let t in this.requests[e])typeof this.requests[e][t].end=="function"&&this.requests[e][t].end(),delete this.requests[e][t];delete this.requests[e]}open(){let e=++this.clientIdCounter;return this.requests[e]={},e}};y.Server=z});var ie=$(l=>{"use strict";var ge=l&&l.__createBinding||(Object.create?(function(o,e,t,r){r===void 0&&(r=t),Object.defineProperty(o,r,{enumerable:!0,get:function(){return e[t]}})}):(function(o,e,t,r){r===void 0&&(r=t),o[r]=e[t]})),re=l&&l.__exportStar||function(o,e){for(var t in o)t!=="default"&&!Object.prototype.hasOwnProperty.call(e,t)&&ge(e,o,t)};Object.defineProperty(l,"__esModule",{value:!0});re(ee(),l);re(te(),l)});var oe=me(ie(),1);var ve=["queued","running"],Q=class extends Error{constructor(e,t){super(e),this.name=this.constructor.name,this.msg=e,this.code=t,Error.captureStackTrace?.(this,this.constructor)}},n=class extends Q{constructor(e){super(e.msg,e.code),this.details=e.details,this.debug=e.debug}toString(){return console.log("Going to log an error... ;-D"),`${super.toString()}
2
+ Field: ${this.details}, ${this.debug}`}};var f=class{constructor(e){this.client=e}async get(e){try{return await this.client.requestAsync("user.get",[e])}catch(t){throw new n(t)}}async current(){try{return await this.client.requestAsync("user.current",[])}catch(e){throw new n(e)}}async list(){try{return await this.client.requestAsync("user.list",[])}catch(e){throw new n(e)}}};var b=class{constructor(e){this.client=e}async list(e,t){try{return await this.client.requestAsync("activity.kanban.list",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async load(e){try{return await this.client.requestAsync("activity.kanban.load",[e])}catch(t){throw new n(t)}}async updatePriority(e,t){try{return await this.client.requestAsync("activity.kanban.updatePriority",[{activityId:e,priority:t}])}catch(r){throw new n(r)}}};var w=class{constructor(e){this.client=e}async pass(e,t){try{return await this.client.requestAsync("activity.ball.pass",[e,t])}catch(r){throw new n(r)}}async take(e){try{return await this.client.requestAsync("activity.ball.take",[e])}catch(t){throw new n(t)}}async list(e){if(Array.isArray(e)&&e.length===0)return[];try{return await this.client.requestAsync("activity.ball.list",[e])}catch(t){throw new n(t)}}};var A=class{constructor(e){this.client=e;this.kanban=new b(e),this.ball=new w(e)}async list(e,t,r){try{return await this.client.requestAsync("activity.list",[e,t,r])}catch(i){throw new n(i)}}async get(e){try{return await this.client.requestAsync("activity.get",[e])}catch(t){throw new n(t)}}async create(e,t,r){try{return await this.client.requestAsync("activity.create",[e,t,...r?[r]:[]])}catch(i){throw new n(i)}}async update(e,t){try{return await this.client.requestAsync("activity.update",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("activity.remove",[e])}catch(t){throw new n(t)}}async print(e,t){try{return await this.client.requestAsync("activity.print",[e,...t?[t]:[]])}catch(r){throw new n(r)}}};var P=class{constructor(e){this.client=e;this.product={publishTemplate:this.publishTemplate.bind(this),isProductInstalled:this.isProductInstalled.bind(this),get:this.get.bind(this),install:this.install.bind(this),getManifest:this.getManifest.bind(this)}}async current(){try{return await this.client.requestAsync("workspace.current",[])}catch(e){throw new n(e)}}async list(){try{return await this.client.requestAsync("workspace.list",[])}catch(e){throw new n(e)}}async create(e){try{return await this.client.requestAsync("workspace.create",[e])}catch(t){throw new n(t)}}async publishTemplate(e){try{return await this.client.requestAsync("workspace.product.publishTemplate",[e])}catch(t){throw new n(t)}}async isProductInstalled(e,t){try{return await this.client.requestAsync("workspace.product.isProductInstalled",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("workspace.product.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("workspace.product.install",[e,t])}catch(r){throw new n(r)}}async getManifest(e){try{return await this.client.requestAsync("workspace.product.getManifest",[e])}catch(t){throw new n(t)}}};var v=class{constructor(e){this.client=e}async list(){try{return await this.client.requestAsync("team.list",[])}catch(e){throw new n(e)}}};var ye=300,fe={workspace:o=>`network_${o}`,team:o=>`team_${o}`,user:o=>`user_${o}`},k=class{constructor(e){this.client=e;this.readers=fe}async get(e){try{return await this.client.requestAsync("file.get",[e])}catch(t){throw new n(t)}}async upload(e,t,r){if(r?.isPublic&&r?.scoped)throw new n({code:400,msg:"A file cannot be both public and scoped",debug:void 0});try{let i=await this.toBase64(e);if(!r?.scoped)return await this.client.requestAsync("file.upload",[i,t,!!r?.isPublic]);let s=await this.client.requestAsync("file.upload",[i,t,!1,!0]);return await this.assertScoped(s),s}catch(i){throw i instanceof n?i:new n(i)}}async addTags(e,t){try{return await this.client.requestAsync("file.addTags",[e,t])}catch(r){throw new n(r)}}async removeTags(e,t){try{return await this.client.requestAsync("file.removeTags",[e,t])}catch(r){throw new n(r)}}async getScope(e){try{return await this.client.requestAsync("file.getScope",[e])}catch(t){throw new n(t)}}async setReaders(e,t){try{return await this.client.requestAsync("file.setReaders",[e,t])}catch(r){throw new n(r)}}async list(e){try{return await this.client.requestAsync("file.list",e?[e]:[])}catch(t){throw new n(t)}}async setOwner(e,t){try{return await this.client.requestAsync("file.setOwner",[e,t])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("file.remove",[e])}catch(t){throw new n(t)}}async assertScoped(e){let t;try{t=await this.client.requestAsync("file.getScope",[e])}catch(r){if(r?.code!==ye)throw new n(r)}if(!t?.workspaceId)throw new n({code:501,msg:`File ${e} was uploaded but not scoped: this Hailer version does not support scoped files`,debug:void 0})}toBase64(e){return new Promise((t,r)=>{let i=new FileReader;i.readAsDataURL(e),i.onload=()=>t(i.result??""),i.onerror=r})}};var x=class{constructor(e){this.client=e}async open(e,t){await this.client.requestAsync("ui.activity.open",[e,...t?[t]:[]])}async create(e,t){return this.client.requestAsync("ui.activity.create",[e,...t?[t]:[]])}async editMultiple(e){return this.client.requestAsync("ui.activity.editMultiple",[e])}};var R=class{constructor(e){this.client=e}async open(e,t){await this.client.requestAsync("ui.discussion.open",[e,...t?[t]:[]])}};var q=class{constructor(e){this.client=e}async open(e,t,r){await this.client.requestAsync("ui.snackbar.open",[e,t,r])}};var I=class{constructor(e){this.client=e}async uploadFile(e,t,r){return this.client.requestAsync("ui.file.upload",[await this.toBase64(e),t,!!r?.isPublic])}toBase64(e){return new Promise((t,r)=>{let i=new FileReader;i.readAsDataURL(e),i.onload=()=>t(i.result??""),i.onerror=r})}};var C=class{constructor(e){this.client=e;this.function={edit:async(e,t)=>{await this.client.requestAsync("ui.workflow.function.edit",[e,t])}}}};var T=class{constructor(e){this.client=e;this.activity=new x(e),this.discussion=new R(e),this.snackbar=new q(e),this.workflow=new C(e),this.insight={create:async t=>{await e.requestAsync("ui.insight.create",[t])},edit:async t=>{await e.requestAsync("ui.insight.edit",[t])},delete:async t=>{await e.requestAsync("ui.insight.delete",[t])},permission:async t=>{await e.requestAsync("ui.insight.permission",[t])}},this.files=new I(e)}};var ne=["https://app.hailer.com","https://next.hailer.com","https://testapp.hailer.biz","https://app.hailer.biz","https://app.hailer.local.gd","https://app.k8s.hailer.com","https://next.k8s.hailer.com","https://localhost:9443"],g="https://api.hailer.com",se={"https://app.hailer.com":g,"https://next.hailer.com":g,"https://app.hailer.biz":"https://api.hailer.biz","https://testapp.hailer.biz":"https://testapi.hailer.biz","https://app.hailer.local.gd":"https://api.hailer.local.gd","https://app.k8s.hailer.com":"https://api.k8s.hailer.com","https://next.k8s.hailer.com":"https://api.k8s.hailer.com","https://localhost:9443":"http://localhost:1337"};var S=class{constructor(e){this.options=e}async config(){let e="manifest.json",t=window.location.origin+window.location.pathname,r=t+e;t.endsWith("/index.html")&&(r=t.slice(0,-10)+e);let i=await(await fetch(r)).text(),a=JSON.parse(i).appId;return(await fetch(`${this.options.publicBackendUrl}/api/v3/app/public`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([a])})).json()}};var U=class{constructor(e){this.options=e}async data(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v2/forms/process/get`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}async submit(e,t){let r=await fetch(`${this.options.publicBackendUrl}/api/v2/forms/activity/create`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e,t])});if(!r.ok)throw new n(await r.json());return r.json()}};var O=class{constructor(e){this.options=e}async data(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v3/insight/public`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}async dataAsObject(e){let r=(await this.data(e)).data,i=[];return r.rows.forEach(s=>{let a={};r.headers.forEach((u,m)=>{a[u]=s[m]}),i.push(a)}),i}};var L=class{constructor(e){this.options=e}async list(e,t){let r=await fetch(`${this.options.publicBackendUrl}/api/v3/product/list`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e,t])});if(!r.ok)throw new n(await r.json());return r.json()}async get(e){let t=await fetch(`${this.options.publicBackendUrl}/api/v3/product/get`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify([e])});if(!t.ok)throw new n(await t.json());return t.json()}};var _=class{constructor(e){this.insight=new O(e),this.form=new U(e),this.app=new S(e),this.product=new L(e)}};var D=class{constructor(e){this.client=e}async list(){try{return await this.client.requestAsync("workflow.list",[])}catch(e){throw console.error(e.msg,e),new n(e)}}async get(e){try{return await this.client.requestAsync("workflow.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("workflow.install",[e,t])}catch(r){throw new n(r)}}};var E=class{constructor(e){this.client=e;this.config={update:async(e,t)=>{try{return await this.client.requestAsync("app.config.update",[e,...t?[t]:[]])}catch(r){throw new n(r)}}};this.product={isProductInstalled:this.isProductInstalled.bind(this),get:this.get.bind(this),install:this.install.bind(this),getInstalledVersion:this.getInstalledVersion.bind(this),getManifest:this.getManifest.bind(this)}}async isProductInstalled(e,t){try{return await this.client.requestAsync("app.product.isProductInstalled",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("app.product.get",[e])}catch(t){throw new n(t)}}async install(e,t){try{return await this.client.requestAsync("app.product.install",[e,t])}catch(r){throw new n(r)}}async getInstalledVersion(e){try{return await this.client.requestAsync("app.product.getInstalledVersion",[e])}catch(t){throw new n(t)}}async getManifest(e){try{return await this.client.requestAsync("app.product.getManifest",[e])}catch(t){throw new n(t)}}};var W=class{constructor(e){this.client=e}async data(e,t){try{return await this.client.requestAsync("insight.data",[e,...t?[t]:[]])}catch(r){throw new n(r)}}async list(){try{return await this.client.requestAsync("insight.list",[])}catch(e){throw new n(e)}}async update(e,t){try{return await this.client.requestAsync("insight.update",[e,t])}catch(r){throw new n(r)}}async query(e,t,r){try{return await this.client.requestAsync("insight.query",[e,{sources:t,query:r}])}catch(i){throw new n(i)}}};var F=class{constructor(e){this.client=e;this.map=async({workspaceId:e}={})=>{try{return await this.client.requestAsync("permission.map",e?[{workspaceId:e}]:[])}catch(t){throw console.log("Failed to read permissions from Hailer, error:",t),new n(t)}}}};var M=class{constructor(e){this.client=e}async list(e,t){try{return await this.client.requestAsync("product.list",[e,t])}catch(r){throw new n(r)}}async get(e){try{return await this.client.requestAsync("product.get",[e])}catch(t){throw new n(t)}}async create(e){try{return await this.client.requestAsync("product.create",[e])}catch(t){throw new n(t)}}async update(e,t){try{return await this.client.requestAsync("product.update",[e,t])}catch(r){throw new n(r)}}async remove(e){try{return await this.client.requestAsync("product.remove",[e])}catch(t){throw new n(t)}}async setPublic(e,t){try{return await this.client.requestAsync("product.setPublic",[e,t])}catch(r){throw new n(r)}}};var B=class{constructor(e){this.client=e}async createPricing(e){try{return await this.client.requestAsync("payment.createPricing",[e])}catch(t){throw new n(t)}}async updatePricing(e){try{return await this.client.requestAsync("payment.updatePricing",[e])}catch(t){throw new n(t)}}async getPricing(e){try{return await this.client.requestAsync("payment.getPricing",[{productId:e}])}catch(t){throw new n(t)}}async createPurchase(e){try{return await this.client.requestAsync("payment.createPurchase",[e])}catch(t){throw new n(t)}}async getPurchases(e){try{return await this.client.requestAsync("payment.getPurchases",[{workspaceId:e}])||[]}catch(t){throw new n(t)}}async calculateStripeTax(e){try{return await this.client.requestAsync("payment.calculateStripeTax",[e])}catch(t){throw new n(t)}}};var N=class{constructor(e){this.client=e;this.referral={listCodes:async e=>{try{return await this.client.requestAsync("admin.referral.listCodes",[e?.filter||null,e?.options||null])}catch(t){throw new n(t)}},listEvents:async e=>{try{return await this.client.requestAsync("admin.referral.listEvents",[e?.filter||null,e?.options||null])}catch(t){throw new n(t)}},updateCode:async(e,t)=>{try{return await this.client.requestAsync("admin.referral.updateCode",[{codeId:e,...t}])}catch(r){throw new n(r)}}}}async listWorkspaces(e){try{return await this.client.requestAsync("admin.workspace.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async getWorkspace(e){try{return await this.client.requestAsync("admin.workspace.get",[e])}catch(t){throw new n(t)}}async createStripeSession(e){try{return await this.client.requestAsync("admin.workspace.createStripeSession",[e])}catch(t){throw new n(t)}}async createInvoiceIntegration(e){try{return await this.client.requestAsync("admin.workspace.createInvoiceIntegration",[e])}catch(t){throw new n(t)}}async updateWorkspaceSubscription(e){try{return await this.client.requestAsync("admin.workspace.updateSubscription",[e])}catch(t){throw new n(t)}}async updatePurchasePrice(e){try{return await this.client.requestAsync("admin.purchase.updatePrice",[e])}catch(t){throw new n(t)}}async listWorkspaceUsers(e){try{return await this.client.requestAsync("admin.workspace.listUsers",[e.workspaceId,e.filter,e.options])}catch(t){throw new n(t)}}async updateUser(e){try{return await this.client.requestAsync("admin.user.update",[e.userId,e.updates])}catch(t){throw new n(t)}}async updateTokenBalance(e){try{return await this.client.requestAsync("admin.workspace.updateTokenBalance",[e])}catch(t){throw new n(t)}}async updateWorkspaceOverrides(e){try{return await this.client.requestAsync("admin.workspace.updateOverrides",[e])}catch(t){throw new n(t)}}async updateWorkspaceMarketplaceSettings(e){try{return await this.client.requestAsync("admin.workspace.updateMarketplaceSettings",[e])}catch(t){throw new n(t)}}async listTokenTransactions(e){try{return await this.client.requestAsync("admin.tokenTransaction.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async listInvoices(e){try{return await this.client.requestAsync("admin.invoice.list",[e?.filter,e?.options])}catch(t){throw new n(t)}}async updateInvoiceHandled(e){try{return await this.client.requestAsync("admin.invoice.updateHandled",[e.purchaseIds,e.handled])}catch(t){throw new n(t)}}async setSubscriptionActivityId(e,t){try{return await this.client.requestAsync("admin.invoice.setSubscriptionActivityId",[e,t])}catch(r){throw new n(r)}}async listMonthlyRevenue(e){try{return await this.client.requestAsync("admin.revenue.list",[e.month,e.year,e.filter,e.options])}catch(t){throw new n(t)}}async getDashboardStatistics(e){try{return await this.client.requestAsync("admin.dashboard.statistics",[e])}catch(t){throw new n(t)}}async getDashboardTrends(e,t){try{return await this.client.requestAsync("admin.dashboard.trends",[e,t])}catch(r){throw new n(r)}}};var H=class{constructor(e){this.client=e;this.admin={workspacesList:async e=>{try{return await this.client.requestAsync("metrics.workspaceSearch",[e])}catch(t){throw new n(t)}},usersList:async e=>{try{return await this.client.requestAsync("metrics.userList",[e])}catch(t){throw new n(t)}}}}async list(){try{return await this.client.requestAsync("metrics.list",[])}catch(e){throw new n(e)}}async get(e,t){try{let r=Array.isArray(e)?e:[e];return await this.client.requestAsync("metrics.get",[r,t])}catch(r){throw new n(r)}}};var Y=class{constructor(e,t){this.client=e;this.onopen=null;this.onmessage=null;this.onclose=null;this.onerror=null;this.readyState=WebSocket.CONNECTING;this.connectionId=null;this.client.request("http.ws.open",[t],(r,i)=>{if(r){this.readyState=WebSocket.CLOSED,this.onerror?.({error:r});return}if(i)switch(i.connectionId&&!this.connectionId&&(this.connectionId=i.connectionId),i.event){case"open":this.readyState=WebSocket.OPEN,this.onopen?.({});break;case"message":this.onmessage?.({data:i.data??""});break;case"close":this.readyState=WebSocket.CLOSED,this.onclose?.({code:i.code,reason:i.reason});break;case"error":this.onerror?.({error:i.data});break}})}send(e){if(this.readyState!==WebSocket.OPEN||!this.connectionId)throw new Error("WebSocket is not open");this.client.requestAsync("http.ws.send",[this.connectionId,e]).catch(t=>{this.onerror?.({error:t})})}close(e,t){this.connectionId&&this.client.requestAsync("http.ws.close",[this.connectionId,e,t]).catch(r=>{this.onerror?.({error:r})}),this.readyState=WebSocket.CLOSING}},j=class{constructor(e){this.client=e}async fetch(e,t){return this.client.requestAsync("http.fetch",[e,t]).catch(r=>{throw r})}async upload(e,t){return this.client.requestAsync("http.upload",[e,t]).catch(r=>{throw r})}openWebSocket(e){return new Y(this.client,e)}};var V=class{constructor(e){this.client=e}async create(e,t,r){try{return await this.client.requestAsync("credential.create",[{name:e,type:t,secret:r}])}catch(i){throw new n(i)}}async list(){try{return await this.client.requestAsync("credential.list",[])}catch(e){throw new n(e)}}async get(e){try{return await this.client.requestAsync("credential.get",[e])}catch(t){throw new n(t)}}async update(e,t){try{return await this.client.requestAsync("credential.update",[e,t])}catch(r){throw new n(r)}}};var K=class{constructor(e){this.client=e}async trigger(e,t){try{return await this.client.requestAsync("action.trigger",[e,t??null])}catch(r){throw new n(r)}}async getRun(e){try{return await this.client.requestAsync("action.getRun",[e])}catch(t){throw new n(t)}}};var X=class{constructor(e={}){this.options=e;this.outside=null;let t=e.allowedUrls??ne;this.client=new oe.Client(i=>{this.hostUrl&&parent.postMessage(JSON.stringify(i),this.hostUrl)}),this.user=new f(this.client),this.app=new E(this.client),this.activity=new A(this.client),this.insight=new W(this.client),this.workspace=new P(this.client),this.team=new v(this.client),this.file=new k(this.client),this.workflow=new D(this.client),this.permission=new F(this.client),this.public=new _(this.options),this.ui=new T(this.client),this.product=new M(this.client),this.payment=new B(this.client),this.admin=new N(this.client),this.metrics=new H(this.client),this.http=new j(this.client),this.credential=new V(this.client),this.action=new K(this.client);let r=JSON.stringify({op:"register",args:[{appApiVersion:"2"}]});window.location===window.parent.location?(this.options.publicBackendUrl||(this.options.publicBackendUrl=g),this.public.app.config().then(i=>{this.outside=!0,this.options.outside?.(i)}).catch(i=>{this.options.error?.(i),console.error("Failed to get app configuration in Public App.",i)})):(t.forEach(i=>parent.postMessage(r,i)),this.timer=setTimeout(()=>{this.outside=!0,this.options.outside?.()},100)),this.createEventListener()}createEventListener(){window.addEventListener("message",async e=>{let t=e.data;try{let r=JSON.parse(t);if(r.op==="register"){if(this.appId){console.error("App Id is already set...! Are you using hot-reload?");return}clearTimeout(this.timer),this.appId=r.data.appId,this.workspaceId=r.data.workspaceId,this.hostUrl=e.origin,this.options.publicBackendUrl||(this.options.publicBackendUrl=se[this.hostUrl]||g),this.client.request("ui.settings",[],(i,s,a)=>{if(i){console.log("ui.settings error:",i,s);return}this.options.settings?.(s)}),this.client.request("config",[],(i,s,a)=>{if(i){console.log("config error:",i,s);return}this.config=s,this.options.config?.(s)}),this.client.request("signal",[],(i,s,a)=>{if(i){console.log("signal error:",i,s);return}s&&(this.options.signals?.(s),typeof s.name=="string"&&s.name.startsWith("workspace.role.")&&this.options.permissions?.())}),this.outside=!1,this.options.permissions?.(),this.options.connected?.();return}if(!this.appId)return;this.client.messageReceived(r)}catch{console.log("Dropped invalid JSON message")}})}info(){return{hostUrl:this.hostUrl,config:this.config,outside:this.outside,workspaceId:this.workspaceId}}};export{ve as ACTION_RUN_ACTIVE_STATUSES,k as FileApi,X as HailerApi,n as HailerError,H as MetricsApi,fe as fileReaders};
3
3
  //# sourceMappingURL=app-sdk.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
- "sources": ["../node_modules/@wishcore/wish-rpc/src/rpc-client.ts", "../node_modules/@wishcore/wish-rpc/src/rpc-server.ts", "../node_modules/@wishcore/wish-rpc/src/index.ts", "../src/hailer-api.ts", "../src/types.ts", "../src/modules/user.ts", "../src/modules/activity/kanban.ts", "../src/modules/activity/ball.ts", "../src/modules/activity.ts", "../src/modules/workspace.ts", "../src/modules/team.ts", "../src/modules/file.ts", "../src/modules/ui/activity.ts", "../src/modules/ui/discussion.ts", "../src/modules/ui/snackbar.ts", "../src/modules/ui/files.ts", "../src/modules/ui/workflow.ts", "../src/modules/ui.ts", "../src/constants.ts", "../src/modules/public/app.ts", "../src/modules/public/form.ts", "../src/modules/public/insight.ts", "../src/modules/public/product.ts", "../src/modules/public.ts", "../src/modules/workflow.ts", "../src/modules/app.ts", "../src/modules/insight.ts", "../src/modules/permission.ts", "../src/modules/product.ts", "../src/modules/payment.ts", "../src/modules/admin.ts", "../src/modules/metrics.ts", "../src/modules/http.ts", "../src/modules/credential.ts"],
4
- "sourcesContent": [null, null, null, "import { Client } from '@wishcore/wish-rpc';\nimport { UserApi } from './modules/user';\nimport { ActivityApi } from './modules/activity';\nimport { WorkspaceApi } from './modules/workspace';\nimport { TeamApi } from './modules/team';\nimport { FileApi } from './modules/file';\nimport { ApiInfo, Config, Settings, Signal } from './types';\nimport { Ui } from './modules/ui';\nimport { DEFAULT_ALLOWED_URLS, DEFAULT_BACKEND_URL, publicBackendMap } from './constants';\nimport { HailerPublicApi } from './modules/public';\nimport { WorkflowApi } from './modules/workflow';\nimport { AppApi } from './modules/app';\nimport { InsightApi } from './modules/insight';\nimport { PermissionApi } from './modules/permission';\nimport { ProductApi } from './modules/product';\nimport { Payment } from './modules/payment';\nimport { Admin } from './modules/admin';\nimport { MetricsApi } from './modules/metrics';\nimport { HttpApi } from './modules/http';\nimport { CredentialApi } from './modules/credential';\n\nexport interface Options {\n /** When connected is called the host is ready to receive calls */\n connected?: () => void;\n /** Callback when app is determined to be outside of Hailer, as a standalone app */\n outside?: (config?: any) => void;\n /** Callback on errors, defaults to printing errors in console */\n error?: (error: Error) => void;\n /** Callback called on app init and when permissions have changed */\n permissions?: () => void;\n /** Callback called on app init and when settings have changed */\n settings?: (data: Settings) => void;\n /** Callback called on app init and when config has changed */\n config?: (config: any) => void;\n /** Will be called each time a subscribed signal is emitted from Hailer frontend. To subscribe to signals, add them to options.subscribedSignals[] */\n signals?: (signal: Signal) => void;\n /** Urls the sdk is allowed to connect to. Defaults to all Hailer instances*/\n allowedUrls?: string[];\n /** Public backend Api url. Defaults to https://api.hailer.com */\n publicBackendUrl?: string;\n}\n\nexport class HailerApi {\n public user: UserApi;\n public app: AppApi;\n public activity: ActivityApi;\n public insight: InsightApi;\n public workspace: WorkspaceApi;\n public team: TeamApi;\n public file: FileApi;\n public workflow: WorkflowApi;\n public permission: PermissionApi;\n public product: ProductApi;\n public payment: Payment;\n public admin: Admin;\n public metrics: MetricsApi;\n /** HTTP proxy for making authenticated HTTP/WebSocket requests through the parent frame */\n public http: HttpApi;\n /** Securely store and retrieve credentials (API keys, username/password pairs, etc.) */\n public credential: CredentialApi;\n /** All public endpoints, which can be accessed while not logged in to Hailer. */\n public public: HailerPublicApi;\n /** User interface commands */\n public ui: Ui;\n /** Url of the Hailer instance hosting the API */\n private hostUrl?: string;\n\n private appId?: string;\n /** If set it indicates that app is locked to a specific workspaceId */\n private workspaceId?: string;\n private client: Client;\n private config?: Config;\n private timer?: NodeJS.Timeout;\n /**\n * Hailer API state\n *\n * ```\n * true // outside hailer\n * false // logged into hailer\n * null // state not yet detected\n * ```\n */\n private outside: boolean | null = null;\n\n /**\n * Create a Hailer API client for inteacting with Hailer. **NOTE** This only works when inside Hailer.\n *\n * This should be run after window is initialized for example in ***onMount*** in Svelte or in ***useEffect*** in React\n */\n constructor(\n public options: Options = {}\n ) {\n const allowedUrls = options.allowedUrls ?? DEFAULT_ALLOWED_URLS;\n\n this.client = new Client(msg => {\n if (this.hostUrl) {\n parent.postMessage(JSON.stringify(msg), this.hostUrl);\n }\n });\n\n this.user = new UserApi(this.client);\n this.app = new AppApi(this.client);\n this.activity = new ActivityApi(this.client);\n this.insight = new InsightApi(this.client);\n this.workspace = new WorkspaceApi(this.client);\n this.team = new TeamApi(this.client);\n this.file = new FileApi(this.client);\n this.workflow = new WorkflowApi(this.client);\n this.permission = new PermissionApi(this.client);\n this.public = new HailerPublicApi(this.options);\n this.ui = new Ui(this.client);\n this.product = new ProductApi(this.client);\n this.payment = new Payment(this.client);\n this.admin = new Admin(this.client);\n this.metrics = new MetricsApi(this.client);\n this.http = new HttpApi(this.client);\n this.credential = new CredentialApi(this.client);\n\n const registerMessage = JSON.stringify({ op: 'register', args: [{ appApiVersion: '2' }] });\n\n // If we are not in Iframe set location to outside, else wait 100ms for response to register to check if we are in Hailer\n if (window.location === window.parent.location) {\n // Pick a backend to use for public requests, unless it is set\n if (!this.options.publicBackendUrl) {\n this.options.publicBackendUrl = DEFAULT_BACKEND_URL;\n }\n\n this.public.app.config().then(config => {\n // CSM app assumes we are inside hailer when config is called... breaks the thing...\n // this.options.config?.(config);\n\n this.outside = true;\n this.options.outside?.(config);\n }).catch(error => {\n this.options.error?.(error);\n console.error('Failed to get app configuration in Public App.', error);\n });\n } else {\n // if in a frame, try register to Hailer by sending register to all allowed urls\n allowedUrls.forEach(url => parent.postMessage(registerMessage, url));\n this.timer = setTimeout(() => {\n this.outside = true;\n this.options.outside?.();\n }, 100);\n }\n\n this.createEventListener();\n }\n\n private createEventListener() {\n window.addEventListener('message', async event => {\n const data = event.data;\n\n try {\n const msg = JSON.parse(data);\n if (msg.op === 'register') {\n if (this.appId) {\n console.error('App Id is already set...! Are you using hot-reload?');\n return;\n }\n\n clearTimeout(this.timer);\n\n this.appId = msg.data.appId;\n this.workspaceId = msg.data.workspaceId;\n\n // Set host url now that we have a response\n this.hostUrl = event.origin;\n\n // Pick a backend to use for public requests, unless it is set\n if (!this.options.publicBackendUrl) {\n this.options.publicBackendUrl = publicBackendMap[this.hostUrl] || DEFAULT_BACKEND_URL;\n }\n\n // Register listeners for config and settings\n this.client.request('ui.settings', [], (error: any, data: Settings, end: boolean) => {\n if (error) {\n console.log('ui.settings error:', error, data);\n return;\n }\n\n this.options.settings?.(data);\n });\n\n this.client.request('config', [], (error: any, data: any, end: boolean) => {\n if (error) {\n console.log('config error:', error, data);\n return;\n }\n this.config = data;\n this.options.config?.(data);\n });\n\n // Register subscribed signals\n this.client.request('signal', [], (error: any, data: any, end: boolean) => {\n if (error) {\n console.log('signal error:', error, data);\n return;\n }\n\n // eslint-disable-next-line no-restricted-syntax\n if (!data) {\n return;\n }\n\n this.options.signals?.(data);\n\n // Permission-changing events re-fire the permissions callback\n // eslint-disable-next-line no-restricted-syntax\n if (typeof data.name === 'string' && data.name.startsWith('workspace.role.')) {\n this.options.permissions?.();\n }\n });\n\n this.outside = false;\n // Notify permissions on init, then call connected\n this.options.permissions?.();\n this.options.connected?.();\n return;\n }\n\n // bail out unless appId is set, as the app is not properly registered\n if (!this.appId) {\n return;\n }\n\n this.client.messageReceived(msg);\n } catch (error) {\n console.log('Dropped invalid JSON message');\n }\n });\n }\n\n info(): ApiInfo {\n return {\n hostUrl: this.hostUrl,\n config: this.config,\n outside: this.outside,\n workspaceId: this.workspaceId,\n };\n }\n}\n", "export interface User {\n _id: string;\n firstname: string;\n lastname: string;\n // email: string;\n // lastSeen: number;\n // status?: string;\n // managedUser?: boolean;\n // removed?: number;\n // defaultProfilepic: string;\n}\n\n/* export interface Workspace {\n _id: string;\n name: string;\n members: string[];\n settings: {\n isolatedTeams?: boolean;\n defaultView: string;\n functionFieldVersion?: 1 | 2;\n color?: string;\n allowPublicCopy?: boolean;\n };\n license: object;\n invoicing?: any;\n propertyFields?: {\n [section: string]: {\n [field: string]: any;\n };\n };\n} */\nexport interface Workspace {\n _id: string;\n name: string;\n}\n\nexport interface Team {\n _id: string;\n name: string;\n}\n\nexport interface TeamsByWorkspace {\n [workspaceId: string]: Team[];\n}\n\nexport interface ActivityFieldRange {\n start: number;\n end: number;\n }\n\nexport interface ActivityFieldLink {\n _id: string;\n name: string;\n }\n\nexport interface ActivityFieldError {\n error?: string\n}\n\nexport type ActivityFieldValue = boolean | number | string | (ActivityFieldCountry & ActivityFieldError & ActivityFieldRange & ActivityFieldLink);\n\nexport type ActivityFieldUpdateValue = ActivityFieldValue | null;\n/*\nexport interface UserMap {\n [userId: string]: User;\n}\n\n*/\n\nexport interface ActivityFieldCountry {\n /** ISO 3166-1 alpha-2 (cca2) */\n code: string;\n}\nexport interface Activity {\n _id: string;\n process: string;\n teamAccount: TeamAccount // TODO: Convert in frontend\n created: number;\n uid: string;\n workspaceId: string;\n discussion: string;\n currentPhase: string;\n active?: boolean;\n history?: any[];\n name: string;\n followers?: string[];\n completePhases?: string[];\n location?: {\n type: 'point' | 'area' | 'polyline',\n label: string | null\n data: {\n lat: number\n lng: number\n }[]\n };\n fields?: {\n [fieldId: string]: ActivityFieldValue\n };\n // fields?: { [fieldId: string]: string | number };\n files?: any[];\n updated?: number;\n updatedBy?: string;\n priority?: number;\n sequence?: number\n}\n\nexport interface TeamAccount {\n account: string;\n team: string;\n}\n\nexport interface FormsData {\n files: string[];\n history: {\n\n 0: {\n [fieldId: string]: {\n value: any;\n };\n };\n };\n name: string;\n location?: boolean;\n uid?: string;\n}\nexport interface FormsResponse {\n name: string;\n description?: string;\n enableUnlinkedMode: boolean;\n enableAttachments: boolean;\n enableMapLocation: boolean;\n locationRequired: 1;\n phases: {\n _id: string;\n followers: [];\n name: string;\n description: string;\n uid: string;\n created: number;\n fields: string[];\n announcementFields: [];\n announcementRecipients: [];\n announcementFieldsOrder: [];\n isEndpoint: boolean;\n }[];\n phasesOrder: string[];\n fields: {\n [id: string]: {\n data: [];\n label: string;\n required: boolean;\n type: string;\n inviteToDiscussionOnChange: boolean;\n _id: string;\n created: number;\n updated: number;\n uid: string;\n functionEnabled: boolean;\n };\n };\n enableMessenger: boolean;\n publicForm: {\n enableMessaging: boolean;\n };\n fieldsOrder: [];\n}\n\nexport interface FormCreateResponse {\n key: string,\n creator: string,\n followers: string,\n active: boolean,\n enableMessaging: boolean,\n allowRead: boolean\n}\n\nexport interface InsightResponse {\n insight: {\n name: string\n },\n data: InsightResponseData\n}\n\nexport interface InsightResponseData {\n headers: string[],\n rows: [],\n time: number\n}\n\nexport interface Config {\n [fieldName: string]: string;\n}\n\nexport type WorkflowFieldType = (\n 'activitylink' |\n 'country' |\n 'date' |\n 'daterange' |\n 'datetime' |\n 'numeric' |\n 'numericunit' |\n 'teams' |\n 'text' |\n 'textarea' |\n 'textunit' |\n 'textpredefinedoptions' |\n 'time' |\n 'timerange' |\n 'datetimerange' |\n 'users' |\n 'linkedfrom' |\n 'subheader'\n);\n\nexport interface WorkflowField {\n _id: string;\n type: WorkflowFieldType;\n label: string;\n required: boolean;\n data: string[];\n functionEnabled: boolean;\n unit?: string;\n placeholder?: string;\n description?: string;\n editable?: boolean;\n functionVariables?: { [key: string]: any };\n key?: string;\n}\n\nexport interface DocumentTemplate {\n templateId?: string; // Valid ObjectId for regular templates, or non-ObjectId string for multi-pdf templates\n name: string;\n order?: number;\n}\n\nexport interface Workflow {\n _id: string;\n name: string;\n description?: string;\n fields: { [fieldId: string]: WorkflowField };\n fieldsOrder: string[];\n phases: { [phase_id: string]: WorkflowPhase };\n phasesOrder: string[];\n enablePredefinedName?: boolean;\n nameFunctionEnabled?: boolean;\n nameEditable?: boolean;\n enableMapLocation?: boolean;\n enableUnlinkedMode?: boolean;\n nameFieldPlaceHolderText?: string;\n order?: number;\n productInstalledId?: string;\n workspaceId: string;\n documentTemplates?: DocumentTemplate[];\n key?: string;\n /*\n defaultView: 'table' | 'kanban' | 'map' | 'calendar';\n fields: { [fieldId: string]: any };\n phasesRemoved: string[];\n members: any;\n updated: number;\n coverImage?: string;\n createNewLabel?: string;\n enableAddedField: boolean;\n enableLinkedAnnouncements?: boolean;\n enableMapLocation?: boolean;\n enableUnlinkedMode?: boolean;\n enableMessenger?: boolean;\n allowGuests?: boolean;\n enableGuestEditing?: boolean;\n enableModifiedField?: boolean;\n enableOwnerField?: boolean;\n enableOwnerTeamField?: boolean;\n ownerTeamFieldTitle?: string;\n enableUniqueName?: boolean;\n enablePreselectedTeam?: boolean;\n initPhaseDescription?: string;\n locationRequired?: boolean;\n nameColumnText?: string;\n nameFunction?: string;\n nameFunctionVariables?: any;\n personInCharge?: string;\n personInChargeLabel?: string;\n publicForm?: {\n key: string;\n active: boolean;\n creator: string;\n team_account: TeamAccount;\n followers: string;\n allowRead: boolean;\n enableMessaging?: boolean;\n }\n predefinedNamePrefix?: string;\n preselectedTeam?: TeamAccount;\n enableAttachments: boolean;\n nameFieldPlaceHolderText: string;\n order?: number;\n allowMultipleTags?: boolean;\n allowCustomTags?: boolean;\n requireFileTag?: boolean;\n color?: string;\n starred?: string[];\n isStarred?: boolean;\n createdActivities?: number;\n */\n}\n\nexport interface WorkflowPhase {\n _id: string;\n name: string;\n description?: string;\n fields?: string[];\n primaryDateField?: string;\n primaryNumericField?: string;\n uid?: string;\n created?: number;\n isEndpoint?: boolean;\n possibleNextPhase?: string[];\n possibleNextPhaseSettings?: { [phaseId: string]: { text?: string } };\n color?: string;\n key?: string;\n /*\n followers: string[];\n created: number;\n uid?: string;\n members?: any[]\n enableAnnouncement?: boolean,\n announcementFields?: string[];\n announcementRecipients?: string[];\n announcementFieldsOrder?: string[];\n announcementToOwner?: boolean;\n announcementToOwnerTeam?: boolean;\n isEndPoint?: boolean;\n possibleNextPhase?: string[];\n possibleNextPhaseSettings?: any;\n fieldOptions?: any;\n primaryNumericField?: string;\n webhooksEnabled?: boolean;\n webhookAdded?: boolean;\n webhookUpdated?: boolean;\n primaryDateField?: string | null | any;\n removed?: number;\n removedBy?: string;\n color?: string | null;\n */\n}\n/**\n * ```ts\n * { [templateId: string]: string }\n * ```\n */\nexport interface IdsMap {\n [templateId: string]: string;\n}\n\nexport type PermissionType = 'admin' | 'own' | 'ownteam' | 'any' | 'edit';\n\nexport interface Member {\n id: string;\n info: { [key: string]: string | number | boolean | null };\n permissions: PermissionType[];\n}\n\nexport type WorkflowPermission = 'admin' | 'any' | 'ownteam' | 'own' | 'guest' | 'none';\nexport type WorkflowPhasePermission = 'edit' | 'view' | 'none';\n\nexport interface PermissionPath {\n type: 'network' | 'user' | 'team' | 'group';\n id: string;\n permission: WorkflowPermission | WorkflowPhasePermission;\n};\n\nexport interface WorkflowPermissionMap {\n [workflowId: string]: {\n // hasAccess: boolean;\n isAdmin: boolean;\n permission: WorkflowPermission;\n permissions: PermissionPath;\n phases: {\n [phaseId: string]: {\n // name: string;\n // hasAccess: boolean;\n permission: WorkflowPhasePermission,\n permissions: PermissionPath[];\n restricted: boolean;\n }\n };\n teams: string[];\n\n }\n};\n\nexport interface WorkspaceRolesPermission {\n isAdmin: boolean;\n isOwner: boolean;\n isGuest: boolean;\n isInviter: boolean;\n isUser: boolean;\n // custom: roleSchema,\n};\n\nexport interface PermissionMap {\n [userId: string]: {\n workflow: WorkflowPermissionMap,\n workspace: WorkspaceRolesPermission,\n // calendar: calendarPermissionMapSchema,\n // insight: insightPermissionMapSchema,\n // app: appPermissionMapSchema,\n // teams: Joi.array().items(validTeamId),\n // permits: Joi.array().items(Joi.string()),\n },\n};\n\nexport interface InsightWorkflowSource {\n name: string;\n workflowId: string;\n fields: {\n name: string;\n fieldId?: string;\n /** Used for phaseLastMove meta */\n phaseId?: string;\n /** Activity information, like _id, created, phaseId etc. */\n meta?: string;\n }[];\n}\nexport interface InsightDoc {\n _id: string;\n name: string;\n /** Key for accessing Insight when set to public */\n publicKey?: string;\n presets: {\n version: 1;\n name: string | 'default';\n options: any;\n }[];\n /** To be used with SQLite if we want to.... */\n query?: string;\n sources: InsightWorkflowSource[];\n public: boolean;\n\n // members: Member[];\n // updated: number;\n /** User id of creator */\n // uid: string;\n // workspaceId: string;\n /** sandboxed javascript with access to all activities in given workflows */\n // function?: string;\n\n\n}\n\nexport type InsightPublic = Omit<InsightDoc, '_id'>;\n\n// These are separate so we can do different configs if necessary without it being a breaking change\nexport interface InsightData {\n headers: string[];\n rows: (string | number | null)[][];\n time: number;\n}\n\nexport interface InsightResponseAsObjectItem {\n [key: string]: any\n}\nexport type InsightResponseAsObjects = InsightResponseAsObjectItem[]\n\nexport type InsightSource = InsightWorkflowSource;\n\nexport interface InsightQueryResult {\n headers: string[];\n rows: (string | number | null)[][];\n /** Per-table breakdown of the temporary tables built from sources */\n details: {\n [tableName: string]: {\n headers: string[];\n rows: number;\n };\n };\n}\n\nexport interface KanbanListResponse {\n map: {\n [phaseId: string]: {\n activities: {\n _id: string,\n followers: string[],\n name: string,\n fields: { [key: string]: any }\n files: string[],\n primaryDateField: number,\n priority: number,\n }[]\n meta: {\n count: number,\n totalPrimaryNumericValue: number,\n primaryNumericFieldUnit: string | null\n }\n }\n }\n}\n\nexport interface KanbanLoadResponse {\n activity: {\n _id: string,\n followers: string[],\n name: string,\n fields: { [key: string]: any },\n files: string[],\n primaryDateField: number | null,\n priority: number,\n linkedFromCount: number\n },\n process: string,\n phase: string\n}\nexport interface ActivityListOptions {\n /** Workspace to resolve a workflow **key** in (keys are unique per workspace) */\n workspaceId?: string,\n sortBy?: 'name' | 'created' | 'updated' | 'following' | 'owner' | 'team' | 'completedOn' | 'priority',\n sortOrder?: 'asc' | 'desc',\n limit?: number,\n skip?: number,\n includeUsers?: boolean,\n includeTeams?: boolean,\n includeHistory?: boolean,\n filters?: any\n}\nexport interface ActivityCreateOptions {\n /** Workspace to resolve a workflow **key** in (keys are unique per workspace) */\n workspaceId?: string;\n teamId?: string;\n fileIds?: string[];\n followerIds?: string[];\n location?: {\n label?: string;\n type: 'area' | 'point' | 'polyline';\n data: [{ lat: number, lng: number }];\n };\n discussionId?: string;\n phaseId?: string;\n returnDocument?: boolean;\n}\n\n\n/** Simplistic syntax for add/remove/replace */\nexport interface IdSetUpdate {\n /** Clear all existing */\n '*'?: null,\n /** Add: true, Remove: null */\n [id: string]: true | null | undefined\n}\nexport interface ActivityLocation {\n data: {\n lat: number;\n lng: number;\n }[],\n label?: string;\n type: 'area' | 'point' | 'polyline';\n};\nexport interface ActivityUpdateOptions {\n fields?: ActivityFieldUpdateValue,\n teamId?: string,\n location?: ActivityLocation\n phaseId?: string,\n files?: IdSetUpdate,\n followers?: IdSetUpdate,\n};\n\nexport interface ActivityKanbanListOptions {\n filter: {\n user?: {\n uid: string;\n field: string;\n },\n account?: string;\n team?: string;\n dates?: {\n field: string;\n start: number;\n end: number;\n };\n },\n search?: string;\n limit?: number;\n skip?: number;\n phase?: string;\n includeUsers?: boolean;\n includeTeams?: boolean;\n}\n\nexport interface PrintRequest {\n activityId: string;\n /** Template ID for regular templates */\n templateId?: string;\n /** Template name for multi-pdf templates (when templateId is empty) */\n templateName?: string;\n /** Whether to save the PDF to the file system */\n savePdf?: boolean;\n}\n\nexport interface PrintOptions {\n /**\n * Open the generated document in the device's own viewer, where the host supports it.\n * Currently only the Hailer Android app does: the document is saved to Downloads and opened\n * in the system PDF viewer, where the user can print or share it. Elsewhere the document is\n * only returned, as without this option; check `openedNatively` in the response.\n */\n openNative?: boolean;\n}\n\nexport interface PrintResponse {\n filename: string;\n /** Base64-encoded document data */\n data: string;\n mimeType: string;\n /**\n * Only set when `openNative` was requested: `true` if the host handed the document to the\n * device's own viewer, `false` if it couldn't (web, iOS). Older Hailer versions leave it unset,\n * so treat anything but `true` as \"not opened\".\n */\n openedNatively?: boolean;\n}\n\nexport interface Settings {\n theme: 'light' | 'dark'\n preferredLanguages: string[];\n}\n\nexport type CredentialType = 'basic' | 'apiKey' | 'custom';\n\nexport interface CredentialBasicData {\n username: string;\n password: string;\n}\n\nexport interface CredentialApiKeyData {\n apiKey: string;\n}\n\n/** Any JSON-serialisable value that can live inside a `custom` secret. */\nexport type CredentialJsonValue =\n | string\n | number\n | boolean\n | null\n | CredentialJsonValue[]\n | { [key: string]: CredentialJsonValue };\n\n/**\n * Free-form secret for `custom` credentials \u2014 any JSON object with 1\u201350\n * top-level keys.\n */\nexport interface CredentialCustomData {\n [key: string]: CredentialJsonValue;\n}\n\nexport type CredentialData =\n | CredentialBasicData\n | CredentialApiKeyData\n | CredentialCustomData;\n\n/**\n * Reader entry granting access to a workspace credential. Credentials created\n * through the app SDK are personal and have no readers; readers only appear on\n * workspace credentials bound to your app and surfaced in `list`.\n */\nexport type CredentialReader = `network_${string}` | `team_${string}` | `user_${string}`;\n\nexport interface CredentialCreateResponse {\n _id: string;\n}\n\nexport interface CredentialListItem {\n _id: string;\n name: string;\n type: CredentialType;\n /** Set only on workspace credentials \u2014 absent on personal ones. */\n workspaceId?: string;\n /** The app the credential is bound to; always your own app's id. */\n appId?: string;\n /** Workspace credentials only. */\n readers?: CredentialReader[];\n createdBy: string;\n created: number;\n updated: number;\n}\n\nexport interface CredentialUpdate {\n name?: string;\n /** Replaces the entire stored payload \u2014 there is no key-level merge. */\n secret?: CredentialData;\n}\n\n/** Decrypted credential as returned by `credential.get`. */\n// eslint-disable-next-line @typescript-eslint/naming-convention\nexport interface CredentialDetails<T extends CredentialData = CredentialData> {\n type: CredentialType;\n secret: T;\n}\n\nexport interface ApiInfo {\n /** Url of the Hailer instance hosting the API */\n hostUrl?: string;\n config?: Config;\n outside: boolean | null;\n workspaceId?: string;\n}\n\nexport interface ApiError {\n code: number,\n msg: string,\n debug: object\n}\n\nclass CustomError extends Error {\n public msg: string;\n public code: number;\n\n constructor(message: string, code: number) {\n super(message);\n this.name = this.constructor.name;\n this.msg = message;\n this.code = code;\n Error.captureStackTrace?.(this, this.constructor);\n }\n}\n\nexport class HailerError extends CustomError {\n public debug: object;\n public details?: any;\n\n constructor(error: {code: number, msg: string, details?: any, debug: any}) {\n super(error.msg, error.code);\n\n this.details = error.details;\n this.debug = error.debug;\n }\n\n toString() {\n console.log('Going to log an error... ;-D');\n return `${super.toString()} \\nField: ${this.details}, ${this.debug}`;\n }\n}\n\nexport interface Signal {\n name: string;\n data: any;\n}\n\nexport interface Product extends ProductType {\n _id: string;\n targetId?: string;\n name: string;\n description?: string;\n icon?: string;\n images?: string[];\n externalUrl?: string;\n publisher?: string;\n ctaLabel: string;\n ctaLink: string;\n /** Available or not in app store */\n public?: boolean;\n cid?: string;\n uid: string;\n}\n\nexport interface ProductListResponse {\n products: Product[];\n totalCount: number;\n}\n\nexport interface ProductSearchOption {\n limit?: number,\n skip?: number,\n search?: string,\n reverse?: boolean,\n sortBy?: 'name' | 'created' | 'updated' | 'type',\n sortOrder?: 'asc' | 'desc'\n}\n\nexport interface ProductSearchFilter extends ProductType {\n public?: boolean,\n cid?: string,\n uid?: string,\n}\n\nexport interface ProductType {\n type?: 'app' | 'template' | 'integration' | 'expert' | 'ai-agent',\n}\n\nexport interface ProductVersion {\n _id: string;\n name: string;\n versions?: Version[];\n cid?: string;\n}\n\nexport interface Version {\n version: string;\n description: string;\n packageHash: string;\n created: number;\n}\n\n// Payment and Pricing Types\nexport interface PricingPlan {\n planId: 'monthly' | 'yearly' | 'one_time';\n label: string;\n price: number;\n currency: string;\n interval: 'month' | 'year' | null;\n}\n\nexport interface PaymentProvider {\n priceId?: {\n monthly?: string;\n yearly?: string;\n one_time?: string;\n };\n trial_days?: number;\n}\n\nexport interface PricingProviders {\n stripe?: PaymentProvider;\n paddle?: PaymentProvider;\n // fuze?: PaymentProvider; // Hidden for now\n}\n\nexport interface PricingData {\n _id?: string;\n productId?: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n created?: number;\n updated?: number;\n}\n\nexport interface CreatePricingRequest {\n productId: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n}\n\nexport interface UpdatePricingRequest {\n productId: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n}\n\nexport interface CreatePurchaseRequest {\n productId: string;\n workspaceId: string;\n planType: 'monthly' | 'yearly' | 'one_time';\n successUrl?: string; // Optional for backward compatibility\n cancelUrl?: string; // Optional for backward compatibility\n useTokens?: boolean; // Optional - use workspace tokens for one-time purchases\n}\n\nexport interface CreatePurchaseResponse {\n status: 'installed_free' | 'subscription_created' | 'checkout_required' | 'payment_processed' | 'payment_failed';\n message?: string;\n productId?: string;\n planType?: string;\n purchaseId?: string;\n subscriptionId?: string;\n provider?: string;\n trialDays?: number;\n checkoutUrl?: string;\n error?: string; // For payment failure details\n}\n\nexport interface Purchase {\n _id: string;\n uid: string;\n cid: string;\n productId?: string;\n productName?: string;\n provider?: 'stripe' | 'paddle' | 'fuze';\n type: 'monthly' | 'yearly' | 'one_time';\n purchaseType: 'workspace' | 'product';\n startedAt: number;\n created: number;\n updated?: number;\n customStatus?: string;\n expiresAt?: number;\n trialDays?: number;\n trialStart?: number;\n trialEnd?: number;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n pricing?: {\n amount: number;\n currency: string;\n interval: string;\n source: string;\n };\n stripe?: {\n customerId?: string;\n checkoutSessionId?: string;\n subscriptionId?: string;\n paymentIntentId?: string;\n status?: string;\n };\n paddle?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n fuze?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n}\n\n// Admin interfaces\nexport interface AdminWorkspaceListItem {\n _id: string;\n name: string;\n memberCount: number;\n created: number;\n updated?: number;\n creatorEmail?: string;\n paymentPlan?: string;\n monthlyPrice?: number;\n paymentMethod?: 'subscription' | 'invoice';\n subscriptionActive?: boolean;\n provider?: string;\n stripeStatus?: string;\n hasPendingSubscription?: boolean;\n tokenBalance?: number;\n autoReloadEnabled?: boolean;\n}\n\nexport interface AdminWorkspaceListRequest {\n filter?: {\n name?: string;\n };\n options?: {\n search?: string;\n sortBy?: string;\n sortOrder?: string;\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminWorkspaceListResponse {\n workspaces: AdminWorkspaceListItem[];\n totalCount: number;\n}\n\n// Purchase data for admin interfaces\nexport interface AdminPurchaseData {\n _id: string;\n uid: string;\n cid: string;\n productId?: string | null;\n productName?: string | null;\n provider?: string;\n type: string;\n purchaseType: 'workspace' | 'product' | 'token';\n billingType?: 'subscription' | 'invoice';\n planName?: 'flexible' | 'pro' | 'business' | 'enterprise';\n startedAt?: number;\n expiresAt?: number;\n created: number;\n updated?: number;\n customStatus?: string;\n trialStart?: number;\n trialEnd?: number;\n invoiceHandled?: boolean;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n hailer?: {\n tokenAmount?: number;\n tokenRate?: number;\n customerActivityId?: string;\n status?: string;\n paymentMethod?: string;\n };\n pricing?: {\n amount: number;\n currency: string;\n interval?: string;\n source: 'purchase_record' | 'pricing_collection';\n };\n availablePricing?: Array<{\n planId: 'monthly' | 'yearly' | 'one_time';\n label: string;\n price: number;\n currency: string;\n interval: string | null;\n }>;\n trialDays?: number;\n stripe?: {\n customerId?: string;\n checkoutSessionId?: string;\n subscriptionId?: string;\n paymentIntentId?: string;\n status?: string;\n };\n paddle?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n fuze?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n}\n\n// Single workspace for admin get method (extends list item with purchase data)\nexport interface AdminWorkspaceOverrides {\n // Boolean overrides\n functionFields?: boolean;\n kanban?: boolean;\n customRoles?: boolean;\n restricted?: boolean;\n insight?: boolean;\n dataExport?: boolean;\n documentGenerator?: boolean;\n groups?: boolean;\n print?: boolean;\n isolatedTeams?: boolean;\n managedUsers?: boolean;\n translations?: boolean;\n indexedData?: boolean;\n fastFunctions?: boolean;\n activityRecovery?: boolean;\n videoCall?: boolean;\n // Number overrides\n users?: number | null;\n // String overrides\n tourIdentifier?: string;\n}\n\nexport interface AdminWorkspaceMarketplaceSettings {\n creatorPercent: number;\n}\n\nexport interface AdminWorkspace extends AdminWorkspaceListItem {\n purchaseId?: string;\n purchases?: AdminPurchaseData[];\n overrides?: AdminWorkspaceOverrides;\n marketplace?: AdminWorkspaceMarketplaceSettings;\n}\n\nexport interface AdminUpdateOverridesRequest {\n workspaceId: string;\n overrides: AdminWorkspaceOverrides;\n}\n\nexport interface AdminUpdateMarketplaceSettingsRequest {\n workspaceId: string;\n creatorPercent: number;\n}\n\nexport interface AdminCreateStripeSessionRequest {\n workspaceId: string;\n planName: 'flexible' | 'pro' | 'business' | 'enterprise';\n customPrice: number;\n paymentMethod: 'stripe';\n baseUrl: string;\n}\n\nexport interface AdminCreateStripeSessionResponse {\n success: boolean;\n message: string;\n sessionUrl?: string;\n}\n\nexport interface AdminCreateInvoiceIntegrationRequest {\n workspaceId: string;\n planName: 'enterprise'; // Only enterprise for invoice\n customPrice: number;\n paymentMethod: 'hailer';\n customerActivityId?: string;\n}\n\nexport interface AdminCreateInvoiceIntegrationResponse {\n success: boolean;\n message: string;\n}\n\nexport interface AdminUpdateWorkspaceSubscriptionRequest {\n purchaseId: string;\n billingType: 'subscription' | 'invoice';\n customPrice: number;\n planName: 'flexible' | 'pro' | 'business' | 'enterprise';\n tokenAmount?: number;\n customerActivityId?: string;\n skipInvoiceHandledReset?: boolean;\n}\n\nexport interface AdminUpdatePurchasePriceRequest {\n purchaseId: string;\n workspaceId: string;\n newPrice: number;\n skipInvoiceHandledReset?: boolean;\n}\n\nexport interface AdminWorkspaceUser {\n _id: string;\n name: string;\n email: string;\n role: 'owner' | 'admin' | 'user' | 'guest' | 'inviter';\n joined?: number;\n lastActive?: number;\n emailVerified?: boolean;\n managedUser?: boolean | null;\n}\n\nexport interface AdminWorkspaceUsersListRequest {\n workspaceId?: string;\n filter?: {\n email?: string;\n role?: string;\n };\n options?: {\n search?: string;\n sortBy?: string;\n sortOrder?: string;\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminWorkspaceUsersListResponse {\n users: AdminWorkspaceUser[];\n totalCount: number;\n}\n\nexport interface AdminUpdateUserRequest {\n userId: string;\n updates: {\n emailVerified?: boolean;\n };\n}\n\nexport interface AdminUpdateUserResponse {\n success: boolean;\n}\n\nexport interface AdminUpdateTokenBalanceRequest {\n workspaceId: string;\n tokenAmount: number;\n payoutType?: 'admin_bonus' | 'creator_payout';\n payoutMonth?: number;\n payoutYear?: number;\n creatorPercent?: number;\n}\n\nexport interface AdminTokenTransaction {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n type: 'purchase' | 'deduction' | 'bonus' | 'admin_adjustment' | 'creator_payout';\n amount: number;\n reason: string;\n meta?: {\n payoutMonth?: number;\n payoutYear?: number;\n creatorProfit?: number;\n creatorPercent?: number;\n [key: string]: any\n };\n createdAt: number;\n}\n\nexport interface AdminTokenTransactionFilter {\n workspaceId?: string;\n type?: 'purchase' | 'deduction' | 'bonus' | 'admin_adjustment' | 'creator_payout';\n operation?: string;\n dateFrom?: number;\n dateTo?: number;\n search?: string;\n}\n\nexport interface AdminTokenTransactionStatistics {\n netChange: number;\n totalPurchases: number;\n totalPurchasesEuro: number;\n purchasesBySource: {\n stripe: {\n count: number;\n tokens: number;\n revenue: number;\n };\n adminPortal: {\n count: number;\n tokens: number;\n revenue: number;\n };\n };\n totalDeductions: number;\n totalDeductionsEuro: number;\n consumptionByOperation: {\n [operation: string]: {\n count: number;\n tokens: number;\n };\n };\n totalBonuses: number;\n totalBonusesEuro: number;\n totalCreatorPayouts: number;\n totalCreatorPayoutsEuro: number;\n totalRefunds: number;\n totalRefundsEuro: number;\n}\n\nexport interface AdminTokenTransactionsListRequest {\n filter?: AdminTokenTransactionFilter;\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminTokenTransactionsListResponse {\n transactions: AdminTokenTransaction[];\n totalCount: number;\n statistics: AdminTokenTransactionStatistics;\n}\n\nexport interface AdminInvoicePurchase {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n purchaseType: 'workspace' | 'product' | 'token';\n type: 'monthly' | 'yearly' | 'one_time';\n provider: 'hailer';\n billingType: 'invoice';\n planName?: string;\n productId?: string;\n productName?: string;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n hailer?: {\n tokenAmount?: number;\n tokenRate?: number;\n customerActivityId?: string;\n };\n customStatus?: string;\n invoiceHandled?: boolean;\n pendingAction?: string;\n startedAt: number;\n expiresAt?: number;\n trialStart?: number;\n trialEnd?: number;\n trialDays?: number;\n}\n\nexport interface AdminInvoiceListRequest {\n filter?: {\n workspaceId?: string;\n purchaseType?: 'workspace' | 'product' | 'token';\n status?: 'handled' | 'unhandled' | 'all';\n search?: string;\n };\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminInvoiceWorkspaceGroup {\n cid: string;\n workspaceName: string;\n allHandled: boolean;\n customerActivityId?: string;\n purchases: AdminInvoicePurchase[];\n}\n\nexport interface AdminInvoiceListResponse {\n invoices: AdminInvoicePurchase[];\n totalCount: number;\n workspaceGroups: AdminInvoiceWorkspaceGroup[];\n}\n\nexport interface AdminInvoiceUpdateHandledRequest {\n purchaseIds: string | string[];\n handled: boolean;\n}\n\nexport interface AdminInvoiceUpdateHandledResponse {\n updatedCount: number;\n}\n\n// Monthly Revenue Tracking Types\nexport interface AdminRevenuePurchase {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n purchaseType: 'workspace' | 'product';\n type: 'monthly' | 'yearly' | 'one_time';\n provider: string;\n productId?: string;\n productName?: string;\n productOwnerCid?: string;\n productOwnerName?: string;\n pricePaid?: { amount: number; currency: string };\n startedAt: number;\n expiresAt?: number;\n // Calculated fields\n normalizedMonthlyRevenue: number; // Yearly \u00F7 12, others as-is\n isMarketplace: boolean;\n profitToHailer: number;\n profitToCreator?: number;\n statusInMonth: 'active' | 'started' | 'ended';\n}\n\nexport interface AdminRevenueWorkspaceGroup {\n cid: string;\n workspaceName: string;\n totalRevenue: number;\n totalMRR: number;\n totalOneTime: number;\n totalCreatorProfit: number;\n totalHailerProfit: number;\n creatorPercent: number;\n productCount: number;\n paidOut?: boolean;\n productBreakdown: Array<{\n productId: string;\n productName: string;\n installationCount: number;\n totalRevenue: number;\n subscriptionTypes: {\n monthly: number;\n yearly: number;\n one_time: number;\n };\n installedBy: Array<{\n cid: string;\n workspaceName: string;\n type: string;\n }>;\n }>;\n purchases: AdminRevenuePurchase[];\n}\n\nexport interface AdminRevenueWorkspaceSubscriptions {\n totalWorkspaces: number;\n totalRevenue: number;\n byPlan: Array<{\n planName: string;\n count: number;\n revenue: number;\n }>;\n}\n\nexport interface AdminRevenueStatistics {\n selectedMonth: { month: number; year: number };\n totalMRR: number;\n totalOneTime: number;\n totalRevenue: number;\n activeCount: number;\n hailerProfit: number;\n creatorProfit: number;\n}\n\nexport interface AdminRevenueListRequest {\n month: number;\n year: number;\n filter?: {\n workspaceId?: string;\n purchaseType?: 'workspace' | 'product';\n subscriptionType?: 'monthly' | 'yearly' | 'one_time';\n search?: string;\n };\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminRevenueListResponse {\n purchases: AdminRevenuePurchase[];\n totalCount: number;\n workspaceGroups: AdminRevenueWorkspaceGroup[];\n statistics: AdminRevenueStatistics;\n}\n\n// Dashboard Statistics Types\nexport interface AdminDashboardEntityStatistics {\n today: number;\n total: number;\n lastWeek: number;\n growth: number;\n}\n\nexport interface AdminDashboardStatisticsResponse {\n users: AdminDashboardEntityStatistics;\n workspaces: AdminDashboardEntityStatistics;\n activities: AdminDashboardEntityStatistics;\n messages: AdminDashboardEntityStatistics;\n userMessages: AdminDashboardEntityStatistics;\n}\n\n// Dashboard Trends Types\nexport interface AdminDashboardTrendDataPoint {\n date: string;\n count: number;\n}\n\nexport interface AdminDashboardTrendsResponse {\n users?: AdminDashboardTrendDataPoint[];\n workspaces?: AdminDashboardTrendDataPoint[];\n}\n\n// Stripe Tax Calculation Types\nexport interface StripeTaxLineItem {\n amount: number;\n reference: string;\n tax_code?: string;\n quantity?: number;\n}\n\nexport interface StripeTaxCalculationRequest {\n workspaceId: string;\n lineItems: StripeTaxLineItem[];\n}\n\nexport interface StripeTaxLineItemResult {\n reference: string;\n amount: number;\n taxAmount: number;\n totalAmount: number;\n}\n\nexport interface StripeTaxCalculationResponse {\n amountSubtotal: number;\n amountTax: number;\n amountTotal: number;\n taxRate?: number;\n country?: string;\n countryName?: string;\n currency: string;\n lineItems: StripeTaxLineItemResult[];\n}\n\n// Admin Referral Types\nexport interface AdminReferralCode {\n _id: string;\n code: string;\n uid: string;\n cid: string;\n ownerEmail?: string;\n workspaceName?: string;\n bonusTokens: number;\n isActive: boolean;\n totalReferrals: number;\n totalTokensAwarded: number;\n created: number;\n}\n\nexport interface AdminReferralCodeListRequest {\n filter?: {\n isActive?: boolean;\n cid?: string;\n };\n options?: {\n search?: string;\n limit?: number;\n skip?: number;\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n };\n}\n\nexport interface AdminReferralCodeListResponse {\n codes: AdminReferralCode[];\n totalCount: number;\n stats: {\n activeCount: number;\n totalReferrals: number;\n totalTokensAwarded: number;\n };\n}\n\nexport interface AdminReferralEvent {\n _id: string;\n referralCodeId: string;\n referralCode: string;\n referrerUid: string;\n referrerCid: string;\n refereeUid: string;\n refereeCid: string;\n refereeEmail?: string;\n refereeWorkspaceName?: string;\n status: 'pending' | 'completed' | 'failed';\n bonusTokensAwarded: number;\n failureReason?: string;\n created: number;\n completedAt?: number;\n}\n\nexport interface AdminReferralEventListRequest {\n filter?: {\n referralCodeId?: string;\n referrerCid?: string;\n status?: 'pending' | 'completed' | 'failed';\n };\n options?: {\n limit?: number;\n skip?: number;\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n };\n}\n\nexport interface AdminReferralEventListResponse {\n events: AdminReferralEvent[];\n totalCount: number;\n stats: {\n completedCount: number;\n pendingCount: number;\n totalTokensAwarded: number;\n };\n}\n\nexport interface BallHolder {\n userId: string;\n assignedAt: string;\n}\n\nexport interface BallHolderEntry {\n activityId: string;\n discussionId: string;\n activityName: string;\n ballHolder: BallHolder;\n}\n\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, User } from '../types';\n\nexport class UserApi {\n constructor(private client: Client) {}\n\n /**\n * Returns the specified user\n *\n * @param userId id of the Hailer user\n *\n * @returns Hailer user information\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(userId: string): Promise<User> {\n try {\n return await this.client.requestAsync('user.get', [userId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Returns the current user\n *\n *\n * @returns the current Hailer user information\n *\n * @throws {HailerError} if request is incorrect\n */\n async current(): Promise<User> {\n try {\n return await this.client.requestAsync('user.current', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists all Hailer users from a workspace\n *\n *\n * @returns list of Hailer users in the workspace the app user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<User[]> {\n try {\n return await this.client.requestAsync('user.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { ActivityKanbanListOptions, HailerError, KanbanListResponse, KanbanLoadResponse } from '../../types';\n\nexport class Kanban {\n constructor(private client: Client) { }\n\n /**\n * Lists all activities in a kanban grouped by phases\n *\n * @param processId the id of the process the kanban relates to\n * @param options ActivityKanbanListOptions\n *\n * @returns activities in kanban list format\n *\n * @throws {HailerError} if request fails\n */\n async list(processId: string, options?: ActivityKanbanListOptions): Promise<KanbanListResponse> {\n try {\n const res = await this.client.requestAsync('activity.kanban.list', [processId, ...options ? [options] : []]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Loads a single activity in kanban format\n *\n * @param activityId activityId of the wanted activity\n *\n * @returns activity in kanban format\n *\n * @throws {HailerError} if request is incorrect\n */\n async load(activityId: string): Promise<KanbanLoadResponse> {\n try {\n const res = await this.client.requestAsync('activity.kanban.load', [activityId]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates priority of activities in kanban\n *\n * @param activityId activityId of the wanted activity\n * @param priority new priority for the activity\n *\n * @throws {HailerError} if request is incorrect\n */\n async updatePriority(activityId: string, priority: number): Promise<void> {\n try {\n const res = await this.client.requestAsync('activity.kanban.updatePriority', [{ activityId, priority }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { BallHolderEntry, HailerError } from '../../types';\n\nexport class Ball {\n constructor(private client: Client) { }\n\n /**\n * Pass the ball (activity responsibility) to another user.\n *\n * @param activityId activity to update\n * @param toUserId recipient user id; must be a participant of the activity's discussion\n *\n * @throws {HailerError} if the activity has no ball tracking, the caller is a guest, or the target is not a participant\n */\n async pass(activityId: string, toUserId: string): Promise<void> {\n try {\n return await this.client.requestAsync('activity.ball.pass', [activityId, toUserId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Take the ball (activity responsibility) for the current user.\n *\n * @param activityId activity to take\n *\n * @throws {HailerError} if ball tracking is disabled, the caller is a guest, or the caller lacks phase access\n */\n async take(activityId: string): Promise<void> {\n try {\n return await this.client.requestAsync('activity.ball.take', [activityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * List ball holders for activity discussions.\n *\n * @param discussionIds `'*'` to load every ball holder the user can see, or an array of discussionIds to restrict the result.\n * Unknown or non-participant discussionIds are silently dropped. An empty array returns `[]` without hitting the backend.\n *\n * @returns array of ball holder entries for activities where the caller can access both the discussion and the workflow\n *\n * @throws {HailerError} if the request is invalid\n */\n async list(discussionIds: string[] | '*'): Promise<BallHolderEntry[]> {\n if (Array.isArray(discussionIds) && discussionIds.length === 0) {\n return [];\n }\n try {\n return await this.client.requestAsync('activity.ball.list', [discussionIds]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { ActivityCreateOptions, ActivityListOptions, Activity, HailerError, ActivityFieldUpdateValue, ActivityUpdateOptions, ActivityFieldValue, PrintRequest, PrintOptions, PrintResponse } from '../types';\nimport { Kanban } from './activity/kanban';\nimport { Ball } from './activity/ball';\n\nexport class ActivityApi {\n public kanban: Kanban;\n public ball: Ball;\n constructor(private client: Client) {\n this.kanban = new Kanban(client);\n this.ball = new Ball(client);\n }\n\n /**\n * Lists all activities from the specified process and phase\n *\n * @param processId process from current network\n * @param phaseId phase in the process specified in processId\n * @param options ActivityListOptions\n *\n * @returns List of Hailer activities from process and phase filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(processId: string, phaseId: string, options?: ActivityListOptions): Promise<Activity[]> {\n try {\n return await this.client.requestAsync('activity.list', [processId, phaseId, options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets single activity\n *\n * @param activityId Id of the activity to fetch\n *\n * @returns Hailer activity information or undefined if no activity is found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(activityId: string): Promise<Activity | undefined> {\n try {\n // Uses the same endpoint as getAll but only returns the activity in question\n return await this.client.requestAsync('activity.get', [activityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(workflowId: string | undefined, activities: { name?: string; fields?: { [id: string]: ActivityFieldValue }, phaseId?: string, teamId?: string }[], options?: ActivityCreateOptions ): Promise<Activity[]> {\n try {\n return await this.client.requestAsync('activity.create', [workflowId, activities, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates activites\n *\n * @returns The number of updated activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(\n activities: { _id: string, name?: string, fields?: { [id: string]: ActivityFieldUpdateValue }, phaseId?: string, teamId?: string }[],\n options?: ActivityUpdateOptions\n ): Promise<number> {\n try {\n return await this.client.requestAsync('activity.update', [activities, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Removes activities\n *\n * @param activities Ids of activities to be removed\n *\n * @returns The number of removed activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async remove(activities: string[]): Promise<number> {\n try {\n return await this.client.requestAsync('activity.remove', [activities]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Prints activities using document templates\n *\n * @param requests Array of print requests\n * @param requests[].activityId The ID of the activity to print\n * @param requests[].templateId Template ID for regular templates\n * @param requests[].templateName Template name for multi-pdf templates (when templateId is empty)\n * @param requests[].savePdf Whether to save the generated PDF\n * @param options.openNative Also open the document in the device's own viewer where the host supports it\n * (the Hailer Android app); see `openedNatively` in the response\n *\n * @returns PDF data with filename, base64 data, and mimeType\n *\n * @throws {HailerError} if request is incorrect\n */\n async print(requests: PrintRequest[], options?: PrintOptions): Promise<PrintResponse> {\n try {\n return await this.client.requestAsync('activity.print', [requests, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, ProductVersion, Workspace } from '../types';\n\nexport class WorkspaceApi {\n product: {\n /** Publish template in Hailer market */\n publishTemplate: (template: {\n workspaceId?: string,\n versionId?: string,\n version: string,\n versionDescription: string,\n title: string,\n description: string\n }) => Promise<ProductVersion>\n\n /** Check if product is installed */\n isProductInstalled(\n id: string,\n workspaceId: string\n ): Promise<boolean>\n\n /** Get version */\n get(\n id: string\n ): Promise<ProductVersion | undefined>\n\n /** Install template from Hailer market */\n install(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get manifest content from Hailer market */\n getManifest(id: string): Promise<any>\n };\n\n constructor(private client: Client) {\n this.product = {\n publishTemplate: this.publishTemplate.bind(this),\n isProductInstalled: this.isProductInstalled.bind(this),\n get: this.get.bind(this),\n install: this.install.bind(this),\n getManifest: this.getManifest.bind(this),\n };\n }\n\n /**\n * Returns the current network\n *\n * @returns the Hailer Workspace information the user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async current(): Promise<Workspace> {\n try {\n const res = await this.client.requestAsync('workspace.current', []);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Returns all workspaces for user if personal app\n * If not personal app it returns only the current workspace\n * @returns the Hailer Workspaces information for the user\n *\n * * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<Workspace[]> {\n try {\n const res = await this.client.requestAsync('workspace.list', []);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n\n /**\n * Creates a new workspace\n *\n * Only available for personal apps \u2014 a workspace-scoped app is bound to a\n * single workspace and cannot create new ones.\n *\n * @param name Name of the new workspace\n *\n * @returns the id and name of the created workspace\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(name: string): Promise<{ _id: string; name: string }> {\n try {\n const res = await this.client.requestAsync('workspace.create', [name]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n\n /**\n * Publish template in Hailer market\n *\n * @param workspaceId Id of workspace\n * @param versionId link to version (empty if first publish)\n * @param version Version number\n * @param versionDescription Version description\n * @param title\n * @param description\n *\n * @returns Created version in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n private async publishTemplate(\n template: {\n workspaceId?: string,\n versionId?: string,\n version: string,\n versionDescription: string,\n title: string,\n description: string\n }\n ): Promise<ProductVersion> {\n try {\n const result = await this.client.requestAsync('workspace.product.publishTemplate', [template]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Check if product is installed\n *\n * @param id Id of product in Hailer market\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async isProductInstalled(\n id: string,\n workspaceId: string\n ): Promise<boolean> {\n try {\n return await this.client.requestAsync('workspace.product.isProductInstalled', [id, workspaceId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get version\n *\n * @param id targetId\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async get(\n id: string\n ): Promise<ProductVersion | undefined> {\n try {\n return await this.client.requestAsync('workspace.product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Install template from Hailer market\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace where the product will be installed\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async install(productId: string, workspaceId: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('workspace.product.install', [productId, workspaceId]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get manifest content from Hailer market\n *\n * @param id target Id\n *\n * @returns Manifest content\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getManifest(id: string): Promise<any> {\n try {\n return await this.client.requestAsync('workspace.product.getManifest', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, TeamsByWorkspace } from '../types';\n\nexport class TeamApi {\n constructor(private client: Client) {}\n\n /**\n * Lists all teams grouped by workspace ID\n *\n * @returns Teams grouped by workspace ID\n *\n * @example\n * const teams = await hailer.team.list();\n * // { \"workspaceId1\": [{ _id: \"...\", name: \"Team A\" }], ... }\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<TeamsByWorkspace> {\n try {\n return await this.client.requestAsync('team.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError } from '../types';\n\nexport interface FileResponse {\n filename: string;\n /** Base64-encoded file data */\n data: string;\n mimeType: string;\n /** Free-form string tags attached to the file */\n tags: string[];\n}\n\nexport interface UploadOptions {\n /** Whether the file should be publicly accessible */\n isPublic?: boolean;\n /**\n * Scope the file to the app's workspace (irreversible). A scoped file is readable only by its owner,\n * workspace admins and its readers; set readers with `setReaders`. Cannot be combined with `isPublic`,\n * and not available to guests. This is the only way to scope a file.\n */\n scoped?: boolean;\n}\n\n/** Owner, workspace and readers of a file. `workspaceId` and `readers` are absent for an unscoped file. */\nexport interface FileScope {\n _id: string;\n /** Owner of the file */\n uid: string;\n /** Workspace the file is scoped to */\n workspaceId?: string;\n /** Reader entries, see `FileApi.readers` */\n readers?: string[];\n}\n\nexport interface FileListOptions {\n /** One keyword or up to 20. A keyword matches a case-insensitive substring of the file name or of any tag. */\n search?: string | string[];\n /** `all` (default) requires every keyword to match, `any` at least one */\n matchType?: 'all' | 'any';\n skip?: number;\n /** 1-100, default 100 */\n limit?: number;\n sortBy?: 'name' | 'created';\n reverse?: boolean;\n}\n\nexport interface ScopedFile {\n _id: string;\n name: string;\n /** Owner of the file */\n uid: string;\n workspaceId: string;\n type?: string;\n length?: number;\n created?: number;\n updated?: number;\n tags?: string[];\n}\n\nexport interface FileListResponse {\n files: ScopedFile[];\n hasMore: boolean;\n total: number;\n}\n\n/** wish-rpc's error code for a method the host does not have */\nconst noSuchMethod = 300;\n\n/**\n * Builders for `setReaders` entries. Only full members of the app's workspace ever match a reader:\n * guests never do, not even through a team or a `user_` entry.\n */\nexport const fileReaders = {\n /** Every full member of the workspace */\n workspace: (workspaceId: string): string => `network_${workspaceId}`,\n /** The full members of a team; guests in the team are skipped */\n team: (teamId: string): string => `team_${teamId}`,\n /** A single full member; a guest is rejected */\n user: (userId: string): string => `user_${userId}`,\n};\n\nexport class FileApi {\n /** Builders for `setReaders` entries: `readers.workspace(id)`, `readers.team(id)`, `readers.user(id)` */\n readonly readers = fileReaders;\n\n constructor(private client: Client) {}\n\n /**\n * Gets a file by ID and returns it as base64 data\n *\n * @param fileId The ID of the file to fetch\n *\n * @returns File data with filename, base64 data, and mimeType\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(fileId: string): Promise<FileResponse> {\n try {\n return await this.client.requestAsync('file.get', [fileId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Uploads a file to Hailer\n *\n * @param file File to be uploaded\n * @param filename Name of the file\n * @param options Upload options\n *\n * @returns File ID in Hailer\n *\n * @throws {HailerError} if upload fails\n */\n async upload(file: File, filename: string, options?: UploadOptions): Promise<string> {\n if (options?.isPublic && options?.scoped) {\n throw new HailerError({ code: 400, msg: 'A file cannot be both public and scoped', debug: undefined });\n }\n\n try {\n const base64Data = await this.toBase64(file);\n if (!options?.scoped) {\n return await this.client.requestAsync('file.upload', [base64Data, filename, !!options?.isPublic]);\n }\n\n const fileId: string = await this.client.requestAsync('file.upload', [base64Data, filename, false, true]);\n await this.assertScoped(fileId);\n return fileId;\n } catch (error: any) {\n throw error instanceof HailerError ? error : new HailerError(error);\n }\n }\n\n /**\n * Appends tags to a file, deduping against the existing list.\n *\n * Tags are case-sensitive free-form strings (trimmed, 1-64 characters, max 50 per file). On a scoped\n * file only its owner or a workspace admin may change tags; readers can read them but not edit.\n *\n * @param fileId The ID of the file to tag\n * @param tags Tags to add\n *\n * @returns The file's resulting tag list\n *\n * @throws {HailerError} if validation fails or the file cannot be edited\n */\n async addTags(fileId: string, tags: string[]): Promise<string[]> {\n try {\n return await this.client.requestAsync('file.addTags', [fileId, tags]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Removes tags from a file by case-sensitive exact match. Tags not present are silently ignored.\n * On a scoped file only its owner or a workspace admin may change tags.\n *\n * @param fileId The ID of the file to untag\n * @param tags Tags to remove\n *\n * @returns The file's resulting tag list\n *\n * @throws {HailerError} if validation fails or the file cannot be edited\n */\n async removeTags(fileId: string, tags: string[]): Promise<string[]> {\n try {\n return await this.client.requestAsync('file.removeTags', [fileId, tags]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets the owner, workspace and readers of a file you can read. Use it as an \"is this file scoped?\"\n * probe: `workspaceId` is absent for an unscoped file.\n *\n * @param fileId The ID of the file\n *\n * @throws {HailerError} if the file does not exist or you cannot read it (guests cannot read scoped\n * files), or if it is scoped to a workspace other than the app's (403)\n */\n async getScope(fileId: string): Promise<FileScope> {\n try {\n return await this.client.requestAsync('file.getScope', [fileId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Replaces the readers of a file scoped to the app's workspace. Files are scoped only at upload\n * (`upload(..., { scoped: true })`); an unscoped file is refused (403) rather than scoped here.\n *\n * Requires being the file's owner (while a full member) or a workspace admin; not available to guests.\n * A non-admin may only add teams they belong to. Every entry must belong to the app's workspace, and\n * `user_` must name a full member, not a guest.\n *\n * @param fileId The ID of the file\n * @param readers The complete new reader list (max 100); build entries with `readers.*`. Send `[]` to\n * leave only the owner and workspace admins.\n *\n * @returns The resulting scope\n *\n * @throws {HailerError} if validation fails, the file is not scoped to the app's workspace, or you may\n * not manage it\n */\n async setReaders(fileId: string, readers: string[]): Promise<FileScope> {\n try {\n return await this.client.requestAsync('file.setReaders', [fileId, readers]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists the scoped files of the app's workspace that the user can read: their own, those they are a\n * reader of, or all of them for a workspace admin. Unscoped files are not listed.\n *\n * @param options Search by name/tags and paging\n *\n * @returns A page of files, whether more exist, and the total match count\n *\n * @throws {HailerError} if validation fails, or for a guest\n */\n async list(options?: FileListOptions): Promise<FileListResponse> {\n try {\n return await this.client.requestAsync('file.list', options ? [options] : []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Transfers a file scoped to the app's workspace to another full member of it (not a guest). Workspace\n * admins only. The previous owner loses access unless they are a reader.\n *\n * @param fileId The ID of the file\n * @param userId The new owner\n *\n * @throws {HailerError} if you are not a workspace admin, the file is not scoped to the app's workspace,\n * or the user is not a full member\n */\n async setOwner(fileId: string, userId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('file.setOwner', [fileId, userId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Permanently deletes files scoped to the app's workspace that you own. Ids of files owned by someone\n * else are skipped without an error, even for a workspace admin; re-list to see what is left. If any id\n * is not a file scoped to the app's workspace, the whole call is refused (403) and nothing is removed:\n * an app can never delete the user's other files.\n *\n * @param fileIds 1-100 file ids\n *\n * @returns `true` once the request is processed\n *\n * @throws {HailerError} if validation fails, or any file is not scoped to the app's workspace\n */\n async remove(fileIds: string[]): Promise<boolean> {\n try {\n return await this.client.requestAsync('file.remove', [fileIds]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * An older Hailer ignores the `scoped` upload argument and stores the file unscoped. Fail loudly rather\n * than hand back a file the app believes is restricted. Only a missing `file.getScope` (wish-rpc code\n * 300) or an unscoped result means an older Hailer; any other error is passed on as is.\n */\n private async assertScoped(fileId: string): Promise<void> {\n let scope: FileScope | undefined;\n try {\n scope = await this.client.requestAsync('file.getScope', [fileId]);\n } catch (error: any) {\n if (error?.code !== noSuchMethod) {\n throw new HailerError(error);\n }\n }\n\n if (!scope?.workspaceId) {\n throw new HailerError({\n code: 501,\n msg: `File ${fileId} was uploaded but not scoped: this Hailer version does not support scoped files`,\n debug: undefined,\n });\n }\n }\n\n private toBase64(file: File): Promise<string> {\n return new Promise((resolve, reject) => {\n const reader = new FileReader();\n reader.readAsDataURL(file);\n reader.onload = () => resolve((reader.result as string) ?? '');\n reader.onerror = reject;\n });\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport type ActivityTabTypes =\n 'detail' |\n 'discussion' |\n 'files' |\n 'location' |\n 'linkedFrom' |\n 'options';\n\nexport class Activity {\n constructor(private client: Client) {}\n\n /** Opens an activity in Hailer sidebar */\n async open(\n /** Hailer Activity Id */\n activityId: string,\n options?: {\n /** Which tab to open in activity aside */\n tab?: ActivityTabTypes\n },\n ): Promise<void> {\n await this.client.requestAsync('ui.activity.open', [activityId, ...options ? [options] : []]);\n }\n\n /** Opens activity creation view in Hailer sidebar */\n async create(\n processId: string,\n options?: {\n /** Activity name/title */\n name?: string,\n /** Phase ID to pre-select */\n phaseId?: string,\n /** Team ID to pre-select */\n teamId?: string,\n /** Prepopulate fields */\n fields?: {\n [fieldId: string]: number | string | { start: number, end: number },\n },\n location?: {\n type: 'area' | 'point' | 'polyline',\n data: { lng: number, lat: number }[],\n },\n }\n ): Promise<{ _id: string, name: string } | null> {\n return this.client.requestAsync('ui.activity.create', [processId, ...options ? [options] : []]);\n }\n\n /**\n * Opens multiple activity edit view in Hailer sidebar\n *\n * @param activityIds Ids of the activities to edit\n */\n async editMultiple(\n activityIds: string[]\n ): Promise<void> {\n return this.client.requestAsync('ui.activity.editMultiple', [activityIds]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\n/**\n * Valid tab types for opening discussions.\n * - Private discussions: \"discussions\" | \"files\" | \"info\" | \"location\"\n * - Group discussions: \"discussion\" | \"overview\" | \"files\"\n */\nexport type DiscussionTabTypes =\n | 'discussions'\n | 'files'\n | 'location'\n | 'info'\n | 'discussion'\n | 'overview'\n | 'detail'\n | 'participants'\n | 'linkedFrom'\n | 'options';\n\nexport class Discussion {\n constructor(private client: Client) {}\n\n /** Opens a discussion/chat in Hailer sidebar */\n async open(\n /** Hailer Discussion Id */\n discussionId: string,\n options?: {\n /** Which tab to open in discussion aside (only applies to group discussions) */\n tab?: DiscussionTabTypes;\n /** Whether to expand the sidebar if collapsed (default: true) */\n expandIfCollapsed?: boolean;\n },\n ): Promise<void> {\n await this.client.requestAsync('ui.discussion.open', [\n discussionId,\n ...(options ? [options] : []),\n ]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport class Snackbar {\n constructor(private client: Client) {}\n\n /**\n * Opens a snackbar in Hailer\n * @param text the text displayed on the snackbar\n * @param buttonLabel the label for the button on the snackbar, for example 'OK'\n * @param duration the time the snackbar is visible in ms\n */\n async open(\n /** The text displayed on the snackbar */\n text: string,\n /** The label for the button on the snackbar, for example 'OK' */\n buttonLabel: string,\n /** The time the snackbar is visible in ms */\n duration?: number,\n ): Promise<void> {\n await this.client.requestAsync('ui.snackbar.open', [text, buttonLabel, duration]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\n/**\n * @deprecated Use FileApi from '@hailer/app-sdk' instead.\n * This class is kept for backwards compatibility.\n *\n * @example\n * // New way (recommended):\n * import { FileApi } from '@hailer/app-sdk';\n * const fileApi = new FileApi(client);\n * const fileId = await fileApi.upload(file, filename, { isPublic: false });\n */\nexport class Files {\n constructor(private client: Client) {}\n\n /**\n * Uploads a file to Hailer\n *\n * @deprecated Use FileApi.upload() instead\n *\n * @param file file to be uploaded\n * @param filename name of the file\n * @param options upload options\n *\n * @returns File ID in Hailer as string\n */\n public async uploadFile(file: File, filename: string, options: { isPublic?: boolean }): Promise<string> {\n return this.client.requestAsync('ui.file.upload', [await this.toBase64(file), filename, !!options?.isPublic]);\n }\n\n private toBase64(file: File): Promise<string | ArrayBuffer> {\n return new Promise((resolve, reject) => {\n const reader = new FileReader();\n reader.readAsDataURL(file);\n reader.onload = () => resolve(reader.result ?? '');\n reader.onerror = reject;\n });\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport class Workflow {\n constructor(private client: Client) {}\n\n function = {\n /**\n * Opens the function editor dialog for a specific field\n * @param fieldId The ID of the field to edit\n * @param options Additional options including workflowId and activityId\n */\n edit: async (\n workflowId: string,\n fieldId: string,\n ): Promise<void> => {\n await this.client.requestAsync('ui.workflow.function.edit', [workflowId, fieldId]);\n }\n };\n}", "import { Client } from '@wishcore/wish-rpc';\nimport { Activity } from './ui/activity';\nimport { Discussion } from './ui/discussion';\nimport { Snackbar } from './ui/snackbar';\nimport { Files } from './ui/files';\nimport { Workflow } from './ui/workflow';\n\n\nexport class Ui {\n public activity;\n public discussion;\n public snackbar;\n public files;\n public insight;\n public workflow;\n\n constructor(private client: Client) {\n this.activity = new Activity(client);\n this.discussion = new Discussion(client);\n this.snackbar = new Snackbar(client);\n this.workflow = new Workflow(client);\n\n this.insight = {\n create: async (\n /** Defaults to App workspace */\n workspaceId?: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.create', [workspaceId]);\n },\n edit: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.edit', [insightId]);\n },\n delete: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.delete', [insightId]);\n },\n permission: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.permission', [insightId]);\n }\n };\n\n this.files = new Files(client);\n }\n}\n", "export const DEFAULT_ALLOWED_URLS = [\n 'https://app.hailer.com',\n 'https://next.hailer.com',\n 'https://testapp.hailer.biz',\n 'https://app.hailer.biz',\n 'https://app.hailer.local.gd',\n 'https://app.k8s.hailer.com',\n 'https://next.k8s.hailer.com',\n 'https://localhost:9443'\n];\n\nexport const DEFAULT_BACKEND_URL = 'https://api.hailer.com';\n\n/** Map of which backend to use depending on which frontend is hosting the app frame, be sure to fall back to production backend if no match */\nexport const publicBackendMap: { [host: string]: string } = {\n 'https://app.hailer.com': DEFAULT_BACKEND_URL,\n 'https://next.hailer.com': DEFAULT_BACKEND_URL,\n 'https://app.hailer.biz': 'https://api.hailer.biz',\n 'https://testapp.hailer.biz': 'https://testapi.hailer.biz',\n 'https://app.hailer.local.gd': 'https://api.hailer.local.gd',\n 'https://app.k8s.hailer.com': 'https://api.k8s.hailer.com',\n 'https://next.k8s.hailer.com': 'https://api.k8s.hailer.com',\n 'https://localhost:9443': 'http://localhost:1337',\n};\n", "import { Options } from '../../hailer-api';\nimport { Config } from '../../types';\n\nexport class App {\n constructor(private options: Options) {}\n\n /**\n * Read data from app API\n *\n * @param appId key of a specific insight\n *\n * @returns App manifest\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async config(): Promise<Config> {\n const manifestFile = 'manifest.json';\n const location = window.location.origin + window.location.pathname;\n let manifestUrl = location + manifestFile;\n\n if (location.endsWith('/index.html')) {\n manifestUrl = location.slice(0, -10) + manifestFile;\n }\n\n const manifestContent = await (await fetch(manifestUrl)).text();\n\n const manifest = JSON.parse(manifestContent);\n\n const appId = manifest.appId;\n\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/app/public`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([appId])\n });\n\n return res.json();\n }\n\n}\n", "import { Options } from '../../hailer-api';\nimport { FormCreateResponse, FormsData, FormsResponse, HailerError } from '../../types';\n\nexport class Form {\n constructor(private options: Options) {}\n\n /**\n * Read data from forms\n *\n * @param formsKey key of a form\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v2/forms\n *\n * @returns forms data as object or null if form could not be found\n *\n * @throws {HailerError} if there is something wrong with the request or form cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async data(formsKey: string): Promise<FormsResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v2/forms/process/get`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([formsKey])\n });\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Submits form to specified process\n *\n * @param formsKey key of a form\n * @param formsData Data to be sent to form endpoint\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v2/forms\n *\n * @returns form creation data or null if form could not be created\n *\n * @throws {HailerError} if there is something wrong with the request or form cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async submit(formsKey: string, formsData: FormsData): Promise<FormCreateResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v2/forms/activity/create`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([formsKey, formsData])\n });\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n}\n", "import { Options } from '../../hailer-api';\nimport { HailerError, InsightResponse, InsightResponseAsObjects, InsightResponseData } from '../../types';\n\nexport class InsightPublicApi {\n constructor(private options: Options) {}\n\n /**\n * Read data from insight API\n *\n * @param insightKey key of a specific insight\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v3/insight/public\n *\n * @returns Insight data as object\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async data(insightKey: string): Promise<InsightResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/insight/public`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([insightKey])\n }\n );\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Read data from insight API and return in an array of JavaScript objects\n *\n * @param insightKey key of a specific insight\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v3/insight/public\n *\n * @returns Insight data as array of JavaScript objects\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async dataAsObject(insightKey: string): Promise<InsightResponseAsObjects> {\n const res = await this.data(insightKey);\n\n const input: InsightResponseData = res.data;\n const data: InsightResponseAsObjects = [];\n\n input.rows.forEach((row) => {\n // The object keys are constructed dynamically, so any is necessary\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const object: any = {};\n input.headers.forEach((header, headerIndex) => {\n object[header] = row[headerIndex];\n });\n data.push(object);\n });\n return data;\n }\n}\n", "import { Options } from '../../hailer-api';\nimport { HailerError, Product, ProductListResponse, ProductSearchFilter, ProductSearchOption, ProductType } from '../../types';\n\nexport class ProductPublicApi {\n constructor(private options: Options) {}\n\n /**\n * Lists products from Hailer market\n *\n * @param filter ProductSearchFilter\n * @param options ProductSearchOption\n *\n * @returns List of products in Hailer market filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(\n filter?: ProductSearchFilter,\n options?: ProductSearchOption\n ): Promise<ProductListResponse> {\n\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/product/list`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([filter, options])\n });\n\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Gets single product from Hailer market\n *\n * @param id Product Id\n *\n * @returns Single product from Hailer market or undefined if no product found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(id: string): Promise<Product | undefined> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/product/get`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([id])\n });\n\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n}\n", "import { Options } from '../hailer-api';\nimport { Product } from '../types';\nimport { App } from './public/app';\nimport { Form } from './public/form';\nimport { InsightPublicApi } from './public/insight';\nimport { ProductPublicApi } from './public/product';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class HailerPublicApi {\n /** Allows accessing public insight methods. Used for reading data from Hailer even when app is outside of Hailer */\n public insight: InsightPublicApi;\n /** Allows accessing public forms methods. Used for sending data to Hailer even when app is outside of Hailer */\n public form: Form;\n /** Access public App information */\n public app: App;\n /** Access public Product information */\n public product: ProductPublicApi;\n\n constructor(options: Options) {\n this.insight = new InsightPublicApi(options);\n this.form = new Form(options);\n this.app = new App(options);\n this.product = new ProductPublicApi(options);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, IdsMap, Workflow } from '../types';\n\nexport class WorkflowApi {\n constructor(private client: Client) {}\n\n /**\n * Lists all processes from a workspace\n *\n * @returns all Hailer processes in the workspace the app user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<Workflow[]> {\n try {\n return await this.client.requestAsync('workflow.list', []);\n } catch (error: any) {\n console.error(error.msg, error);\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets a single process from a workspace\n *\n * @param workflowId the id of the process in question\n *\n * @returns the specified Hailer process\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(workflowId: string): Promise<Workflow> {\n try {\n return await this.client.requestAsync('workflow.get', [workflowId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Installs a workflow (process) from a spec\n *\n * @param workflowSpec the workflow specification to install\n * @param option optional target workspace\n *\n * @returns a map of template ids to the created ids\n *\n * @throws {HailerError} if request is incorrect\n */\n async install(workflowSpec: any, option?: { workspaceId?: string }): Promise<IdsMap> {\n try {\n return await this.client.requestAsync('workflow.install', [workflowSpec, option]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { Config, HailerError, ProductVersion, Version } from '../types';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class AppApi {\n product: {\n /** Check if product is installed */\n isProductInstalled(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get version */\n get(\n id: string\n ): Promise<ProductVersion | undefined>\n\n /** Install app from Hailer market */\n install(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get installed version */\n getInstalledVersion(id: string): Promise<Version>\n\n /** Get manifest content from Hailer market */\n getManifest(id: string): Promise<any>\n };\n\n constructor(private client: Client) {\n this.product = {\n isProductInstalled: this.isProductInstalled.bind(this),\n get: this.get.bind(this),\n install: this.install.bind(this),\n getInstalledVersion: this.getInstalledVersion.bind(this),\n getManifest: this.getManifest.bind(this),\n };\n }\n\n config = {\n update: async (config: Config, option?: { appId?: string }): Promise<void> => {\n try {\n return await this.client.requestAsync('app.config.update', [config, ...option ? [option] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n\n /**\n * Check if product is installed\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async isProductInstalled(productId: string, workspaceId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('app.product.isProductInstalled', [productId, workspaceId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get version\n *\n * @param id targetId\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async get(\n id: string\n ): Promise<ProductVersion | undefined> {\n try {\n return await this.client.requestAsync('app.product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Install app from Hailer market\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace where the product will be installed\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async install(productId: string, workspaceId: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('app.product.install', [productId, workspaceId]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get installed version from Hailer market\n *\n * @param id Id of product in Hailer market\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getInstalledVersion(id: string): Promise<Version> {\n try {\n const result = await this.client.requestAsync('app.product.getInstalledVersion', [id]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get manifest content from Hailer market\n *\n * @param id target Id\n *\n * @returns Manifest content\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getManifest(id: string): Promise<any> {\n try {\n return await this.client.requestAsync('app.product.getManifest', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, InsightData, InsightDoc, InsightQueryResult, InsightSource } from '../types';\n\nexport class InsightApi {\n constructor(private client: Client) {}\n\n /**\n * Get Insight data\n *\n * @param insightId the id of the Insight the data is fetched from\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async data(insightId: string, options: { update?: true }): Promise<InsightData> {\n\n try {\n /*data = [{ insightId, { headers, rows, time } }] */\n return await this.client.requestAsync('insight.data', [insightId, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get Insight data\n *\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<InsightDoc[]> {\n try {\n return await this.client.requestAsync('insight.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get Insight data\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(insightId: string, update: Partial<InsightDoc>): Promise<InsightDoc[]> {\n try {\n return await this.client.requestAsync('insight.update', [insightId, update]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Run an ad-hoc query against Insight sources\n *\n * @param workspaceId the workspace to query within\n * @param sources the Insight sources to query\n * @param query the query string\n *\n * @returns query result with headers, rows, and details\n *\n * @throws {HailerError} if request is incorrect\n */\n async query(workspaceId: string, sources: InsightSource[], query: string): Promise<InsightQueryResult> {\n try {\n return await this.client.requestAsync('insight.query', [workspaceId, { sources, query }]);\n } catch (error: unknown) {\n throw new HailerError(error as { code: number; msg: string; debug: object });\n }\n }\n}\n\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, PermissionMap } from '../types';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class PermissionApi {\n\n constructor(private client: Client) {}\n\n /**\n * Returns the user's permission map.\n *\n * For personal apps (no cid):\n * - With workspaceId: returns permissions for that specific workspace,\n * fetching from the backend if not yet loaded.\n * - Without workspaceId: returns all currently loaded permissions.\n *\n * For workspace apps (has cid):\n * - Always returns permissions scoped to the app's workspace,\n * if workspaceId is provided and it's not equal to the app's `cid`, it will throw an error.\n *\n * @param options.workspaceId - Optional workspace ID to scope permissions to (personal apps only)\n *\n * @returns Permission map keyed by workspace ID\n *\n * @throws {HailerError} if the request fails\n */\n map = async({ workspaceId }: { workspaceId?: string } = {}): Promise<PermissionMap> => {\n try {\n return await this.client.requestAsync('permission.map', workspaceId ? [{ workspaceId }] : []);\n } catch (error: any) {\n console.log('Failed to read permissions from Hailer, error:', error);\n throw new HailerError(error);\n }\n };\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, Product, ProductSearchOption, ProductSearchFilter, ProductListResponse } from '../types';\n\nexport class ProductApi {\n constructor(private client: Client) {}\n\n /**\n * Lists products from Hailer market\n *\n * @param filter ProductSearchFilter\n * @param options ProductSearchOption\n *\n * @returns List of products in Hailer market filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(\n filter?: ProductSearchFilter,\n options?: ProductSearchOption): Promise<ProductListResponse> {\n try {\n const res = await this.client.requestAsync('product.list', [filter, options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets single product from Hailer market\n *\n * @param id Product Id\n *\n * @returns Single product from Hailer market or undefined if no product found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(id: string): Promise<Product | undefined> {\n try {\n return await this.client.requestAsync('product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates product in Hailer market\n *\n * @param targetId link to targetId (version)\n * @param name Name of the product\n * @param description Description what this product is doing\n * @param icon Icon id for the product\n * @param images List of fileIds for showing pictures of the product\n * @param externalUrl Public URL for creator to show more information about the product\n * @param publisher Publisher (author)\n * @param type App, template, music etc.\n *\n * @returns Created product in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(\n product: {\n targetId?: string,\n name: string,\n description?: string,\n icon?: string,\n images?: string[],\n externalUrl?: string,\n publisher?: string,\n type?: string\n }\n ): Promise<Product> {\n try {\n const result = await this.client.requestAsync('product.create', [product]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates product in Hailer market\n *\n * @param id Id of product in Hailer market\n * @param name Name of the product\n * @param description Description what this product is doing\n * @param icon Icon id for the product\n * @param images List of fileIds for showing pictures of the product\n * @param externalUrl Public URL for creator to show more information about the product\n * @param publisher Publisher (Author)\n * @param public: Visible or not in Hailer market\n * @param type App, template, music etc.\n *\n * @returns Updated product in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(\n id: string,\n product: {\n name?: string,\n description?: string,\n icon?: string,\n images?: string[],\n externalUrl?: string,\n publisher?: string,\n public?: boolean,\n type?: string\n }\n ): Promise<Product> {\n try {\n const result = await this.client.requestAsync('product.update', [id, product]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Remove product from Hailer market\n *\n * @param id Id of product in Hailer market\n *\n * @returns true, if removed\n *\n * @throws {HailerError} if request is incorrect\n */\n async remove(id: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('product.remove', [id]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Set product as public or not (visible) in Hailer market\n *\n * @param id Id of product in Hailer market\n * @param isPublic Visible or not in Hailer market\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n async setPublic(\n id: string,\n isPublic: boolean\n ): Promise<boolean> {\n try {\n return await this.client.requestAsync('product.setPublic', [id, isPublic]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport {\n HailerError,\n PricingData,\n CreatePricingRequest,\n UpdatePricingRequest,\n CreatePurchaseRequest,\n CreatePurchaseResponse,\n Purchase,\n StripeTaxCalculationRequest,\n StripeTaxCalculationResponse\n} from '../types';\n\nexport class Payment {\n constructor(private client: Client) {}\n\n /**\n * Creates pricing configuration for a product\n *\n * @param request CreatePricingRequest containing productId, types, and providers\n *\n * @returns Created pricing configuration\n *\n * @throws {HailerError} if request is incorrect or product not found\n */\n async createPricing(request: CreatePricingRequest): Promise<PricingData> {\n try {\n const res = await this.client.requestAsync('payment.createPricing', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates pricing configuration for a product\n *\n * @param request UpdatePricingRequest containing productId, types, and providers\n *\n * @returns Updated pricing configuration\n *\n * @throws {HailerError} if request is incorrect, product not found, or pricing doesn't exist\n */\n async updatePricing(request: UpdatePricingRequest): Promise<PricingData> {\n try {\n const res = await this.client.requestAsync('payment.updatePricing', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets pricing configuration for a product\n *\n * @param productId Product ID to get pricing for\n *\n * @returns Pricing configuration or null if not found\n *\n * @throws {HailerError} if request is incorrect or product not found\n */\n async getPricing(productId: string): Promise<PricingData | null> {\n try {\n const res = await this.client.requestAsync('payment.getPricing', [{ productId }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates a product purchase/subscription\n *\n * @param request CreatePurchaseRequest containing productId, workspaceId, and planType\n *\n * @returns Purchase creation result with status and details\n *\n * @throws {HailerError} if request is incorrect, product not found, or payment fails\n */\n async createPurchase(request: CreatePurchaseRequest): Promise<CreatePurchaseResponse> {\n try {\n const res = await this.client.requestAsync('payment.createPurchase', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets purchases for a workspace\n *\n * @param workspaceId Workspace ID to get purchases for\n *\n * @returns Array of purchases for the workspace\n *\n * @throws {HailerError} if request is incorrect or workspace not found\n */\n async getPurchases(workspaceId: string): Promise<Purchase[]> {\n try {\n const res = await this.client.requestAsync('payment.getPurchases', [{ workspaceId }]);\n return res || [];\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Calculates Stripe tax for line items\n *\n * @param request StripeTaxCalculationRequest containing workspaceId and lineItems\n *\n * @returns Tax calculation result with amounts, rates, and country information\n *\n * @throws {HailerError} if request is incorrect, workspace not found, or Stripe customer not found\n */\n async calculateStripeTax(request: StripeTaxCalculationRequest): Promise<StripeTaxCalculationResponse> {\n try {\n const res = await this.client.requestAsync('payment.calculateStripeTax', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}", "import { Client } from '@wishcore/wish-rpc';\nimport {\n HailerError,\n AdminWorkspaceListRequest,\n AdminWorkspaceListResponse,\n AdminWorkspace,\n AdminCreateStripeSessionRequest,\n AdminCreateStripeSessionResponse,\n AdminCreateInvoiceIntegrationRequest,\n AdminCreateInvoiceIntegrationResponse,\n AdminUpdateWorkspaceSubscriptionRequest,\n AdminUpdatePurchasePriceRequest,\n AdminWorkspaceUsersListRequest,\n AdminWorkspaceUsersListResponse,\n AdminUpdateUserRequest,\n AdminUpdateUserResponse,\n AdminTokenTransactionsListRequest,\n AdminTokenTransactionsListResponse,\n AdminUpdateOverridesRequest,\n AdminUpdateMarketplaceSettingsRequest,\n AdminInvoiceListRequest,\n AdminInvoiceListResponse,\n AdminInvoiceUpdateHandledRequest,\n AdminInvoiceUpdateHandledResponse,\n AdminRevenueListRequest,\n AdminRevenueListResponse,\n AdminDashboardStatisticsResponse,\n AdminDashboardTrendsResponse,\n AdminReferralCodeListRequest,\n AdminReferralCodeListResponse,\n AdminReferralEventListRequest,\n AdminReferralEventListResponse\n} from '../types';\n\nexport class Admin {\n constructor(private client: Client) {}\n\n /**\n * Referral management endpoints\n */\n public referral = {\n /**\n * Lists all referral codes with optional filters\n */\n listCodes: async (request?: AdminReferralCodeListRequest): Promise<AdminReferralCodeListResponse> => {\n try {\n const res = await this.client.requestAsync('admin.referral.listCodes', [request?.filter || null, request?.options || null]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Lists referral events with optional filters\n */\n listEvents: async (request?: AdminReferralEventListRequest): Promise<AdminReferralEventListResponse> => {\n try {\n const res = await this.client.requestAsync('admin.referral.listEvents', [request?.filter || null, request?.options || null]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Updates a referral code's bonus amount or active status\n */\n updateCode: async (codeId: string, updates: { bonusTokens?: number; isActive?: boolean }): Promise<boolean> => {\n try {\n const res = await this.client.requestAsync('admin.referral.updateCode', [{ codeId, ...updates }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n\n /**\n * Lists workspaces with search, pagination, and sorting\n *\n * @param request AdminWorkspaceListRequest containing filter and options\n *\n * @returns List of workspaces with total count\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listWorkspaces(request?: AdminWorkspaceListRequest): Promise<AdminWorkspaceListResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets detailed information about a specific workspace\n *\n * @param workspaceId The ID of the workspace to retrieve\n *\n * @returns Workspace details including payment information\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async getWorkspace(workspaceId: string): Promise<AdminWorkspace> {\n try {\n const res = await this.client.requestAsync('admin.workspace.get', [workspaceId]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates a Stripe checkout session for workspace subscription\n *\n * @param request AdminCreateStripeSessionRequest containing workspace details and payment info\n *\n * @returns AdminCreateStripeSessionResponse with success status and session URL\n *\n * @throws {HailerError} if request fails, user not authorized, or workspace already has subscription\n */\n async createStripeSession(request: AdminCreateStripeSessionRequest): Promise<AdminCreateStripeSessionResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.createStripeSession', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates an invoice integration for workspace subscription\n *\n * @param request AdminCreateInvoiceIntegrationRequest containing workspace details and payment info\n *\n * @returns AdminCreateInvoiceIntegrationResponse with success status\n *\n * @throws {HailerError} if request fails, user not authorized, or workspace already has subscription\n */\n async createInvoiceIntegration(request: AdminCreateInvoiceIntegrationRequest): Promise<AdminCreateInvoiceIntegrationResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.createInvoiceIntegration', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace subscription billing information\n *\n * @param request AdminUpdateWorkspaceSubscriptionRequest containing purchase ID and new billing details\n *\n * @returns boolean indicating whether the update was successful\n *\n * @throws {HailerError} if request fails, user not authorized, or purchase not found\n */\n async updateWorkspaceSubscription(request: AdminUpdateWorkspaceSubscriptionRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateSubscription', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates purchase price for active invoice products\n *\n * @param request AdminUpdatePurchasePriceRequest containing purchase ID, workspace ID, and new price\n *\n * @returns boolean indicating whether the update was successful\n *\n * @throws {HailerError} if request fails, user not authorized, purchase not found, or not an invoice product\n */\n async updatePurchasePrice(request: AdminUpdatePurchasePriceRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.purchase.updatePrice', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists users in a workspace with search, filtering, pagination, and sorting\n * If no workspaceId provided, lists all users across all workspaces\n *\n * @param request AdminWorkspaceUsersListRequest containing optional workspace ID, filter and options\n *\n * @returns List of workspace users with total count and role information\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async listWorkspaceUsers(request: AdminWorkspaceUsersListRequest): Promise<AdminWorkspaceUsersListResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.listUsers', [request.workspaceId, request.filter, request.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates a user's information (currently supports email verification only)\n *\n * @param request AdminUpdateUserRequest containing user ID and updates\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, user not found, or user not authorized\n */\n async updateUser(request: AdminUpdateUserRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.user.update', [request.userId, request.updates]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace token balance\n *\n * @param request Object containing workspaceId, tokenAmount, and optional payout parameters\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateTokenBalance(request: {\n workspaceId: string;\n tokenAmount: number;\n payoutMonth?: number;\n payoutYear?: number;\n payoutType?: 'admin_bonus' | 'creator_payout';\n creatorPercent?: number;\n }): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateTokenBalance', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace license overrides\n *\n * @param request AdminUpdateOverridesRequest containing workspaceId and overrides object\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateWorkspaceOverrides(request: AdminUpdateOverridesRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateOverrides', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace marketplace settings\n *\n * @param request AdminUpdateMarketplaceSettingsRequest containing workspaceId and settings\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateWorkspaceMarketplaceSettings(request: AdminUpdateMarketplaceSettingsRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateMarketplaceSettings', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists token transactions with filtering, pagination, and statistics\n *\n * @param request AdminTokenTransactionsListRequest containing optional filter and pagination options\n *\n * @returns AdminTokenTransactionsListResponse with transactions, total count, and statistics\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listTokenTransactions(request?: AdminTokenTransactionsListRequest): Promise<AdminTokenTransactionsListResponse> {\n try {\n const res = await this.client.requestAsync('admin.tokenTransaction.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists Hailer invoice purchases with filtering, pagination, and workspace grouping\n *\n * @param request AdminInvoiceListRequest containing optional filter and pagination options\n *\n * @returns AdminInvoiceListResponse with invoices, total count, and workspace groups\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listInvoices(request?: AdminInvoiceListRequest): Promise<AdminInvoiceListResponse> {\n try {\n const res = await this.client.requestAsync('admin.invoice.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates the handled status for one or more Hailer invoice purchases\n *\n * @param request AdminInvoiceUpdateHandledRequest containing purchase ID(s) and handled status\n *\n * @returns AdminInvoiceUpdateHandledResponse with count of updated records\n *\n * @throws {HailerError} if request fails, purchase not found, or not a Hailer invoice purchase\n */\n async updateInvoiceHandled(request: AdminInvoiceUpdateHandledRequest): Promise<AdminInvoiceUpdateHandledResponse> {\n try {\n const res = await this.client.requestAsync('admin.invoice.updateHandled', [request.purchaseIds, request.handled]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Links a subscription purchase to its activity\n *\n * @param purchaseId The purchase to update\n * @param subscriptionActivityId The activity id to associate with the subscription\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async setSubscriptionActivityId(purchaseId: string, subscriptionActivityId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('admin.invoice.setSubscriptionActivityId', [purchaseId, subscriptionActivityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists revenue for a given month with optional filtering and pagination\n *\n * @param request AdminRevenueListRequest containing month, year, and optional filter/options\n *\n * @returns AdminRevenueListResponse with revenue rows and totals\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listMonthlyRevenue(request: AdminRevenueListRequest): Promise<AdminRevenueListResponse> {\n try {\n const res = await this.client.requestAsync('admin.revenue.list', [\n request.month,\n request.year,\n request.filter,\n request.options\n ]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets dashboard statistics including counts for users, workspaces, activities, and messages\n * Includes today's count, total count, last week count, and week-over-week growth percentage\n *\n * @param entities Optional array of entity types to fetch. Defaults to all entities.\n * Valid values: 'users', 'workspaces', 'activities', 'messages', 'userMessages'\n *\n * @returns AdminDashboardStatisticsResponse with statistics for requested entity types\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async getDashboardStatistics(entities?: string[]): Promise<AdminDashboardStatisticsResponse> {\n try {\n const res = await this.client.requestAsync('admin.dashboard.statistics', [entities]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets dashboard trends showing daily creation counts over time\n *\n * @param days Number of days to fetch (30, 90, 180, or 365). Defaults to 30.\n * @param entities Optional array of entity types to fetch. Defaults to ['users', 'workspaces'].\n * Valid values: 'users', 'workspaces'\n *\n * @returns AdminDashboardTrendsResponse with daily counts for requested entity types\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async getDashboardTrends(days?: 30 | 90 | 180 | 365, entities?: string[]): Promise<AdminDashboardTrendsResponse> {\n try {\n const res = await this.client.requestAsync('admin.dashboard.trends', [days, entities]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError } from '../types';\n\nexport interface MetricDefinition {\n id: string;\n name: string;\n description: string;\n category: string;\n supportsTimeRange: boolean;\n supportsBreakdown: boolean;\n}\n\nexport interface MetricData {\n /** Current scalar value (when not grouped into a series) */\n value?: number;\n /** Labels attached to the value */\n labels?: Record<string, string>;\n /** One series per group, each a list of { timestamp, value } */\n timeSeries?: Array<{\n labels: Record<string, string>;\n values: Array<{ timestamp: number; value: number }>;\n }>;\n /** Set if this metric failed */\n error?: boolean;\n /** Failure detail */\n errorMessage?: string;\n}\nexport interface MetricOptions {\n workspaceId?: string;\n userId?: string;\n timeRange?: {\n start: number;\n end: number;\n };\n interval?: '1m' | '5m' | '15m' | '30m' | '1h' | '5h';\n\n // Query Builder options (optional)\n /** Aggregation function to apply */\n aggregation?: 'sum' | 'avg' | 'max' | 'min' | 'count' | 'rate' | 'increase';\n\n /** Group results by specified labels (max 3). Allowed: userId, userRole, workspaceId, teamId, processId, workflowId, discussionId, activityId, signal, type */\n groupBy?: string[];\n\n /** Limit results to top N values (1-100) */\n topk?: number;\n\n /** Additional label filters. Allowed keys: userId, userRole, workspaceId, teamId, processId, workflowId, discussionId, activityId, signal, type */\n labelFilters?: Record<string, string>;\n}\n\nexport interface WorkspaceMetricsListOptions {\n /** Array of workspace IDs to look up */\n workspaceIds?: string[];\n /** Search by workspace name (minimum 3 characters) */\n name?: string;\n}\n\nexport type WorkspaceMetricsListResult = Array<{\n _id: string;\n name: string;\n}>;\n\nexport interface UserMetricsListOptions {\n /** Array of user IDs to look up */\n userIds: string[];\n}\n\nexport type UserMetricsListResult = Array<{\n _id: string;\n name?: string;\n email: string;\n}>;\n\nexport class MetricsApi {\n constructor(private client: Client) {}\n\n /**\n * Get list of available metrics for current user based on permissions\n * @returns Array of metric IDs or detailed metric definitions\n */\n async list(): Promise<string[] | MetricDefinition[]> {\n try {\n return await this.client.requestAsync('metrics.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get metrics data with optional Query Builder\n * @param metricTypes Single metric or array of metrics to fetch\n * @param options Optional filtering, time range, and Query Builder options\n * @returns Array of metric data, one entry per requested metric (in request order)\n *\n * @example\n * // Simple query\n * await api.metrics.get('hailer.activity.create', { workspaceId: 'abc123' });\n *\n * @example\n * // Query Builder: Top 10 users by activity\n * await api.metrics.get('hailer.activity.create', {\n * workspaceId: 'abc123',\n * timeRange: { start: Date.now() - 86400000, end: Date.now() },\n * aggregation: 'sum',\n * groupBy: ['user'],\n * topk: 10\n * });\n */\n async get(metricTypes: string | string[], options?: MetricOptions): Promise<MetricData[]> {\n try {\n // Backend expects array, convert string to array if needed\n const metricsArray = Array.isArray(metricTypes) ? metricTypes : [metricTypes];\n return await this.client.requestAsync('metrics.get', [metricsArray, options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Admin endpoints for metrics management\n */\n admin = {\n /**\n * Get list of workspaces for admin metrics filtering\n * @param options Lookup by workspaceIds array or name search (min 3 chars)\n * @returns List of workspaces\n *\n * @example\n * // Look up by workspace IDs\n * await api.metrics.admin.workspacesList({ workspaceIds: ['id1', 'id2'] });\n *\n * @example\n * // Search by workspace name\n * await api.metrics.admin.workspacesList({ name: 'Sales' });\n */\n workspacesList: async (options: WorkspaceMetricsListOptions): Promise<WorkspaceMetricsListResult> => {\n try {\n return await this.client.requestAsync('metrics.workspaceSearch', [options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Get list of users for admin metrics filtering\n * @param options Lookup by userIds array\n * @returns List of users with _id, name, email\n *\n * @example\n * // Look up by user IDs\n * await api.metrics.admin.usersList({ userIds: ['id1', 'id2'] });\n */\n usersList: async (options: UserMetricsListOptions): Promise<UserMetricsListResult> => {\n try {\n return await this.client.requestAsync('metrics.userList', [options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport interface HTTPFetchOptions {\n method?: string;\n headers?: Record<string, string>;\n body?: string;\n}\n\nexport interface HTTPUploadEntry {\n /** Form field name */\n name: string;\n /** Value: plain string for fields, base64 string for files */\n value: string;\n /** When present, entry is a file with this filename (value is base64) */\n filename?: string;\n}\n\nexport interface HTTPFetchResponse {\n status: number;\n statusText: string;\n headers: Record<string, string>;\n body: string;\n}\n\n/**\n * Events emitted by the parent frame for a HTTP WebSocket connection.\n */\ninterface HTTPWsEvent {\n connectionId: string;\n event: 'open' | 'message' | 'close' | 'error';\n data?: string;\n code?: number;\n reason?: string;\n}\n\n/**\n * A WebSocket-like object that proxies through the parent Hailer frame.\n */\nexport class HTTPWebSocket {\n public onopen: ((event: any) => void) | null = null;\n public onmessage: ((event: { data: string }) => void) | null = null;\n public onclose: ((event: { code?: number; reason?: string }) => void) | null =\n null;\n public onerror: ((event: any) => void) | null = null;\n public readyState: number = WebSocket.CONNECTING;\n\n public connectionId: string | null = null;\n\n constructor(\n private client: Client,\n url: string,\n ) {\n // Open a streaming RPC request \u2014 callback fires for each WS event from parent\n this.client.request(\n 'http.ws.open',\n [url],\n (error: any, data: HTTPWsEvent) => {\n if (error) {\n this.readyState = WebSocket.CLOSED;\n this.onerror?.({ error });\n return;\n }\n\n if (!data) {\n return;\n }\n\n // Store connectionId from first event\n if (data.connectionId && !this.connectionId) {\n this.connectionId = data.connectionId;\n }\n\n switch (data.event) {\n case 'open':\n this.readyState = WebSocket.OPEN;\n this.onopen?.({});\n break;\n case 'message':\n this.onmessage?.({ data: data.data ?? '' });\n break;\n case 'close':\n this.readyState = WebSocket.CLOSED;\n this.onclose?.({ code: data.code, reason: data.reason });\n break;\n case 'error':\n this.onerror?.({ error: data.data });\n break;\n }\n },\n );\n }\n\n send(data: string): void {\n if (this.readyState !== WebSocket.OPEN || !this.connectionId) {\n throw new Error('WebSocket is not open');\n }\n this.client\n .requestAsync('http.ws.send', [this.connectionId, data])\n .catch((error) => {\n this.onerror?.({ error });\n });\n }\n\n close(code?: number, reason?: string): void {\n if (this.connectionId) {\n this.client\n .requestAsync('http.ws.close', [this.connectionId, code, reason])\n .catch((error) => {\n this.onerror?.({ error });\n });\n }\n this.readyState = WebSocket.CLOSING;\n }\n}\n\n/**\n * Proxy module for making authenticated HTTP and WebSocket requests\n * through the parent Hailer frame.\n */\nexport class HttpApi {\n constructor(private client: Client) {}\n\n /**\n * Make an HTTP request through the parent frame.\n * The parent's browser context sends the hlrkey cookie automatically.\n */\n async fetch(\n url: string,\n options?: HTTPFetchOptions,\n ): Promise<HTTPFetchResponse> {\n return this.client\n .requestAsync('http.fetch', [url, options])\n .catch((error) => {\n throw error;\n });\n }\n\n /**\n * Upload files through the parent frame as multipart/form-data.\n * Files are sent as base64 strings and reconstructed into FormData by the parent.\n * The parent's browser context sends the hlrkey cookie automatically.\n */\n async upload(\n url: string,\n entries: HTTPUploadEntry[],\n ): Promise<HTTPFetchResponse> {\n return this.client\n .requestAsync('http.upload', [url, entries])\n .catch((error) => {\n throw error;\n });\n }\n\n /**\n * Open a WebSocket connection through the parent frame.\n * Returns a HTTPWebSocket that mimics the native WebSocket API.\n */\n openWebSocket(url: string): HTTPWebSocket {\n return new HTTPWebSocket(this.client, url);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport {\n CredentialCreateResponse,\n CredentialData,\n CredentialDetails,\n CredentialListItem,\n CredentialType,\n CredentialUpdate,\n HailerError,\n} from '../types';\n\n/**\n * Securely store and retrieve credentials \u2014 API keys, username/password pairs,\n * or any custom key-value secret.\n *\n * Every operation is scoped to credentials bound to your app: the host tags each\n * credential you create with your app's id and re-checks that tag on every read\n * and write, so you can never reach another app's credentials. Credentials\n * created through the SDK are always **personal** \u2014 visible only to the acting\n * user \u2014 and cannot be deleted through the SDK.\n *\n * A workspace app additionally sees, in `list`, the workspace credentials tagged\n * with it that the acting user may read, and can `get` them; those cannot be\n * modified through the SDK.\n *\n * `credential.get` returns the decrypted payload directly \u2014 there is no token\n * exchange.\n */\nexport class CredentialApi {\n constructor(private client: Client) {}\n\n /**\n * Store a new encrypted credential. The credential is personal (owner-only)\n * and is automatically bound to your app \u2014 the host forces the app\n * association and drops any workspace or reader association.\n *\n * @throws {HailerError} if the request fails or the caller lacks permission\n */\n async create(\n name: string,\n type: CredentialType,\n secret: CredentialData,\n ): Promise<CredentialCreateResponse> {\n try {\n return await this.client.requestAsync('credential.create', [{ name, type, secret }]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * List your app's credentials. Encrypted fields are never returned. Results\n * are always scoped to credentials bound to your app.\n */\n async list(): Promise<CredentialListItem[]> {\n try {\n return await this.client.requestAsync('credential.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Fetch and decrypt one of your app's credentials. The plaintext payload is\n * returned directly in the RPC response \u2014 no token exchange.\n */\n // eslint-disable-next-line @typescript-eslint/naming-convention\n async get<T extends CredentialData = CredentialData>(\n credentialId: string,\n ): Promise<CredentialDetails<T>> {\n try {\n return await this.client.requestAsync('credential.get', [credentialId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Rename or rotate the secret of one of your app's personal credentials. At\n * least one field must be provided in `updates`, and `secret` replaces the\n * entire stored payload \u2014 there is no key-level merge. Workspace\n * credentials cannot be updated through the SDK.\n */\n async update(credentialId: string, updates: CredentialUpdate): Promise<boolean> {\n try {\n return await this.client.requestAsync('credential.update', [credentialId, updates]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n"],
5
- "mappings": "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",
6
- "names": ["Client", "write", "opts", "msg", "end", "id", "request", "retval", "err", "op", "args", "resolve", "reject", "data", "cb", "exports", "debug", "Server", "methods", "i", "j", "o", "path", "prefix", "ip", "e", "args", "context", "cb", "result", "copy", "s", "filter", "d", "clientId", "msg", "respond", "id", "err", "data", "op", "client", "send", "ctx", "reqCtx", "exports", "__exportStar", "exports", "import_wish_rpc", "CustomError", "message", "code", "HailerError", "error", "UserApi", "client", "userId", "error", "HailerError", "Kanban", "client", "processId", "options", "error", "HailerError", "activityId", "priority", "Ball", "client", "activityId", "toUserId", "error", "HailerError", "discussionIds", "ActivityApi", "client", "Kanban", "Ball", "processId", "phaseId", "options", "error", "HailerError", "activityId", "workflowId", "activities", "requests", "WorkspaceApi", "client", "error", "HailerError", "name", "template", "id", "workspaceId", "productId", "TeamApi", "client", "error", "HailerError", "noSuchMethod", "fileReaders", "workspaceId", "teamId", "userId", "FileApi", "client", "fileId", "error", "HailerError", "file", "filename", "options", "base64Data", "tags", "readers", "fileIds", "scope", "resolve", "reject", "reader", "Activity", "client", "activityId", "options", "processId", "activityIds", "Discussion", "client", "discussionId", "options", "Snackbar", "client", "text", "buttonLabel", "duration", "Files", "client", "file", "filename", "options", "resolve", "reject", "reader", "Workflow", "client", "workflowId", "fieldId", "Ui", "client", "Activity", "Discussion", "Snackbar", "Workflow", "workspaceId", "insightId", "Files", "DEFAULT_ALLOWED_URLS", "DEFAULT_BACKEND_URL", "publicBackendMap", "App", "options", "manifestFile", "location", "manifestUrl", "manifestContent", "appId", "Form", "options", "formsKey", "res", "HailerError", "formsData", "InsightPublicApi", "options", "insightKey", "res", "HailerError", "input", "data", "row", "object", "header", "headerIndex", "ProductPublicApi", "options", "filter", "res", "HailerError", "id", "HailerPublicApi", "options", "InsightPublicApi", "Form", "App", "ProductPublicApi", "WorkflowApi", "client", "error", "HailerError", "workflowId", "workflowSpec", "option", "AppApi", "client", "config", "option", "error", "HailerError", "productId", "workspaceId", "id", "InsightApi", "client", "insightId", "options", "error", "HailerError", "update", "workspaceId", "sources", "query", "PermissionApi", "client", "workspaceId", "error", "HailerError", "ProductApi", "client", "filter", "options", "error", "HailerError", "id", "product", "isPublic", "Payment", "client", "request", "error", "HailerError", "productId", "workspaceId", "Admin", "client", "request", "error", "HailerError", "codeId", "updates", "workspaceId", "purchaseId", "subscriptionActivityId", "entities", "days", "MetricsApi", "client", "options", "error", "HailerError", "metricTypes", "metricsArray", "HTTPWebSocket", "client", "url", "error", "data", "code", "reason", "HttpApi", "options", "entries", "CredentialApi", "client", "name", "type", "secret", "error", "HailerError", "credentialId", "updates", "HailerApi", "options", "allowedUrls", "DEFAULT_ALLOWED_URLS", "msg", "UserApi", "AppApi", "ActivityApi", "InsightApi", "WorkspaceApi", "TeamApi", "FileApi", "WorkflowApi", "PermissionApi", "HailerPublicApi", "Ui", "ProductApi", "Payment", "Admin", "MetricsApi", "HttpApi", "CredentialApi", "registerMessage", "DEFAULT_BACKEND_URL", "config", "error", "url", "event", "data", "publicBackendMap", "end"]
3
+ "sources": ["../node_modules/@wishcore/wish-rpc/src/rpc-client.ts", "../node_modules/@wishcore/wish-rpc/src/rpc-server.ts", "../node_modules/@wishcore/wish-rpc/src/index.ts", "../src/hailer-api.ts", "../src/types.ts", "../src/modules/user.ts", "../src/modules/activity/kanban.ts", "../src/modules/activity/ball.ts", "../src/modules/activity.ts", "../src/modules/workspace.ts", "../src/modules/team.ts", "../src/modules/file.ts", "../src/modules/ui/activity.ts", "../src/modules/ui/discussion.ts", "../src/modules/ui/snackbar.ts", "../src/modules/ui/files.ts", "../src/modules/ui/workflow.ts", "../src/modules/ui.ts", "../src/constants.ts", "../src/modules/public/app.ts", "../src/modules/public/form.ts", "../src/modules/public/insight.ts", "../src/modules/public/product.ts", "../src/modules/public.ts", "../src/modules/workflow.ts", "../src/modules/app.ts", "../src/modules/insight.ts", "../src/modules/permission.ts", "../src/modules/product.ts", "../src/modules/payment.ts", "../src/modules/admin.ts", "../src/modules/metrics.ts", "../src/modules/http.ts", "../src/modules/credential.ts", "../src/modules/action.ts"],
4
+ "sourcesContent": [null, null, null, "import { Client } from '@wishcore/wish-rpc';\nimport { UserApi } from './modules/user';\nimport { ActivityApi } from './modules/activity';\nimport { WorkspaceApi } from './modules/workspace';\nimport { TeamApi } from './modules/team';\nimport { FileApi } from './modules/file';\nimport { ApiInfo, Config, Settings, Signal } from './types';\nimport { Ui } from './modules/ui';\nimport { DEFAULT_ALLOWED_URLS, DEFAULT_BACKEND_URL, publicBackendMap } from './constants';\nimport { HailerPublicApi } from './modules/public';\nimport { WorkflowApi } from './modules/workflow';\nimport { AppApi } from './modules/app';\nimport { InsightApi } from './modules/insight';\nimport { PermissionApi } from './modules/permission';\nimport { ProductApi } from './modules/product';\nimport { Payment } from './modules/payment';\nimport { Admin } from './modules/admin';\nimport { MetricsApi } from './modules/metrics';\nimport { HttpApi } from './modules/http';\nimport { CredentialApi } from './modules/credential';\nimport { ActionApi } from './modules/action';\n\nexport interface Options {\n /** When connected is called the host is ready to receive calls */\n connected?: () => void;\n /** Callback when app is determined to be outside of Hailer, as a standalone app */\n outside?: (config?: any) => void;\n /** Callback on errors, defaults to printing errors in console */\n error?: (error: Error) => void;\n /** Callback called on app init and when permissions have changed */\n permissions?: () => void;\n /** Callback called on app init and when settings have changed */\n settings?: (data: Settings) => void;\n /** Callback called on app init and when config has changed */\n config?: (config: any) => void;\n /** Will be called each time a subscribed signal is emitted from Hailer frontend. To subscribe to signals, add them to options.subscribedSignals[] */\n signals?: (signal: Signal) => void;\n /** Urls the sdk is allowed to connect to. Defaults to all Hailer instances*/\n allowedUrls?: string[];\n /** Public backend Api url. Defaults to https://api.hailer.com */\n publicBackendUrl?: string;\n}\n\nexport class HailerApi {\n public user: UserApi;\n public app: AppApi;\n public activity: ActivityApi;\n public insight: InsightApi;\n public workspace: WorkspaceApi;\n public team: TeamApi;\n public file: FileApi;\n public workflow: WorkflowApi;\n public permission: PermissionApi;\n public product: ProductApi;\n public payment: Payment;\n public admin: Admin;\n public metrics: MetricsApi;\n /** HTTP proxy for making authenticated HTTP/WebSocket requests through the parent frame */\n public http: HttpApi;\n /** Securely store and retrieve credentials (API keys, username/password pairs, etc.) */\n public credential: CredentialApi;\n /** Trigger workspace actions and read back their runs */\n public action: ActionApi;\n /** All public endpoints, which can be accessed while not logged in to Hailer. */\n public public: HailerPublicApi;\n /** User interface commands */\n public ui: Ui;\n /** Url of the Hailer instance hosting the API */\n private hostUrl?: string;\n\n private appId?: string;\n /** If set it indicates that app is locked to a specific workspaceId */\n private workspaceId?: string;\n private client: Client;\n private config?: Config;\n private timer?: NodeJS.Timeout;\n /**\n * Hailer API state\n *\n * ```\n * true // outside hailer\n * false // logged into hailer\n * null // state not yet detected\n * ```\n */\n private outside: boolean | null = null;\n\n /**\n * Create a Hailer API client for inteacting with Hailer. **NOTE** This only works when inside Hailer.\n *\n * This should be run after window is initialized for example in ***onMount*** in Svelte or in ***useEffect*** in React\n */\n constructor(\n public options: Options = {}\n ) {\n const allowedUrls = options.allowedUrls ?? DEFAULT_ALLOWED_URLS;\n\n this.client = new Client(msg => {\n if (this.hostUrl) {\n parent.postMessage(JSON.stringify(msg), this.hostUrl);\n }\n });\n\n this.user = new UserApi(this.client);\n this.app = new AppApi(this.client);\n this.activity = new ActivityApi(this.client);\n this.insight = new InsightApi(this.client);\n this.workspace = new WorkspaceApi(this.client);\n this.team = new TeamApi(this.client);\n this.file = new FileApi(this.client);\n this.workflow = new WorkflowApi(this.client);\n this.permission = new PermissionApi(this.client);\n this.public = new HailerPublicApi(this.options);\n this.ui = new Ui(this.client);\n this.product = new ProductApi(this.client);\n this.payment = new Payment(this.client);\n this.admin = new Admin(this.client);\n this.metrics = new MetricsApi(this.client);\n this.http = new HttpApi(this.client);\n this.credential = new CredentialApi(this.client);\n this.action = new ActionApi(this.client);\n\n const registerMessage = JSON.stringify({ op: 'register', args: [{ appApiVersion: '2' }] });\n\n // If we are not in Iframe set location to outside, else wait 100ms for response to register to check if we are in Hailer\n if (window.location === window.parent.location) {\n // Pick a backend to use for public requests, unless it is set\n if (!this.options.publicBackendUrl) {\n this.options.publicBackendUrl = DEFAULT_BACKEND_URL;\n }\n\n this.public.app.config().then(config => {\n // CSM app assumes we are inside hailer when config is called... breaks the thing...\n // this.options.config?.(config);\n\n this.outside = true;\n this.options.outside?.(config);\n }).catch(error => {\n this.options.error?.(error);\n console.error('Failed to get app configuration in Public App.', error);\n });\n } else {\n // if in a frame, try register to Hailer by sending register to all allowed urls\n allowedUrls.forEach(url => parent.postMessage(registerMessage, url));\n this.timer = setTimeout(() => {\n this.outside = true;\n this.options.outside?.();\n }, 100);\n }\n\n this.createEventListener();\n }\n\n private createEventListener() {\n window.addEventListener('message', async event => {\n const data = event.data;\n\n try {\n const msg = JSON.parse(data);\n if (msg.op === 'register') {\n if (this.appId) {\n console.error('App Id is already set...! Are you using hot-reload?');\n return;\n }\n\n clearTimeout(this.timer);\n\n this.appId = msg.data.appId;\n this.workspaceId = msg.data.workspaceId;\n\n // Set host url now that we have a response\n this.hostUrl = event.origin;\n\n // Pick a backend to use for public requests, unless it is set\n if (!this.options.publicBackendUrl) {\n this.options.publicBackendUrl = publicBackendMap[this.hostUrl] || DEFAULT_BACKEND_URL;\n }\n\n // Register listeners for config and settings\n this.client.request('ui.settings', [], (error: any, data: Settings, end: boolean) => {\n if (error) {\n console.log('ui.settings error:', error, data);\n return;\n }\n\n this.options.settings?.(data);\n });\n\n this.client.request('config', [], (error: any, data: any, end: boolean) => {\n if (error) {\n console.log('config error:', error, data);\n return;\n }\n this.config = data;\n this.options.config?.(data);\n });\n\n // Register subscribed signals\n this.client.request('signal', [], (error: any, data: any, end: boolean) => {\n if (error) {\n console.log('signal error:', error, data);\n return;\n }\n\n // eslint-disable-next-line no-restricted-syntax\n if (!data) {\n return;\n }\n\n this.options.signals?.(data);\n\n // Permission-changing events re-fire the permissions callback\n // eslint-disable-next-line no-restricted-syntax\n if (typeof data.name === 'string' && data.name.startsWith('workspace.role.')) {\n this.options.permissions?.();\n }\n });\n\n this.outside = false;\n // Notify permissions on init, then call connected\n this.options.permissions?.();\n this.options.connected?.();\n return;\n }\n\n // bail out unless appId is set, as the app is not properly registered\n if (!this.appId) {\n return;\n }\n\n this.client.messageReceived(msg);\n } catch (error) {\n console.log('Dropped invalid JSON message');\n }\n });\n }\n\n info(): ApiInfo {\n return {\n hostUrl: this.hostUrl,\n config: this.config,\n outside: this.outside,\n workspaceId: this.workspaceId,\n };\n }\n}\n", "export interface User {\n _id: string;\n firstname: string;\n lastname: string;\n // email: string;\n // lastSeen: number;\n // status?: string;\n // managedUser?: boolean;\n // removed?: number;\n // defaultProfilepic: string;\n}\n\n/* export interface Workspace {\n _id: string;\n name: string;\n members: string[];\n settings: {\n isolatedTeams?: boolean;\n defaultView: string;\n functionFieldVersion?: 1 | 2;\n color?: string;\n allowPublicCopy?: boolean;\n };\n license: object;\n invoicing?: any;\n propertyFields?: {\n [section: string]: {\n [field: string]: any;\n };\n };\n} */\nexport interface Workspace {\n _id: string;\n name: string;\n}\n\nexport interface Team {\n _id: string;\n name: string;\n}\n\nexport interface TeamsByWorkspace {\n [workspaceId: string]: Team[];\n}\n\nexport interface ActivityFieldRange {\n start: number;\n end: number;\n }\n\nexport interface ActivityFieldLink {\n _id: string;\n name: string;\n }\n\nexport interface ActivityFieldError {\n error?: string\n}\n\nexport type ActivityFieldValue = boolean | number | string | (ActivityFieldCountry & ActivityFieldError & ActivityFieldRange & ActivityFieldLink);\n\nexport type ActivityFieldUpdateValue = ActivityFieldValue | null;\n/*\nexport interface UserMap {\n [userId: string]: User;\n}\n\n*/\n\nexport interface ActivityFieldCountry {\n /** ISO 3166-1 alpha-2 (cca2) */\n code: string;\n}\nexport interface Activity {\n _id: string;\n process: string;\n teamAccount: TeamAccount // TODO: Convert in frontend\n created: number;\n uid: string;\n workspaceId: string;\n discussion: string;\n currentPhase: string;\n active?: boolean;\n history?: any[];\n name: string;\n followers?: string[];\n completePhases?: string[];\n location?: {\n type: 'point' | 'area' | 'polyline',\n label: string | null\n data: {\n lat: number\n lng: number\n }[]\n };\n fields?: {\n [fieldId: string]: ActivityFieldValue\n };\n // fields?: { [fieldId: string]: string | number };\n files?: any[];\n updated?: number;\n updatedBy?: string;\n priority?: number;\n sequence?: number\n}\n\nexport interface TeamAccount {\n account: string;\n team: string;\n}\n\nexport interface FormsData {\n files: string[];\n history: {\n\n 0: {\n [fieldId: string]: {\n value: any;\n };\n };\n };\n name: string;\n location?: boolean;\n uid?: string;\n}\nexport interface FormsResponse {\n name: string;\n description?: string;\n enableUnlinkedMode: boolean;\n enableAttachments: boolean;\n enableMapLocation: boolean;\n locationRequired: 1;\n phases: {\n _id: string;\n followers: [];\n name: string;\n description: string;\n uid: string;\n created: number;\n fields: string[];\n announcementFields: [];\n announcementRecipients: [];\n announcementFieldsOrder: [];\n isEndpoint: boolean;\n }[];\n phasesOrder: string[];\n fields: {\n [id: string]: {\n data: [];\n label: string;\n required: boolean;\n type: string;\n inviteToDiscussionOnChange: boolean;\n _id: string;\n created: number;\n updated: number;\n uid: string;\n functionEnabled: boolean;\n };\n };\n enableMessenger: boolean;\n publicForm: {\n enableMessaging: boolean;\n };\n fieldsOrder: [];\n}\n\nexport interface FormCreateResponse {\n key: string,\n creator: string,\n followers: string,\n active: boolean,\n enableMessaging: boolean,\n allowRead: boolean\n}\n\nexport interface InsightResponse {\n insight: {\n name: string\n },\n data: InsightResponseData\n}\n\nexport interface InsightResponseData {\n headers: string[],\n rows: [],\n time: number\n}\n\nexport interface Config {\n [fieldName: string]: string;\n}\n\nexport type WorkflowFieldType = (\n 'activitylink' |\n 'country' |\n 'date' |\n 'daterange' |\n 'datetime' |\n 'numeric' |\n 'numericunit' |\n 'teams' |\n 'text' |\n 'textarea' |\n 'textunit' |\n 'textpredefinedoptions' |\n 'time' |\n 'timerange' |\n 'datetimerange' |\n 'users' |\n 'linkedfrom' |\n 'subheader'\n);\n\nexport interface WorkflowField {\n _id: string;\n type: WorkflowFieldType;\n label: string;\n required: boolean;\n data: string[];\n functionEnabled: boolean;\n unit?: string;\n placeholder?: string;\n description?: string;\n editable?: boolean;\n functionVariables?: { [key: string]: any };\n key?: string;\n}\n\nexport interface DocumentTemplate {\n templateId?: string; // Valid ObjectId for regular templates, or non-ObjectId string for multi-pdf templates\n name: string;\n order?: number;\n}\n\nexport interface Workflow {\n _id: string;\n name: string;\n description?: string;\n fields: { [fieldId: string]: WorkflowField };\n fieldsOrder: string[];\n phases: { [phase_id: string]: WorkflowPhase };\n phasesOrder: string[];\n enablePredefinedName?: boolean;\n nameFunctionEnabled?: boolean;\n nameEditable?: boolean;\n enableMapLocation?: boolean;\n enableUnlinkedMode?: boolean;\n nameFieldPlaceHolderText?: string;\n order?: number;\n productInstalledId?: string;\n workspaceId: string;\n documentTemplates?: DocumentTemplate[];\n key?: string;\n /*\n defaultView: 'table' | 'kanban' | 'map' | 'calendar';\n fields: { [fieldId: string]: any };\n phasesRemoved: string[];\n members: any;\n updated: number;\n coverImage?: string;\n createNewLabel?: string;\n enableAddedField: boolean;\n enableLinkedAnnouncements?: boolean;\n enableMapLocation?: boolean;\n enableUnlinkedMode?: boolean;\n enableMessenger?: boolean;\n allowGuests?: boolean;\n enableGuestEditing?: boolean;\n enableModifiedField?: boolean;\n enableOwnerField?: boolean;\n enableOwnerTeamField?: boolean;\n ownerTeamFieldTitle?: string;\n enableUniqueName?: boolean;\n enablePreselectedTeam?: boolean;\n initPhaseDescription?: string;\n locationRequired?: boolean;\n nameColumnText?: string;\n nameFunction?: string;\n nameFunctionVariables?: any;\n personInCharge?: string;\n personInChargeLabel?: string;\n publicForm?: {\n key: string;\n active: boolean;\n creator: string;\n team_account: TeamAccount;\n followers: string;\n allowRead: boolean;\n enableMessaging?: boolean;\n }\n predefinedNamePrefix?: string;\n preselectedTeam?: TeamAccount;\n enableAttachments: boolean;\n nameFieldPlaceHolderText: string;\n order?: number;\n allowMultipleTags?: boolean;\n allowCustomTags?: boolean;\n requireFileTag?: boolean;\n color?: string;\n starred?: string[];\n isStarred?: boolean;\n createdActivities?: number;\n */\n}\n\nexport interface WorkflowPhase {\n _id: string;\n name: string;\n description?: string;\n fields?: string[];\n primaryDateField?: string;\n primaryNumericField?: string;\n uid?: string;\n created?: number;\n isEndpoint?: boolean;\n possibleNextPhase?: string[];\n possibleNextPhaseSettings?: { [phaseId: string]: { text?: string } };\n color?: string;\n key?: string;\n /*\n followers: string[];\n created: number;\n uid?: string;\n members?: any[]\n enableAnnouncement?: boolean,\n announcementFields?: string[];\n announcementRecipients?: string[];\n announcementFieldsOrder?: string[];\n announcementToOwner?: boolean;\n announcementToOwnerTeam?: boolean;\n isEndPoint?: boolean;\n possibleNextPhase?: string[];\n possibleNextPhaseSettings?: any;\n fieldOptions?: any;\n primaryNumericField?: string;\n webhooksEnabled?: boolean;\n webhookAdded?: boolean;\n webhookUpdated?: boolean;\n primaryDateField?: string | null | any;\n removed?: number;\n removedBy?: string;\n color?: string | null;\n */\n}\n/**\n * ```ts\n * { [templateId: string]: string }\n * ```\n */\nexport interface IdsMap {\n [templateId: string]: string;\n}\n\nexport type PermissionType = 'admin' | 'own' | 'ownteam' | 'any' | 'edit';\n\nexport interface Member {\n id: string;\n info: { [key: string]: string | number | boolean | null };\n permissions: PermissionType[];\n}\n\nexport type WorkflowPermission = 'admin' | 'any' | 'ownteam' | 'own' | 'guest' | 'none';\nexport type WorkflowPhasePermission = 'edit' | 'view' | 'none';\n\nexport interface PermissionPath {\n type: 'network' | 'user' | 'team' | 'group';\n id: string;\n permission: WorkflowPermission | WorkflowPhasePermission;\n};\n\nexport interface WorkflowPermissionMap {\n [workflowId: string]: {\n // hasAccess: boolean;\n isAdmin: boolean;\n permission: WorkflowPermission;\n permissions: PermissionPath;\n phases: {\n [phaseId: string]: {\n // name: string;\n // hasAccess: boolean;\n permission: WorkflowPhasePermission,\n permissions: PermissionPath[];\n restricted: boolean;\n }\n };\n teams: string[];\n\n }\n};\n\nexport interface WorkspaceRolesPermission {\n isAdmin: boolean;\n isOwner: boolean;\n isGuest: boolean;\n isInviter: boolean;\n isUser: boolean;\n // custom: roleSchema,\n};\n\nexport interface PermissionMap {\n [userId: string]: {\n workflow: WorkflowPermissionMap,\n workspace: WorkspaceRolesPermission,\n // calendar: calendarPermissionMapSchema,\n // insight: insightPermissionMapSchema,\n // app: appPermissionMapSchema,\n // teams: Joi.array().items(validTeamId),\n // permits: Joi.array().items(Joi.string()),\n },\n};\n\nexport interface InsightWorkflowSource {\n name: string;\n workflowId: string;\n fields: {\n name: string;\n fieldId?: string;\n /** Used for phaseLastMove meta */\n phaseId?: string;\n /** Activity information, like _id, created, phaseId etc. */\n meta?: string;\n }[];\n}\nexport interface InsightDoc {\n _id: string;\n name: string;\n /** Key for accessing Insight when set to public */\n publicKey?: string;\n presets: {\n version: 1;\n name: string | 'default';\n options: any;\n }[];\n /** To be used with SQLite if we want to.... */\n query?: string;\n sources: InsightWorkflowSource[];\n public: boolean;\n\n // members: Member[];\n // updated: number;\n /** User id of creator */\n // uid: string;\n // workspaceId: string;\n /** sandboxed javascript with access to all activities in given workflows */\n // function?: string;\n\n\n}\n\nexport type InsightPublic = Omit<InsightDoc, '_id'>;\n\n// These are separate so we can do different configs if necessary without it being a breaking change\nexport interface InsightData {\n headers: string[];\n rows: (string | number | null)[][];\n time: number;\n}\n\nexport interface InsightResponseAsObjectItem {\n [key: string]: any\n}\nexport type InsightResponseAsObjects = InsightResponseAsObjectItem[]\n\nexport type InsightSource = InsightWorkflowSource;\n\nexport interface InsightQueryResult {\n headers: string[];\n rows: (string | number | null)[][];\n /** Per-table breakdown of the temporary tables built from sources */\n details: {\n [tableName: string]: {\n headers: string[];\n rows: number;\n };\n };\n}\n\nexport interface KanbanListResponse {\n map: {\n [phaseId: string]: {\n activities: {\n _id: string,\n followers: string[],\n name: string,\n fields: { [key: string]: any }\n files: string[],\n primaryDateField: number,\n priority: number,\n }[]\n meta: {\n count: number,\n totalPrimaryNumericValue: number,\n primaryNumericFieldUnit: string | null\n }\n }\n }\n}\n\nexport interface KanbanLoadResponse {\n activity: {\n _id: string,\n followers: string[],\n name: string,\n fields: { [key: string]: any },\n files: string[],\n primaryDateField: number | null,\n priority: number,\n linkedFromCount: number\n },\n process: string,\n phase: string\n}\nexport interface ActivityListOptions {\n /** Workspace to resolve a workflow **key** in (keys are unique per workspace) */\n workspaceId?: string,\n sortBy?: 'name' | 'created' | 'updated' | 'following' | 'owner' | 'team' | 'completedOn' | 'priority',\n sortOrder?: 'asc' | 'desc',\n limit?: number,\n skip?: number,\n includeUsers?: boolean,\n includeTeams?: boolean,\n includeHistory?: boolean,\n filters?: any\n}\nexport interface ActivityCreateOptions {\n /** Workspace to resolve a workflow **key** in (keys are unique per workspace) */\n workspaceId?: string;\n teamId?: string;\n fileIds?: string[];\n followerIds?: string[];\n location?: {\n label?: string;\n type: 'area' | 'point' | 'polyline';\n data: [{ lat: number, lng: number }];\n };\n discussionId?: string;\n phaseId?: string;\n returnDocument?: boolean;\n}\n\n\n/** Simplistic syntax for add/remove/replace */\nexport interface IdSetUpdate {\n /** Clear all existing */\n '*'?: null,\n /** Add: true, Remove: null */\n [id: string]: true | null | undefined\n}\nexport interface ActivityLocation {\n data: {\n lat: number;\n lng: number;\n }[],\n label?: string;\n type: 'area' | 'point' | 'polyline';\n};\nexport interface ActivityUpdateOptions {\n fields?: ActivityFieldUpdateValue,\n teamId?: string,\n location?: ActivityLocation\n phaseId?: string,\n files?: IdSetUpdate,\n followers?: IdSetUpdate,\n};\n\nexport interface ActivityKanbanListOptions {\n filter: {\n user?: {\n uid: string;\n field: string;\n },\n account?: string;\n team?: string;\n dates?: {\n field: string;\n start: number;\n end: number;\n };\n },\n search?: string;\n limit?: number;\n skip?: number;\n phase?: string;\n includeUsers?: boolean;\n includeTeams?: boolean;\n}\n\nexport interface PrintRequest {\n activityId: string;\n /** Template ID for regular templates */\n templateId?: string;\n /** Template name for multi-pdf templates (when templateId is empty) */\n templateName?: string;\n /** Whether to save the PDF to the file system */\n savePdf?: boolean;\n}\n\nexport interface PrintOptions {\n /**\n * Open the generated document in the device's own viewer, where the host supports it.\n * Currently only the Hailer Android app does: the document is saved to Downloads and opened\n * in the system PDF viewer, where the user can print or share it. Elsewhere the document is\n * only returned, as without this option; check `openedNatively` in the response.\n */\n openNative?: boolean;\n}\n\nexport interface PrintResponse {\n filename: string;\n /** Base64-encoded document data */\n data: string;\n mimeType: string;\n /**\n * Only set when `openNative` was requested: `true` if the host handed the document to the\n * device's own viewer, `false` if it couldn't (web, iOS). Older Hailer versions leave it unset,\n * so treat anything but `true` as \"not opened\".\n */\n openedNatively?: boolean;\n}\n\nexport interface Settings {\n theme: 'light' | 'dark'\n preferredLanguages: string[];\n}\n\n// Action types\n\n/** One of actionId or key. workspaceId is optional, needed with a key in a private app. */\nexport interface ActionTriggerTarget {\n actionId?: string;\n key?: string;\n workspaceId?: string;\n}\n\n/** `queued` and `running` are in progress, the rest are final. */\nexport type ActionRunStatus =\n | 'queued'\n | 'running'\n | 'completed'\n | 'runtime_error'\n | 'timeout'\n | 'output_limit'\n | 'infra_error'\n | 'cancelled'\n | 'config_error'\n | 'denied';\n\nexport type ActionEvent =\n | 'manual'\n | 'phase.activity-created'\n | 'phase.activity-updated'\n | 'phase.activity-moved'\n | 'workspace.member-joined'\n | 'workspace.member-left'\n | 'schedule.run';\n\nexport const ACTION_RUN_ACTIVE_STATUSES: ActionRunStatus[] = ['queued', 'running'];\n\n/** One run of an action. Fields marked \"admins only\" are absent for other users. */\nexport interface ActionRun {\n _id: string;\n actionId: string;\n workspaceId: string;\n event: ActionEvent;\n /** Absent on scheduled runs */\n triggeredBy?: string;\n status: ActionRunStatus;\n exitCode?: number | null;\n /** Return value of `execute(input)` */\n output?: unknown;\n /** Detail for abnormal statuses */\n message?: string | null;\n wallTimeMs?: number | null;\n created: number;\n finishedAt?: number | null;\n /** Admins only */\n arguments?: string;\n /** Admins only */\n stdout?: string | null;\n /** Admins only */\n stderr?: string | null;\n /** Admins only */\n execRunId?: string | null;\n}\n\nexport type CredentialType = 'basic' | 'apiKey' | 'custom';\n\nexport interface CredentialBasicData {\n username: string;\n password: string;\n}\n\nexport interface CredentialApiKeyData {\n apiKey: string;\n}\n\n/** Any JSON-serialisable value that can live inside a `custom` secret. */\nexport type CredentialJsonValue =\n | string\n | number\n | boolean\n | null\n | CredentialJsonValue[]\n | { [key: string]: CredentialJsonValue };\n\n/**\n * Free-form secret for `custom` credentials \u2014 any JSON object with 1\u201350\n * top-level keys.\n */\nexport interface CredentialCustomData {\n [key: string]: CredentialJsonValue;\n}\n\nexport type CredentialData =\n | CredentialBasicData\n | CredentialApiKeyData\n | CredentialCustomData;\n\n/**\n * Reader entry granting access to a workspace credential. Credentials created\n * through the app SDK are personal and have no readers; readers only appear on\n * workspace credentials bound to your app and surfaced in `list`.\n */\nexport type CredentialReader = `network_${string}` | `team_${string}` | `user_${string}`;\n\nexport interface CredentialCreateResponse {\n _id: string;\n}\n\nexport interface CredentialListItem {\n _id: string;\n name: string;\n type: CredentialType;\n /** Set only on workspace credentials \u2014 absent on personal ones. */\n workspaceId?: string;\n /** The app the credential is bound to; always your own app's id. */\n appId?: string;\n /** Workspace credentials only. */\n readers?: CredentialReader[];\n createdBy: string;\n created: number;\n updated: number;\n}\n\nexport interface CredentialUpdate {\n name?: string;\n /** Replaces the entire stored payload \u2014 there is no key-level merge. */\n secret?: CredentialData;\n}\n\n/** Decrypted credential as returned by `credential.get`. */\n// eslint-disable-next-line @typescript-eslint/naming-convention\nexport interface CredentialDetails<T extends CredentialData = CredentialData> {\n type: CredentialType;\n secret: T;\n}\n\nexport interface ApiInfo {\n /** Url of the Hailer instance hosting the API */\n hostUrl?: string;\n config?: Config;\n outside: boolean | null;\n workspaceId?: string;\n}\n\nexport interface ApiError {\n code: number,\n msg: string,\n debug: object\n}\n\nclass CustomError extends Error {\n public msg: string;\n public code: number;\n\n constructor(message: string, code: number) {\n super(message);\n this.name = this.constructor.name;\n this.msg = message;\n this.code = code;\n Error.captureStackTrace?.(this, this.constructor);\n }\n}\n\nexport class HailerError extends CustomError {\n public debug: object;\n public details?: any;\n\n constructor(error: {code: number, msg: string, details?: any, debug: any}) {\n super(error.msg, error.code);\n\n this.details = error.details;\n this.debug = error.debug;\n }\n\n toString() {\n console.log('Going to log an error... ;-D');\n return `${super.toString()} \\nField: ${this.details}, ${this.debug}`;\n }\n}\n\nexport interface Signal {\n name: string;\n data: any;\n}\n\nexport interface Product extends ProductType {\n _id: string;\n targetId?: string;\n name: string;\n description?: string;\n icon?: string;\n images?: string[];\n externalUrl?: string;\n publisher?: string;\n ctaLabel: string;\n ctaLink: string;\n /** Available or not in app store */\n public?: boolean;\n cid?: string;\n uid: string;\n}\n\nexport interface ProductListResponse {\n products: Product[];\n totalCount: number;\n}\n\nexport interface ProductSearchOption {\n limit?: number,\n skip?: number,\n search?: string,\n reverse?: boolean,\n sortBy?: 'name' | 'created' | 'updated' | 'type',\n sortOrder?: 'asc' | 'desc'\n}\n\nexport interface ProductSearchFilter extends ProductType {\n public?: boolean,\n cid?: string,\n uid?: string,\n}\n\nexport interface ProductType {\n type?: 'app' | 'template' | 'integration' | 'expert' | 'ai-agent',\n}\n\nexport interface ProductVersion {\n _id: string;\n name: string;\n versions?: Version[];\n cid?: string;\n}\n\nexport interface Version {\n version: string;\n description: string;\n packageHash: string;\n created: number;\n}\n\n// Payment and Pricing Types\nexport interface PricingPlan {\n planId: 'monthly' | 'yearly' | 'one_time';\n label: string;\n price: number;\n currency: string;\n interval: 'month' | 'year' | null;\n}\n\nexport interface PaymentProvider {\n priceId?: {\n monthly?: string;\n yearly?: string;\n one_time?: string;\n };\n trial_days?: number;\n}\n\nexport interface PricingProviders {\n stripe?: PaymentProvider;\n paddle?: PaymentProvider;\n // fuze?: PaymentProvider; // Hidden for now\n}\n\nexport interface PricingData {\n _id?: string;\n productId?: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n created?: number;\n updated?: number;\n}\n\nexport interface CreatePricingRequest {\n productId: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n}\n\nexport interface UpdatePricingRequest {\n productId: string;\n types: PricingPlan[];\n providers: PricingProviders;\n paymentEnabled?: boolean;\n}\n\nexport interface CreatePurchaseRequest {\n productId: string;\n workspaceId: string;\n planType: 'monthly' | 'yearly' | 'one_time';\n successUrl?: string; // Optional for backward compatibility\n cancelUrl?: string; // Optional for backward compatibility\n useTokens?: boolean; // Optional - use workspace tokens for one-time purchases\n}\n\nexport interface CreatePurchaseResponse {\n status: 'installed_free' | 'subscription_created' | 'checkout_required' | 'payment_processed' | 'payment_failed';\n message?: string;\n productId?: string;\n planType?: string;\n purchaseId?: string;\n subscriptionId?: string;\n provider?: string;\n trialDays?: number;\n checkoutUrl?: string;\n error?: string; // For payment failure details\n}\n\nexport interface Purchase {\n _id: string;\n uid: string;\n cid: string;\n productId?: string;\n productName?: string;\n provider?: 'stripe' | 'paddle' | 'fuze';\n type: 'monthly' | 'yearly' | 'one_time';\n purchaseType: 'workspace' | 'product';\n startedAt: number;\n created: number;\n updated?: number;\n customStatus?: string;\n expiresAt?: number;\n trialDays?: number;\n trialStart?: number;\n trialEnd?: number;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n pricing?: {\n amount: number;\n currency: string;\n interval: string;\n source: string;\n };\n stripe?: {\n customerId?: string;\n checkoutSessionId?: string;\n subscriptionId?: string;\n paymentIntentId?: string;\n status?: string;\n };\n paddle?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n fuze?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n}\n\n// Admin interfaces\nexport interface AdminWorkspaceListItem {\n _id: string;\n name: string;\n memberCount: number;\n created: number;\n updated?: number;\n creatorEmail?: string;\n paymentPlan?: string;\n monthlyPrice?: number;\n paymentMethod?: 'subscription' | 'invoice';\n subscriptionActive?: boolean;\n provider?: string;\n stripeStatus?: string;\n hasPendingSubscription?: boolean;\n tokenBalance?: number;\n autoReloadEnabled?: boolean;\n}\n\nexport interface AdminWorkspaceListRequest {\n filter?: {\n name?: string;\n };\n options?: {\n search?: string;\n sortBy?: string;\n sortOrder?: string;\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminWorkspaceListResponse {\n workspaces: AdminWorkspaceListItem[];\n totalCount: number;\n}\n\n// Purchase data for admin interfaces\nexport interface AdminPurchaseData {\n _id: string;\n uid: string;\n cid: string;\n productId?: string | null;\n productName?: string | null;\n provider?: string;\n type: string;\n purchaseType: 'workspace' | 'product' | 'token';\n billingType?: 'subscription' | 'invoice';\n planName?: 'flexible' | 'pro' | 'business' | 'enterprise';\n startedAt?: number;\n expiresAt?: number;\n created: number;\n updated?: number;\n customStatus?: string;\n trialStart?: number;\n trialEnd?: number;\n invoiceHandled?: boolean;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n hailer?: {\n tokenAmount?: number;\n tokenRate?: number;\n customerActivityId?: string;\n status?: string;\n paymentMethod?: string;\n };\n pricing?: {\n amount: number;\n currency: string;\n interval?: string;\n source: 'purchase_record' | 'pricing_collection';\n };\n availablePricing?: Array<{\n planId: 'monthly' | 'yearly' | 'one_time';\n label: string;\n price: number;\n currency: string;\n interval: string | null;\n }>;\n trialDays?: number;\n stripe?: {\n customerId?: string;\n checkoutSessionId?: string;\n subscriptionId?: string;\n paymentIntentId?: string;\n status?: string;\n };\n paddle?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n fuze?: {\n customerId?: string;\n subscriptionId?: string;\n status?: string;\n };\n}\n\n// Single workspace for admin get method (extends list item with purchase data)\nexport interface AdminWorkspaceOverrides {\n // Boolean overrides\n functionFields?: boolean;\n kanban?: boolean;\n customRoles?: boolean;\n restricted?: boolean;\n insight?: boolean;\n dataExport?: boolean;\n documentGenerator?: boolean;\n groups?: boolean;\n print?: boolean;\n isolatedTeams?: boolean;\n managedUsers?: boolean;\n translations?: boolean;\n indexedData?: boolean;\n fastFunctions?: boolean;\n activityRecovery?: boolean;\n videoCall?: boolean;\n // Number overrides\n users?: number | null;\n // String overrides\n tourIdentifier?: string;\n}\n\nexport interface AdminWorkspaceMarketplaceSettings {\n creatorPercent: number;\n}\n\nexport interface AdminWorkspace extends AdminWorkspaceListItem {\n purchaseId?: string;\n purchases?: AdminPurchaseData[];\n overrides?: AdminWorkspaceOverrides;\n marketplace?: AdminWorkspaceMarketplaceSettings;\n}\n\nexport interface AdminUpdateOverridesRequest {\n workspaceId: string;\n overrides: AdminWorkspaceOverrides;\n}\n\nexport interface AdminUpdateMarketplaceSettingsRequest {\n workspaceId: string;\n creatorPercent: number;\n}\n\nexport interface AdminCreateStripeSessionRequest {\n workspaceId: string;\n planName: 'flexible' | 'pro' | 'business' | 'enterprise';\n customPrice: number;\n paymentMethod: 'stripe';\n baseUrl: string;\n}\n\nexport interface AdminCreateStripeSessionResponse {\n success: boolean;\n message: string;\n sessionUrl?: string;\n}\n\nexport interface AdminCreateInvoiceIntegrationRequest {\n workspaceId: string;\n planName: 'enterprise'; // Only enterprise for invoice\n customPrice: number;\n paymentMethod: 'hailer';\n customerActivityId?: string;\n}\n\nexport interface AdminCreateInvoiceIntegrationResponse {\n success: boolean;\n message: string;\n}\n\nexport interface AdminUpdateWorkspaceSubscriptionRequest {\n purchaseId: string;\n billingType: 'subscription' | 'invoice';\n customPrice: number;\n planName: 'flexible' | 'pro' | 'business' | 'enterprise';\n tokenAmount?: number;\n customerActivityId?: string;\n skipInvoiceHandledReset?: boolean;\n}\n\nexport interface AdminUpdatePurchasePriceRequest {\n purchaseId: string;\n workspaceId: string;\n newPrice: number;\n skipInvoiceHandledReset?: boolean;\n}\n\nexport interface AdminWorkspaceUser {\n _id: string;\n name: string;\n email: string;\n role: 'owner' | 'admin' | 'user' | 'guest' | 'inviter';\n joined?: number;\n lastActive?: number;\n emailVerified?: boolean;\n managedUser?: boolean | null;\n}\n\nexport interface AdminWorkspaceUsersListRequest {\n workspaceId?: string;\n filter?: {\n email?: string;\n role?: string;\n };\n options?: {\n search?: string;\n sortBy?: string;\n sortOrder?: string;\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminWorkspaceUsersListResponse {\n users: AdminWorkspaceUser[];\n totalCount: number;\n}\n\nexport interface AdminUpdateUserRequest {\n userId: string;\n updates: {\n emailVerified?: boolean;\n };\n}\n\nexport interface AdminUpdateUserResponse {\n success: boolean;\n}\n\nexport interface AdminUpdateTokenBalanceRequest {\n workspaceId: string;\n tokenAmount: number;\n payoutType?: 'admin_bonus' | 'creator_payout';\n payoutMonth?: number;\n payoutYear?: number;\n creatorPercent?: number;\n}\n\nexport interface AdminTokenTransaction {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n type: 'purchase' | 'deduction' | 'bonus' | 'admin_adjustment' | 'creator_payout';\n amount: number;\n reason: string;\n meta?: {\n payoutMonth?: number;\n payoutYear?: number;\n creatorProfit?: number;\n creatorPercent?: number;\n [key: string]: any\n };\n createdAt: number;\n}\n\nexport interface AdminTokenTransactionFilter {\n workspaceId?: string;\n type?: 'purchase' | 'deduction' | 'bonus' | 'admin_adjustment' | 'creator_payout';\n operation?: string;\n dateFrom?: number;\n dateTo?: number;\n search?: string;\n}\n\nexport interface AdminTokenTransactionStatistics {\n netChange: number;\n totalPurchases: number;\n totalPurchasesEuro: number;\n purchasesBySource: {\n stripe: {\n count: number;\n tokens: number;\n revenue: number;\n };\n adminPortal: {\n count: number;\n tokens: number;\n revenue: number;\n };\n };\n totalDeductions: number;\n totalDeductionsEuro: number;\n consumptionByOperation: {\n [operation: string]: {\n count: number;\n tokens: number;\n };\n };\n totalBonuses: number;\n totalBonusesEuro: number;\n totalCreatorPayouts: number;\n totalCreatorPayoutsEuro: number;\n totalRefunds: number;\n totalRefundsEuro: number;\n}\n\nexport interface AdminTokenTransactionsListRequest {\n filter?: AdminTokenTransactionFilter;\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminTokenTransactionsListResponse {\n transactions: AdminTokenTransaction[];\n totalCount: number;\n statistics: AdminTokenTransactionStatistics;\n}\n\nexport interface AdminInvoicePurchase {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n purchaseType: 'workspace' | 'product' | 'token';\n type: 'monthly' | 'yearly' | 'one_time';\n provider: 'hailer';\n billingType: 'invoice';\n planName?: string;\n productId?: string;\n productName?: string;\n pricePaid?: {\n amount: number;\n currency: string;\n };\n hailer?: {\n tokenAmount?: number;\n tokenRate?: number;\n customerActivityId?: string;\n };\n customStatus?: string;\n invoiceHandled?: boolean;\n pendingAction?: string;\n startedAt: number;\n expiresAt?: number;\n trialStart?: number;\n trialEnd?: number;\n trialDays?: number;\n}\n\nexport interface AdminInvoiceListRequest {\n filter?: {\n workspaceId?: string;\n purchaseType?: 'workspace' | 'product' | 'token';\n status?: 'handled' | 'unhandled' | 'all';\n search?: string;\n };\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminInvoiceWorkspaceGroup {\n cid: string;\n workspaceName: string;\n allHandled: boolean;\n customerActivityId?: string;\n purchases: AdminInvoicePurchase[];\n}\n\nexport interface AdminInvoiceListResponse {\n invoices: AdminInvoicePurchase[];\n totalCount: number;\n workspaceGroups: AdminInvoiceWorkspaceGroup[];\n}\n\nexport interface AdminInvoiceUpdateHandledRequest {\n purchaseIds: string | string[];\n handled: boolean;\n}\n\nexport interface AdminInvoiceUpdateHandledResponse {\n updatedCount: number;\n}\n\n// Monthly Revenue Tracking Types\nexport interface AdminRevenuePurchase {\n _id: string;\n uid: string;\n cid: string;\n workspaceName: string;\n created: number;\n purchaseType: 'workspace' | 'product';\n type: 'monthly' | 'yearly' | 'one_time';\n provider: string;\n productId?: string;\n productName?: string;\n productOwnerCid?: string;\n productOwnerName?: string;\n pricePaid?: { amount: number; currency: string };\n startedAt: number;\n expiresAt?: number;\n // Calculated fields\n normalizedMonthlyRevenue: number; // Yearly \u00F7 12, others as-is\n isMarketplace: boolean;\n profitToHailer: number;\n profitToCreator?: number;\n statusInMonth: 'active' | 'started' | 'ended';\n}\n\nexport interface AdminRevenueWorkspaceGroup {\n cid: string;\n workspaceName: string;\n totalRevenue: number;\n totalMRR: number;\n totalOneTime: number;\n totalCreatorProfit: number;\n totalHailerProfit: number;\n creatorPercent: number;\n productCount: number;\n paidOut?: boolean;\n productBreakdown: Array<{\n productId: string;\n productName: string;\n installationCount: number;\n totalRevenue: number;\n subscriptionTypes: {\n monthly: number;\n yearly: number;\n one_time: number;\n };\n installedBy: Array<{\n cid: string;\n workspaceName: string;\n type: string;\n }>;\n }>;\n purchases: AdminRevenuePurchase[];\n}\n\nexport interface AdminRevenueWorkspaceSubscriptions {\n totalWorkspaces: number;\n totalRevenue: number;\n byPlan: Array<{\n planName: string;\n count: number;\n revenue: number;\n }>;\n}\n\nexport interface AdminRevenueStatistics {\n selectedMonth: { month: number; year: number };\n totalMRR: number;\n totalOneTime: number;\n totalRevenue: number;\n activeCount: number;\n hailerProfit: number;\n creatorProfit: number;\n}\n\nexport interface AdminRevenueListRequest {\n month: number;\n year: number;\n filter?: {\n workspaceId?: string;\n purchaseType?: 'workspace' | 'product';\n subscriptionType?: 'monthly' | 'yearly' | 'one_time';\n search?: string;\n };\n options?: {\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n limit?: number;\n skip?: number;\n };\n}\n\nexport interface AdminRevenueListResponse {\n purchases: AdminRevenuePurchase[];\n totalCount: number;\n workspaceGroups: AdminRevenueWorkspaceGroup[];\n statistics: AdminRevenueStatistics;\n}\n\n// Dashboard Statistics Types\nexport interface AdminDashboardEntityStatistics {\n today: number;\n total: number;\n lastWeek: number;\n growth: number;\n}\n\nexport interface AdminDashboardStatisticsResponse {\n users: AdminDashboardEntityStatistics;\n workspaces: AdminDashboardEntityStatistics;\n activities: AdminDashboardEntityStatistics;\n messages: AdminDashboardEntityStatistics;\n userMessages: AdminDashboardEntityStatistics;\n}\n\n// Dashboard Trends Types\nexport interface AdminDashboardTrendDataPoint {\n date: string;\n count: number;\n}\n\nexport interface AdminDashboardTrendsResponse {\n users?: AdminDashboardTrendDataPoint[];\n workspaces?: AdminDashboardTrendDataPoint[];\n}\n\n// Stripe Tax Calculation Types\nexport interface StripeTaxLineItem {\n amount: number;\n reference: string;\n tax_code?: string;\n quantity?: number;\n}\n\nexport interface StripeTaxCalculationRequest {\n workspaceId: string;\n lineItems: StripeTaxLineItem[];\n}\n\nexport interface StripeTaxLineItemResult {\n reference: string;\n amount: number;\n taxAmount: number;\n totalAmount: number;\n}\n\nexport interface StripeTaxCalculationResponse {\n amountSubtotal: number;\n amountTax: number;\n amountTotal: number;\n taxRate?: number;\n country?: string;\n countryName?: string;\n currency: string;\n lineItems: StripeTaxLineItemResult[];\n}\n\n// Admin Referral Types\nexport interface AdminReferralCode {\n _id: string;\n code: string;\n uid: string;\n cid: string;\n ownerEmail?: string;\n workspaceName?: string;\n bonusTokens: number;\n isActive: boolean;\n totalReferrals: number;\n totalTokensAwarded: number;\n created: number;\n}\n\nexport interface AdminReferralCodeListRequest {\n filter?: {\n isActive?: boolean;\n cid?: string;\n };\n options?: {\n search?: string;\n limit?: number;\n skip?: number;\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n };\n}\n\nexport interface AdminReferralCodeListResponse {\n codes: AdminReferralCode[];\n totalCount: number;\n stats: {\n activeCount: number;\n totalReferrals: number;\n totalTokensAwarded: number;\n };\n}\n\nexport interface AdminReferralEvent {\n _id: string;\n referralCodeId: string;\n referralCode: string;\n referrerUid: string;\n referrerCid: string;\n refereeUid: string;\n refereeCid: string;\n refereeEmail?: string;\n refereeWorkspaceName?: string;\n status: 'pending' | 'completed' | 'failed';\n bonusTokensAwarded: number;\n failureReason?: string;\n created: number;\n completedAt?: number;\n}\n\nexport interface AdminReferralEventListRequest {\n filter?: {\n referralCodeId?: string;\n referrerCid?: string;\n status?: 'pending' | 'completed' | 'failed';\n };\n options?: {\n limit?: number;\n skip?: number;\n sortBy?: string;\n sortOrder?: 'asc' | 'desc';\n };\n}\n\nexport interface AdminReferralEventListResponse {\n events: AdminReferralEvent[];\n totalCount: number;\n stats: {\n completedCount: number;\n pendingCount: number;\n totalTokensAwarded: number;\n };\n}\n\nexport interface BallHolder {\n userId: string;\n assignedAt: string;\n}\n\nexport interface BallHolderEntry {\n activityId: string;\n discussionId: string;\n activityName: string;\n ballHolder: BallHolder;\n}\n\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, User } from '../types';\n\nexport class UserApi {\n constructor(private client: Client) {}\n\n /**\n * Returns the specified user\n *\n * @param userId id of the Hailer user\n *\n * @returns Hailer user information\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(userId: string): Promise<User> {\n try {\n return await this.client.requestAsync('user.get', [userId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Returns the current user\n *\n *\n * @returns the current Hailer user information\n *\n * @throws {HailerError} if request is incorrect\n */\n async current(): Promise<User> {\n try {\n return await this.client.requestAsync('user.current', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists all Hailer users from a workspace\n *\n *\n * @returns list of Hailer users in the workspace the app user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<User[]> {\n try {\n return await this.client.requestAsync('user.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { ActivityKanbanListOptions, HailerError, KanbanListResponse, KanbanLoadResponse } from '../../types';\n\nexport class Kanban {\n constructor(private client: Client) { }\n\n /**\n * Lists all activities in a kanban grouped by phases\n *\n * @param processId the id of the process the kanban relates to\n * @param options ActivityKanbanListOptions\n *\n * @returns activities in kanban list format\n *\n * @throws {HailerError} if request fails\n */\n async list(processId: string, options?: ActivityKanbanListOptions): Promise<KanbanListResponse> {\n try {\n const res = await this.client.requestAsync('activity.kanban.list', [processId, ...options ? [options] : []]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Loads a single activity in kanban format\n *\n * @param activityId activityId of the wanted activity\n *\n * @returns activity in kanban format\n *\n * @throws {HailerError} if request is incorrect\n */\n async load(activityId: string): Promise<KanbanLoadResponse> {\n try {\n const res = await this.client.requestAsync('activity.kanban.load', [activityId]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates priority of activities in kanban\n *\n * @param activityId activityId of the wanted activity\n * @param priority new priority for the activity\n *\n * @throws {HailerError} if request is incorrect\n */\n async updatePriority(activityId: string, priority: number): Promise<void> {\n try {\n const res = await this.client.requestAsync('activity.kanban.updatePriority', [{ activityId, priority }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { BallHolderEntry, HailerError } from '../../types';\n\nexport class Ball {\n constructor(private client: Client) { }\n\n /**\n * Pass the ball (activity responsibility) to another user.\n *\n * @param activityId activity to update\n * @param toUserId recipient user id; must be a participant of the activity's discussion\n *\n * @throws {HailerError} if the activity has no ball tracking, the caller is a guest, or the target is not a participant\n */\n async pass(activityId: string, toUserId: string): Promise<void> {\n try {\n return await this.client.requestAsync('activity.ball.pass', [activityId, toUserId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Take the ball (activity responsibility) for the current user.\n *\n * @param activityId activity to take\n *\n * @throws {HailerError} if ball tracking is disabled, the caller is a guest, or the caller lacks phase access\n */\n async take(activityId: string): Promise<void> {\n try {\n return await this.client.requestAsync('activity.ball.take', [activityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * List ball holders for activity discussions.\n *\n * @param discussionIds `'*'` to load every ball holder the user can see, or an array of discussionIds to restrict the result.\n * Unknown or non-participant discussionIds are silently dropped. An empty array returns `[]` without hitting the backend.\n *\n * @returns array of ball holder entries for activities where the caller can access both the discussion and the workflow\n *\n * @throws {HailerError} if the request is invalid\n */\n async list(discussionIds: string[] | '*'): Promise<BallHolderEntry[]> {\n if (Array.isArray(discussionIds) && discussionIds.length === 0) {\n return [];\n }\n try {\n return await this.client.requestAsync('activity.ball.list', [discussionIds]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { ActivityCreateOptions, ActivityListOptions, Activity, HailerError, ActivityFieldUpdateValue, ActivityUpdateOptions, ActivityFieldValue, PrintRequest, PrintOptions, PrintResponse } from '../types';\nimport { Kanban } from './activity/kanban';\nimport { Ball } from './activity/ball';\n\nexport class ActivityApi {\n public kanban: Kanban;\n public ball: Ball;\n constructor(private client: Client) {\n this.kanban = new Kanban(client);\n this.ball = new Ball(client);\n }\n\n /**\n * Lists all activities from the specified process and phase\n *\n * @param processId process from current network\n * @param phaseId phase in the process specified in processId\n * @param options ActivityListOptions\n *\n * @returns List of Hailer activities from process and phase filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(processId: string, phaseId: string, options?: ActivityListOptions): Promise<Activity[]> {\n try {\n return await this.client.requestAsync('activity.list', [processId, phaseId, options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets single activity\n *\n * @param activityId Id of the activity to fetch\n *\n * @returns Hailer activity information or undefined if no activity is found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(activityId: string): Promise<Activity | undefined> {\n try {\n // Uses the same endpoint as getAll but only returns the activity in question\n return await this.client.requestAsync('activity.get', [activityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(workflowId: string | undefined, activities: { name?: string; fields?: { [id: string]: ActivityFieldValue }, phaseId?: string, teamId?: string }[], options?: ActivityCreateOptions ): Promise<Activity[]> {\n try {\n return await this.client.requestAsync('activity.create', [workflowId, activities, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates activites\n *\n * @returns The number of updated activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(\n activities: { _id: string, name?: string, fields?: { [id: string]: ActivityFieldUpdateValue }, phaseId?: string, teamId?: string }[],\n options?: ActivityUpdateOptions\n ): Promise<number> {\n try {\n return await this.client.requestAsync('activity.update', [activities, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Removes activities\n *\n * @param activities Ids of activities to be removed\n *\n * @returns The number of removed activities\n *\n * @throws {HailerError} if request is incorrect\n */\n async remove(activities: string[]): Promise<number> {\n try {\n return await this.client.requestAsync('activity.remove', [activities]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Prints activities using document templates\n *\n * @param requests Array of print requests\n * @param requests[].activityId The ID of the activity to print\n * @param requests[].templateId Template ID for regular templates\n * @param requests[].templateName Template name for multi-pdf templates (when templateId is empty)\n * @param requests[].savePdf Whether to save the generated PDF\n * @param options.openNative Also open the document in the device's own viewer where the host supports it\n * (the Hailer Android app); see `openedNatively` in the response\n *\n * @returns PDF data with filename, base64 data, and mimeType\n *\n * @throws {HailerError} if request is incorrect\n */\n async print(requests: PrintRequest[], options?: PrintOptions): Promise<PrintResponse> {\n try {\n return await this.client.requestAsync('activity.print', [requests, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, ProductVersion, Workspace } from '../types';\n\nexport class WorkspaceApi {\n product: {\n /** Publish template in Hailer market */\n publishTemplate: (template: {\n workspaceId?: string,\n versionId?: string,\n version: string,\n versionDescription: string,\n title: string,\n description: string\n }) => Promise<ProductVersion>\n\n /** Check if product is installed */\n isProductInstalled(\n id: string,\n workspaceId: string\n ): Promise<boolean>\n\n /** Get version */\n get(\n id: string\n ): Promise<ProductVersion | undefined>\n\n /** Install template from Hailer market */\n install(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get manifest content from Hailer market */\n getManifest(id: string): Promise<any>\n };\n\n constructor(private client: Client) {\n this.product = {\n publishTemplate: this.publishTemplate.bind(this),\n isProductInstalled: this.isProductInstalled.bind(this),\n get: this.get.bind(this),\n install: this.install.bind(this),\n getManifest: this.getManifest.bind(this),\n };\n }\n\n /**\n * Returns the current network\n *\n * @returns the Hailer Workspace information the user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async current(): Promise<Workspace> {\n try {\n const res = await this.client.requestAsync('workspace.current', []);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Returns all workspaces for user if personal app\n * If not personal app it returns only the current workspace\n * @returns the Hailer Workspaces information for the user\n *\n * * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<Workspace[]> {\n try {\n const res = await this.client.requestAsync('workspace.list', []);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n\n /**\n * Creates a new workspace\n *\n * Only available for personal apps \u2014 a workspace-scoped app is bound to a\n * single workspace and cannot create new ones.\n *\n * @param name Name of the new workspace\n *\n * @returns the id and name of the created workspace\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(name: string): Promise<{ _id: string; name: string }> {\n try {\n const res = await this.client.requestAsync('workspace.create', [name]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n\n /**\n * Publish template in Hailer market\n *\n * @param workspaceId Id of workspace\n * @param versionId link to version (empty if first publish)\n * @param version Version number\n * @param versionDescription Version description\n * @param title\n * @param description\n *\n * @returns Created version in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n private async publishTemplate(\n template: {\n workspaceId?: string,\n versionId?: string,\n version: string,\n versionDescription: string,\n title: string,\n description: string\n }\n ): Promise<ProductVersion> {\n try {\n const result = await this.client.requestAsync('workspace.product.publishTemplate', [template]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Check if product is installed\n *\n * @param id Id of product in Hailer market\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async isProductInstalled(\n id: string,\n workspaceId: string\n ): Promise<boolean> {\n try {\n return await this.client.requestAsync('workspace.product.isProductInstalled', [id, workspaceId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get version\n *\n * @param id targetId\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async get(\n id: string\n ): Promise<ProductVersion | undefined> {\n try {\n return await this.client.requestAsync('workspace.product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Install template from Hailer market\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace where the product will be installed\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async install(productId: string, workspaceId: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('workspace.product.install', [productId, workspaceId]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get manifest content from Hailer market\n *\n * @param id target Id\n *\n * @returns Manifest content\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getManifest(id: string): Promise<any> {\n try {\n return await this.client.requestAsync('workspace.product.getManifest', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, TeamsByWorkspace } from '../types';\n\nexport class TeamApi {\n constructor(private client: Client) {}\n\n /**\n * Lists all teams grouped by workspace ID\n *\n * @returns Teams grouped by workspace ID\n *\n * @example\n * const teams = await hailer.team.list();\n * // { \"workspaceId1\": [{ _id: \"...\", name: \"Team A\" }], ... }\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<TeamsByWorkspace> {\n try {\n return await this.client.requestAsync('team.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError } from '../types';\n\nexport interface FileResponse {\n filename: string;\n /** Base64-encoded file data */\n data: string;\n mimeType: string;\n /** Free-form string tags attached to the file */\n tags: string[];\n}\n\nexport interface UploadOptions {\n /** Whether the file should be publicly accessible */\n isPublic?: boolean;\n /**\n * Scope the file to the app's workspace (irreversible). A scoped file is readable only by its owner,\n * workspace admins and its readers; set readers with `setReaders`. Cannot be combined with `isPublic`,\n * and not available to guests. This is the only way to scope a file.\n */\n scoped?: boolean;\n}\n\n/** Owner, workspace and readers of a file. `workspaceId` and `readers` are absent for an unscoped file. */\nexport interface FileScope {\n _id: string;\n /** Owner of the file */\n uid: string;\n /** Workspace the file is scoped to */\n workspaceId?: string;\n /** Reader entries, see `FileApi.readers` */\n readers?: string[];\n}\n\nexport interface FileListOptions {\n /** One keyword or up to 20. A keyword matches a case-insensitive substring of the file name or of any tag. */\n search?: string | string[];\n /** `all` (default) requires every keyword to match, `any` at least one */\n matchType?: 'all' | 'any';\n skip?: number;\n /** 1-100, default 100 */\n limit?: number;\n sortBy?: 'name' | 'created';\n reverse?: boolean;\n}\n\nexport interface ScopedFile {\n _id: string;\n name: string;\n /** Owner of the file */\n uid: string;\n workspaceId: string;\n type?: string;\n length?: number;\n created?: number;\n updated?: number;\n tags?: string[];\n}\n\nexport interface FileListResponse {\n files: ScopedFile[];\n hasMore: boolean;\n total: number;\n}\n\n/** wish-rpc's error code for a method the host does not have */\nconst noSuchMethod = 300;\n\n/**\n * Builders for `setReaders` entries. Only full members of the app's workspace ever match a reader:\n * guests never do, not even through a team or a `user_` entry.\n */\nexport const fileReaders = {\n /** Every full member of the workspace */\n workspace: (workspaceId: string): string => `network_${workspaceId}`,\n /** The full members of a team; guests in the team are skipped */\n team: (teamId: string): string => `team_${teamId}`,\n /** A single full member; a guest is rejected */\n user: (userId: string): string => `user_${userId}`,\n};\n\nexport class FileApi {\n /** Builders for `setReaders` entries: `readers.workspace(id)`, `readers.team(id)`, `readers.user(id)` */\n readonly readers = fileReaders;\n\n constructor(private client: Client) {}\n\n /**\n * Gets a file by ID and returns it as base64 data\n *\n * @param fileId The ID of the file to fetch\n *\n * @returns File data with filename, base64 data, and mimeType\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(fileId: string): Promise<FileResponse> {\n try {\n return await this.client.requestAsync('file.get', [fileId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Uploads a file to Hailer\n *\n * @param file File to be uploaded\n * @param filename Name of the file\n * @param options Upload options\n *\n * @returns File ID in Hailer\n *\n * @throws {HailerError} if upload fails\n */\n async upload(file: File, filename: string, options?: UploadOptions): Promise<string> {\n if (options?.isPublic && options?.scoped) {\n throw new HailerError({ code: 400, msg: 'A file cannot be both public and scoped', debug: undefined });\n }\n\n try {\n const base64Data = await this.toBase64(file);\n if (!options?.scoped) {\n return await this.client.requestAsync('file.upload', [base64Data, filename, !!options?.isPublic]);\n }\n\n const fileId: string = await this.client.requestAsync('file.upload', [base64Data, filename, false, true]);\n await this.assertScoped(fileId);\n return fileId;\n } catch (error: any) {\n throw error instanceof HailerError ? error : new HailerError(error);\n }\n }\n\n /**\n * Appends tags to a file, deduping against the existing list.\n *\n * Tags are case-sensitive free-form strings (trimmed, 1-64 characters, max 50 per file). On a scoped\n * file only its owner or a workspace admin may change tags; readers can read them but not edit.\n *\n * @param fileId The ID of the file to tag\n * @param tags Tags to add\n *\n * @returns The file's resulting tag list\n *\n * @throws {HailerError} if validation fails or the file cannot be edited\n */\n async addTags(fileId: string, tags: string[]): Promise<string[]> {\n try {\n return await this.client.requestAsync('file.addTags', [fileId, tags]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Removes tags from a file by case-sensitive exact match. Tags not present are silently ignored.\n * On a scoped file only its owner or a workspace admin may change tags.\n *\n * @param fileId The ID of the file to untag\n * @param tags Tags to remove\n *\n * @returns The file's resulting tag list\n *\n * @throws {HailerError} if validation fails or the file cannot be edited\n */\n async removeTags(fileId: string, tags: string[]): Promise<string[]> {\n try {\n return await this.client.requestAsync('file.removeTags', [fileId, tags]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets the owner, workspace and readers of a file you can read. Use it as an \"is this file scoped?\"\n * probe: `workspaceId` is absent for an unscoped file.\n *\n * @param fileId The ID of the file\n *\n * @throws {HailerError} if the file does not exist or you cannot read it (guests cannot read scoped\n * files), or if it is scoped to a workspace other than the app's (403)\n */\n async getScope(fileId: string): Promise<FileScope> {\n try {\n return await this.client.requestAsync('file.getScope', [fileId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Replaces the readers of a file scoped to the app's workspace. Files are scoped only at upload\n * (`upload(..., { scoped: true })`); an unscoped file is refused (403) rather than scoped here.\n *\n * Requires being the file's owner (while a full member) or a workspace admin; not available to guests.\n * A non-admin may only add teams they belong to. Every entry must belong to the app's workspace, and\n * `user_` must name a full member, not a guest.\n *\n * @param fileId The ID of the file\n * @param readers The complete new reader list (max 100); build entries with `readers.*`. Send `[]` to\n * leave only the owner and workspace admins.\n *\n * @returns The resulting scope\n *\n * @throws {HailerError} if validation fails, the file is not scoped to the app's workspace, or you may\n * not manage it\n */\n async setReaders(fileId: string, readers: string[]): Promise<FileScope> {\n try {\n return await this.client.requestAsync('file.setReaders', [fileId, readers]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists the scoped files of the app's workspace that the user can read: their own, those they are a\n * reader of, or all of them for a workspace admin. Unscoped files are not listed.\n *\n * @param options Search by name/tags and paging\n *\n * @returns A page of files, whether more exist, and the total match count\n *\n * @throws {HailerError} if validation fails, or for a guest\n */\n async list(options?: FileListOptions): Promise<FileListResponse> {\n try {\n return await this.client.requestAsync('file.list', options ? [options] : []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Transfers a file scoped to the app's workspace to another full member of it (not a guest). Workspace\n * admins only. The previous owner loses access unless they are a reader.\n *\n * @param fileId The ID of the file\n * @param userId The new owner\n *\n * @throws {HailerError} if you are not a workspace admin, the file is not scoped to the app's workspace,\n * or the user is not a full member\n */\n async setOwner(fileId: string, userId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('file.setOwner', [fileId, userId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Permanently deletes files scoped to the app's workspace that you own. Ids of files owned by someone\n * else are skipped without an error, even for a workspace admin; re-list to see what is left. If any id\n * is not a file scoped to the app's workspace, the whole call is refused (403) and nothing is removed:\n * an app can never delete the user's other files.\n *\n * @param fileIds 1-100 file ids\n *\n * @returns `true` once the request is processed\n *\n * @throws {HailerError} if validation fails, or any file is not scoped to the app's workspace\n */\n async remove(fileIds: string[]): Promise<boolean> {\n try {\n return await this.client.requestAsync('file.remove', [fileIds]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * An older Hailer ignores the `scoped` upload argument and stores the file unscoped. Fail loudly rather\n * than hand back a file the app believes is restricted. Only a missing `file.getScope` (wish-rpc code\n * 300) or an unscoped result means an older Hailer; any other error is passed on as is.\n */\n private async assertScoped(fileId: string): Promise<void> {\n let scope: FileScope | undefined;\n try {\n scope = await this.client.requestAsync('file.getScope', [fileId]);\n } catch (error: any) {\n if (error?.code !== noSuchMethod) {\n throw new HailerError(error);\n }\n }\n\n if (!scope?.workspaceId) {\n throw new HailerError({\n code: 501,\n msg: `File ${fileId} was uploaded but not scoped: this Hailer version does not support scoped files`,\n debug: undefined,\n });\n }\n }\n\n private toBase64(file: File): Promise<string> {\n return new Promise((resolve, reject) => {\n const reader = new FileReader();\n reader.readAsDataURL(file);\n reader.onload = () => resolve((reader.result as string) ?? '');\n reader.onerror = reject;\n });\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport type ActivityTabTypes =\n 'detail' |\n 'discussion' |\n 'files' |\n 'location' |\n 'linkedFrom' |\n 'options';\n\nexport class Activity {\n constructor(private client: Client) {}\n\n /** Opens an activity in Hailer sidebar */\n async open(\n /** Hailer Activity Id */\n activityId: string,\n options?: {\n /** Which tab to open in activity aside */\n tab?: ActivityTabTypes\n },\n ): Promise<void> {\n await this.client.requestAsync('ui.activity.open', [activityId, ...options ? [options] : []]);\n }\n\n /** Opens activity creation view in Hailer sidebar */\n async create(\n processId: string,\n options?: {\n /** Activity name/title */\n name?: string,\n /** Phase ID to pre-select */\n phaseId?: string,\n /** Team ID to pre-select */\n teamId?: string,\n /** Prepopulate fields */\n fields?: {\n [fieldId: string]: number | string | { start: number, end: number },\n },\n location?: {\n type: 'area' | 'point' | 'polyline',\n data: { lng: number, lat: number }[],\n },\n }\n ): Promise<{ _id: string, name: string } | null> {\n return this.client.requestAsync('ui.activity.create', [processId, ...options ? [options] : []]);\n }\n\n /**\n * Opens multiple activity edit view in Hailer sidebar\n *\n * @param activityIds Ids of the activities to edit\n */\n async editMultiple(\n activityIds: string[]\n ): Promise<void> {\n return this.client.requestAsync('ui.activity.editMultiple', [activityIds]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\n/**\n * Valid tab types for opening discussions.\n * - Private discussions: \"discussions\" | \"files\" | \"info\" | \"location\"\n * - Group discussions: \"discussion\" | \"overview\" | \"files\"\n */\nexport type DiscussionTabTypes =\n | 'discussions'\n | 'files'\n | 'location'\n | 'info'\n | 'discussion'\n | 'overview'\n | 'detail'\n | 'participants'\n | 'linkedFrom'\n | 'options';\n\nexport class Discussion {\n constructor(private client: Client) {}\n\n /** Opens a discussion/chat in Hailer sidebar */\n async open(\n /** Hailer Discussion Id */\n discussionId: string,\n options?: {\n /** Which tab to open in discussion aside (only applies to group discussions) */\n tab?: DiscussionTabTypes;\n /** Whether to expand the sidebar if collapsed (default: true) */\n expandIfCollapsed?: boolean;\n },\n ): Promise<void> {\n await this.client.requestAsync('ui.discussion.open', [\n discussionId,\n ...(options ? [options] : []),\n ]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport class Snackbar {\n constructor(private client: Client) {}\n\n /**\n * Opens a snackbar in Hailer\n * @param text the text displayed on the snackbar\n * @param buttonLabel the label for the button on the snackbar, for example 'OK'\n * @param duration the time the snackbar is visible in ms\n */\n async open(\n /** The text displayed on the snackbar */\n text: string,\n /** The label for the button on the snackbar, for example 'OK' */\n buttonLabel: string,\n /** The time the snackbar is visible in ms */\n duration?: number,\n ): Promise<void> {\n await this.client.requestAsync('ui.snackbar.open', [text, buttonLabel, duration]);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\n/**\n * @deprecated Use FileApi from '@hailer/app-sdk' instead.\n * This class is kept for backwards compatibility.\n *\n * @example\n * // New way (recommended):\n * import { FileApi } from '@hailer/app-sdk';\n * const fileApi = new FileApi(client);\n * const fileId = await fileApi.upload(file, filename, { isPublic: false });\n */\nexport class Files {\n constructor(private client: Client) {}\n\n /**\n * Uploads a file to Hailer\n *\n * @deprecated Use FileApi.upload() instead\n *\n * @param file file to be uploaded\n * @param filename name of the file\n * @param options upload options\n *\n * @returns File ID in Hailer as string\n */\n public async uploadFile(file: File, filename: string, options: { isPublic?: boolean }): Promise<string> {\n return this.client.requestAsync('ui.file.upload', [await this.toBase64(file), filename, !!options?.isPublic]);\n }\n\n private toBase64(file: File): Promise<string | ArrayBuffer> {\n return new Promise((resolve, reject) => {\n const reader = new FileReader();\n reader.readAsDataURL(file);\n reader.onload = () => resolve(reader.result ?? '');\n reader.onerror = reject;\n });\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport class Workflow {\n constructor(private client: Client) {}\n\n function = {\n /**\n * Opens the function editor dialog for a specific field\n * @param fieldId The ID of the field to edit\n * @param options Additional options including workflowId and activityId\n */\n edit: async (\n workflowId: string,\n fieldId: string,\n ): Promise<void> => {\n await this.client.requestAsync('ui.workflow.function.edit', [workflowId, fieldId]);\n }\n };\n}", "import { Client } from '@wishcore/wish-rpc';\nimport { Activity } from './ui/activity';\nimport { Discussion } from './ui/discussion';\nimport { Snackbar } from './ui/snackbar';\nimport { Files } from './ui/files';\nimport { Workflow } from './ui/workflow';\n\n\nexport class Ui {\n public activity;\n public discussion;\n public snackbar;\n public files;\n public insight;\n public workflow;\n\n constructor(private client: Client) {\n this.activity = new Activity(client);\n this.discussion = new Discussion(client);\n this.snackbar = new Snackbar(client);\n this.workflow = new Workflow(client);\n\n this.insight = {\n create: async (\n /** Defaults to App workspace */\n workspaceId?: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.create', [workspaceId]);\n },\n edit: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.edit', [insightId]);\n },\n delete: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.delete', [insightId]);\n },\n permission: async (\n insightId: string\n ): Promise<void> => {\n await client.requestAsync('ui.insight.permission', [insightId]);\n }\n };\n\n this.files = new Files(client);\n }\n}\n", "export const DEFAULT_ALLOWED_URLS = [\n 'https://app.hailer.com',\n 'https://next.hailer.com',\n 'https://testapp.hailer.biz',\n 'https://app.hailer.biz',\n 'https://app.hailer.local.gd',\n 'https://app.k8s.hailer.com',\n 'https://next.k8s.hailer.com',\n 'https://localhost:9443'\n];\n\nexport const DEFAULT_BACKEND_URL = 'https://api.hailer.com';\n\n/** Map of which backend to use depending on which frontend is hosting the app frame, be sure to fall back to production backend if no match */\nexport const publicBackendMap: { [host: string]: string } = {\n 'https://app.hailer.com': DEFAULT_BACKEND_URL,\n 'https://next.hailer.com': DEFAULT_BACKEND_URL,\n 'https://app.hailer.biz': 'https://api.hailer.biz',\n 'https://testapp.hailer.biz': 'https://testapi.hailer.biz',\n 'https://app.hailer.local.gd': 'https://api.hailer.local.gd',\n 'https://app.k8s.hailer.com': 'https://api.k8s.hailer.com',\n 'https://next.k8s.hailer.com': 'https://api.k8s.hailer.com',\n 'https://localhost:9443': 'http://localhost:1337',\n};\n", "import { Options } from '../../hailer-api';\nimport { Config } from '../../types';\n\nexport class App {\n constructor(private options: Options) {}\n\n /**\n * Read data from app API\n *\n * @param appId key of a specific insight\n *\n * @returns App manifest\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async config(): Promise<Config> {\n const manifestFile = 'manifest.json';\n const location = window.location.origin + window.location.pathname;\n let manifestUrl = location + manifestFile;\n\n if (location.endsWith('/index.html')) {\n manifestUrl = location.slice(0, -10) + manifestFile;\n }\n\n const manifestContent = await (await fetch(manifestUrl)).text();\n\n const manifest = JSON.parse(manifestContent);\n\n const appId = manifest.appId;\n\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/app/public`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([appId])\n });\n\n return res.json();\n }\n\n}\n", "import { Options } from '../../hailer-api';\nimport { FormCreateResponse, FormsData, FormsResponse, HailerError } from '../../types';\n\nexport class Form {\n constructor(private options: Options) {}\n\n /**\n * Read data from forms\n *\n * @param formsKey key of a form\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v2/forms\n *\n * @returns forms data as object or null if form could not be found\n *\n * @throws {HailerError} if there is something wrong with the request or form cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async data(formsKey: string): Promise<FormsResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v2/forms/process/get`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([formsKey])\n });\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Submits form to specified process\n *\n * @param formsKey key of a form\n * @param formsData Data to be sent to form endpoint\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v2/forms\n *\n * @returns form creation data or null if form could not be created\n *\n * @throws {HailerError} if there is something wrong with the request or form cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async submit(formsKey: string, formsData: FormsData): Promise<FormCreateResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v2/forms/activity/create`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([formsKey, formsData])\n });\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n}\n", "import { Options } from '../../hailer-api';\nimport { HailerError, InsightResponse, InsightResponseAsObjects, InsightResponseData } from '../../types';\n\nexport class InsightPublicApi {\n constructor(private options: Options) {}\n\n /**\n * Read data from insight API\n *\n * @param insightKey key of a specific insight\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v3/insight/public\n *\n * @returns Insight data as object\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async data(insightKey: string): Promise<InsightResponse> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/insight/public`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([insightKey])\n }\n );\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Read data from insight API and return in an array of JavaScript objects\n *\n * @param insightKey key of a specific insight\n * @param options Overrides default request options, url defaults to https://api.hailer.com/api/v3/insight/public\n *\n * @returns Insight data as array of JavaScript objects\n *\n * @throws {HailerError} if there is something wrong with the request or insight cannot be found\n * @throws {TypeError} if Hailer cannot be reached\n */\n async dataAsObject(insightKey: string): Promise<InsightResponseAsObjects> {\n const res = await this.data(insightKey);\n\n const input: InsightResponseData = res.data;\n const data: InsightResponseAsObjects = [];\n\n input.rows.forEach((row) => {\n // The object keys are constructed dynamically, so any is necessary\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const object: any = {};\n input.headers.forEach((header, headerIndex) => {\n object[header] = row[headerIndex];\n });\n data.push(object);\n });\n return data;\n }\n}\n", "import { Options } from '../../hailer-api';\nimport { HailerError, Product, ProductListResponse, ProductSearchFilter, ProductSearchOption, ProductType } from '../../types';\n\nexport class ProductPublicApi {\n constructor(private options: Options) {}\n\n /**\n * Lists products from Hailer market\n *\n * @param filter ProductSearchFilter\n * @param options ProductSearchOption\n *\n * @returns List of products in Hailer market filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(\n filter?: ProductSearchFilter,\n options?: ProductSearchOption\n ): Promise<ProductListResponse> {\n\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/product/list`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([filter, options])\n });\n\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n\n /**\n * Gets single product from Hailer market\n *\n * @param id Product Id\n *\n * @returns Single product from Hailer market or undefined if no product found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(id: string): Promise<Product | undefined> {\n const res = await fetch(`${this.options.publicBackendUrl }/api/v3/product/get`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify([id])\n });\n\n if (!res.ok) {\n throw new HailerError(await res.json());\n }\n return res.json();\n }\n}\n", "import { Options } from '../hailer-api';\nimport { Product } from '../types';\nimport { App } from './public/app';\nimport { Form } from './public/form';\nimport { InsightPublicApi } from './public/insight';\nimport { ProductPublicApi } from './public/product';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class HailerPublicApi {\n /** Allows accessing public insight methods. Used for reading data from Hailer even when app is outside of Hailer */\n public insight: InsightPublicApi;\n /** Allows accessing public forms methods. Used for sending data to Hailer even when app is outside of Hailer */\n public form: Form;\n /** Access public App information */\n public app: App;\n /** Access public Product information */\n public product: ProductPublicApi;\n\n constructor(options: Options) {\n this.insight = new InsightPublicApi(options);\n this.form = new Form(options);\n this.app = new App(options);\n this.product = new ProductPublicApi(options);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, IdsMap, Workflow } from '../types';\n\nexport class WorkflowApi {\n constructor(private client: Client) {}\n\n /**\n * Lists all processes from a workspace\n *\n * @returns all Hailer processes in the workspace the app user is currently in\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<Workflow[]> {\n try {\n return await this.client.requestAsync('workflow.list', []);\n } catch (error: any) {\n console.error(error.msg, error);\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets a single process from a workspace\n *\n * @param workflowId the id of the process in question\n *\n * @returns the specified Hailer process\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(workflowId: string): Promise<Workflow> {\n try {\n return await this.client.requestAsync('workflow.get', [workflowId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Installs a workflow (process) from a spec\n *\n * @param workflowSpec the workflow specification to install\n * @param option optional target workspace\n *\n * @returns a map of template ids to the created ids\n *\n * @throws {HailerError} if request is incorrect\n */\n async install(workflowSpec: any, option?: { workspaceId?: string }): Promise<IdsMap> {\n try {\n return await this.client.requestAsync('workflow.install', [workflowSpec, option]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { Config, HailerError, ProductVersion, Version } from '../types';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class AppApi {\n product: {\n /** Check if product is installed */\n isProductInstalled(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get version */\n get(\n id: string\n ): Promise<ProductVersion | undefined>\n\n /** Install app from Hailer market */\n install(productId: string, workspaceId: string): Promise<boolean>\n\n /** Get installed version */\n getInstalledVersion(id: string): Promise<Version>\n\n /** Get manifest content from Hailer market */\n getManifest(id: string): Promise<any>\n };\n\n constructor(private client: Client) {\n this.product = {\n isProductInstalled: this.isProductInstalled.bind(this),\n get: this.get.bind(this),\n install: this.install.bind(this),\n getInstalledVersion: this.getInstalledVersion.bind(this),\n getManifest: this.getManifest.bind(this),\n };\n }\n\n config = {\n update: async (config: Config, option?: { appId?: string }): Promise<void> => {\n try {\n return await this.client.requestAsync('app.config.update', [config, ...option ? [option] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n\n /**\n * Check if product is installed\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async isProductInstalled(productId: string, workspaceId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('app.product.isProductInstalled', [productId, workspaceId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get version\n *\n * @param id targetId\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n private async get(\n id: string\n ): Promise<ProductVersion | undefined> {\n try {\n return await this.client.requestAsync('app.product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Install app from Hailer market\n *\n * @param productId Id of product in Hailer market\n *\n * @param workspaceId Id of workspace where the product will be installed\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async install(productId: string, workspaceId: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('app.product.install', [productId, workspaceId]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get installed version from Hailer market\n *\n * @param id Id of product in Hailer market\n *\n * @returns true, if installed else error\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getInstalledVersion(id: string): Promise<Version> {\n try {\n const result = await this.client.requestAsync('app.product.getInstalledVersion', [id]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get manifest content from Hailer market\n *\n * @param id target Id\n *\n * @returns Manifest content\n *\n * @throws {HailerError} if request is incorrect\n */\n private async getManifest(id: string): Promise<any> {\n try {\n return await this.client.requestAsync('app.product.getManifest', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, InsightData, InsightDoc, InsightQueryResult, InsightSource } from '../types';\n\nexport class InsightApi {\n constructor(private client: Client) {}\n\n /**\n * Get Insight data\n *\n * @param insightId the id of the Insight the data is fetched from\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async data(insightId: string, options: { update?: true }): Promise<InsightData> {\n\n try {\n /*data = [{ insightId, { headers, rows, time } }] */\n return await this.client.requestAsync('insight.data', [insightId, ...options ? [options] : []]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get Insight data\n *\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(): Promise<InsightDoc[]> {\n try {\n return await this.client.requestAsync('insight.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get Insight data\n *\n * @returns data from the Insight\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(insightId: string, update: Partial<InsightDoc>): Promise<InsightDoc[]> {\n try {\n return await this.client.requestAsync('insight.update', [insightId, update]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Run an ad-hoc query against Insight sources\n *\n * @param workspaceId the workspace to query within\n * @param sources the Insight sources to query\n * @param query the query string\n *\n * @returns query result with headers, rows, and details\n *\n * @throws {HailerError} if request is incorrect\n */\n async query(workspaceId: string, sources: InsightSource[], query: string): Promise<InsightQueryResult> {\n try {\n return await this.client.requestAsync('insight.query', [workspaceId, { sources, query }]);\n } catch (error: unknown) {\n throw new HailerError(error as { code: number; msg: string; debug: object });\n }\n }\n}\n\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, PermissionMap } from '../types';\n\n/**\n * This class is used to access Hailer public API even when the app is outside of Hailer\n */\nexport class PermissionApi {\n\n constructor(private client: Client) {}\n\n /**\n * Returns the user's permission map.\n *\n * For personal apps (no cid):\n * - With workspaceId: returns permissions for that specific workspace,\n * fetching from the backend if not yet loaded.\n * - Without workspaceId: returns all currently loaded permissions.\n *\n * For workspace apps (has cid):\n * - Always returns permissions scoped to the app's workspace,\n * if workspaceId is provided and it's not equal to the app's `cid`, it will throw an error.\n *\n * @param options.workspaceId - Optional workspace ID to scope permissions to (personal apps only)\n *\n * @returns Permission map keyed by workspace ID\n *\n * @throws {HailerError} if the request fails\n */\n map = async({ workspaceId }: { workspaceId?: string } = {}): Promise<PermissionMap> => {\n try {\n return await this.client.requestAsync('permission.map', workspaceId ? [{ workspaceId }] : []);\n } catch (error: any) {\n console.log('Failed to read permissions from Hailer, error:', error);\n throw new HailerError(error);\n }\n };\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError, Product, ProductSearchOption, ProductSearchFilter, ProductListResponse } from '../types';\n\nexport class ProductApi {\n constructor(private client: Client) {}\n\n /**\n * Lists products from Hailer market\n *\n * @param filter ProductSearchFilter\n * @param options ProductSearchOption\n *\n * @returns List of products in Hailer market filtered with supplied options\n *\n * @throws {HailerError} if request is incorrect\n */\n async list(\n filter?: ProductSearchFilter,\n options?: ProductSearchOption): Promise<ProductListResponse> {\n try {\n const res = await this.client.requestAsync('product.list', [filter, options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets single product from Hailer market\n *\n * @param id Product Id\n *\n * @returns Single product from Hailer market or undefined if no product found\n *\n * @throws {HailerError} if request is incorrect\n */\n async get(id: string): Promise<Product | undefined> {\n try {\n return await this.client.requestAsync('product.get', [id]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates product in Hailer market\n *\n * @param targetId link to targetId (version)\n * @param name Name of the product\n * @param description Description what this product is doing\n * @param icon Icon id for the product\n * @param images List of fileIds for showing pictures of the product\n * @param externalUrl Public URL for creator to show more information about the product\n * @param publisher Publisher (author)\n * @param type App, template, music etc.\n *\n * @returns Created product in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n async create(\n product: {\n targetId?: string,\n name: string,\n description?: string,\n icon?: string,\n images?: string[],\n externalUrl?: string,\n publisher?: string,\n type?: string\n }\n ): Promise<Product> {\n try {\n const result = await this.client.requestAsync('product.create', [product]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates product in Hailer market\n *\n * @param id Id of product in Hailer market\n * @param name Name of the product\n * @param description Description what this product is doing\n * @param icon Icon id for the product\n * @param images List of fileIds for showing pictures of the product\n * @param externalUrl Public URL for creator to show more information about the product\n * @param publisher Publisher (Author)\n * @param public: Visible or not in Hailer market\n * @param type App, template, music etc.\n *\n * @returns Updated product in Hailer market\n *\n * @throws {HailerError} if request is incorrect\n */\n async update(\n id: string,\n product: {\n name?: string,\n description?: string,\n icon?: string,\n images?: string[],\n externalUrl?: string,\n publisher?: string,\n public?: boolean,\n type?: string\n }\n ): Promise<Product> {\n try {\n const result = await this.client.requestAsync('product.update', [id, product]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Remove product from Hailer market\n *\n * @param id Id of product in Hailer market\n *\n * @returns true, if removed\n *\n * @throws {HailerError} if request is incorrect\n */\n async remove(id: string): Promise<boolean> {\n try {\n const result = await this.client.requestAsync('product.remove', [id]);\n return result;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Set product as public or not (visible) in Hailer market\n *\n * @param id Id of product in Hailer market\n * @param isPublic Visible or not in Hailer market\n *\n * @returns true if ok else false\n *\n * @throws {HailerError} if request is incorrect\n */\n async setPublic(\n id: string,\n isPublic: boolean\n ): Promise<boolean> {\n try {\n return await this.client.requestAsync('product.setPublic', [id, isPublic]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport {\n HailerError,\n PricingData,\n CreatePricingRequest,\n UpdatePricingRequest,\n CreatePurchaseRequest,\n CreatePurchaseResponse,\n Purchase,\n StripeTaxCalculationRequest,\n StripeTaxCalculationResponse\n} from '../types';\n\nexport class Payment {\n constructor(private client: Client) {}\n\n /**\n * Creates pricing configuration for a product\n *\n * @param request CreatePricingRequest containing productId, types, and providers\n *\n * @returns Created pricing configuration\n *\n * @throws {HailerError} if request is incorrect or product not found\n */\n async createPricing(request: CreatePricingRequest): Promise<PricingData> {\n try {\n const res = await this.client.requestAsync('payment.createPricing', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates pricing configuration for a product\n *\n * @param request UpdatePricingRequest containing productId, types, and providers\n *\n * @returns Updated pricing configuration\n *\n * @throws {HailerError} if request is incorrect, product not found, or pricing doesn't exist\n */\n async updatePricing(request: UpdatePricingRequest): Promise<PricingData> {\n try {\n const res = await this.client.requestAsync('payment.updatePricing', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets pricing configuration for a product\n *\n * @param productId Product ID to get pricing for\n *\n * @returns Pricing configuration or null if not found\n *\n * @throws {HailerError} if request is incorrect or product not found\n */\n async getPricing(productId: string): Promise<PricingData | null> {\n try {\n const res = await this.client.requestAsync('payment.getPricing', [{ productId }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates a product purchase/subscription\n *\n * @param request CreatePurchaseRequest containing productId, workspaceId, and planType\n *\n * @returns Purchase creation result with status and details\n *\n * @throws {HailerError} if request is incorrect, product not found, or payment fails\n */\n async createPurchase(request: CreatePurchaseRequest): Promise<CreatePurchaseResponse> {\n try {\n const res = await this.client.requestAsync('payment.createPurchase', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets purchases for a workspace\n *\n * @param workspaceId Workspace ID to get purchases for\n *\n * @returns Array of purchases for the workspace\n *\n * @throws {HailerError} if request is incorrect or workspace not found\n */\n async getPurchases(workspaceId: string): Promise<Purchase[]> {\n try {\n const res = await this.client.requestAsync('payment.getPurchases', [{ workspaceId }]);\n return res || [];\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Calculates Stripe tax for line items\n *\n * @param request StripeTaxCalculationRequest containing workspaceId and lineItems\n *\n * @returns Tax calculation result with amounts, rates, and country information\n *\n * @throws {HailerError} if request is incorrect, workspace not found, or Stripe customer not found\n */\n async calculateStripeTax(request: StripeTaxCalculationRequest): Promise<StripeTaxCalculationResponse> {\n try {\n const res = await this.client.requestAsync('payment.calculateStripeTax', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}", "import { Client } from '@wishcore/wish-rpc';\nimport {\n HailerError,\n AdminWorkspaceListRequest,\n AdminWorkspaceListResponse,\n AdminWorkspace,\n AdminCreateStripeSessionRequest,\n AdminCreateStripeSessionResponse,\n AdminCreateInvoiceIntegrationRequest,\n AdminCreateInvoiceIntegrationResponse,\n AdminUpdateWorkspaceSubscriptionRequest,\n AdminUpdatePurchasePriceRequest,\n AdminWorkspaceUsersListRequest,\n AdminWorkspaceUsersListResponse,\n AdminUpdateUserRequest,\n AdminUpdateUserResponse,\n AdminTokenTransactionsListRequest,\n AdminTokenTransactionsListResponse,\n AdminUpdateOverridesRequest,\n AdminUpdateMarketplaceSettingsRequest,\n AdminInvoiceListRequest,\n AdminInvoiceListResponse,\n AdminInvoiceUpdateHandledRequest,\n AdminInvoiceUpdateHandledResponse,\n AdminRevenueListRequest,\n AdminRevenueListResponse,\n AdminDashboardStatisticsResponse,\n AdminDashboardTrendsResponse,\n AdminReferralCodeListRequest,\n AdminReferralCodeListResponse,\n AdminReferralEventListRequest,\n AdminReferralEventListResponse\n} from '../types';\n\nexport class Admin {\n constructor(private client: Client) {}\n\n /**\n * Referral management endpoints\n */\n public referral = {\n /**\n * Lists all referral codes with optional filters\n */\n listCodes: async (request?: AdminReferralCodeListRequest): Promise<AdminReferralCodeListResponse> => {\n try {\n const res = await this.client.requestAsync('admin.referral.listCodes', [request?.filter || null, request?.options || null]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Lists referral events with optional filters\n */\n listEvents: async (request?: AdminReferralEventListRequest): Promise<AdminReferralEventListResponse> => {\n try {\n const res = await this.client.requestAsync('admin.referral.listEvents', [request?.filter || null, request?.options || null]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Updates a referral code's bonus amount or active status\n */\n updateCode: async (codeId: string, updates: { bonusTokens?: number; isActive?: boolean }): Promise<boolean> => {\n try {\n const res = await this.client.requestAsync('admin.referral.updateCode', [{ codeId, ...updates }]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n\n /**\n * Lists workspaces with search, pagination, and sorting\n *\n * @param request AdminWorkspaceListRequest containing filter and options\n *\n * @returns List of workspaces with total count\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listWorkspaces(request?: AdminWorkspaceListRequest): Promise<AdminWorkspaceListResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets detailed information about a specific workspace\n *\n * @param workspaceId The ID of the workspace to retrieve\n *\n * @returns Workspace details including payment information\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async getWorkspace(workspaceId: string): Promise<AdminWorkspace> {\n try {\n const res = await this.client.requestAsync('admin.workspace.get', [workspaceId]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates a Stripe checkout session for workspace subscription\n *\n * @param request AdminCreateStripeSessionRequest containing workspace details and payment info\n *\n * @returns AdminCreateStripeSessionResponse with success status and session URL\n *\n * @throws {HailerError} if request fails, user not authorized, or workspace already has subscription\n */\n async createStripeSession(request: AdminCreateStripeSessionRequest): Promise<AdminCreateStripeSessionResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.createStripeSession', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Creates an invoice integration for workspace subscription\n *\n * @param request AdminCreateInvoiceIntegrationRequest containing workspace details and payment info\n *\n * @returns AdminCreateInvoiceIntegrationResponse with success status\n *\n * @throws {HailerError} if request fails, user not authorized, or workspace already has subscription\n */\n async createInvoiceIntegration(request: AdminCreateInvoiceIntegrationRequest): Promise<AdminCreateInvoiceIntegrationResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.createInvoiceIntegration', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace subscription billing information\n *\n * @param request AdminUpdateWorkspaceSubscriptionRequest containing purchase ID and new billing details\n *\n * @returns boolean indicating whether the update was successful\n *\n * @throws {HailerError} if request fails, user not authorized, or purchase not found\n */\n async updateWorkspaceSubscription(request: AdminUpdateWorkspaceSubscriptionRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateSubscription', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates purchase price for active invoice products\n *\n * @param request AdminUpdatePurchasePriceRequest containing purchase ID, workspace ID, and new price\n *\n * @returns boolean indicating whether the update was successful\n *\n * @throws {HailerError} if request fails, user not authorized, purchase not found, or not an invoice product\n */\n async updatePurchasePrice(request: AdminUpdatePurchasePriceRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.purchase.updatePrice', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists users in a workspace with search, filtering, pagination, and sorting\n * If no workspaceId provided, lists all users across all workspaces\n *\n * @param request AdminWorkspaceUsersListRequest containing optional workspace ID, filter and options\n *\n * @returns List of workspace users with total count and role information\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async listWorkspaceUsers(request: AdminWorkspaceUsersListRequest): Promise<AdminWorkspaceUsersListResponse> {\n try {\n const res = await this.client.requestAsync('admin.workspace.listUsers', [request.workspaceId, request.filter, request.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates a user's information (currently supports email verification only)\n *\n * @param request AdminUpdateUserRequest containing user ID and updates\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, user not found, or user not authorized\n */\n async updateUser(request: AdminUpdateUserRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.user.update', [request.userId, request.updates]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace token balance\n *\n * @param request Object containing workspaceId, tokenAmount, and optional payout parameters\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateTokenBalance(request: {\n workspaceId: string;\n tokenAmount: number;\n payoutMonth?: number;\n payoutYear?: number;\n payoutType?: 'admin_bonus' | 'creator_payout';\n creatorPercent?: number;\n }): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateTokenBalance', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace license overrides\n *\n * @param request AdminUpdateOverridesRequest containing workspaceId and overrides object\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateWorkspaceOverrides(request: AdminUpdateOverridesRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateOverrides', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates workspace marketplace settings\n *\n * @param request AdminUpdateMarketplaceSettingsRequest containing workspaceId and settings\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails, workspace not found, or user not authorized\n */\n async updateWorkspaceMarketplaceSettings(request: AdminUpdateMarketplaceSettingsRequest): Promise<boolean> {\n try {\n const res = await this.client.requestAsync('admin.workspace.updateMarketplaceSettings', [request]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists token transactions with filtering, pagination, and statistics\n *\n * @param request AdminTokenTransactionsListRequest containing optional filter and pagination options\n *\n * @returns AdminTokenTransactionsListResponse with transactions, total count, and statistics\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listTokenTransactions(request?: AdminTokenTransactionsListRequest): Promise<AdminTokenTransactionsListResponse> {\n try {\n const res = await this.client.requestAsync('admin.tokenTransaction.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists Hailer invoice purchases with filtering, pagination, and workspace grouping\n *\n * @param request AdminInvoiceListRequest containing optional filter and pagination options\n *\n * @returns AdminInvoiceListResponse with invoices, total count, and workspace groups\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listInvoices(request?: AdminInvoiceListRequest): Promise<AdminInvoiceListResponse> {\n try {\n const res = await this.client.requestAsync('admin.invoice.list', [request?.filter, request?.options]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Updates the handled status for one or more Hailer invoice purchases\n *\n * @param request AdminInvoiceUpdateHandledRequest containing purchase ID(s) and handled status\n *\n * @returns AdminInvoiceUpdateHandledResponse with count of updated records\n *\n * @throws {HailerError} if request fails, purchase not found, or not a Hailer invoice purchase\n */\n async updateInvoiceHandled(request: AdminInvoiceUpdateHandledRequest): Promise<AdminInvoiceUpdateHandledResponse> {\n try {\n const res = await this.client.requestAsync('admin.invoice.updateHandled', [request.purchaseIds, request.handled]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Links a subscription purchase to its activity\n *\n * @param purchaseId The purchase to update\n * @param subscriptionActivityId The activity id to associate with the subscription\n *\n * @returns boolean indicating success\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async setSubscriptionActivityId(purchaseId: string, subscriptionActivityId: string): Promise<boolean> {\n try {\n return await this.client.requestAsync('admin.invoice.setSubscriptionActivityId', [purchaseId, subscriptionActivityId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Lists revenue for a given month with optional filtering and pagination\n *\n * @param request AdminRevenueListRequest containing month, year, and optional filter/options\n *\n * @returns AdminRevenueListResponse with revenue rows and totals\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async listMonthlyRevenue(request: AdminRevenueListRequest): Promise<AdminRevenueListResponse> {\n try {\n const res = await this.client.requestAsync('admin.revenue.list', [\n request.month,\n request.year,\n request.filter,\n request.options\n ]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets dashboard statistics including counts for users, workspaces, activities, and messages\n * Includes today's count, total count, last week count, and week-over-week growth percentage\n *\n * @param entities Optional array of entity types to fetch. Defaults to all entities.\n * Valid values: 'users', 'workspaces', 'activities', 'messages', 'userMessages'\n *\n * @returns AdminDashboardStatisticsResponse with statistics for requested entity types\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async getDashboardStatistics(entities?: string[]): Promise<AdminDashboardStatisticsResponse> {\n try {\n const res = await this.client.requestAsync('admin.dashboard.statistics', [entities]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets dashboard trends showing daily creation counts over time\n *\n * @param days Number of days to fetch (30, 90, 180, or 365). Defaults to 30.\n * @param entities Optional array of entity types to fetch. Defaults to ['users', 'workspaces'].\n * Valid values: 'users', 'workspaces'\n *\n * @returns AdminDashboardTrendsResponse with daily counts for requested entity types\n *\n * @throws {HailerError} if request fails or user not authorized\n */\n async getDashboardTrends(days?: 30 | 90 | 180 | 365, entities?: string[]): Promise<AdminDashboardTrendsResponse> {\n try {\n const res = await this.client.requestAsync('admin.dashboard.trends', [days, entities]);\n return res;\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}", "import { Client } from '@wishcore/wish-rpc';\nimport { HailerError } from '../types';\n\nexport interface MetricDefinition {\n id: string;\n name: string;\n description: string;\n category: string;\n supportsTimeRange: boolean;\n supportsBreakdown: boolean;\n}\n\nexport interface MetricData {\n /** Current scalar value (when not grouped into a series) */\n value?: number;\n /** Labels attached to the value */\n labels?: Record<string, string>;\n /** One series per group, each a list of { timestamp, value } */\n timeSeries?: Array<{\n labels: Record<string, string>;\n values: Array<{ timestamp: number; value: number }>;\n }>;\n /** Set if this metric failed */\n error?: boolean;\n /** Failure detail */\n errorMessage?: string;\n}\nexport interface MetricOptions {\n workspaceId?: string;\n userId?: string;\n timeRange?: {\n start: number;\n end: number;\n };\n interval?: '1m' | '5m' | '15m' | '30m' | '1h' | '5h';\n\n // Query Builder options (optional)\n /** Aggregation function to apply */\n aggregation?: 'sum' | 'avg' | 'max' | 'min' | 'count' | 'rate' | 'increase';\n\n /** Group results by specified labels (max 3). Allowed: userId, userRole, workspaceId, teamId, processId, workflowId, discussionId, activityId, signal, type */\n groupBy?: string[];\n\n /** Limit results to top N values (1-100) */\n topk?: number;\n\n /** Additional label filters. Allowed keys: userId, userRole, workspaceId, teamId, processId, workflowId, discussionId, activityId, signal, type */\n labelFilters?: Record<string, string>;\n}\n\nexport interface WorkspaceMetricsListOptions {\n /** Array of workspace IDs to look up */\n workspaceIds?: string[];\n /** Search by workspace name (minimum 3 characters) */\n name?: string;\n}\n\nexport type WorkspaceMetricsListResult = Array<{\n _id: string;\n name: string;\n}>;\n\nexport interface UserMetricsListOptions {\n /** Array of user IDs to look up */\n userIds: string[];\n}\n\nexport type UserMetricsListResult = Array<{\n _id: string;\n name?: string;\n email: string;\n}>;\n\nexport class MetricsApi {\n constructor(private client: Client) {}\n\n /**\n * Get list of available metrics for current user based on permissions\n * @returns Array of metric IDs or detailed metric definitions\n */\n async list(): Promise<string[] | MetricDefinition[]> {\n try {\n return await this.client.requestAsync('metrics.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Get metrics data with optional Query Builder\n * @param metricTypes Single metric or array of metrics to fetch\n * @param options Optional filtering, time range, and Query Builder options\n * @returns Array of metric data, one entry per requested metric (in request order)\n *\n * @example\n * // Simple query\n * await api.metrics.get('hailer.activity.create', { workspaceId: 'abc123' });\n *\n * @example\n * // Query Builder: Top 10 users by activity\n * await api.metrics.get('hailer.activity.create', {\n * workspaceId: 'abc123',\n * timeRange: { start: Date.now() - 86400000, end: Date.now() },\n * aggregation: 'sum',\n * groupBy: ['user'],\n * topk: 10\n * });\n */\n async get(metricTypes: string | string[], options?: MetricOptions): Promise<MetricData[]> {\n try {\n // Backend expects array, convert string to array if needed\n const metricsArray = Array.isArray(metricTypes) ? metricTypes : [metricTypes];\n return await this.client.requestAsync('metrics.get', [metricsArray, options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Admin endpoints for metrics management\n */\n admin = {\n /**\n * Get list of workspaces for admin metrics filtering\n * @param options Lookup by workspaceIds array or name search (min 3 chars)\n * @returns List of workspaces\n *\n * @example\n * // Look up by workspace IDs\n * await api.metrics.admin.workspacesList({ workspaceIds: ['id1', 'id2'] });\n *\n * @example\n * // Search by workspace name\n * await api.metrics.admin.workspacesList({ name: 'Sales' });\n */\n workspacesList: async (options: WorkspaceMetricsListOptions): Promise<WorkspaceMetricsListResult> => {\n try {\n return await this.client.requestAsync('metrics.workspaceSearch', [options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n },\n\n /**\n * Get list of users for admin metrics filtering\n * @param options Lookup by userIds array\n * @returns List of users with _id, name, email\n *\n * @example\n * // Look up by user IDs\n * await api.metrics.admin.usersList({ userIds: ['id1', 'id2'] });\n */\n usersList: async (options: UserMetricsListOptions): Promise<UserMetricsListResult> => {\n try {\n return await this.client.requestAsync('metrics.userList', [options]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n };\n}\n", "import { Client } from '@wishcore/wish-rpc';\n\nexport interface HTTPFetchOptions {\n method?: string;\n headers?: Record<string, string>;\n body?: string;\n}\n\nexport interface HTTPUploadEntry {\n /** Form field name */\n name: string;\n /** Value: plain string for fields, base64 string for files */\n value: string;\n /** When present, entry is a file with this filename (value is base64) */\n filename?: string;\n}\n\nexport interface HTTPFetchResponse {\n status: number;\n statusText: string;\n headers: Record<string, string>;\n body: string;\n}\n\n/**\n * Events emitted by the parent frame for a HTTP WebSocket connection.\n */\ninterface HTTPWsEvent {\n connectionId: string;\n event: 'open' | 'message' | 'close' | 'error';\n data?: string;\n code?: number;\n reason?: string;\n}\n\n/**\n * A WebSocket-like object that proxies through the parent Hailer frame.\n */\nexport class HTTPWebSocket {\n public onopen: ((event: any) => void) | null = null;\n public onmessage: ((event: { data: string }) => void) | null = null;\n public onclose: ((event: { code?: number; reason?: string }) => void) | null =\n null;\n public onerror: ((event: any) => void) | null = null;\n public readyState: number = WebSocket.CONNECTING;\n\n public connectionId: string | null = null;\n\n constructor(\n private client: Client,\n url: string,\n ) {\n // Open a streaming RPC request \u2014 callback fires for each WS event from parent\n this.client.request(\n 'http.ws.open',\n [url],\n (error: any, data: HTTPWsEvent) => {\n if (error) {\n this.readyState = WebSocket.CLOSED;\n this.onerror?.({ error });\n return;\n }\n\n if (!data) {\n return;\n }\n\n // Store connectionId from first event\n if (data.connectionId && !this.connectionId) {\n this.connectionId = data.connectionId;\n }\n\n switch (data.event) {\n case 'open':\n this.readyState = WebSocket.OPEN;\n this.onopen?.({});\n break;\n case 'message':\n this.onmessage?.({ data: data.data ?? '' });\n break;\n case 'close':\n this.readyState = WebSocket.CLOSED;\n this.onclose?.({ code: data.code, reason: data.reason });\n break;\n case 'error':\n this.onerror?.({ error: data.data });\n break;\n }\n },\n );\n }\n\n send(data: string): void {\n if (this.readyState !== WebSocket.OPEN || !this.connectionId) {\n throw new Error('WebSocket is not open');\n }\n this.client\n .requestAsync('http.ws.send', [this.connectionId, data])\n .catch((error) => {\n this.onerror?.({ error });\n });\n }\n\n close(code?: number, reason?: string): void {\n if (this.connectionId) {\n this.client\n .requestAsync('http.ws.close', [this.connectionId, code, reason])\n .catch((error) => {\n this.onerror?.({ error });\n });\n }\n this.readyState = WebSocket.CLOSING;\n }\n}\n\n/**\n * Proxy module for making authenticated HTTP and WebSocket requests\n * through the parent Hailer frame.\n */\nexport class HttpApi {\n constructor(private client: Client) {}\n\n /**\n * Make an HTTP request through the parent frame.\n * The parent's browser context sends the hlrkey cookie automatically.\n */\n async fetch(\n url: string,\n options?: HTTPFetchOptions,\n ): Promise<HTTPFetchResponse> {\n return this.client\n .requestAsync('http.fetch', [url, options])\n .catch((error) => {\n throw error;\n });\n }\n\n /**\n * Upload files through the parent frame as multipart/form-data.\n * Files are sent as base64 strings and reconstructed into FormData by the parent.\n * The parent's browser context sends the hlrkey cookie automatically.\n */\n async upload(\n url: string,\n entries: HTTPUploadEntry[],\n ): Promise<HTTPFetchResponse> {\n return this.client\n .requestAsync('http.upload', [url, entries])\n .catch((error) => {\n throw error;\n });\n }\n\n /**\n * Open a WebSocket connection through the parent frame.\n * Returns a HTTPWebSocket that mimics the native WebSocket API.\n */\n openWebSocket(url: string): HTTPWebSocket {\n return new HTTPWebSocket(this.client, url);\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport {\n CredentialCreateResponse,\n CredentialData,\n CredentialDetails,\n CredentialListItem,\n CredentialType,\n CredentialUpdate,\n HailerError,\n} from '../types';\n\n/**\n * Securely store and retrieve credentials \u2014 API keys, username/password pairs,\n * or any custom key-value secret.\n *\n * Every operation is scoped to credentials bound to your app: the host tags each\n * credential you create with your app's id and re-checks that tag on every read\n * and write, so you can never reach another app's credentials. Credentials\n * created through the SDK are always **personal** \u2014 visible only to the acting\n * user \u2014 and cannot be deleted through the SDK.\n *\n * A workspace app additionally sees, in `list`, the workspace credentials tagged\n * with it that the acting user may read, and can `get` them; those cannot be\n * modified through the SDK.\n *\n * `credential.get` returns the decrypted payload directly \u2014 there is no token\n * exchange.\n */\nexport class CredentialApi {\n constructor(private client: Client) {}\n\n /**\n * Store a new encrypted credential. The credential is personal (owner-only)\n * and is automatically bound to your app \u2014 the host forces the app\n * association and drops any workspace or reader association.\n *\n * @throws {HailerError} if the request fails or the caller lacks permission\n */\n async create(\n name: string,\n type: CredentialType,\n secret: CredentialData,\n ): Promise<CredentialCreateResponse> {\n try {\n return await this.client.requestAsync('credential.create', [{ name, type, secret }]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * List your app's credentials. Encrypted fields are never returned. Results\n * are always scoped to credentials bound to your app.\n */\n async list(): Promise<CredentialListItem[]> {\n try {\n return await this.client.requestAsync('credential.list', []);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Fetch and decrypt one of your app's credentials. The plaintext payload is\n * returned directly in the RPC response \u2014 no token exchange.\n */\n // eslint-disable-next-line @typescript-eslint/naming-convention\n async get<T extends CredentialData = CredentialData>(\n credentialId: string,\n ): Promise<CredentialDetails<T>> {\n try {\n return await this.client.requestAsync('credential.get', [credentialId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Rename or rotate the secret of one of your app's personal credentials. At\n * least one field must be provided in `updates`, and `secret` replaces the\n * entire stored payload \u2014 there is no key-level merge. Workspace\n * credentials cannot be updated through the SDK.\n */\n async update(credentialId: string, updates: CredentialUpdate): Promise<boolean> {\n try {\n return await this.client.requestAsync('credential.update', [credentialId, updates]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n", "import { Client } from '@wishcore/wish-rpc';\nimport { ActionRun, ActionTriggerTarget, HailerError } from '../types';\n\nexport class ActionApi {\n constructor(private client: Client) {}\n\n /**\n * Triggers an action. Waits up to 25 s; a longer run is returned still\n * in progress and must be polled with `getRun`.\n *\n * @param target one of `actionId` or `key`, plus optional `workspaceId` (defaults to the app's workspace)\n * @param input delivered as the payload of a `manual` event\n *\n * @throws {HailerError} if the action is not found or the user may not trigger it\n */\n async trigger(target: ActionTriggerTarget, input?: unknown): Promise<ActionRun> {\n try {\n return await this.client.requestAsync('action.trigger', [target, input ?? null]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n\n /**\n * Gets one run. Non-admins can only read runs they triggered.\n *\n * @throws {HailerError} if the run is not found or the user may not read it\n */\n async getRun(runId: string): Promise<ActionRun> {\n try {\n return await this.client.requestAsync('action.getRun', [runId]);\n } catch (error: any) {\n throw new HailerError(error);\n }\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": ["Client", "write", "opts", "msg", "end", "id", "request", "retval", "err", "op", "args", "resolve", "reject", "data", "cb", "exports", "debug", "Server", "methods", "i", "j", "o", "path", "prefix", "ip", "e", "args", "context", "cb", "result", "copy", "s", "filter", "d", "clientId", "msg", "respond", "id", "err", "data", "op", "client", "send", "ctx", "reqCtx", "exports", "__exportStar", "exports", "import_wish_rpc", "ACTION_RUN_ACTIVE_STATUSES", "CustomError", "message", "code", "HailerError", "error", "UserApi", "client", "userId", "error", "HailerError", "Kanban", "client", "processId", "options", "error", "HailerError", "activityId", "priority", "Ball", "client", "activityId", "toUserId", "error", "HailerError", "discussionIds", "ActivityApi", "client", "Kanban", "Ball", "processId", "phaseId", "options", "error", "HailerError", "activityId", "workflowId", "activities", "requests", "WorkspaceApi", "client", "error", "HailerError", "name", "template", "id", "workspaceId", "productId", "TeamApi", "client", "error", "HailerError", "noSuchMethod", "fileReaders", "workspaceId", "teamId", "userId", "FileApi", "client", "fileId", "error", "HailerError", "file", "filename", "options", "base64Data", "tags", "readers", "fileIds", "scope", "resolve", "reject", "reader", "Activity", "client", "activityId", "options", "processId", "activityIds", "Discussion", "client", "discussionId", "options", "Snackbar", "client", "text", "buttonLabel", "duration", "Files", "client", "file", "filename", "options", "resolve", "reject", "reader", "Workflow", "client", "workflowId", "fieldId", "Ui", "client", "Activity", "Discussion", "Snackbar", "Workflow", "workspaceId", "insightId", "Files", "DEFAULT_ALLOWED_URLS", "DEFAULT_BACKEND_URL", "publicBackendMap", "App", "options", "manifestFile", "location", "manifestUrl", "manifestContent", "appId", "Form", "options", "formsKey", "res", "HailerError", "formsData", "InsightPublicApi", "options", "insightKey", "res", "HailerError", "input", "data", "row", "object", "header", "headerIndex", "ProductPublicApi", "options", "filter", "res", "HailerError", "id", "HailerPublicApi", "options", "InsightPublicApi", "Form", "App", "ProductPublicApi", "WorkflowApi", "client", "error", "HailerError", "workflowId", "workflowSpec", "option", "AppApi", "client", "config", "option", "error", "HailerError", "productId", "workspaceId", "id", "InsightApi", "client", "insightId", "options", "error", "HailerError", "update", "workspaceId", "sources", "query", "PermissionApi", "client", "workspaceId", "error", "HailerError", "ProductApi", "client", "filter", "options", "error", "HailerError", "id", "product", "isPublic", "Payment", "client", "request", "error", "HailerError", "productId", "workspaceId", "Admin", "client", "request", "error", "HailerError", "codeId", "updates", "workspaceId", "purchaseId", "subscriptionActivityId", "entities", "days", "MetricsApi", "client", "options", "error", "HailerError", "metricTypes", "metricsArray", "HTTPWebSocket", "client", "url", "error", "data", "code", "reason", "HttpApi", "options", "entries", "CredentialApi", "client", "name", "type", "secret", "error", "HailerError", "credentialId", "updates", "ActionApi", "client", "target", "input", "error", "HailerError", "runId", "HailerApi", "options", "allowedUrls", "DEFAULT_ALLOWED_URLS", "msg", "UserApi", "AppApi", "ActivityApi", "InsightApi", "WorkspaceApi", "TeamApi", "FileApi", "WorkflowApi", "PermissionApi", "HailerPublicApi", "Ui", "ProductApi", "Payment", "Admin", "MetricsApi", "HttpApi", "CredentialApi", "ActionApi", "registerMessage", "DEFAULT_BACKEND_URL", "config", "error", "url", "event", "data", "publicBackendMap", "end"]
7
7
  }
@@ -16,6 +16,7 @@ import { Admin } from './modules/admin';
16
16
  import { MetricsApi } from './modules/metrics';
17
17
  import { HttpApi } from './modules/http';
18
18
  import { CredentialApi } from './modules/credential';
19
+ import { ActionApi } from './modules/action';
19
20
  export interface Options {
20
21
  /** When connected is called the host is ready to receive calls */
21
22
  connected?: () => void;
@@ -55,6 +56,8 @@ export declare class HailerApi {
55
56
  http: HttpApi;
56
57
  /** Securely store and retrieve credentials (API keys, username/password pairs, etc.) */
57
58
  credential: CredentialApi;
59
+ /** Trigger workspace actions and read back their runs */
60
+ action: ActionApi;
58
61
  /** All public endpoints, which can be accessed while not logged in to Hailer. */
59
62
  public: HailerPublicApi;
60
63
  /** User interface commands */
@@ -0,0 +1,22 @@
1
+ import { Client } from '@wishcore/wish-rpc';
2
+ import { ActionRun, ActionTriggerTarget } from '../types';
3
+ export declare class ActionApi {
4
+ private client;
5
+ constructor(client: Client);
6
+ /**
7
+ * Triggers an action. Waits up to 25 s; a longer run is returned still
8
+ * in progress and must be polled with `getRun`.
9
+ *
10
+ * @param target one of `actionId` or `key`, plus optional `workspaceId` (defaults to the app's workspace)
11
+ * @param input delivered as the payload of a `manual` event
12
+ *
13
+ * @throws {HailerError} if the action is not found or the user may not trigger it
14
+ */
15
+ trigger(target: ActionTriggerTarget, input?: unknown): Promise<ActionRun>;
16
+ /**
17
+ * Gets one run. Non-admins can only read runs they triggered.
18
+ *
19
+ * @throws {HailerError} if the run is not found or the user may not read it
20
+ */
21
+ getRun(runId: string): Promise<ActionRun>;
22
+ }
package/lib/types.d.ts CHANGED
@@ -453,6 +453,42 @@ export interface Settings {
453
453
  theme: 'light' | 'dark';
454
454
  preferredLanguages: string[];
455
455
  }
456
+ /** One of actionId or key. workspaceId is optional, needed with a key in a private app. */
457
+ export interface ActionTriggerTarget {
458
+ actionId?: string;
459
+ key?: string;
460
+ workspaceId?: string;
461
+ }
462
+ /** `queued` and `running` are in progress, the rest are final. */
463
+ export type ActionRunStatus = 'queued' | 'running' | 'completed' | 'runtime_error' | 'timeout' | 'output_limit' | 'infra_error' | 'cancelled' | 'config_error' | 'denied';
464
+ export type ActionEvent = 'manual' | 'phase.activity-created' | 'phase.activity-updated' | 'phase.activity-moved' | 'workspace.member-joined' | 'workspace.member-left' | 'schedule.run';
465
+ export declare const ACTION_RUN_ACTIVE_STATUSES: ActionRunStatus[];
466
+ /** One run of an action. Fields marked "admins only" are absent for other users. */
467
+ export interface ActionRun {
468
+ _id: string;
469
+ actionId: string;
470
+ workspaceId: string;
471
+ event: ActionEvent;
472
+ /** Absent on scheduled runs */
473
+ triggeredBy?: string;
474
+ status: ActionRunStatus;
475
+ exitCode?: number | null;
476
+ /** Return value of `execute(input)` */
477
+ output?: unknown;
478
+ /** Detail for abnormal statuses */
479
+ message?: string | null;
480
+ wallTimeMs?: number | null;
481
+ created: number;
482
+ finishedAt?: number | null;
483
+ /** Admins only */
484
+ arguments?: string;
485
+ /** Admins only */
486
+ stdout?: string | null;
487
+ /** Admins only */
488
+ stderr?: string | null;
489
+ /** Admins only */
490
+ execRunId?: string | null;
491
+ }
456
492
  export type CredentialType = 'basic' | 'apiKey' | 'custom';
457
493
  export interface CredentialBasicData {
458
494
  username: string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hailer/app-sdk",
3
- "version": "2.14.0",
3
+ "version": "2.15.0",
4
4
  "description": "SDK for building Hailer Apps",
5
5
  "author": "",
6
6
  "license": "ISC",