@zhama/tego-plugin-sdk 1.37.1 → 1.40.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 +48 -9
- package/agent/RULES.md +34 -11
- package/agent/guides/agent-templates.md +51 -0
- package/agent/guides/backend.md +8 -0
- package/agent/guides/host-api-versions.md +3 -0
- package/agent/reference/plugin-sdk-api.md +1 -0
- package/agent/rules.json +500 -0
- package/agent/skills/add-agent-template/SKILL.md +19 -0
- package/agent/skills/add-claw-tool/SKILL.md +21 -0
- package/agent/skills/add-i18n-strings/SKILL.md +19 -0
- package/agent/skills/add-migration/SKILL.md +22 -0
- package/agent/skills/add-route-with-access/SKILL.md +30 -0
- package/agent/skills/add-screen/SKILL.md +27 -0
- package/bin/tego-plugin.mjs +7 -3
- package/dist/access.d.cts +1 -0
- package/dist/access.d.ts +1 -0
- package/dist/{chunk-EIVA5BR6.js → chunk-2KXEYXM2.js} +1 -1
- package/dist/{chunk-I5Z3ECC4.js → chunk-44LPR67H.js} +1 -1
- package/dist/chunk-66LDWN4T.cjs +1 -0
- package/dist/{chunk-HZ4YWRYX.cjs → chunk-6EKQMOYT.cjs} +2 -2
- package/dist/{chunk-SKNPNPJP.cjs → chunk-H6GXDFLP.cjs} +1 -1
- package/dist/{chunk-6HNG5OZI.cjs → chunk-IOZFHJ4F.cjs} +1 -1
- package/dist/chunk-JV2G2Z33.js +1 -0
- package/dist/{chunk-4LKRXDYY.cjs → chunk-QQOUNXLC.cjs} +8 -8
- package/dist/{chunk-FCYAAOHC.js → chunk-UZBWS5AR.js} +2 -2
- package/dist/{chunk-56QOZQTY.js → chunk-XOXUS4VI.js} +1 -1
- package/dist/decision-card-IF2c4wvM.d.cts +161 -0
- package/dist/decision-card-IF2c4wvM.d.ts +161 -0
- package/dist/dev.cjs +8 -3
- package/dist/dev.d.cts +33 -2
- package/dist/dev.d.ts +33 -2
- package/dist/dev.js +13 -8
- package/dist/doctor.cjs +15 -8
- package/dist/doctor.d.cts +99 -2
- package/dist/doctor.d.ts +99 -2
- package/dist/doctor.js +15 -8
- package/dist/eslint.cjs +1 -0
- package/dist/eslint.d.cts +29 -0
- package/dist/eslint.d.ts +29 -0
- package/dist/eslint.js +1 -0
- package/dist/hono.d.cts +1 -0
- package/dist/hono.d.ts +1 -0
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +14 -1
- package/dist/index.d.ts +14 -1
- package/dist/index.js +1 -1
- package/dist/manifest.cjs +1 -1
- package/dist/manifest.js +1 -1
- package/dist/pack.cjs +1 -1
- package/dist/pack.d.cts +5 -0
- package/dist/pack.d.ts +5 -0
- package/dist/pack.js +1 -1
- package/dist/publish.cjs +1 -1
- package/dist/publish.js +1 -1
- package/dist/scaffold.cjs +53 -8
- package/dist/scaffold.js +59 -14
- package/dist/server-runtime.cjs +1 -1
- package/dist/server-runtime.d.cts +1 -0
- package/dist/server-runtime.d.ts +1 -0
- package/dist/server-runtime.js +1 -1
- package/dist/server.cjs +1 -1
- package/dist/server.d.cts +25 -0
- package/dist/server.d.ts +25 -0
- package/dist/server.js +1 -1
- package/dist/testing.d.cts +1 -0
- package/dist/testing.d.ts +1 -0
- package/dist/vite.cjs +1 -1
- package/dist/vite.js +1 -1
- package/package.json +8 -1
- /package/dist/{chunk-QKSPPMVN.js → chunk-CDJQ7OPA.js} +0 -0
- /package/dist/{chunk-BN6TGHSB.cjs → chunk-SR5V7ZC2.cjs} +0 -0
package/dist/scaffold.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
var I=Object.defineProperty;var o=(e,t)=>I(e,"name",{value:t,configurable:!0});import{HOST_API_VERSION as $}from"./chunk-
|
|
1
|
+
var I=Object.defineProperty;var o=(e,t)=>I(e,"name",{value:t,configurable:!0});import{HOST_API_VERSION as $}from"./chunk-XOXUS4VI.js";import{existsSync as j,mkdirSync as T,mkdtempSync as U,writeFileSync as q,renameSync as M,rmSync as H}from"fs";import{join as m,dirname as z,resolve as G}from"path";var K=`-- Generated by \`pnpm -F @tego/plugin-sdk access:sql\` from src/access/drizzle.ts. Do not edit.
|
|
2
2
|
CREATE TABLE IF NOT EXISTS "tego_access_assignments" (
|
|
3
3
|
"id" text PRIMARY KEY NOT NULL,
|
|
4
4
|
"tenant_id" text NOT NULL,
|
|
@@ -363,6 +363,18 @@ export default definePluginFrontend({
|
|
|
363
363
|
const { t } = useTranslation();
|
|
364
364
|
const access = useAccess();
|
|
365
365
|
if (access.loading) return <Loading />;
|
|
366
|
+
// Not knowing is not being refused: say why (the backend is down, the network
|
|
367
|
+
// failed) and offer a retry instead of a misleading "no permission".
|
|
368
|
+
if (access.error) {
|
|
369
|
+
const { key, message } = describeApiError(access.error, '${t}');
|
|
370
|
+
return (
|
|
371
|
+
<EmptyState
|
|
372
|
+
icon={<TriangleAlert />}
|
|
373
|
+
title={key ? t(key, { defaultValue: message }) : message}
|
|
374
|
+
action={{ label: t('${t}.crashed.retry'), onClick: access.refetch }}
|
|
375
|
+
/>
|
|
376
|
+
);
|
|
377
|
+
}
|
|
366
378
|
// The catalog's \`menus\` decide who sees a page; the backend still checks every call.
|
|
367
379
|
if (route.page !== 'notFound' && !access.sees(route.page)) {
|
|
368
380
|
return <EmptyState icon={<Lock />} title={t('${t}.errors.permission_required')} />;
|
|
@@ -370,7 +382,8 @@ export default definePluginFrontend({
|
|
|
370
382
|
${s}import { pluginI18nNamespace } from '@tego/plugin-sdk';
|
|
371
383
|
import type { PluginHostContext } from '@tego/plugin-sdk/frontend';
|
|
372
384
|
import {
|
|
373
|
-
|
|
385
|
+
${n?`describeApiError,
|
|
386
|
+
`:""}HostProvider,
|
|
374
387
|
PluginErrorBoundary,
|
|
375
388
|
usePluginRoute,
|
|
376
389
|
} from '@tego/plugin-sdk/react';
|
|
@@ -652,7 +665,7 @@ export function SettingsScreen() {
|
|
|
652
665
|
</section>
|
|
653
666
|
);
|
|
654
667
|
}
|
|
655
|
-
`}o(de,"settingsTsx");function le(e){return{$schema:"../node_modules/@tego/plugin-sdk/access-catalog.schema.json",version:1,groups:[{key:"notes",labelKey:`${e}.access.group.notes`}],scopes:{},permissions:{"note.view":{group:"notes",labelKey:`${e}.access.permission.view`},"note.create":{group:"notes",labelKey:`${e}.access.permission.create`,implies:["note.view"]},"note.delete":{group:"notes",labelKey:`${e}.access.permission.delete`,implies:["note.view"]}},menus:{home:"note.view"},roles:{admin:{nameKey:`${e}.access.role.admin`,descriptionKey:`${e}.access.role.adminDescription`,grants:{"note.view":!0,"note.create":!0,"note.delete":!0,"access.manage":!0}},member:{nameKey:`${e}.access.role.member`,descriptionKey:`${e}.access.role.memberDescription`,grants:{"note.view":!0,"note.create":!0}}},hostRoleBindings:{admin:["admin"],super_admin:["admin"]},defaults:{unassigned:"member"},assignment:{principals:["user","unit"]}}}o(le,"standardAccessCatalog");var pe={nav:{settings:"\u8BBE\u7F6E"},home:{placeholder:"\u5199\u4E00\u6761\u7B14\u8BB0",add:"\u6DFB\u52A0",empty:"\u8FD8\u6CA1\u6709\u7B14\u8BB0",delete:"\u5220\u9664"},settings:{title:"\u8BBE\u7F6E",access:"\u6743\u9650"},crashed:{title:"\u9875\u9762\u51FA\u9519\u4E86",description:"\u8FD9\u4E00\u9875\u6CA1\u80FD\u663E\u793A\u51FA\u6765\u3002\u4F60\u53EF\u4EE5\u91CD\u8BD5\uFF0C\u95EE\u9898\u6301\u7EED\u65F6\u8BF7\u8054\u7CFB\u7BA1\u7406\u5458\u3002",retry:"\u91CD\u8BD5"},errors:{invalid_json:"\u8BF7\u6C42\u683C\u5F0F\u4E0D\u6B63\u786E\u3002",invalid_body:"\u586B\u5199\u7684\u5185\u5BB9\u4E0D\u5B8C\u6574\u6216\u683C\u5F0F\u4E0D\u5BF9\u3002",permission_required:"\u4F60\u6CA1\u6709\u6267\u884C\u8FD9\u4E2A\u64CD\u4F5C\u7684\u6743\u9650\u3002",not_found:"\u6CA1\u6709\u627E\u5230\uFF0C\u6216\u4F60\u65E0\u6743\u67E5\u770B\u3002",no_route:"\u8FD9\u4E2A\u529F\u80FD\u6682\u4E0D\u53EF\u7528\u3002",rate_limited:"\u64CD\u4F5C\u592A\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5\u3002",internal:"\u64CD\u4F5C\u6CA1\u6709\u5B8C\u6210\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5\u3002"},access:{group:{notes:"\u7B14\u8BB0"},permission:{view:"\u67E5\u770B\u7B14\u8BB0",create:"\u6DFB\u52A0\u7B14\u8BB0",delete:"\u5220\u9664\u7B14\u8BB0"},role:{admin:"\u7BA1\u7406\u5458",adminDescription:"\u7BA1\u7406\u5168\u90E8\u7B14\u8BB0\u4E0E\u6743\u9650",member:"\u6210\u5458",memberDescription:"\u67E5\u770B\u4E0E\u6DFB\u52A0\u7B14\u8BB0"}}},me={nav:{settings:"\u8A2D\u5B9A"},home:{placeholder:"\u5BEB\u4E00\u5247\u7B46\u8A18",add:"\u65B0\u589E",empty:"\u9084\u6C92\u6709\u7B46\u8A18",delete:"\u522A\u9664"},settings:{title:"\u8A2D\u5B9A",access:"\u6B0A\u9650"},crashed:{title:"\u9801\u9762\u51FA\u932F\u4E86",description:"\u9019\u4E00\u9801\u6C92\u80FD\u986F\u793A\u51FA\u4F86\u3002\u4F60\u53EF\u4EE5\u91CD\u8A66\uFF0C\u554F\u984C\u6301\u7E8C\u6642\u8ACB\u806F\u7D61\u7BA1\u7406\u54E1\u3002",retry:"\u91CD\u8A66"},errors:{invalid_json:"\u8ACB\u6C42\u683C\u5F0F\u4E0D\u6B63\u78BA\u3002",invalid_body:"\u586B\u5BEB\u7684\u5167\u5BB9\u4E0D\u5B8C\u6574\u6216\u683C\u5F0F\u4E0D\u5C0D\u3002",permission_required:"\u4F60\u6C92\u6709\u57F7\u884C\u9019\u500B\u64CD\u4F5C\u7684\u6B0A\u9650\u3002",not_found:"\u6C92\u6709\u627E\u5230\uFF0C\u6216\u4F60\u7121\u6B0A\u67E5\u770B\u3002",no_route:"\u9019\u500B\u529F\u80FD\u66AB\u4E0D\u53EF\u7528\u3002",rate_limited:"\u64CD\u4F5C\u592A\u983B\u7E41\uFF0C\u8ACB\u7A0D\u5F8C\u518D\u8A66\u3002",internal:"\u64CD\u4F5C\u6C92\u6709\u5B8C\u6210\uFF0C\u8ACB\u7A0D\u5F8C\u91CD\u8A66\u3002"},access:{group:{notes:"\u7B46\u8A18"},permission:{view:"\u67E5\u770B\u7B46\u8A18",create:"\u65B0\u589E\u7B46\u8A18",delete:"\u522A\u9664\u7B46\u8A18"},role:{admin:"\u7BA1\u7406\u54E1",adminDescription:"\u7BA1\u7406\u5168\u90E8\u7B46\u8A18\u8207\u6B0A\u9650",member:"\u6210\u54E1",memberDescription:"\u67E5\u770B\u8207\u65B0\u589E\u7B46\u8A18"}}},T={nav:{settings:"Settings"},home:{placeholder:"Write a note",add:"Add",empty:"No notes yet",delete:"Delete"},settings:{title:"Settings",access:"Access"},crashed:{title:"Something went wrong",description:"This page couldn't be shown. Try again, or contact your admin if it keeps happening.",retry:"Try again"},errors:{invalid_json:"The request was malformed.",invalid_body:"Some fields are missing or invalid.",permission_required:"You don't have permission to do that.",not_found:"Not found, or you can't see it.",no_route:"This feature isn't available.",rate_limited:"Too many requests; try again shortly.",internal:"That didn't go through. Try again later."},access:{group:{notes:"Notes"},permission:{view:"View notes",create:"Add notes",delete:"Delete notes"},role:{admin:"Admin",adminDescription:"Manages all notes and access",member:"Member",memberDescription:"Views and adds notes"}}},ge={nav:{settings:"\u8A2D\u5B9A"},home:{placeholder:"\u30E1\u30E2\u3092\u66F8\u304F",add:"\u8FFD\u52A0",empty:"\u30E1\u30E2\u306F\u307E\u3060\u3042\u308A\u307E\u305B\u3093",delete:"\u524A\u9664"},settings:{title:"\u8A2D\u5B9A",access:"\u6A29\u9650"},crashed:{title:"\u30A8\u30E9\u30FC\u304C\u767A\u751F\u3057\u307E\u3057\u305F",description:"\u3053\u306E\u30DA\u30FC\u30B8\u3092\u8868\u793A\u3067\u304D\u307E\u305B\u3093\u3067\u3057\u305F\u3002\u518D\u8A66\u884C\u3057\u3001\u89E3\u6C7A\u3057\u306A\u3044\u5834\u5408\u306F\u7BA1\u7406\u8005\u306B\u9023\u7D61\u3057\u3066\u304F\u3060\u3055\u3044\u3002",retry:"\u518D\u8A66\u884C"},errors:{invalid_json:"\u30EA\u30AF\u30A8\u30B9\u30C8\u306E\u5F62\u5F0F\u304C\u6B63\u3057\u304F\u3042\u308A\u307E\u305B\u3093\u3002",invalid_body:"\u5165\u529B\u5185\u5BB9\u304C\u4E0D\u8DB3\u3057\u3066\u3044\u308B\u304B\u3001\u5F62\u5F0F\u304C\u6B63\u3057\u304F\u3042\u308A\u307E\u305B\u3093\u3002",permission_required:"\u3053\u306E\u64CD\u4F5C\u3092\u884C\u3046\u6A29\u9650\u304C\u3042\u308A\u307E\u305B\u3093\u3002",not_found:"\u898B\u3064\u304B\u3089\u306A\u3044\u304B\u3001\u8868\u793A\u3059\u308B\u6A29\u9650\u304C\u3042\u308A\u307E\u305B\u3093\u3002",no_route:"\u3053\u306E\u6A5F\u80FD\u306F\u5229\u7528\u3067\u304D\u307E\u305B\u3093\u3002",rate_limited:"\u30EA\u30AF\u30A8\u30B9\u30C8\u304C\u591A\u3059\u304E\u307E\u3059\u3002\u3057\u3070\u3089\u304F\u3057\u3066\u304B\u3089\u518D\u8A66\u884C\u3057\u3066\u304F\u3060\u3055\u3044\u3002",internal:"\u51E6\u7406\u3092\u5B8C\u4E86\u3067\u304D\u307E\u305B\u3093\u3067\u3057\u305F\u3002\u5F8C\u3067\u518D\u8A66\u884C\u3057\u3066\u304F\u3060\u3055\u3044\u3002"},access:{group:{notes:"\u30E1\u30E2"},permission:{view:"\u30E1\u30E2\u3092\u8868\u793A",create:"\u30E1\u30E2\u3092\u8FFD\u52A0",delete:"\u30E1\u30E2\u3092\u524A\u9664"},role:{admin:"\u7BA1\u7406\u8005",adminDescription:"\u3059\u3079\u3066\u306E\u30E1\u30E2\u3068\u6A29\u9650\u3092\u7BA1\u7406",member:"\u30E1\u30F3\u30D0\u30FC",memberDescription:"\u30E1\u30E2\u306E\u8868\u793A\u3068\u8FFD\u52A0"}}},he={nav:{settings:"\uC124\uC815"},home:{placeholder:"\uBA54\uBAA8 \uC791\uC131",add:"\uCD94\uAC00",empty:"\uC544\uC9C1 \uBA54\uBAA8\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4",delete:"\uC0AD\uC81C"},settings:{title:"\uC124\uC815",access:"\uAD8C\uD55C"},crashed:{title:"\uBB38\uC81C\uAC00 \uBC1C\uC0DD\uD588\uC2B5\uB2C8\uB2E4",description:"\uC774 \uD398\uC774\uC9C0\uB97C \uD45C\uC2DC\uD558\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4. \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uACE0, \uACC4\uC18D\uB418\uBA74 \uAD00\uB9AC\uC790\uC5D0\uAC8C \uBB38\uC758\uD558\uC138\uC694.",retry:"\uB2E4\uC2DC \uC2DC\uB3C4"},errors:{invalid_json:"\uC694\uCCAD \uD615\uC2DD\uC774 \uC62C\uBC14\uB974\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4.",invalid_body:"\uC785\uB825 \uB0B4\uC6A9\uC774 \uB204\uB77D\uB418\uC5C8\uAC70\uB098 \uD615\uC2DD\uC774 \uC62C\uBC14\uB974\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4.",permission_required:"\uC774 \uC791\uC5C5\uC744 \uC218\uD589\uD560 \uAD8C\uD55C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4.",not_found:"\uCC3E\uC744 \uC218 \uC5C6\uAC70\uB098 \uBCFC \uAD8C\uD55C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4.",no_route:"\uC774 \uAE30\uB2A5\uC740 \uC0AC\uC6A9\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4.",rate_limited:"\uC694\uCCAD\uC774 \uB108\uBB34 \uB9CE\uC2B5\uB2C8\uB2E4. \uC7A0\uC2DC \uD6C4 \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uC138\uC694.",internal:"\uC791\uC5C5\uC744 \uC644\uB8CC\uD558\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4. \uB098\uC911\uC5D0 \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uC138\uC694."},access:{group:{notes:"\uBA54\uBAA8"},permission:{view:"\uBA54\uBAA8 \uBCF4\uAE30",create:"\uBA54\uBAA8 \uCD94\uAC00",delete:"\uBA54\uBAA8 \uC0AD\uC81C"},role:{admin:"\uAD00\uB9AC\uC790",adminDescription:"\uBAA8\uB4E0 \uBA54\uBAA8\uC640 \uAD8C\uD55C \uAD00\uB9AC",member:"\uBA64\uBC84",memberDescription:"\uBA54\uBAA8 \uBCF4\uAE30 \uBC0F \uCD94\uAC00"}}},fe={nav:{settings:"Einstellungen"},home:{placeholder:"Notiz schreiben",add:"Hinzuf\xFCgen",empty:"Noch keine Notizen",delete:"L\xF6schen"},settings:{title:"Einstellungen",access:"Zugriff"},crashed:{title:"Etwas ist schiefgelaufen",description:"Diese Seite konnte nicht angezeigt werden. Versuche es erneut oder wende dich an deinen Admin.",retry:"Erneut versuchen"},errors:{invalid_json:"Die Anfrage war fehlerhaft.",invalid_body:"Einige Felder fehlen oder sind ung\xFCltig.",permission_required:"Dazu fehlt dir die Berechtigung.",not_found:"Nicht gefunden oder nicht sichtbar f\xFCr dich.",no_route:"Diese Funktion ist nicht verf\xFCgbar.",rate_limited:"Zu viele Anfragen; versuche es gleich noch einmal.",internal:"Das hat nicht geklappt. Versuche es sp\xE4ter erneut."},access:{group:{notes:"Notizen"},permission:{view:"Notizen ansehen",create:"Notizen hinzuf\xFCgen",delete:"Notizen l\xF6schen"},role:{admin:"Admin",adminDescription:"Verwaltet alle Notizen und Zugriffe",member:"Mitglied",memberDescription:"Sieht und erstellt Notizen"}}},Ee={nav:{settings:"Ajustes"},home:{placeholder:"Escribe una nota",add:"A\xF1adir",empty:"A\xFAn no hay notas",delete:"Eliminar"},settings:{title:"Ajustes",access:"Acceso"},crashed:{title:"Algo sali\xF3 mal",description:"No se pudo mostrar esta p\xE1gina. Int\xE9ntalo de nuevo o contacta con tu administrador.",retry:"Reintentar"},errors:{invalid_json:"La solicitud no tiene un formato v\xE1lido.",invalid_body:"Faltan campos o no son v\xE1lidos.",permission_required:"No tienes permiso para hacer eso.",not_found:"No se encontr\xF3 o no puedes verlo.",no_route:"Esta funci\xF3n no est\xE1 disponible.",rate_limited:"Demasiadas solicitudes; int\xE9ntalo en un momento.",internal:"No se pudo completar. Int\xE9ntalo m\xE1s tarde."},access:{group:{notes:"Notas"},permission:{view:"Ver notas",create:"A\xF1adir notas",delete:"Eliminar notas"},role:{admin:"Administrador",adminDescription:"Gestiona todas las notas y el acceso",member:"Miembro",memberDescription:"Ve y a\xF1ade notas"}}},Ce={nav:{settings:"Param\xE8tres"},home:{placeholder:"\xC9crire une note",add:"Ajouter",empty:"Aucune note pour le moment",delete:"Supprimer"},settings:{title:"Param\xE8tres",access:"Acc\xE8s"},crashed:{title:"Un probl\xE8me est survenu",description:"Cette page n'a pas pu s'afficher. R\xE9essayez ou contactez votre administrateur.",retry:"R\xE9essayer"},errors:{invalid_json:"La requ\xEAte n'est pas valide.",invalid_body:"Des champs sont manquants ou invalides.",permission_required:"Vous n'avez pas l'autorisation de faire cela.",not_found:"Introuvable, ou vous ne pouvez pas le voir.",no_route:"Cette fonctionnalit\xE9 n'est pas disponible.",rate_limited:"Trop de requ\xEAtes ; r\xE9essayez dans un instant.",internal:"L'op\xE9ration n'a pas abouti. R\xE9essayez plus tard."},access:{group:{notes:"Notes"},permission:{view:"Voir les notes",create:"Ajouter des notes",delete:"Supprimer des notes"},role:{admin:"Administrateur",adminDescription:"G\xE8re toutes les notes et les acc\xE8s",member:"Membre",memberDescription:"Voit et ajoute des notes"}}},ye={nav:{settings:"Impostazioni"},home:{placeholder:"Scrivi una nota",add:"Aggiungi",empty:"Ancora nessuna nota",delete:"Elimina"},settings:{title:"Impostazioni",access:"Accesso"},crashed:{title:"Qualcosa \xE8 andato storto",description:"Impossibile mostrare questa pagina. Riprova o contatta l'amministratore.",retry:"Riprova"},errors:{invalid_json:"La richiesta non \xE8 valida.",invalid_body:"Alcuni campi mancano o non sono validi.",permission_required:"Non hai il permesso per farlo.",not_found:"Non trovato, o non puoi vederlo.",no_route:"Questa funzione non \xE8 disponibile.",rate_limited:"Troppe richieste; riprova tra poco.",internal:"Operazione non riuscita. Riprova pi\xF9 tardi."},access:{group:{notes:"Note"},permission:{view:"Vedere le note",create:"Aggiungere note",delete:"Eliminare note"},role:{admin:"Amministratore",adminDescription:"Gestisce tutte le note e gli accessi",member:"Membro",memberDescription:"Vede e aggiunge note"}}},be={nav:{settings:"Configura\xE7\xF5es"},home:{placeholder:"Escreva uma nota",add:"Adicionar",empty:"Ainda n\xE3o h\xE1 notas",delete:"Excluir"},settings:{title:"Configura\xE7\xF5es",access:"Acesso"},crashed:{title:"Algo deu errado",description:"N\xE3o foi poss\xEDvel mostrar esta p\xE1gina. Tente novamente ou fale com o administrador.",retry:"Tentar novamente"},errors:{invalid_json:"A solicita\xE7\xE3o est\xE1 malformada.",invalid_body:"Alguns campos est\xE3o faltando ou s\xE3o inv\xE1lidos.",permission_required:"Voc\xEA n\xE3o tem permiss\xE3o para fazer isso.",not_found:"N\xE3o encontrado, ou voc\xEA n\xE3o pode v\xEA-lo.",no_route:"Este recurso n\xE3o est\xE1 dispon\xEDvel.",rate_limited:"Muitas solicita\xE7\xF5es; tente novamente em instantes.",internal:"N\xE3o foi poss\xEDvel concluir. Tente novamente mais tarde."},access:{group:{notes:"Notas"},permission:{view:"Ver notas",create:"Adicionar notas",delete:"Excluir notas"},role:{admin:"Administrador",adminDescription:"Gerencia todas as notas e acessos",member:"Membro",memberDescription:"V\xEA e adiciona notas"}}},Ae={"zh-CN":pe,"zh-TW":me,en:T,ja:ge,ko:he,de:fe,es:Ee,fr:Ce,it:ye,pt:be};function Be(e,t){const n=Ae[e]??T,{nav:s,settings:a,access:i,...r}=n;return t?{...r,nav:s,settings:a,access:i}:r}o(Be,"standardStrings");var f=["standard","minimal"];function p(e){return e.template==="standard"&&e.parts.includes("frontend")&&e.parts.includes("backend")}o(p,"standardAccess");var N={"@tego/plugin-access-ui":"@zhama/tego-plugin-access-ui","@tego/plugin-sdk":"@zhama/tego-plugin-sdk","@tego/ui":"@zhama/tego-ui"};function E(e,t,n){if(n==="workspace")return"workspace:*";const s=N[e];if(!s)throw new Error(`${e} is not a published SDK package`);return`npm:${s}@${t.hostApiRange}`}o(E,"sdkSpec");var C={semi:!0,trailingComma:"es5",singleQuote:!0,printWidth:80,tabWidth:2,useTabs:!1,bracketSpacing:!0,bracketSameLine:!1,arrowParens:"avoid",endOfLine:"lf",quoteProps:"as-needed",jsxSingleQuote:!0,proseWrap:"preserve"},ve=`node_modules/
|
|
668
|
+
`}o(de,"settingsTsx");function le(e){return{$schema:"../node_modules/@tego/plugin-sdk/access-catalog.schema.json",version:1,groups:[{key:"notes",labelKey:`${e}.access.group.notes`}],scopes:{},permissions:{"note.view":{group:"notes",labelKey:`${e}.access.permission.view`},"note.create":{group:"notes",labelKey:`${e}.access.permission.create`,implies:["note.view"]},"note.delete":{group:"notes",labelKey:`${e}.access.permission.delete`,implies:["note.view"]}},menus:{home:"note.view"},roles:{admin:{nameKey:`${e}.access.role.admin`,descriptionKey:`${e}.access.role.adminDescription`,grants:{"note.view":!0,"note.create":!0,"note.delete":!0,"access.manage":!0}},member:{nameKey:`${e}.access.role.member`,descriptionKey:`${e}.access.role.memberDescription`,grants:{"note.view":!0,"note.create":!0}}},hostRoleBindings:{admin:["admin"],super_admin:["admin"]},defaults:{unassigned:"member"},assignment:{principals:["user","unit"]}}}o(le,"standardAccessCatalog");var pe={nav:{settings:"\u8BBE\u7F6E"},home:{placeholder:"\u5199\u4E00\u6761\u7B14\u8BB0",add:"\u6DFB\u52A0",empty:"\u8FD8\u6CA1\u6709\u7B14\u8BB0",delete:"\u5220\u9664"},settings:{title:"\u8BBE\u7F6E",access:"\u6743\u9650"},crashed:{title:"\u9875\u9762\u51FA\u9519\u4E86",description:"\u9875\u9762\u6CA1\u80FD\u663E\u793A\uFF0C\u8BF7\u91CD\u8BD5\u6216\u8054\u7CFB\u7BA1\u7406\u5458\u3002",retry:"\u91CD\u8BD5"},errors:{invalid_json:"\u8BF7\u6C42\u683C\u5F0F\u4E0D\u6B63\u786E\u3002",invalid_body:"\u586B\u5199\u7684\u5185\u5BB9\u4E0D\u5B8C\u6574\u6216\u683C\u5F0F\u4E0D\u5BF9\u3002",permission_required:"\u4F60\u6CA1\u6709\u6267\u884C\u8FD9\u4E2A\u64CD\u4F5C\u7684\u6743\u9650\u3002",not_found:"\u6CA1\u6709\u627E\u5230\uFF0C\u6216\u4F60\u65E0\u6743\u67E5\u770B\u3002",no_route:"\u8FD9\u4E2A\u529F\u80FD\u6682\u4E0D\u53EF\u7528\u3002",rate_limited:"\u64CD\u4F5C\u592A\u9891\u7E41\uFF0C\u8BF7\u7A0D\u540E\u518D\u8BD5\u3002",internal:"\u64CD\u4F5C\u6CA1\u6709\u5B8C\u6210\uFF0C\u8BF7\u7A0D\u540E\u91CD\u8BD5\u3002"},access:{group:{notes:"\u7B14\u8BB0"},permission:{view:"\u67E5\u770B\u7B14\u8BB0",create:"\u6DFB\u52A0\u7B14\u8BB0",delete:"\u5220\u9664\u7B14\u8BB0"},role:{admin:"\u7BA1\u7406\u5458",adminDescription:"\u7BA1\u7406\u5168\u90E8\u7B14\u8BB0\u4E0E\u6743\u9650",member:"\u6210\u5458",memberDescription:"\u67E5\u770B\u4E0E\u6DFB\u52A0\u7B14\u8BB0"}}},me={nav:{settings:"\u8A2D\u5B9A"},home:{placeholder:"\u5BEB\u4E00\u5247\u7B46\u8A18",add:"\u65B0\u589E",empty:"\u9084\u6C92\u6709\u7B46\u8A18",delete:"\u522A\u9664"},settings:{title:"\u8A2D\u5B9A",access:"\u6B0A\u9650"},crashed:{title:"\u9801\u9762\u51FA\u932F\u4E86",description:"\u9801\u9762\u6C92\u80FD\u986F\u793A\uFF0C\u8ACB\u91CD\u8A66\u6216\u806F\u7D61\u7BA1\u7406\u54E1\u3002",retry:"\u91CD\u8A66"},errors:{invalid_json:"\u8ACB\u6C42\u683C\u5F0F\u4E0D\u6B63\u78BA\u3002",invalid_body:"\u586B\u5BEB\u7684\u5167\u5BB9\u4E0D\u5B8C\u6574\u6216\u683C\u5F0F\u4E0D\u5C0D\u3002",permission_required:"\u4F60\u6C92\u6709\u57F7\u884C\u9019\u500B\u64CD\u4F5C\u7684\u6B0A\u9650\u3002",not_found:"\u6C92\u6709\u627E\u5230\uFF0C\u6216\u4F60\u7121\u6B0A\u67E5\u770B\u3002",no_route:"\u9019\u500B\u529F\u80FD\u66AB\u4E0D\u53EF\u7528\u3002",rate_limited:"\u64CD\u4F5C\u592A\u983B\u7E41\uFF0C\u8ACB\u7A0D\u5F8C\u518D\u8A66\u3002",internal:"\u64CD\u4F5C\u6C92\u6709\u5B8C\u6210\uFF0C\u8ACB\u7A0D\u5F8C\u91CD\u8A66\u3002"},access:{group:{notes:"\u7B46\u8A18"},permission:{view:"\u67E5\u770B\u7B46\u8A18",create:"\u65B0\u589E\u7B46\u8A18",delete:"\u522A\u9664\u7B46\u8A18"},role:{admin:"\u7BA1\u7406\u54E1",adminDescription:"\u7BA1\u7406\u5168\u90E8\u7B46\u8A18\u8207\u6B0A\u9650",member:"\u6210\u54E1",memberDescription:"\u67E5\u770B\u8207\u65B0\u589E\u7B46\u8A18"}}},F={nav:{settings:"Settings"},home:{placeholder:"Write a note",add:"Add",empty:"No notes yet",delete:"Delete"},settings:{title:"Settings",access:"Access"},crashed:{title:"Something went wrong",description:"This page couldn't be shown. Try again, or contact your admin if it keeps happening.",retry:"Try again"},errors:{invalid_json:"The request was malformed.",invalid_body:"Some fields are missing or invalid.",permission_required:"You don't have permission to do that.",not_found:"Not found, or you can't see it.",no_route:"This feature isn't available.",rate_limited:"Too many requests; try again shortly.",internal:"That didn't go through. Try again later."},access:{group:{notes:"Notes"},permission:{view:"View notes",create:"Add notes",delete:"Delete notes"},role:{admin:"Admin",adminDescription:"Manages all notes and access",member:"Member",memberDescription:"Views and adds notes"}}},ge={nav:{settings:"\u8A2D\u5B9A"},home:{placeholder:"\u30E1\u30E2\u3092\u66F8\u304F",add:"\u8FFD\u52A0",empty:"\u30E1\u30E2\u306F\u307E\u3060\u3042\u308A\u307E\u305B\u3093",delete:"\u524A\u9664"},settings:{title:"\u8A2D\u5B9A",access:"\u6A29\u9650"},crashed:{title:"\u30A8\u30E9\u30FC\u304C\u767A\u751F\u3057\u307E\u3057\u305F",description:"\u3053\u306E\u30DA\u30FC\u30B8\u3092\u8868\u793A\u3067\u304D\u307E\u305B\u3093\u3067\u3057\u305F\u3002\u518D\u8A66\u884C\u3057\u3001\u89E3\u6C7A\u3057\u306A\u3044\u5834\u5408\u306F\u7BA1\u7406\u8005\u306B\u9023\u7D61\u3057\u3066\u304F\u3060\u3055\u3044\u3002",retry:"\u518D\u8A66\u884C"},errors:{invalid_json:"\u30EA\u30AF\u30A8\u30B9\u30C8\u306E\u5F62\u5F0F\u304C\u6B63\u3057\u304F\u3042\u308A\u307E\u305B\u3093\u3002",invalid_body:"\u5165\u529B\u5185\u5BB9\u304C\u4E0D\u8DB3\u3057\u3066\u3044\u308B\u304B\u3001\u5F62\u5F0F\u304C\u6B63\u3057\u304F\u3042\u308A\u307E\u305B\u3093\u3002",permission_required:"\u3053\u306E\u64CD\u4F5C\u3092\u884C\u3046\u6A29\u9650\u304C\u3042\u308A\u307E\u305B\u3093\u3002",not_found:"\u898B\u3064\u304B\u3089\u306A\u3044\u304B\u3001\u8868\u793A\u3059\u308B\u6A29\u9650\u304C\u3042\u308A\u307E\u305B\u3093\u3002",no_route:"\u3053\u306E\u6A5F\u80FD\u306F\u5229\u7528\u3067\u304D\u307E\u305B\u3093\u3002",rate_limited:"\u30EA\u30AF\u30A8\u30B9\u30C8\u304C\u591A\u3059\u304E\u307E\u3059\u3002\u3057\u3070\u3089\u304F\u3057\u3066\u304B\u3089\u518D\u8A66\u884C\u3057\u3066\u304F\u3060\u3055\u3044\u3002",internal:"\u51E6\u7406\u3092\u5B8C\u4E86\u3067\u304D\u307E\u305B\u3093\u3067\u3057\u305F\u3002\u5F8C\u3067\u518D\u8A66\u884C\u3057\u3066\u304F\u3060\u3055\u3044\u3002"},access:{group:{notes:"\u30E1\u30E2"},permission:{view:"\u30E1\u30E2\u3092\u8868\u793A",create:"\u30E1\u30E2\u3092\u8FFD\u52A0",delete:"\u30E1\u30E2\u3092\u524A\u9664"},role:{admin:"\u7BA1\u7406\u8005",adminDescription:"\u3059\u3079\u3066\u306E\u30E1\u30E2\u3068\u6A29\u9650\u3092\u7BA1\u7406",member:"\u30E1\u30F3\u30D0\u30FC",memberDescription:"\u30E1\u30E2\u306E\u8868\u793A\u3068\u8FFD\u52A0"}}},he={nav:{settings:"\uC124\uC815"},home:{placeholder:"\uBA54\uBAA8 \uC791\uC131",add:"\uCD94\uAC00",empty:"\uC544\uC9C1 \uBA54\uBAA8\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4",delete:"\uC0AD\uC81C"},settings:{title:"\uC124\uC815",access:"\uAD8C\uD55C"},crashed:{title:"\uBB38\uC81C\uAC00 \uBC1C\uC0DD\uD588\uC2B5\uB2C8\uB2E4",description:"\uC774 \uD398\uC774\uC9C0\uB97C \uD45C\uC2DC\uD558\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4. \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uACE0, \uACC4\uC18D\uB418\uBA74 \uAD00\uB9AC\uC790\uC5D0\uAC8C \uBB38\uC758\uD558\uC138\uC694.",retry:"\uB2E4\uC2DC \uC2DC\uB3C4"},errors:{invalid_json:"\uC694\uCCAD \uD615\uC2DD\uC774 \uC62C\uBC14\uB974\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4.",invalid_body:"\uC785\uB825 \uB0B4\uC6A9\uC774 \uB204\uB77D\uB418\uC5C8\uAC70\uB098 \uD615\uC2DD\uC774 \uC62C\uBC14\uB974\uC9C0 \uC54A\uC2B5\uB2C8\uB2E4.",permission_required:"\uC774 \uC791\uC5C5\uC744 \uC218\uD589\uD560 \uAD8C\uD55C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4.",not_found:"\uCC3E\uC744 \uC218 \uC5C6\uAC70\uB098 \uBCFC \uAD8C\uD55C\uC774 \uC5C6\uC2B5\uB2C8\uB2E4.",no_route:"\uC774 \uAE30\uB2A5\uC740 \uC0AC\uC6A9\uD560 \uC218 \uC5C6\uC2B5\uB2C8\uB2E4.",rate_limited:"\uC694\uCCAD\uC774 \uB108\uBB34 \uB9CE\uC2B5\uB2C8\uB2E4. \uC7A0\uC2DC \uD6C4 \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uC138\uC694.",internal:"\uC791\uC5C5\uC744 \uC644\uB8CC\uD558\uC9C0 \uBABB\uD588\uC2B5\uB2C8\uB2E4. \uB098\uC911\uC5D0 \uB2E4\uC2DC \uC2DC\uB3C4\uD558\uC138\uC694."},access:{group:{notes:"\uBA54\uBAA8"},permission:{view:"\uBA54\uBAA8 \uBCF4\uAE30",create:"\uBA54\uBAA8 \uCD94\uAC00",delete:"\uBA54\uBAA8 \uC0AD\uC81C"},role:{admin:"\uAD00\uB9AC\uC790",adminDescription:"\uBAA8\uB4E0 \uBA54\uBAA8\uC640 \uAD8C\uD55C \uAD00\uB9AC",member:"\uBA64\uBC84",memberDescription:"\uBA54\uBAA8 \uBCF4\uAE30 \uBC0F \uCD94\uAC00"}}},fe={nav:{settings:"Einstellungen"},home:{placeholder:"Notiz schreiben",add:"Hinzuf\xFCgen",empty:"Noch keine Notizen",delete:"L\xF6schen"},settings:{title:"Einstellungen",access:"Zugriff"},crashed:{title:"Etwas ist schiefgelaufen",description:"Diese Seite konnte nicht angezeigt werden. Versuche es erneut oder wende dich an deinen Admin.",retry:"Erneut versuchen"},errors:{invalid_json:"Die Anfrage war fehlerhaft.",invalid_body:"Einige Felder fehlen oder sind ung\xFCltig.",permission_required:"Dazu fehlt dir die Berechtigung.",not_found:"Nicht gefunden oder nicht sichtbar f\xFCr dich.",no_route:"Diese Funktion ist nicht verf\xFCgbar.",rate_limited:"Zu viele Anfragen; versuche es gleich noch einmal.",internal:"Das hat nicht geklappt. Versuche es sp\xE4ter erneut."},access:{group:{notes:"Notizen"},permission:{view:"Notizen ansehen",create:"Notizen hinzuf\xFCgen",delete:"Notizen l\xF6schen"},role:{admin:"Admin",adminDescription:"Verwaltet alle Notizen und Zugriffe",member:"Mitglied",memberDescription:"Sieht und erstellt Notizen"}}},Ee={nav:{settings:"Ajustes"},home:{placeholder:"Escribe una nota",add:"A\xF1adir",empty:"A\xFAn no hay notas",delete:"Eliminar"},settings:{title:"Ajustes",access:"Acceso"},crashed:{title:"Algo sali\xF3 mal",description:"No se pudo mostrar esta p\xE1gina. Int\xE9ntalo de nuevo o contacta con tu administrador.",retry:"Reintentar"},errors:{invalid_json:"La solicitud no tiene un formato v\xE1lido.",invalid_body:"Faltan campos o no son v\xE1lidos.",permission_required:"No tienes permiso para hacer eso.",not_found:"No se encontr\xF3 o no puedes verlo.",no_route:"Esta funci\xF3n no est\xE1 disponible.",rate_limited:"Demasiadas solicitudes; int\xE9ntalo en un momento.",internal:"No se pudo completar. Int\xE9ntalo m\xE1s tarde."},access:{group:{notes:"Notas"},permission:{view:"Ver notas",create:"A\xF1adir notas",delete:"Eliminar notas"},role:{admin:"Administrador",adminDescription:"Gestiona todas las notas y el acceso",member:"Miembro",memberDescription:"Ve y a\xF1ade notas"}}},Ce={nav:{settings:"Param\xE8tres"},home:{placeholder:"\xC9crire une note",add:"Ajouter",empty:"Aucune note pour le moment",delete:"Supprimer"},settings:{title:"Param\xE8tres",access:"Acc\xE8s"},crashed:{title:"Un probl\xE8me est survenu",description:"Cette page n'a pas pu s'afficher. R\xE9essayez ou contactez votre administrateur.",retry:"R\xE9essayer"},errors:{invalid_json:"La requ\xEAte n'est pas valide.",invalid_body:"Des champs sont manquants ou invalides.",permission_required:"Vous n'avez pas l'autorisation de faire cela.",not_found:"Introuvable, ou vous ne pouvez pas le voir.",no_route:"Cette fonctionnalit\xE9 n'est pas disponible.",rate_limited:"Trop de requ\xEAtes ; r\xE9essayez dans un instant.",internal:"L'op\xE9ration n'a pas abouti. R\xE9essayez plus tard."},access:{group:{notes:"Notes"},permission:{view:"Voir les notes",create:"Ajouter des notes",delete:"Supprimer des notes"},role:{admin:"Administrateur",adminDescription:"G\xE8re toutes les notes et les acc\xE8s",member:"Membre",memberDescription:"Voit et ajoute des notes"}}},ye={nav:{settings:"Impostazioni"},home:{placeholder:"Scrivi una nota",add:"Aggiungi",empty:"Ancora nessuna nota",delete:"Elimina"},settings:{title:"Impostazioni",access:"Accesso"},crashed:{title:"Qualcosa \xE8 andato storto",description:"Impossibile mostrare questa pagina. Riprova o contatta l'amministratore.",retry:"Riprova"},errors:{invalid_json:"La richiesta non \xE8 valida.",invalid_body:"Alcuni campi mancano o non sono validi.",permission_required:"Non hai il permesso per farlo.",not_found:"Non trovato, o non puoi vederlo.",no_route:"Questa funzione non \xE8 disponibile.",rate_limited:"Troppe richieste; riprova tra poco.",internal:"Operazione non riuscita. Riprova pi\xF9 tardi."},access:{group:{notes:"Note"},permission:{view:"Vedere le note",create:"Aggiungere note",delete:"Eliminare note"},role:{admin:"Amministratore",adminDescription:"Gestisce tutte le note e gli accessi",member:"Membro",memberDescription:"Vede e aggiunge note"}}},be={nav:{settings:"Configura\xE7\xF5es"},home:{placeholder:"Escreva uma nota",add:"Adicionar",empty:"Ainda n\xE3o h\xE1 notas",delete:"Excluir"},settings:{title:"Configura\xE7\xF5es",access:"Acesso"},crashed:{title:"Algo deu errado",description:"N\xE3o foi poss\xEDvel mostrar esta p\xE1gina. Tente novamente ou fale com o administrador.",retry:"Tentar novamente"},errors:{invalid_json:"A solicita\xE7\xE3o est\xE1 malformada.",invalid_body:"Alguns campos est\xE3o faltando ou s\xE3o inv\xE1lidos.",permission_required:"Voc\xEA n\xE3o tem permiss\xE3o para fazer isso.",not_found:"N\xE3o encontrado, ou voc\xEA n\xE3o pode v\xEA-lo.",no_route:"Este recurso n\xE3o est\xE1 dispon\xEDvel.",rate_limited:"Muitas solicita\xE7\xF5es; tente novamente em instantes.",internal:"N\xE3o foi poss\xEDvel concluir. Tente novamente mais tarde."},access:{group:{notes:"Notas"},permission:{view:"Ver notas",create:"Adicionar notas",delete:"Excluir notas"},role:{admin:"Administrador",adminDescription:"Gerencia todas as notas e acessos",member:"Membro",memberDescription:"V\xEA e adiciona notas"}}},Ae={"zh-CN":pe,"zh-TW":me,en:F,ja:ge,ko:he,de:fe,es:Ee,fr:Ce,it:ye,pt:be};function ve(e,t){const n=Ae[e]??F,{nav:s,settings:a,access:i,...r}=n;return t?{...r,nav:s,settings:a,access:i}:r}o(ve,"standardStrings");var f=["standard","minimal"];function p(e){return e.template==="standard"&&e.parts.includes("frontend")&&e.parts.includes("backend")}o(p,"standardAccess");var N={"@tego/plugin-access-ui":"@zhama/tego-plugin-access-ui","@tego/plugin-sdk":"@zhama/tego-plugin-sdk","@tego/ui":"@zhama/tego-ui"};function E(e,t,n){if(n==="workspace")return"workspace:*";const s=N[e];if(!s)throw new Error(`${e} is not a published SDK package`);return`npm:${s}@${t.hostApiRange}`}o(E,"sdkSpec");var C={semi:!0,trailingComma:"es5",singleQuote:!0,printWidth:80,tabWidth:2,useTabs:!1,bracketSpacing:!0,bracketSameLine:!1,arrowParens:"avoid",endOfLine:"lf",quoteProps:"as-needed",jsxSingleQuote:!0,proseWrap:"preserve"},Be=`node_modules/
|
|
656
669
|
build/
|
|
657
670
|
dist/
|
|
658
671
|
frontend/dist/
|
|
@@ -663,7 +676,8 @@ coverage/
|
|
|
663
676
|
.tego-dev/
|
|
664
677
|
`,xe=`allowBuilds:
|
|
665
678
|
esbuild: true
|
|
666
|
-
`,D={"tsconfig.base.json":{$schema:"https://json.schemastore.org/tsconfig",compilerOptions:{strict:!0,useUnknownInCatchVariables:!0,allowJs:!0,skipLibCheck:!0,forceConsistentCasingInFileNames:!0,resolveJsonModule:!0,isolatedModules:!0,verbatimModuleSyntax:!0,declaration:!0,declarationMap:!0,esModuleInterop:!0,incremental:!1,noUncheckedIndexedAccess:!0,moduleDetection:"force",exactOptionalPropertyTypes:!0,target:"ES2022",lib:["ES2022","DOM","DOM.Iterable"],module:"ESNext",moduleResolution:"bundler"},exclude:["node_modules"]},"tsconfig.frontend.json":{$schema:"https://json.schemastore.org/tsconfig",extends:"./tsconfig.base.json",compilerOptions:{target:"ES2020",lib:["ES2020","DOM","DOM.Iterable"],module:"ESNext",moduleResolution:"bundler",jsx:"react-jsx",noEmit:!1,declaration:!0,declarationMap:!0,outDir:"dist"}},"tsconfig.backend.json":{$schema:"https://json.schemastore.org/tsconfig",extends:"./tsconfig.base.json",compilerOptions:{target:"ES2022",lib:["ES2022"],module:"ESNext",moduleResolution:"bundler",types:["node"],noEmit:!1,declaration:!0,declarationMap:!0,outDir:"dist"}}};function g(e,t){return t==="workspace"?`@tego/tsconfig/plugin-${e}.json`:`../tsconfig.${e}.json`}o(g,"tsconfigPreset");var
|
|
679
|
+
`,D={"tsconfig.base.json":{$schema:"https://json.schemastore.org/tsconfig",compilerOptions:{strict:!0,useUnknownInCatchVariables:!0,allowJs:!0,skipLibCheck:!0,forceConsistentCasingInFileNames:!0,resolveJsonModule:!0,isolatedModules:!0,verbatimModuleSyntax:!0,declaration:!0,declarationMap:!0,esModuleInterop:!0,incremental:!1,noUncheckedIndexedAccess:!0,moduleDetection:"force",exactOptionalPropertyTypes:!0,target:"ES2022",lib:["ES2022","DOM","DOM.Iterable"],module:"ESNext",moduleResolution:"bundler"},exclude:["node_modules"]},"tsconfig.frontend.json":{$schema:"https://json.schemastore.org/tsconfig",extends:"./tsconfig.base.json",compilerOptions:{target:"ES2020",lib:["ES2020","DOM","DOM.Iterable"],module:"ESNext",moduleResolution:"bundler",jsx:"react-jsx",noEmit:!1,declaration:!0,declarationMap:!0,outDir:"dist"}},"tsconfig.backend.json":{$schema:"https://json.schemastore.org/tsconfig",extends:"./tsconfig.base.json",compilerOptions:{target:"ES2022",lib:["ES2022"],module:"ESNext",moduleResolution:"bundler",types:["node"],noEmit:!1,declaration:!0,declarationMap:!0,outDir:"dist"}}};function g(e,t){return t==="workspace"?`@tego/tsconfig/plugin-${e}.json`:`../tsconfig.${e}.json`}o(g,"tsconfigPreset");var Te=`import js from '@eslint/js';
|
|
680
|
+
import { tegoPluginEslint } from '@tego/plugin-sdk/eslint';
|
|
667
681
|
import prettierConfig from 'eslint-config-prettier';
|
|
668
682
|
import prettier from 'eslint-plugin-prettier';
|
|
669
683
|
import reactHooks from 'eslint-plugin-react-hooks';
|
|
@@ -677,6 +691,8 @@ export default tseslint.config(
|
|
|
677
691
|
'dist/**',
|
|
678
692
|
'**/dist/**',
|
|
679
693
|
'.turbo/**',
|
|
694
|
+
// The local preview's generated shell and backend build.
|
|
695
|
+
'.tego-dev/**',
|
|
680
696
|
'node_modules/**',
|
|
681
697
|
],
|
|
682
698
|
},
|
|
@@ -693,15 +709,17 @@ export default tseslint.config(
|
|
|
693
709
|
'prettier/prettier': 'warn',
|
|
694
710
|
},
|
|
695
711
|
},
|
|
712
|
+
// The platform's rules (TP-* ids from tego-plugin doctor), flagged while you type.
|
|
713
|
+
...tegoPluginEslint(),
|
|
696
714
|
prettierConfig
|
|
697
715
|
);
|
|
698
|
-
`,
|
|
699
|
-
`}o(u,"json");function
|
|
716
|
+
`,Fe={"@eslint/js":"^9.16.0","eslint-config-prettier":"^10.1.8","eslint-plugin-prettier":"^5.5.4","eslint-plugin-react-hooks":"^5.2.0",globals:"^15.13.0","typescript-eslint":"^8.17.0"};function Ne(){return[{path:".prettierrc.json",contents:u(C)},{path:".gitignore",contents:Be},{path:"pnpm-workspace.yaml",contents:xe},...Object.entries(D).map(([e,t])=>({path:e,contents:u(t)}))]}o(Ne,"standaloneRootFiles");var De={"@typescript/native-preview":"7.0.0-dev.20260519.1",eslint:"^9.39.1",prettier:"^3.7.4",typescript:"^5.9.3"},ke=["zh-CN","zh-TW","en","ja","ko","de","es","fr","it","pt"];function y(e){return`@tego/plugin-${e.replace(/^tego-/,"")}`}o(y,"packageNameFor");function b(e){return e.replace(/^tego-/,"")}o(b,"keyNamespaceFor");function u(e){return`${JSON.stringify(e,null,2)}
|
|
717
|
+
`}o(u,"json");function _e(e){const t=b(e.id),n=e.parts.includes("frontend"),s=e.parts.includes("backend"),a=e.parts.includes("claw"),i={};n&&(i.frontend={icon:"puzzle",nav:[{key:"home",labelKey:`${t}.nav.home`,icon:"layout-dashboard",order:0,path:"/home"}]}),s&&(i.backend={limits:{memoryMb:256,requestTimeoutMs:15e3}}),a&&(i.claw={hooks:{}});const r={manifestVersion:1,id:e.id,version:"0.1.0",displayName:{"zh-CN":e.displayNameZh,en:e.displayNameEn},description:{"zh-CN":e.descriptionZh,en:e.descriptionEn},author:"Tego"};return(n||s)&&(r.hostApiRange=e.hostApiRange),r.scope=e.scope,s&&(r.declares={database:!0}),r.parts=i,p(e)&&(i.frontend.nav.push({key:"settings",labelKey:`${t}.nav.settings`,icon:"settings",order:1,path:"/settings"}),r.access={catalog:"shared/access.json"},r.permissions={required:["directory.read"]},r.declares={database:!0,events:!0}),{path:"tego.plugin.json",contents:u(r)}}o(_e,"manifest");function we(e,t){const n=e.parts.includes("frontend"),s=e.parts.includes("backend"),a=e.parts.includes("claw"),i=["tsgo --noEmit -p shared/tsconfig.json"];n&&i.push("tsgo --noEmit -p frontend/tsconfig.json"),s&&i.push("tsgo --noEmit -p backend/tsconfig.json"),a&&i.push("tsgo --noEmit -p claw/tsconfig.json");const r={"@tego/plugin-sdk":E("@tego/plugin-sdk",e,t),"@types/node":"^22.10.1",vitest:"^4.1.10"};t==="workspace"&&Object.assign(r,{"@tego/eslint-config":"workspace:*","@tego/tsconfig":"workspace:*"}),n&&Object.assign(r,{"@tanstack/react-query":"^5.62.7","@tego/ui":E("@tego/ui",e,t),"@types/react":"^19.2.1","@types/react-dom":"^19.2.1","lucide-react":"^0.469.0",react:"^19.0.0","react-dom":"^19.0.0","react-i18next":"15.4.1",vite:"^6.3.5"}),s&&Object.assign(r,{"@types/pg":"^8.11.10",hono:"^4.10.7",pg:"^8.13.1"}),a&&(r.typebox="1.3.16"),e.template==="standard"&&(n&&(r.tailwindcss="^3.4.19"),s&&(r.zod="^3.24.1"),p(e)&&(r["@tego/plugin-access-ui"]=E("@tego/plugin-access-ui",e,t))),t==="npm"&&Object.assign(r,De,Fe);const c={name:y(e.id),version:"0.1.0",private:!0,type:"module",description:e.descriptionEn,scripts:{build:"tego-plugin-pack",watch:"tego-plugin-pack --watch",dev:"tego-plugin dev",doctor:"tego-plugin doctor",check:"tego-plugin check","type-check":i.join(" && "),lint:"eslint .","lint:fix":"eslint . --fix",test:"vitest run",...t==="npm"?{format:"prettier --write .","format:check":"prettier --check ."}:{}},devDependencies:Se(r)};return{path:"package.json",contents:u(c)}}o(we,"rootPackageJson");function Se(e){const t={};for(const n of Object.keys(e).sort())t[n]=e[n];return t}o(Se,"sortedRecord");function Oe(e){return e==="npm"?{path:"eslint.config.js",contents:Te}:{path:"eslint.config.js",contents:`import baseConfig from '@tego/eslint-config';
|
|
700
718
|
|
|
701
719
|
export default [
|
|
702
720
|
...baseConfig,
|
|
703
721
|
{
|
|
704
|
-
ignores: ['build/**', 'dist/**', '**/dist/**', '.turbo/**'],
|
|
722
|
+
ignores: ['build/**', 'dist/**', '**/dist/**', '.turbo/**', '.tego-dev/**'],
|
|
705
723
|
},
|
|
706
724
|
];
|
|
707
725
|
`}}o(Oe,"eslintConfig");function Le(e){return[{path:"shared/tsconfig.json",contents:u({extends:g("backend",e),compilerOptions:{noEmit:!0,declaration:!1,declarationMap:!1},include:["**/*.ts"]})},{path:"shared/index.ts",contents:`export {};
|
|
@@ -730,7 +748,7 @@ export default defineConfig({
|
|
|
730
748
|
hookTimeout: 30_000,
|
|
731
749
|
},
|
|
732
750
|
});
|
|
733
|
-
`}}o(Pe,"vitestConfig");function Re(e,t){if(t==="npm")return
|
|
751
|
+
`}}o(Pe,"vitestConfig");function Re(e,t){if(t==="npm")return $e(e);const n=y(e.id);return{path:"README.md",contents:`# ${e.displayNameEn}
|
|
734
752
|
|
|
735
753
|
${e.descriptionEn}
|
|
736
754
|
|
|
@@ -749,7 +767,30 @@ pnpm -F ${n} build
|
|
|
749
767
|
|
|
750
768
|
Run \`pnpm install\` once after generating, so the new package links into the
|
|
751
769
|
workspace and \`@tego/plugin-sdk\` resolves.
|
|
752
|
-
`}}o(Re,"readme");function Ie(e){return{path:"
|
|
770
|
+
`}}o(Re,"readme");function Ie(e,t){const n="node_modules/@tego/plugin-sdk",s=t==="npm"?"npm run":"pnpm";return[{path:"AGENTS.md",contents:`# ${e.displayNameEn} \u2014 agent guide
|
|
771
|
+
|
|
772
|
+
This is a Tego platform plugin (\`tego.plugin.json\`). It runs inside Tego: its frontend in both
|
|
773
|
+
the web app and the desktop app, its backend in a platform container. Follow the platform's rules;
|
|
774
|
+
they ship with the SDK this plugin installed:
|
|
775
|
+
|
|
776
|
+
- \`${n}/agent/RULES.md\` \u2014 every rule, with the guide that explains it. Read it first.
|
|
777
|
+
- \`${n}/agent/guides/*.md\` \u2014 read the guide for the kind of code you are about to write
|
|
778
|
+
(frontend, ui, i18n, backend, storage, access, migrations, claw, testing, agent-templates\u2026).
|
|
779
|
+
- \`${n}/agent/skills/*/SKILL.md\` \u2014 step-by-step playbooks for common changes (a route with
|
|
780
|
+
access control, a screen, a migration, strings, a claw tool, an agent template).
|
|
781
|
+
- \`${n}/agent/reference/plugin-sdk-api.md\` \u2014 the full API; look signatures up instead of guessing.
|
|
782
|
+
|
|
783
|
+
## Working loop
|
|
784
|
+
|
|
785
|
+
1. Read the rules, the relevant guide and the code you change.
|
|
786
|
+
2. Make focused changes with the SDK's helpers (\`@tego/plugin-sdk/react\`, \`/hono\`, \`/testing\`)
|
|
787
|
+
and \`@tego/ui\` components.
|
|
788
|
+
3. Run \`${s} check\` (doctor, lint, type-check, test) and fix everything it reports. Never weaken a
|
|
789
|
+
check, a rule or a test to make it pass; a \`tego-doctor-ignore\` needs a real reason.
|
|
790
|
+
4. Every new user-visible string goes into all ten locales.
|
|
791
|
+
5. \`${s} build\` writes the uploadable archive; \`${s} dev\` previews the plugin locally.
|
|
792
|
+
`},{path:"CLAUDE.md",contents:`@AGENTS.md
|
|
793
|
+
`}]}o(Ie,"agentFiles");function $e(e){return{path:"README.md",contents:`# ${e.displayNameEn}
|
|
753
794
|
|
|
754
795
|
${e.descriptionEn}
|
|
755
796
|
|
|
@@ -770,7 +811,7 @@ npm run build # writes the uploadable archive
|
|
|
770
811
|
|
|
771
812
|
\`hostApiRange\` in \`tego.plugin.json\` and the SDK ranges in \`package.json\`
|
|
772
813
|
move together: raise both when the plugin starts using a newer host API.
|
|
773
|
-
`}}o(
|
|
814
|
+
`}}o($e,"standaloneReadme");function je(e,t){const n=b(e.id),s=`import { readFile, readdir } from 'node:fs/promises';
|
|
774
815
|
import { resolve } from 'node:path';
|
|
775
816
|
|
|
776
817
|
import { tegoPluginFrontend } from '@tego/plugin-sdk/vite';
|
|
@@ -881,7 +922,7 @@ export function App({ ctx }: { ctx: PluginHostContext }) {
|
|
|
881
922
|
</PluginErrorBoundary>
|
|
882
923
|
);
|
|
883
924
|
}
|
|
884
|
-
`,c=e.template==="standard",d=c?[{path:"frontend/tsconfig.json",contents:a},...Z({id:e.id,ns:n,withBackend:e.parts.includes("backend"),withAccess:p(e)})]:[{path:"frontend/vite.config.ts",contents:s},{path:"frontend/tsconfig.json",contents:a},{path:"frontend/src/index.tsx",contents:i},{path:"frontend/src/app.tsx",contents:r}];for(const l of
|
|
925
|
+
`,c=e.template==="standard",d=c?[{path:"frontend/tsconfig.json",contents:a},...Z({id:e.id,ns:n,withBackend:e.parts.includes("backend"),withAccess:p(e)})]:[{path:"frontend/vite.config.ts",contents:s},{path:"frontend/tsconfig.json",contents:a},{path:"frontend/src/index.tsx",contents:i},{path:"frontend/src/app.tsx",contents:r}];for(const l of ke){const h=l==="zh-CN",x={nav:{home:h?"\u9996\u9875":"Home"},home:{title:h?e.displayNameZh:e.displayNameEn,description:h?e.descriptionZh:e.descriptionEn}},R={[n]:c?k(x,ve(l,p(e))):x};d.push({path:`frontend/i18n/${l}.json`,contents:u(R)})}return d}o(je,"frontendFiles");function k(e,t){const n={...e};for(const[s,a]of Object.entries(t)){const i=n[s];n[s]=i&&typeof i=="object"&&a&&typeof a=="object"?k(i,a):a}return n}o(k,"mergeStrings");function Ue(e,t){const n=u({extends:g("backend",e),compilerOptions:{noEmit:!0,declaration:!1,declarationMap:!1,rootDir:".."},include:["src/**/*"],exclude:["node_modules"]}),s=`import { serveBackend } from '@tego/plugin-sdk/server-runtime';
|
|
885
926
|
|
|
886
927
|
import { backend } from './app';
|
|
887
928
|
|
|
@@ -892,7 +933,8 @@ import { backend } from './app';
|
|
|
892
933
|
* headers; everything below it is a plain fetch handler.
|
|
893
934
|
*/
|
|
894
935
|
serveBackend(backend);
|
|
895
|
-
`,a=`import {
|
|
936
|
+
`,a=`import { pluginErrorHandler } from '@tego/plugin-sdk/hono';
|
|
937
|
+
import { definePluginBackend } from '@tego/plugin-sdk/server';
|
|
896
938
|
import type { PluginHostApi, PluginUserContext } from '@tego/plugin-sdk/server';
|
|
897
939
|
import { Hono } from 'hono';
|
|
898
940
|
|
|
@@ -910,6 +952,9 @@ interface Env {
|
|
|
910
952
|
|
|
911
953
|
const app = new Hono<Env>();
|
|
912
954
|
|
|
955
|
+
// Every error becomes JSON the frontend can show; a 500 never echoes SQL.
|
|
956
|
+
app.onError(pluginErrorHandler());
|
|
957
|
+
|
|
913
958
|
app.get('/ping', c => c.json({ ok: true }));
|
|
914
959
|
|
|
915
960
|
app.get('/notes', async c => {
|
|
@@ -1049,7 +1094,7 @@ CREATE TABLE notes (
|
|
|
1049
1094
|
body text NOT NULL,
|
|
1050
1095
|
created_at timestamptz NOT NULL DEFAULT now()
|
|
1051
1096
|
);
|
|
1052
|
-
`;return t?.template==="standard"?[{path:"backend/tsconfig.json",contents:n},...V({id:t.id,withAccess:p(t)})]:[{path:"backend/tsconfig.json",contents:n},{path:"backend/src/index.ts",contents:s},{path:"backend/src/app.ts",contents:a},{path:"backend/src/app.test.ts",contents:i},{path:"backend/migrations/0001_init.sql",contents:r}]}o(
|
|
1097
|
+
`;return t?.template==="standard"?[{path:"backend/tsconfig.json",contents:n},...V({id:t.id,withAccess:p(t)})]:[{path:"backend/tsconfig.json",contents:n},{path:"backend/src/index.ts",contents:s},{path:"backend/src/app.ts",contents:a},{path:"backend/src/app.test.ts",contents:i},{path:"backend/migrations/0001_init.sql",contents:r}]}o(Ue,"backendFiles");function qe(e,t){const n=u({id:e.id,name:e.displayNameEn,description:e.descriptionEn,enabledByDefault:!0,activation:{onStartup:!0},configSchema:{type:"object",additionalProperties:!1,properties:{}}}),s=u({name:e.id,private:!0,type:"module",openclaw:{extensions:["./index.js"]},version:"0.1.0"}),a=`{
|
|
1053
1098
|
"extends": "${g("backend",t)}",
|
|
1054
1099
|
"compilerOptions": {
|
|
1055
1100
|
"rootDir": "..",
|
|
@@ -1175,4 +1220,4 @@ export default definePluginEntry({
|
|
|
1175
1220
|
// refuses the registration.
|
|
1176
1221
|
},
|
|
1177
1222
|
});
|
|
1178
|
-
`;return[{path:"claw/openclaw.plugin.json",contents:n},{path:"claw/package.json",contents:s},{path:"claw/tsconfig.json",contents:a},{path:"claw/types/openclaw-plugin-sdk.d.ts",contents:i},{path:"claw/src/index.ts",contents:r}]}o(
|
|
1223
|
+
`;return[{path:"claw/openclaw.plugin.json",contents:n},{path:"claw/package.json",contents:s},{path:"claw/tsconfig.json",contents:a},{path:"claw/types/openclaw-plugin-sdk.d.ts",contents:i},{path:"claw/src/index.ts",contents:r}]}o(qe,"clawFiles");function A(e,{dependencies:t="workspace"}={}){const n=[_e(e),we(e,t),Oe(t),...Le(t),Pe(),Re(e,t),...Ie(e,t)];return t==="npm"&&n.push(...Ne()),e.parts.includes("frontend")&&n.push(...je(e,t)),e.parts.includes("backend")&&n.push(...Ue(t,e)),p(e)&&n.push({path:"shared/access.json",contents:u(le(b(e.id)))}),e.parts.includes("claw")&&n.push(...qe(e,t)),n}o(A,"buildPluginFiles");var _=/^[a-z0-9][a-z0-9._-]*$/,v=["frontend","backend","claw"],B=["avatar","tenant"],w="lowercase letters and digits, may contain . _ -, starting with a letter or digit";function S(e,t){if(typeof e!="object"||e===null||Array.isArray(e))throw new Error("answers must be a JSON object");const n=e,s=o(d=>{const l=n[d];if(typeof l!="string"||l.trim()==="")throw new Error(`${d} is required`);return l.trim()},"text"),a=s("id");if(!_.test(a))throw new Error(`id must be ${w}`);const i=n.parts;if(!Array.isArray(i)||i.length===0||i.some(d=>!v.includes(d)))throw new Error(`parts must be a non-empty list of ${v.join(", ")}`);const r=n.scope??"avatar";if(!B.includes(r))throw new Error(`scope must be one of ${B.join(", ")}`);const c=n.template??"standard";if(!f.includes(c))throw new Error(`template must be one of ${f.join(", ")}`);return{id:a,displayNameZh:s("displayNameZh"),displayNameEn:s("displayNameEn"),descriptionZh:s("descriptionZh"),descriptionEn:s("descriptionEn"),parts:[...new Set(i)],scope:r,hostApiRange:t,template:c}}o(S,"validatePluginAnswers");function Me(e,t){return P(m(e,"plugins"),t,A(t))}o(Me,"writePlugin");async function O(e,t){return P(e,t,await L(A(t,{dependencies:"npm"})))}o(O,"writeStandalonePlugin");var He=/\.(?:[cm]?[jt]sx?|json|css)$/;async function L(e){const t=await import("prettier");return Promise.all(e.map(async n=>He.test(n.path)?{...n,contents:await t.format(n.contents,{...C,filepath:n.path})}:n))}o(L,"formatPluginFiles");function P(e,t,n){const s=m(e,t.id);if(j(s))throw new Error(`${s} already exists \u2014 pick another id or remove it first`);T(e,{recursive:!0});const a=U(m(e,`.${t.id}-`));try{for(const i of n){const r=m(a,i.path);T(z(r),{recursive:!0}),q(r,i.contents)}M(a,s)}catch(i){throw H(a,{recursive:!0,force:!0}),i}return{directory:s,files:n.map(i=>i.path)}}o(P,"writePluginDirectory");async function ze(e,t){let n;try{n=JSON.parse(e)}catch(a){throw new Error(`answers must be JSON: ${a instanceof Error?a.message:String(a)}`)}const s=S(n,`^${$}`);return O(G(t.cwd,t.parent),s)}o(ze,"createStandalonePlugin");export{w as PLUGIN_ID_HINT,_ as PLUGIN_ID_PATTERN,v as PLUGIN_PARTS,B as PLUGIN_SCOPES,f as PLUGIN_TEMPLATES,N as PUBLISHED_SDK_PACKAGES,C as STANDALONE_PRETTIER,D as STANDALONE_TSCONFIG_FILES,A as buildPluginFiles,ze as createStandalonePlugin,L as formatPluginFiles,y as packageNameFor,S as validatePluginAnswers,Me as writePlugin,O as writeStandalonePlugin};
|
package/dist/server-runtime.cjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";var S=Object.defineProperty;var n=(a,e)=>S(a,"name",{value:e,configurable:!0});var chunkIMAVYQ4U_cjs=require("./chunk-IMAVYQ4U.cjs"),chunkBN6TGHSB_cjs=require("./chunk-BN6TGHSB.cjs"),http=require("http");function toArrayBuffer(a){const e=new ArrayBuffer(a.byteLength);return new Uint8Array(e).set(a),e}n(toArrayBuffer,"toArrayBuffer");function readEnv(a){const e=n(s=>{const c=a[s];if(!c)throw new Error(`${s} is required but was not set`);return c},"require_");return{pluginId:e("TEGO_PLUGIN_ID"),tenantId:e("TEGO_TENANT_ID"),port:Number(e("TEGO_PLUGIN_PORT")),healthPath:a.TEGO_PLUGIN_HEALTH_PATH??"/healthz",hostApiUrl:e("TEGO_PLUGIN_HOST_API_URL"),hostApiToken:e("TEGO_PLUGIN_HOST_API_TOKEN"),databaseUrl:e("DATABASE_URL"),gatewayKey:e("TEGO_PLUGIN_GATEWAY_KEY")}}n(readEnv,"readEnv");function readUserContext(a,e){const s=n(f=>{const A=a[f],v=Array.isArray(A)?A[0]:A;return v&&v.length>0?v:null},"read"),c=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.userId),d=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.tenantId);if(!c||!d)return null;const l=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.signature),w=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.issuedAt);if(!l||!w)return null;const h=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.avatarId),y=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.roles),i=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.delegation),u={userId:c,tenantId:d,rolesHeader:y??"",avatarId:h??"",issuedAt:w,...i?{delegationHeader:i}:{}};if(!chunkIMAVYQ4U_cjs.verifyPluginContext({context:u,signature:l,key:e.key,nowMs:e.nowMs}))return null;let E=[];if(y)try{const f=JSON.parse(y);if(!Array.isArray(f))return null;E=f.filter(A=>typeof A=="string")}catch{return null}let m;if(i){if(!h)return null;try{const f=JSON.parse(i);if(!f||typeof f.id!="string"||!f.id||!Array.isArray(f.actions)||f.actions.some(A=>A!=="records.read"&&A!=="work.prepare"))return null;m={id:f.id,actions:f.actions}}catch{return null}}return{userId:c,tenantId:d,roles:E,...h?{avatarId:h}:{},...m?{delegation:m}:{}}}n(readUserContext,"readUserContext");function readPublicContext(a,e){const s=n(E=>{const m=a[E],f=Array.isArray(m)?m[0]:m;return f&&f.length>0?f:null},"read"),c=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.tenantId),d=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.installId),l=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.publicRoute),w=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.clientIp),h=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.avatarId),y=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.issuedAt),i=s(chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.signature);if(!c||!d||!l||!w||!y||!i)return null;const u={tenantId:c,installId:d,route:l,clientIp:w,...h?{avatarId:h}:{}};return chunkIMAVYQ4U_cjs.verifyPluginPublicContext({context:{...u,issuedAt:y},signature:i,key:e.key,nowMs:e.nowMs})?u:null}n(readPublicContext,"readPublicContext");function createHostClient(a){const e=n(async(t,o)=>{const r=await fetch(`${a.hostApiUrl}${t}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify(o),...t.startsWith("/knowledge/collections/")||t.startsWith("/knowledge/admin/")?{signal:AbortSignal.timeout(12e4)}:t==="/mail/send"?{signal:AbortSignal.timeout(6e4)}:t.startsWith("/directory/")||t.startsWith("/knowledge/")||t.startsWith("/delegations/")||t.startsWith("/proactive/")||t==="/mail/status"||t==="/mail/unsubscribes"||t==="/events"?{signal:AbortSignal.timeout(1e4)}:{}});if(!r.ok){const p=await r.text();let g;try{if(g=JSON.parse(p)?.error?.details,typeof g=="string")try{g=JSON.parse(g)}catch{}}catch{}throw Object.assign(new Error(`Tego host API ${t} failed: ${r.status} ${p}`),{status:r.status,details:g,retryAfter:r.headers.get("retry-after")})}return r},"call"),s={debug:n((t,o)=>void c("debug",t,o),"debug"),info:n((t,o)=>void c("info",t,o),"info"),warn:n((t,o)=>void c("warn",t,o),"warn"),error:n((t,o)=>void c("error",t,o),"error")};async function c(t,o,r){try{await e("/log",{level:t,message:o,fields:r})}catch{}}n(c,"emitLog");const d=n((t,o)=>`${a.hostApiUrl}/storage/${t}?key=${encodeURIComponent(o)}`,"storageUrl"),l={copy:n(async(t,o)=>{const p=await(await e("/storage/copy",{sourceKey:t,destinationKey:o})).json();if(!p.data)throw new Error("Tego host API returned no copied object");return p.data},"copy"),getStream:n(async t=>{const o=await fetch(d("stream",t),{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage stream failed: ${o.status}`);return o.body},"getStream"),putStream:n(async(t,o,r)=>{const p={method:"POST",duplex:"half",body:o,headers:{authorization:`Bearer ${a.hostApiToken}`,"content-length":String(r.sizeBytes),"content-type":r.contentType??"application/octet-stream"}},g=await fetch(d("stream",t),p);if(!g.ok)throw new Error(`Tego storage stream write failed: ${g.status}`)},"putStream"),put:n(async(t,o,r)=>{const p=await fetch(d("put",t),{method:"POST",headers:{authorization:`Bearer ${a.hostApiToken}`,"content-type":r??"application/octet-stream"},body:toArrayBuffer(o)});if(!p.ok)throw new Error(`Tego storage put failed: ${p.status}`)},"put"),get:n(async(t,o)=>{const r=o?.firstBytes,p=d("get",t),g=await fetch(r===void 0?p:`${p}&bytes=${r}`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(g.status===404)return null;if(!g.ok)throw new Error(`Tego storage get failed: ${g.status}`);return new Uint8Array(await g.arrayBuffer())},"get"),head:n(async t=>{const o=await fetch(`${a.hostApiUrl}/storage/head`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify({key:t})});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage head failed: ${o.status}`);const r=await o.json();if(!r.data)throw new Error("Tego host API returned no object head");return r.data},"head"),delete:n(async t=>{await e("/storage/delete",{key:t})},"delete"),signedUrl:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.url;if(!g)throw new Error("Tego host API returned no signed url");return g},"signedUrl"),signedPath:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.path;if(!g)throw new Error("Tego host API returned no signed path");return g},"signedPath"),managedPath:n(async(t,o,r)=>{const g=await(await e("/storage/signed-url",{key:t,policy:o,ttlSeconds:r})).json();if(!g.data?.path)throw new Error("Tego host API returned no managed path");return g.data.path},"managedPath"),uploadPath:n(async(t,o)=>{const p=await(await e("/storage/upload-url",{key:t,maxBytes:o?.maxBytes,ttlSeconds:o?.ttlSeconds})).json();if(!p.data?.path)throw new Error("Tego host API returned no upload path");return p.data},"uploadPath")},w={publish:n(async(t,o)=>{await e("/events",{name:t,payload:o})},"publish")},h={send:n(async t=>{const r=await(await e("/notifications",t)).json();if(!r.data?.id)throw new Error("Tego host API returned no notification id");return{id:r.data.id}},"send")},y={async emit(t){const r=await(await e("/proactive/emit",t)).json();if(!r.data)throw new Error("Tego proactive response is missing data");return r.data}},i=n(async(t,o)=>{const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego attention response is missing data");return p.data},"attentionStatus"),u={async request(t){const r=await(await e("/attention/requests",t)).json();if(!r.data?.itemId)throw new Error("Tego host API returned no attention item");return r.data},get:n(t=>i("/attention/requests/get",{itemId:t}),"get"),cancel:n(t=>i("/attention/requests/cancel",{itemId:t}),"cancel")},E={async send(t){const r=await(await e("/mail/send",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async status(t){const r=await(await e("/mail/status",{userId:t})).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async unsubscribes(t={}){const r=await(await e("/mail/unsubscribes",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data}};let m={};const A={current:n(()=>m,"current"),refresh:n(async()=>{const t=await fetch(`${a.hostApiUrl}/config`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(!t.ok)throw new Error(`Tego host API /config failed: ${t.status} ${await t.text()}`);return m=(await t.json()).data?.values??{},m},"refresh")},v={async read(t,o){return(await(await e("/sources/read",{id:t,...o})).json()).data}},I={async list(t){const r=await(await e("/delegations/list",{userId:t})).json();if(!r.data)throw new Error("Tego delegation response is missing data");return r.data}},P={async verify(t){const r=await(await e("/knowledge/verify",t)).json();if(!r.data)throw new Error("Tego knowledge response is missing data");return r.data},collections:{ensure:n(t=>T("ensure",t),"ensure"),permissions:n(t=>T("permissions",t),"permissions"),move:n(t=>T("move",t),"move"),access:n(t=>T("access",t),"access"),import:n(t=>T("import",t),"import"),importFiles:n(t=>T("import-files",t),"importFiles"),status:n(t=>T("status",t),"status"),delete:n(t=>T("delete",t),"delete"),documentsStatus:n(t=>T("documents-status",t),"documentsStatus"),documentContent:n(t=>T("document-content",t),"documentContent"),search:n(t=>T("search",t),"search"),remove:n(t=>T("remove",t),"remove")}};async function T(t,o){const p=await(await e(`/knowledge/collections/${t}`,o)).json();if(!p.data)throw new Error("Tego knowledge collection response is missing data");return p.data}n(T,"collectionCall");const _={async identity(t){const r=await(await e("/directory/identity",{userId:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async validate(t){const r=await(await e("/directory/validate",{principals:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async list(t){const r=await(await e("/directory/list",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async match(t){const r=await(await e("/directory/match",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data}},k={provisionUser:n(t=>b("/accounts/provision",t),"provisionUser"),resetPassword:n(t=>b("/accounts/password/reset",t),"resetPassword"),inviteUser:n(t=>b("/accounts/invite",t),"inviteUser"),getInvitation:n(t=>b("/accounts/get",{invitationId:t}),"getInvitation"),resendInvitation:n(t=>b("/accounts/resend",{invitationId:t}),"resendInvitation")};async function b(t,o){const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego account response is missing data");return p.data}return n(b,"collectionEnvelope"),{accounts:k,log:s,storage:l,diagrams:{status:n(async()=>{const o=await(await e("/diagrams/status",{})).json();if(!o.data)throw new Error("Tego host API returned no renderer status");return o.data},"status"),render:n(async t=>{const r=await(await e("/diagrams/render",t)).json();if(!r.data?.key)throw new Error("Tego host API returned no diagram artifact");return r.data},"render")},events:w,notifications:h,proactive:y,attention:u,mail:E,config:A,sources:v,directory:_,knowledge:P,knowledgeAdmin:{listManageableBases:n(t=>b("/knowledge/admin/list",t),"listManageableBases"),previewCreateBase:n(t=>b("/knowledge/admin/create-preview",t),"previewCreateBase"),createApprovedBase:n(t=>b("/knowledge/admin/create",t),"createApprovedBase"),prepareDocumentContent:n(t=>b("/knowledge/admin/prepare",t),"prepareDocumentContent"),previewDocumentBatch:n(t=>b("/knowledge/admin/preview",t),"previewDocumentBatch"),stageApprovedDocumentBatch:n(t=>b("/knowledge/admin/import",t),"stageApprovedDocumentBatch"),getTask:n(t=>b("/knowledge/admin/task",t),"getTask")},delegations:I}}n(createHostClient,"createHostClient");var ACQUIRE_TIMEOUT_MS=5e3,IDLE_IN_TRANSACTION_TIMEOUT_MS=15e3;function createScopedDb(a){let e=null;async function s(){if(e)return e;const c=await import("pg"),d=c.default?.Pool??c.Pool;if(!d)throw new Error('The "pg" module resolved without a Pool constructor. The plugin runtime expects the driver the runner image provides.');return e=new d({connectionString:a,connectionTimeoutMillis:ACQUIRE_TIMEOUT_MS}),e}return n(s,"ensurePool"),{query:n(async(c,d)=>(await(await s()).query(c,d)).rows,"query"),transaction:n(async c=>{const l=await(await s()).connect();let w=!0,h=!1;const y={query:n(async(i,u)=>{if(h)throw new Error("This transaction has already ended; its `tx` cannot be used afterwards.");return(await l.query(i,u)).rows},"query")};try{await l.query("BEGIN"),await l.query(`SET LOCAL idle_in_transaction_session_timeout = ${IDLE_IN_TRANSACTION_TIMEOUT_MS}`);const i=await c(y);return await l.query("COMMIT"),i}catch(i){try{await l.query("ROLLBACK")}catch{w=!1}throw i}finally{h=!0,l.release(w?void 0:!0)}},"transaction")}}n(createScopedDb,"createScopedDb");function toWebRequest(a,e){const s=`http://localhost${a.url??"/"}`,c=new Headers;for(const[l,w]of Object.entries(a.headers))w!==void 0&&c.set(l,Array.isArray(w)?w.join(", "):w);const d=a.method??"GET";return new Request(s,{method:d,headers:c,...d==="GET"||d==="HEAD"?{}:{body:e}})}n(toWebRequest,"toWebRequest");async function writeWebResponse(a,e){const s={};e.headers.forEach((c,d)=>{s[d]=c}),a.writeHead(e.status,s),a.end(Buffer.from(await e.arrayBuffer()))}n(writeWebResponse,"writeWebResponse");function readBody(a,e){return new Promise((s,c)=>{const d=[];let l=0;a.on("data",w=>{if(l+=w.length,e!==void 0&&l>e){c(new Error("Policy request body too large")),a.destroy();return}d.push(w)}),a.on("end",()=>{s(toArrayBuffer(Buffer.concat(d)))}),a.on("error",c)})}n(readBody,"readBody");function serveBackend(a){const e=readEnv(process.env),s={pluginId:e.pluginId,tenantId:e.tenantId,db:createScopedDb(e.databaseUrl),...createHostClient(e)},c=http.createServer((i,u)=>{(async()=>{try{const E=(i.url??"/").split("?")[0];if(E===e.healthPath){u.writeHead(200,{"content-type":"application/json"}),u.end('{"status":"ok"}');return}if(i.headers["x-tego-plugin-storage-policy"]==="1"){const v=await readBody(i,16384),I=n(T=>typeof i.headers[T]=="string"?i.headers[T]:"","header"),P={installId:I("x-tego-plugin-install-id"),tenantId:I("x-tego-plugin-tenant-id"),issuedAt:I("x-tego-plugin-issued-at"),bodyHash:I("x-tego-plugin-body-hash")};if(E!==chunkIMAVYQ4U_cjs.PLUGIN_STORAGE_POLICY_PATH||i.method!=="POST"||!P.installId||!P.tenantId||!chunkIMAVYQ4U_cjs.verifyPluginStoragePolicy({context:P,signature:I("x-tego-plugin-signature"),key:e.gatewayKey,nowMs:Date.now(),body:Buffer.from(v).toString("utf8")})){u.writeHead(401),u.end();return}if(!a.authorizeStorage){u.writeHead(404),u.end();return}await writeWebResponse(u,await a.authorizeStorage(toWebRequest(i,v),P,s));return}if(i.headers[chunkBN6TGHSB_cjs.PLUGIN_CONTEXT_HEADERS.public]==="1"){const v=readPublicContext(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!v){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}if(!a.fetchPublic){u.writeHead(404,{"content-type":"application/json"}),u.end('{"error":"not found"}');return}const I=await readBody(i);await writeWebResponse(u,await a.fetchPublic(toWebRequest(i,I),v,s));return}const m=readUserContext(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!m){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}const f=await readBody(i),A=await a.fetch(toWebRequest(i,f),m,s);await writeWebResponse(u,A)}catch(E){s.log.error("Unhandled error in plugin backend",{error:E instanceof Error?E.message:String(E)}),u.headersSent?u.end():(u.writeHead(500,{"content-type":"application/json"}),u.end('{"error":"plugin backend failed"}'))}})()});let d=!1,l=!1,w;const h=n(()=>(w??=Promise.resolve().then(()=>a.stop?.()),w),"stopModule"),y=(async()=>{const i=await startUp(s,e);if(i)throw new Error(i);d||(l=!0,await a.start?.(s),!d&&c.listen(e.port,()=>{s.log.info(`Plugin backend listening on ${e.port}`)}))})();y.catch(async i=>{console.error("Plugin backend startup failed",i);try{l&&await h()}catch(u){console.error("Plugin backend shutdown failed",u)}process.exit(1)}),process.on("SIGTERM",()=>{d||(d=!0,Promise.all([new Promise(i=>c.close(()=>i())),y.then(async()=>{l&&await h()})]).then(()=>process.exit(0)).catch(i=>{console.error("Plugin backend shutdown failed",i),process.exit(1)}))})}n(serveBackend,"serveBackend");async function startUp(a,e){const s=await checkDatabaseReachable(a.db,e.databaseUrl);if(s)return s;try{await a.config.refresh()}catch(c){return`Plugin backend cannot read its configuration from the host API: ${c instanceof Error?c.message:String(c)}`}return null}n(startUp,"startUp");async function checkDatabaseReachable(a,e){try{return await a.query("select 1"),null}catch(s){return`Plugin backend cannot reach its database at ${describeDatabaseTarget(e)}: ${s instanceof Error?s.message:String(s)}`}}n(checkDatabaseReachable,"checkDatabaseReachable");function describeDatabaseTarget(a){try{const e=new URL(a);return`${e.host}${e.pathname}`}catch{return"the address in DATABASE_URL"}}n(describeDatabaseTarget,"describeDatabaseTarget");function createMaintenance(a,e={}){const s=e.intervalMs??3e4,c=[];let d,l,w=!0;const h=n(i=>{w||(d&&clearTimeout(d),d=setTimeout(()=>void y(),i))},"schedule"),y=n(async()=>{if(d=void 0,l)return h(s);l=(async()=>{for(const i of c){if(w)break;try{await i.run()}catch(u){a.log.error(`maintenance step ${i.name} failed`,{error:u instanceof Error?u.message:String(u)})}}})(),await l,l=void 0,h(s)},"tick");return{step(i,u){c.push({name:i,run:u})},start(){w&&(w=!1,h(0))},wake(){h(0)},async stop(){w=!0,d&&clearTimeout(d),d=void 0,await l}}}n(createMaintenance,"createMaintenance"),exports.checkDatabaseReachable=checkDatabaseReachable,exports.createMaintenance=createMaintenance,exports.createScopedDb=createScopedDb,exports.readPublicContext=readPublicContext,exports.readUserContext=readUserContext,exports.serveBackend=serveBackend;
|
|
1
|
+
"use strict";var S=Object.defineProperty;var n=(o,t)=>S(o,"name",{value:t,configurable:!0});var chunkIMAVYQ4U_cjs=require("./chunk-IMAVYQ4U.cjs"),chunkSR5V7ZC2_cjs=require("./chunk-SR5V7ZC2.cjs");require("./chunk-66LDWN4T.cjs");var http=require("http");function toArrayBuffer(o){const t=new ArrayBuffer(o.byteLength);return new Uint8Array(t).set(o),t}n(toArrayBuffer,"toArrayBuffer");function readEnv(o){const t=n(s=>{const c=o[s];if(!c)throw new Error(`${s} is required but was not set`);return c},"require_");return{pluginId:t("TEGO_PLUGIN_ID"),tenantId:t("TEGO_TENANT_ID"),port:Number(t("TEGO_PLUGIN_PORT")),healthPath:o.TEGO_PLUGIN_HEALTH_PATH??"/healthz",hostApiUrl:t("TEGO_PLUGIN_HOST_API_URL"),hostApiToken:t("TEGO_PLUGIN_HOST_API_TOKEN"),databaseUrl:t("DATABASE_URL"),gatewayKey:t("TEGO_PLUGIN_GATEWAY_KEY")}}n(readEnv,"readEnv");function readUserContext(o,t){const s=n(f=>{const A=o[f],v=Array.isArray(A)?A[0]:A;return v&&v.length>0?v:null},"read"),c=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.userId),d=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.tenantId);if(!c||!d)return null;const l=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.signature),w=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.issuedAt);if(!l||!w)return null;const h=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.avatarId),y=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.roles),i=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.delegation),u={userId:c,tenantId:d,rolesHeader:y??"",avatarId:h??"",issuedAt:w,...i?{delegationHeader:i}:{}};if(!chunkIMAVYQ4U_cjs.verifyPluginContext({context:u,signature:l,key:t.key,nowMs:t.nowMs}))return null;let E=[];if(y)try{const f=JSON.parse(y);if(!Array.isArray(f))return null;E=f.filter(A=>typeof A=="string")}catch{return null}let m;if(i){if(!h)return null;try{const f=JSON.parse(i);if(!f||typeof f.id!="string"||!f.id||!Array.isArray(f.actions)||f.actions.some(A=>A!=="records.read"&&A!=="work.prepare"))return null;m={id:f.id,actions:f.actions}}catch{return null}}return{userId:c,tenantId:d,roles:E,...h?{avatarId:h}:{},...m?{delegation:m}:{}}}n(readUserContext,"readUserContext");function readPublicContext(o,t){const s=n(E=>{const m=o[E],f=Array.isArray(m)?m[0]:m;return f&&f.length>0?f:null},"read"),c=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.tenantId),d=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.installId),l=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.publicRoute),w=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.clientIp),h=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.avatarId),y=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.issuedAt),i=s(chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.signature);if(!c||!d||!l||!w||!y||!i)return null;const u={tenantId:c,installId:d,route:l,clientIp:w,...h?{avatarId:h}:{}};return chunkIMAVYQ4U_cjs.verifyPluginPublicContext({context:{...u,issuedAt:y},signature:i,key:t.key,nowMs:t.nowMs})?u:null}n(readPublicContext,"readPublicContext");function createHostClient(o){const t=n(async(e,a)=>{const r=await fetch(`${o.hostApiUrl}${e}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${o.hostApiToken}`},body:JSON.stringify(a),...e.startsWith("/knowledge/collections/")||e.startsWith("/knowledge/admin/")?{signal:AbortSignal.timeout(12e4)}:e==="/mail/send"?{signal:AbortSignal.timeout(6e4)}:e.startsWith("/directory/")||e.startsWith("/knowledge/")||e.startsWith("/delegations/")||e.startsWith("/proactive/")||e==="/mail/status"||e==="/mail/unsubscribes"||e==="/events"?{signal:AbortSignal.timeout(1e4)}:{}});if(!r.ok){const p=await r.text();let g;try{if(g=JSON.parse(p)?.error?.details,typeof g=="string")try{g=JSON.parse(g)}catch{}}catch{}throw Object.assign(new Error(`Tego host API ${e} failed: ${r.status} ${p}`),{status:r.status,details:g,retryAfter:r.headers.get("retry-after")})}return r},"call"),s={debug:n((e,a)=>void c("debug",e,a),"debug"),info:n((e,a)=>void c("info",e,a),"info"),warn:n((e,a)=>void c("warn",e,a),"warn"),error:n((e,a)=>void c("error",e,a),"error")};async function c(e,a,r){try{await t("/log",{level:e,message:a,fields:r})}catch{}}n(c,"emitLog");const d=n((e,a)=>`${o.hostApiUrl}/storage/${e}?key=${encodeURIComponent(a)}`,"storageUrl"),l={copy:n(async(e,a)=>{const p=await(await t("/storage/copy",{sourceKey:e,destinationKey:a})).json();if(!p.data)throw new Error("Tego host API returned no copied object");return p.data},"copy"),getStream:n(async e=>{const a=await fetch(d("stream",e),{headers:{authorization:`Bearer ${o.hostApiToken}`}});if(a.status===404)return null;if(!a.ok)throw new Error(`Tego storage stream failed: ${a.status}`);return a.body},"getStream"),putStream:n(async(e,a,r)=>{const p={method:"POST",duplex:"half",body:a,headers:{authorization:`Bearer ${o.hostApiToken}`,"content-length":String(r.sizeBytes),"content-type":r.contentType??"application/octet-stream"}},g=await fetch(d("stream",e),p);if(!g.ok)throw new Error(`Tego storage stream write failed: ${g.status}`)},"putStream"),put:n(async(e,a,r)=>{const p=await fetch(d("put",e),{method:"POST",headers:{authorization:`Bearer ${o.hostApiToken}`,"content-type":r??"application/octet-stream"},body:toArrayBuffer(a)});if(!p.ok)throw new Error(`Tego storage put failed: ${p.status}`)},"put"),get:n(async(e,a)=>{const r=a?.firstBytes,p=d("get",e),g=await fetch(r===void 0?p:`${p}&bytes=${r}`,{headers:{authorization:`Bearer ${o.hostApiToken}`}});if(g.status===404)return null;if(!g.ok)throw new Error(`Tego storage get failed: ${g.status}`);return new Uint8Array(await g.arrayBuffer())},"get"),head:n(async e=>{const a=await fetch(`${o.hostApiUrl}/storage/head`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${o.hostApiToken}`},body:JSON.stringify({key:e})});if(a.status===404)return null;if(!a.ok)throw new Error(`Tego storage head failed: ${a.status}`);const r=await a.json();if(!r.data)throw new Error("Tego host API returned no object head");return r.data},"head"),delete:n(async e=>{await t("/storage/delete",{key:e})},"delete"),signedUrl:n(async(e,a)=>{const g=(await(await t("/storage/signed-url",{key:e,ttlSeconds:a})).json()).data?.url;if(!g)throw new Error("Tego host API returned no signed url");return g},"signedUrl"),signedPath:n(async(e,a)=>{const g=(await(await t("/storage/signed-url",{key:e,ttlSeconds:a})).json()).data?.path;if(!g)throw new Error("Tego host API returned no signed path");return g},"signedPath"),managedPath:n(async(e,a,r)=>{const g=await(await t("/storage/signed-url",{key:e,policy:a,ttlSeconds:r})).json();if(!g.data?.path)throw new Error("Tego host API returned no managed path");return g.data.path},"managedPath"),uploadPath:n(async(e,a)=>{const p=await(await t("/storage/upload-url",{key:e,maxBytes:a?.maxBytes,ttlSeconds:a?.ttlSeconds})).json();if(!p.data?.path)throw new Error("Tego host API returned no upload path");return p.data},"uploadPath")},w={publish:n(async(e,a)=>{await t("/events",{name:e,payload:a})},"publish")},h={send:n(async e=>{const r=await(await t("/notifications",e)).json();if(!r.data?.id)throw new Error("Tego host API returned no notification id");return{id:r.data.id}},"send")},y={async emit(e){const r=await(await t("/proactive/emit",e)).json();if(!r.data)throw new Error("Tego proactive response is missing data");return r.data}},i=n(async(e,a)=>{const p=await(await t(e,a)).json();if(!p.data)throw new Error("Tego attention response is missing data");return p.data},"attentionStatus"),u={async request(e){const r=await(await t("/attention/requests",e)).json();if(!r.data?.itemId)throw new Error("Tego host API returned no attention item");return r.data},get:n(e=>i("/attention/requests/get",{itemId:e}),"get"),cancel:n(e=>i("/attention/requests/cancel",{itemId:e}),"cancel")},E={async send(e){const r=await(await t("/mail/send",e)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async status(e){const r=await(await t("/mail/status",{userId:e})).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async unsubscribes(e={}){const r=await(await t("/mail/unsubscribes",e)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data}};let m={};const A={current:n(()=>m,"current"),refresh:n(async()=>{const e=await fetch(`${o.hostApiUrl}/config`,{headers:{authorization:`Bearer ${o.hostApiToken}`}});if(!e.ok)throw new Error(`Tego host API /config failed: ${e.status} ${await e.text()}`);return m=(await e.json()).data?.values??{},m},"refresh")},v={async read(e,a){return(await(await t("/sources/read",{id:e,...a})).json()).data},async latestUserMessage(e){return(await(await t("/sources/latest-user-message",e)).json()).data}},I={async list(e){const r=await(await t("/delegations/list",{userId:e})).json();if(!r.data)throw new Error("Tego delegation response is missing data");return r.data}},P={async verify(e){const r=await(await t("/knowledge/verify",e)).json();if(!r.data)throw new Error("Tego knowledge response is missing data");return r.data},collections:{ensure:n(e=>T("ensure",e),"ensure"),permissions:n(e=>T("permissions",e),"permissions"),move:n(e=>T("move",e),"move"),access:n(e=>T("access",e),"access"),import:n(e=>T("import",e),"import"),importFiles:n(e=>T("import-files",e),"importFiles"),status:n(e=>T("status",e),"status"),delete:n(e=>T("delete",e),"delete"),documentsStatus:n(e=>T("documents-status",e),"documentsStatus"),documentContent:n(e=>T("document-content",e),"documentContent"),search:n(e=>T("search",e),"search"),remove:n(e=>T("remove",e),"remove")}};async function T(e,a){const p=await(await t(`/knowledge/collections/${e}`,a)).json();if(!p.data)throw new Error("Tego knowledge collection response is missing data");return p.data}n(T,"collectionCall");const _={async identity(e){const r=await(await t("/directory/identity",{userId:e})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async validate(e){const r=await(await t("/directory/validate",{principals:e})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async list(e){const r=await(await t("/directory/list",e)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async match(e){const r=await(await t("/directory/match",e)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data}},k={provisionUser:n(e=>b("/accounts/provision",e),"provisionUser"),resetPassword:n(e=>b("/accounts/password/reset",e),"resetPassword"),inviteUser:n(e=>b("/accounts/invite",e),"inviteUser"),getInvitation:n(e=>b("/accounts/get",{invitationId:e}),"getInvitation"),resendInvitation:n(e=>b("/accounts/resend",{invitationId:e}),"resendInvitation")};async function b(e,a){const p=await(await t(e,a)).json();if(!p.data)throw new Error("Tego account response is missing data");return p.data}return n(b,"collectionEnvelope"),{accounts:k,log:s,storage:l,diagrams:{status:n(async()=>{const a=await(await t("/diagrams/status",{})).json();if(!a.data)throw new Error("Tego host API returned no renderer status");return a.data},"status"),render:n(async e=>{const r=await(await t("/diagrams/render",e)).json();if(!r.data?.key)throw new Error("Tego host API returned no diagram artifact");return r.data},"render")},events:w,notifications:h,proactive:y,attention:u,mail:E,config:A,sources:v,directory:_,knowledge:P,knowledgeAdmin:{listManageableBases:n(e=>b("/knowledge/admin/list",e),"listManageableBases"),previewCreateBase:n(e=>b("/knowledge/admin/create-preview",e),"previewCreateBase"),createApprovedBase:n(e=>b("/knowledge/admin/create",e),"createApprovedBase"),prepareDocumentContent:n(e=>b("/knowledge/admin/prepare",e),"prepareDocumentContent"),previewDocumentBatch:n(e=>b("/knowledge/admin/preview",e),"previewDocumentBatch"),stageApprovedDocumentBatch:n(e=>b("/knowledge/admin/import",e),"stageApprovedDocumentBatch"),getTask:n(e=>b("/knowledge/admin/task",e),"getTask")},delegations:I}}n(createHostClient,"createHostClient");var ACQUIRE_TIMEOUT_MS=5e3,IDLE_IN_TRANSACTION_TIMEOUT_MS=15e3;function createScopedDb(o){let t=null;async function s(){if(t)return t;const c=await import("pg"),d=c.default?.Pool??c.Pool;if(!d)throw new Error('The "pg" module resolved without a Pool constructor. The plugin runtime expects the driver the runner image provides.');return t=new d({connectionString:o,connectionTimeoutMillis:ACQUIRE_TIMEOUT_MS}),t}return n(s,"ensurePool"),{query:n(async(c,d)=>(await(await s()).query(c,d)).rows,"query"),transaction:n(async c=>{const l=await(await s()).connect();let w=!0,h=!1;const y={query:n(async(i,u)=>{if(h)throw new Error("This transaction has already ended; its `tx` cannot be used afterwards.");return(await l.query(i,u)).rows},"query")};try{await l.query("BEGIN"),await l.query(`SET LOCAL idle_in_transaction_session_timeout = ${IDLE_IN_TRANSACTION_TIMEOUT_MS}`);const i=await c(y);return await l.query("COMMIT"),i}catch(i){try{await l.query("ROLLBACK")}catch{w=!1}throw i}finally{h=!0,l.release(w?void 0:!0)}},"transaction")}}n(createScopedDb,"createScopedDb");function toWebRequest(o,t){const s=`http://localhost${o.url??"/"}`,c=new Headers;for(const[l,w]of Object.entries(o.headers))w!==void 0&&c.set(l,Array.isArray(w)?w.join(", "):w);const d=o.method??"GET";return new Request(s,{method:d,headers:c,...d==="GET"||d==="HEAD"?{}:{body:t}})}n(toWebRequest,"toWebRequest");async function writeWebResponse(o,t){const s={};t.headers.forEach((c,d)=>{s[d]=c}),o.writeHead(t.status,s),o.end(Buffer.from(await t.arrayBuffer()))}n(writeWebResponse,"writeWebResponse");function readBody(o,t){return new Promise((s,c)=>{const d=[];let l=0;o.on("data",w=>{if(l+=w.length,t!==void 0&&l>t){c(new Error("Policy request body too large")),o.destroy();return}d.push(w)}),o.on("end",()=>{s(toArrayBuffer(Buffer.concat(d)))}),o.on("error",c)})}n(readBody,"readBody");function serveBackend(o){const t=readEnv(process.env),s={pluginId:t.pluginId,tenantId:t.tenantId,db:createScopedDb(t.databaseUrl),...createHostClient(t)},c=http.createServer((i,u)=>{(async()=>{try{const E=(i.url??"/").split("?")[0];if(E===t.healthPath){u.writeHead(200,{"content-type":"application/json"}),u.end('{"status":"ok"}');return}if(i.headers["x-tego-plugin-storage-policy"]==="1"){const v=await readBody(i,16384),I=n(T=>typeof i.headers[T]=="string"?i.headers[T]:"","header"),P={installId:I("x-tego-plugin-install-id"),tenantId:I("x-tego-plugin-tenant-id"),issuedAt:I("x-tego-plugin-issued-at"),bodyHash:I("x-tego-plugin-body-hash")};if(E!==chunkIMAVYQ4U_cjs.PLUGIN_STORAGE_POLICY_PATH||i.method!=="POST"||!P.installId||!P.tenantId||!chunkIMAVYQ4U_cjs.verifyPluginStoragePolicy({context:P,signature:I("x-tego-plugin-signature"),key:t.gatewayKey,nowMs:Date.now(),body:Buffer.from(v).toString("utf8")})){u.writeHead(401),u.end();return}if(!o.authorizeStorage){u.writeHead(404),u.end();return}await writeWebResponse(u,await o.authorizeStorage(toWebRequest(i,v),P,s));return}if(i.headers[chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS.public]==="1"){const v=readPublicContext(i.headers,{key:t.gatewayKey,nowMs:Date.now()});if(!v){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}if(!o.fetchPublic){u.writeHead(404,{"content-type":"application/json"}),u.end('{"error":"not found"}');return}const I=await readBody(i);await writeWebResponse(u,await o.fetchPublic(toWebRequest(i,I),v,s));return}const m=readUserContext(i.headers,{key:t.gatewayKey,nowMs:Date.now()});if(!m){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}const f=await readBody(i),A=await o.fetch(toWebRequest(i,f),m,s);await writeWebResponse(u,A)}catch(E){s.log.error("Unhandled error in plugin backend",{error:E instanceof Error?E.message:String(E)}),u.headersSent?u.end():(u.writeHead(500,{"content-type":"application/json"}),u.end('{"error":"plugin backend failed"}'))}})()});let d=!1,l=!1,w;const h=n(()=>(w??=Promise.resolve().then(()=>o.stop?.()),w),"stopModule"),y=(async()=>{const i=await startUp(s,t);if(i)throw new Error(i);d||(l=!0,await o.start?.(s),!d&&c.listen(t.port,()=>{s.log.info(`Plugin backend listening on ${t.port}`)}))})();y.catch(async i=>{console.error("Plugin backend startup failed",i);try{l&&await h()}catch(u){console.error("Plugin backend shutdown failed",u)}process.exit(1)}),process.on("SIGTERM",()=>{d||(d=!0,Promise.all([new Promise(i=>c.close(()=>i())),y.then(async()=>{l&&await h()})]).then(()=>process.exit(0)).catch(i=>{console.error("Plugin backend shutdown failed",i),process.exit(1)}))})}n(serveBackend,"serveBackend");async function startUp(o,t){const s=await checkDatabaseReachable(o.db,t.databaseUrl);if(s)return s;try{await o.config.refresh()}catch(c){return`Plugin backend cannot read its configuration from the host API: ${c instanceof Error?c.message:String(c)}`}return null}n(startUp,"startUp");async function checkDatabaseReachable(o,t){try{return await o.query("select 1"),null}catch(s){return`Plugin backend cannot reach its database at ${describeDatabaseTarget(t)}: ${s instanceof Error?s.message:String(s)}`}}n(checkDatabaseReachable,"checkDatabaseReachable");function describeDatabaseTarget(o){try{const t=new URL(o);return`${t.host}${t.pathname}`}catch{return"the address in DATABASE_URL"}}n(describeDatabaseTarget,"describeDatabaseTarget");function createMaintenance(o,t={}){const s=t.intervalMs??3e4,c=[];let d,l,w=!0;const h=n(i=>{w||(d&&clearTimeout(d),d=setTimeout(()=>void y(),i))},"schedule"),y=n(async()=>{if(d=void 0,l)return h(s);l=(async()=>{for(const i of c){if(w)break;try{await i.run()}catch(u){o.log.error(`maintenance step ${i.name} failed`,{error:u instanceof Error?u.message:String(u)})}}})(),await l,l=void 0,h(s)},"tick");return{step(i,u){c.push({name:i,run:u})},start(){w&&(w=!1,h(0))},wake(){h(0)},async stop(){w=!0,d&&clearTimeout(d),d=void 0,await l}}}n(createMaintenance,"createMaintenance"),exports.checkDatabaseReachable=checkDatabaseReachable,exports.createMaintenance=createMaintenance,exports.createScopedDb=createScopedDb,exports.readPublicContext=readPublicContext,exports.readUserContext=readUserContext,exports.serveBackend=serveBackend;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { PluginUserContext } from './frontend.cjs';
|
|
2
2
|
import { PluginScopedDb, PluginHostApi, PluginPublicContext, PluginBackendModule } from './server.cjs';
|
|
3
3
|
import 'zod';
|
|
4
|
+
import './decision-card-IF2c4wvM.cjs';
|
|
4
5
|
|
|
5
6
|
/**
|
|
6
7
|
* Runs a backend part: the bridge between the container it lives in and the
|
package/dist/server-runtime.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { PluginUserContext } from './frontend.js';
|
|
2
2
|
import { PluginScopedDb, PluginHostApi, PluginPublicContext, PluginBackendModule } from './server.js';
|
|
3
3
|
import 'zod';
|
|
4
|
+
import './decision-card-IF2c4wvM.js';
|
|
4
5
|
|
|
5
6
|
/**
|
|
6
7
|
* Runs a backend part: the bridge between the container it lives in and the
|
package/dist/server-runtime.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var H=Object.defineProperty;var n=(a,e)=>H(a,"name",{value:e,configurable:!0});import{verifyPluginContext as L,verifyPluginPublicContext as M,PLUGIN_STORAGE_POLICY_PATH as C,verifyPluginStoragePolicy as R}from"./chunk-WLTASJF6.js";import{PLUGIN_CONTEXT_HEADERS as T}from"./chunk-QKSPPMVN.js";import{createServer as D}from"http";function j(a){const e=new ArrayBuffer(a.byteLength);return new Uint8Array(e).set(a),e}n(j,"toArrayBuffer");function z(a){const e=n(s=>{const c=a[s];if(!c)throw new Error(`${s} is required but was not set`);return c},"require_");return{pluginId:e("TEGO_PLUGIN_ID"),tenantId:e("TEGO_TENANT_ID"),port:Number(e("TEGO_PLUGIN_PORT")),healthPath:a.TEGO_PLUGIN_HEALTH_PATH??"/healthz",hostApiUrl:e("TEGO_PLUGIN_HOST_API_URL"),hostApiToken:e("TEGO_PLUGIN_HOST_API_TOKEN"),databaseUrl:e("DATABASE_URL"),gatewayKey:e("TEGO_PLUGIN_GATEWAY_KEY")}}n(z,"readEnv");function O(a,e){const s=n(f=>{const A=a[f],I=Array.isArray(A)?A[0]:A;return I&&I.length>0?I:null},"read"),c=s(T.userId),d=s(T.tenantId);if(!c||!d)return null;const l=s(T.signature),w=s(T.issuedAt);if(!l||!w)return null;const h=s(T.avatarId),y=s(T.roles),i=s(T.delegation),u={userId:c,tenantId:d,rolesHeader:y??"",avatarId:h??"",issuedAt:w,...i?{delegationHeader:i}:{}};if(!L({context:u,signature:l,key:e.key,nowMs:e.nowMs}))return null;let b=[];if(y)try{const f=JSON.parse(y);if(!Array.isArray(f))return null;b=f.filter(A=>typeof A=="string")}catch{return null}let v;if(i){if(!h)return null;try{const f=JSON.parse(i);if(!f||typeof f.id!="string"||!f.id||!Array.isArray(f.actions)||f.actions.some(A=>A!=="records.read"&&A!=="work.prepare"))return null;v={id:f.id,actions:f.actions}}catch{return null}}return{userId:c,tenantId:d,roles:b,...h?{avatarId:h}:{},...v?{delegation:v}:{}}}n(O,"readUserContext");function U(a,e){const s=n(b=>{const v=a[b],f=Array.isArray(v)?v[0]:v;return f&&f.length>0?f:null},"read"),c=s(T.tenantId),d=s(T.installId),l=s(T.publicRoute),w=s(T.clientIp),h=s(T.avatarId),y=s(T.issuedAt),i=s(T.signature);if(!c||!d||!l||!w||!y||!i)return null;const u={tenantId:c,installId:d,route:l,clientIp:w,...h?{avatarId:h}:{}};return M({context:{...u,issuedAt:y},signature:i,key:e.key,nowMs:e.nowMs})?u:null}n(U,"readPublicContext");function W(a){const e=n(async(t,o)=>{const r=await fetch(`${a.hostApiUrl}${t}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify(o),...t.startsWith("/knowledge/collections/")||t.startsWith("/knowledge/admin/")?{signal:AbortSignal.timeout(12e4)}:t==="/mail/send"?{signal:AbortSignal.timeout(6e4)}:t.startsWith("/directory/")||t.startsWith("/knowledge/")||t.startsWith("/delegations/")||t.startsWith("/proactive/")||t==="/mail/status"||t==="/mail/unsubscribes"||t==="/events"?{signal:AbortSignal.timeout(1e4)}:{}});if(!r.ok){const p=await r.text();let g;try{if(g=JSON.parse(p)?.error?.details,typeof g=="string")try{g=JSON.parse(g)}catch{}}catch{}throw Object.assign(new Error(`Tego host API ${t} failed: ${r.status} ${p}`),{status:r.status,details:g,retryAfter:r.headers.get("retry-after")})}return r},"call"),s={debug:n((t,o)=>void c("debug",t,o),"debug"),info:n((t,o)=>void c("info",t,o),"info"),warn:n((t,o)=>void c("warn",t,o),"warn"),error:n((t,o)=>void c("error",t,o),"error")};async function c(t,o,r){try{await e("/log",{level:t,message:o,fields:r})}catch{}}n(c,"emitLog");const d=n((t,o)=>`${a.hostApiUrl}/storage/${t}?key=${encodeURIComponent(o)}`,"storageUrl"),l={copy:n(async(t,o)=>{const p=await(await e("/storage/copy",{sourceKey:t,destinationKey:o})).json();if(!p.data)throw new Error("Tego host API returned no copied object");return p.data},"copy"),getStream:n(async t=>{const o=await fetch(d("stream",t),{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage stream failed: ${o.status}`);return o.body},"getStream"),putStream:n(async(t,o,r)=>{const p={method:"POST",duplex:"half",body:o,headers:{authorization:`Bearer ${a.hostApiToken}`,"content-length":String(r.sizeBytes),"content-type":r.contentType??"application/octet-stream"}},g=await fetch(d("stream",t),p);if(!g.ok)throw new Error(`Tego storage stream write failed: ${g.status}`)},"putStream"),put:n(async(t,o,r)=>{const p=await fetch(d("put",t),{method:"POST",headers:{authorization:`Bearer ${a.hostApiToken}`,"content-type":r??"application/octet-stream"},body:j(o)});if(!p.ok)throw new Error(`Tego storage put failed: ${p.status}`)},"put"),get:n(async(t,o)=>{const r=o?.firstBytes,p=d("get",t),g=await fetch(r===void 0?p:`${p}&bytes=${r}`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(g.status===404)return null;if(!g.ok)throw new Error(`Tego storage get failed: ${g.status}`);return new Uint8Array(await g.arrayBuffer())},"get"),head:n(async t=>{const o=await fetch(`${a.hostApiUrl}/storage/head`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify({key:t})});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage head failed: ${o.status}`);const r=await o.json();if(!r.data)throw new Error("Tego host API returned no object head");return r.data},"head"),delete:n(async t=>{await e("/storage/delete",{key:t})},"delete"),signedUrl:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.url;if(!g)throw new Error("Tego host API returned no signed url");return g},"signedUrl"),signedPath:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.path;if(!g)throw new Error("Tego host API returned no signed path");return g},"signedPath"),managedPath:n(async(t,o,r)=>{const g=await(await e("/storage/signed-url",{key:t,policy:o,ttlSeconds:r})).json();if(!g.data?.path)throw new Error("Tego host API returned no managed path");return g.data.path},"managedPath"),uploadPath:n(async(t,o)=>{const p=await(await e("/storage/upload-url",{key:t,maxBytes:o?.maxBytes,ttlSeconds:o?.ttlSeconds})).json();if(!p.data?.path)throw new Error("Tego host API returned no upload path");return p.data},"uploadPath")},w={publish:n(async(t,o)=>{await e("/events",{name:t,payload:o})},"publish")},h={send:n(async t=>{const r=await(await e("/notifications",t)).json();if(!r.data?.id)throw new Error("Tego host API returned no notification id");return{id:r.data.id}},"send")},y={async emit(t){const r=await(await e("/proactive/emit",t)).json();if(!r.data)throw new Error("Tego proactive response is missing data");return r.data}},i=n(async(t,o)=>{const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego attention response is missing data");return p.data},"attentionStatus"),u={async request(t){const r=await(await e("/attention/requests",t)).json();if(!r.data?.itemId)throw new Error("Tego host API returned no attention item");return r.data},get:n(t=>i("/attention/requests/get",{itemId:t}),"get"),cancel:n(t=>i("/attention/requests/cancel",{itemId:t}),"cancel")},b={async send(t){const r=await(await e("/mail/send",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async status(t){const r=await(await e("/mail/status",{userId:t})).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async unsubscribes(t={}){const r=await(await e("/mail/unsubscribes",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data}};let v={};const A={current:n(()=>v,"current"),refresh:n(async()=>{const t=await fetch(`${a.hostApiUrl}/config`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(!t.ok)throw new Error(`Tego host API /config failed: ${t.status} ${await t.text()}`);return v=(await t.json()).data?.values??{},v},"refresh")},I={async read(t,o){return(await(await e("/sources/read",{id:t,...o})).json()).data}},P={async list(t){const r=await(await e("/delegations/list",{userId:t})).json();if(!r.data)throw new Error("Tego delegation response is missing data");return r.data}},k={async verify(t){const r=await(await e("/knowledge/verify",t)).json();if(!r.data)throw new Error("Tego knowledge response is missing data");return r.data},collections:{ensure:n(t=>m("ensure",t),"ensure"),permissions:n(t=>m("permissions",t),"permissions"),move:n(t=>m("move",t),"move"),access:n(t=>m("access",t),"access"),import:n(t=>m("import",t),"import"),importFiles:n(t=>m("import-files",t),"importFiles"),status:n(t=>m("status",t),"status"),delete:n(t=>m("delete",t),"delete"),documentsStatus:n(t=>m("documents-status",t),"documentsStatus"),documentContent:n(t=>m("document-content",t),"documentContent"),search:n(t=>m("search",t),"search"),remove:n(t=>m("remove",t),"remove")}};async function m(t,o){const p=await(await e(`/knowledge/collections/${t}`,o)).json();if(!p.data)throw new Error("Tego knowledge collection response is missing data");return p.data}n(m,"collectionCall");const N={async identity(t){const r=await(await e("/directory/identity",{userId:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async validate(t){const r=await(await e("/directory/validate",{principals:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async list(t){const r=await(await e("/directory/list",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async match(t){const r=await(await e("/directory/match",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data}},G={provisionUser:n(t=>E("/accounts/provision",t),"provisionUser"),resetPassword:n(t=>E("/accounts/password/reset",t),"resetPassword"),inviteUser:n(t=>E("/accounts/invite",t),"inviteUser"),getInvitation:n(t=>E("/accounts/get",{invitationId:t}),"getInvitation"),resendInvitation:n(t=>E("/accounts/resend",{invitationId:t}),"resendInvitation")};async function E(t,o){const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego account response is missing data");return p.data}return n(E,"collectionEnvelope"),{accounts:G,log:s,storage:l,diagrams:{status:n(async()=>{const o=await(await e("/diagrams/status",{})).json();if(!o.data)throw new Error("Tego host API returned no renderer status");return o.data},"status"),render:n(async t=>{const r=await(await e("/diagrams/render",t)).json();if(!r.data?.key)throw new Error("Tego host API returned no diagram artifact");return r.data},"render")},events:w,notifications:h,proactive:y,attention:u,mail:b,config:A,sources:I,directory:N,knowledge:k,knowledgeAdmin:{listManageableBases:n(t=>E("/knowledge/admin/list",t),"listManageableBases"),previewCreateBase:n(t=>E("/knowledge/admin/create-preview",t),"previewCreateBase"),createApprovedBase:n(t=>E("/knowledge/admin/create",t),"createApprovedBase"),prepareDocumentContent:n(t=>E("/knowledge/admin/prepare",t),"prepareDocumentContent"),previewDocumentBatch:n(t=>E("/knowledge/admin/preview",t),"previewDocumentBatch"),stageApprovedDocumentBatch:n(t=>E("/knowledge/admin/import",t),"stageApprovedDocumentBatch"),getTask:n(t=>E("/knowledge/admin/task",t),"getTask")},delegations:P}}n(W,"createHostClient");var K=5e3,J=15e3;function x(a){let e=null;async function s(){if(e)return e;const c=await import("pg"),d=c.default?.Pool??c.Pool;if(!d)throw new Error('The "pg" module resolved without a Pool constructor. The plugin runtime expects the driver the runner image provides.');return e=new d({connectionString:a,connectionTimeoutMillis:K}),e}return n(s,"ensurePool"),{query:n(async(c,d)=>(await(await s()).query(c,d)).rows,"query"),transaction:n(async c=>{const l=await(await s()).connect();let w=!0,h=!1;const y={query:n(async(i,u)=>{if(h)throw new Error("This transaction has already ended; its `tx` cannot be used afterwards.");return(await l.query(i,u)).rows},"query")};try{await l.query("BEGIN"),await l.query(`SET LOCAL idle_in_transaction_session_timeout = ${J}`);const i=await c(y);return await l.query("COMMIT"),i}catch(i){try{await l.query("ROLLBACK")}catch{w=!1}throw i}finally{h=!0,l.release(w?void 0:!0)}},"transaction")}}n(x,"createScopedDb");function S(a,e){const s=`http://localhost${a.url??"/"}`,c=new Headers;for(const[l,w]of Object.entries(a.headers))w!==void 0&&c.set(l,Array.isArray(w)?w.join(", "):w);const d=a.method??"GET";return new Request(s,{method:d,headers:c,...d==="GET"||d==="HEAD"?{}:{body:e}})}n(S,"toWebRequest");async function _(a,e){const s={};e.headers.forEach((c,d)=>{s[d]=c}),a.writeHead(e.status,s),a.end(Buffer.from(await e.arrayBuffer()))}n(_,"writeWebResponse");function $(a,e){return new Promise((s,c)=>{const d=[];let l=0;a.on("data",w=>{if(l+=w.length,e!==void 0&&l>e){c(new Error("Policy request body too large")),a.destroy();return}d.push(w)}),a.on("end",()=>{s(j(Buffer.concat(d)))}),a.on("error",c)})}n($,"readBody");function Y(a){const e=z(process.env),s={pluginId:e.pluginId,tenantId:e.tenantId,db:x(e.databaseUrl),...W(e)},c=D((i,u)=>{(async()=>{try{const b=(i.url??"/").split("?")[0];if(b===e.healthPath){u.writeHead(200,{"content-type":"application/json"}),u.end('{"status":"ok"}');return}if(i.headers["x-tego-plugin-storage-policy"]==="1"){const I=await $(i,16384),P=n(m=>typeof i.headers[m]=="string"?i.headers[m]:"","header"),k={installId:P("x-tego-plugin-install-id"),tenantId:P("x-tego-plugin-tenant-id"),issuedAt:P("x-tego-plugin-issued-at"),bodyHash:P("x-tego-plugin-body-hash")};if(b!==C||i.method!=="POST"||!k.installId||!k.tenantId||!R({context:k,signature:P("x-tego-plugin-signature"),key:e.gatewayKey,nowMs:Date.now(),body:Buffer.from(I).toString("utf8")})){u.writeHead(401),u.end();return}if(!a.authorizeStorage){u.writeHead(404),u.end();return}await _(u,await a.authorizeStorage(S(i,I),k,s));return}if(i.headers[T.public]==="1"){const I=U(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!I){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}if(!a.fetchPublic){u.writeHead(404,{"content-type":"application/json"}),u.end('{"error":"not found"}');return}const P=await $(i);await _(u,await a.fetchPublic(S(i,P),I,s));return}const v=O(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!v){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}const f=await $(i),A=await a.fetch(S(i,f),v,s);await _(u,A)}catch(b){s.log.error("Unhandled error in plugin backend",{error:b instanceof Error?b.message:String(b)}),u.headersSent?u.end():(u.writeHead(500,{"content-type":"application/json"}),u.end('{"error":"plugin backend failed"}'))}})()});let d=!1,l=!1,w;const h=n(()=>(w??=Promise.resolve().then(()=>a.stop?.()),w),"stopModule"),y=(async()=>{const i=await F(s,e);if(i)throw new Error(i);d||(l=!0,await a.start?.(s),!d&&c.listen(e.port,()=>{s.log.info(`Plugin backend listening on ${e.port}`)}))})();y.catch(async i=>{console.error("Plugin backend startup failed",i);try{l&&await h()}catch(u){console.error("Plugin backend shutdown failed",u)}process.exit(1)}),process.on("SIGTERM",()=>{d||(d=!0,Promise.all([new Promise(i=>c.close(()=>i())),y.then(async()=>{l&&await h()})]).then(()=>process.exit(0)).catch(i=>{console.error("Plugin backend shutdown failed",i),process.exit(1)}))})}n(Y,"serveBackend");async function F(a,e){const s=await B(a.db,e.databaseUrl);if(s)return s;try{await a.config.refresh()}catch(c){return`Plugin backend cannot read its configuration from the host API: ${c instanceof Error?c.message:String(c)}`}return null}n(F,"startUp");async function B(a,e){try{return await a.query("select 1"),null}catch(s){return`Plugin backend cannot reach its database at ${Q(e)}: ${s instanceof Error?s.message:String(s)}`}}n(B,"checkDatabaseReachable");function Q(a){try{const e=new URL(a);return`${e.host}${e.pathname}`}catch{return"the address in DATABASE_URL"}}n(Q,"describeDatabaseTarget");function X(a,e={}){const s=e.intervalMs??3e4,c=[];let d,l,w=!0;const h=n(i=>{w||(d&&clearTimeout(d),d=setTimeout(()=>void y(),i))},"schedule"),y=n(async()=>{if(d=void 0,l)return h(s);l=(async()=>{for(const i of c){if(w)break;try{await i.run()}catch(u){a.log.error(`maintenance step ${i.name} failed`,{error:u instanceof Error?u.message:String(u)})}}})(),await l,l=void 0,h(s)},"tick");return{step(i,u){c.push({name:i,run:u})},start(){w&&(w=!1,h(0))},wake(){h(0)},async stop(){w=!0,d&&clearTimeout(d),d=void 0,await l}}}n(X,"createMaintenance");export{B as checkDatabaseReachable,X as createMaintenance,x as createScopedDb,U as readPublicContext,O as readUserContext,Y as serveBackend};
|
|
1
|
+
var H=Object.defineProperty;var n=(a,e)=>H(a,"name",{value:e,configurable:!0});import{verifyPluginContext as L,verifyPluginPublicContext as M,PLUGIN_STORAGE_POLICY_PATH as C,verifyPluginStoragePolicy as R}from"./chunk-WLTASJF6.js";import{PLUGIN_CONTEXT_HEADERS as T}from"./chunk-CDJQ7OPA.js";import"./chunk-JV2G2Z33.js";import{createServer as D}from"http";function $(a){const e=new ArrayBuffer(a.byteLength);return new Uint8Array(e).set(a),e}n($,"toArrayBuffer");function z(a){const e=n(s=>{const c=a[s];if(!c)throw new Error(`${s} is required but was not set`);return c},"require_");return{pluginId:e("TEGO_PLUGIN_ID"),tenantId:e("TEGO_TENANT_ID"),port:Number(e("TEGO_PLUGIN_PORT")),healthPath:a.TEGO_PLUGIN_HEALTH_PATH??"/healthz",hostApiUrl:e("TEGO_PLUGIN_HOST_API_URL"),hostApiToken:e("TEGO_PLUGIN_HOST_API_TOKEN"),databaseUrl:e("DATABASE_URL"),gatewayKey:e("TEGO_PLUGIN_GATEWAY_KEY")}}n(z,"readEnv");function U(a,e){const s=n(f=>{const A=a[f],I=Array.isArray(A)?A[0]:A;return I&&I.length>0?I:null},"read"),c=s(T.userId),d=s(T.tenantId);if(!c||!d)return null;const l=s(T.signature),w=s(T.issuedAt);if(!l||!w)return null;const h=s(T.avatarId),y=s(T.roles),i=s(T.delegation),u={userId:c,tenantId:d,rolesHeader:y??"",avatarId:h??"",issuedAt:w,...i?{delegationHeader:i}:{}};if(!L({context:u,signature:l,key:e.key,nowMs:e.nowMs}))return null;let b=[];if(y)try{const f=JSON.parse(y);if(!Array.isArray(f))return null;b=f.filter(A=>typeof A=="string")}catch{return null}let v;if(i){if(!h)return null;try{const f=JSON.parse(i);if(!f||typeof f.id!="string"||!f.id||!Array.isArray(f.actions)||f.actions.some(A=>A!=="records.read"&&A!=="work.prepare"))return null;v={id:f.id,actions:f.actions}}catch{return null}}return{userId:c,tenantId:d,roles:b,...h?{avatarId:h}:{},...v?{delegation:v}:{}}}n(U,"readUserContext");function O(a,e){const s=n(b=>{const v=a[b],f=Array.isArray(v)?v[0]:v;return f&&f.length>0?f:null},"read"),c=s(T.tenantId),d=s(T.installId),l=s(T.publicRoute),w=s(T.clientIp),h=s(T.avatarId),y=s(T.issuedAt),i=s(T.signature);if(!c||!d||!l||!w||!y||!i)return null;const u={tenantId:c,installId:d,route:l,clientIp:w,...h?{avatarId:h}:{}};return M({context:{...u,issuedAt:y},signature:i,key:e.key,nowMs:e.nowMs})?u:null}n(O,"readPublicContext");function W(a){const e=n(async(t,o)=>{const r=await fetch(`${a.hostApiUrl}${t}`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify(o),...t.startsWith("/knowledge/collections/")||t.startsWith("/knowledge/admin/")?{signal:AbortSignal.timeout(12e4)}:t==="/mail/send"?{signal:AbortSignal.timeout(6e4)}:t.startsWith("/directory/")||t.startsWith("/knowledge/")||t.startsWith("/delegations/")||t.startsWith("/proactive/")||t==="/mail/status"||t==="/mail/unsubscribes"||t==="/events"?{signal:AbortSignal.timeout(1e4)}:{}});if(!r.ok){const p=await r.text();let g;try{if(g=JSON.parse(p)?.error?.details,typeof g=="string")try{g=JSON.parse(g)}catch{}}catch{}throw Object.assign(new Error(`Tego host API ${t} failed: ${r.status} ${p}`),{status:r.status,details:g,retryAfter:r.headers.get("retry-after")})}return r},"call"),s={debug:n((t,o)=>void c("debug",t,o),"debug"),info:n((t,o)=>void c("info",t,o),"info"),warn:n((t,o)=>void c("warn",t,o),"warn"),error:n((t,o)=>void c("error",t,o),"error")};async function c(t,o,r){try{await e("/log",{level:t,message:o,fields:r})}catch{}}n(c,"emitLog");const d=n((t,o)=>`${a.hostApiUrl}/storage/${t}?key=${encodeURIComponent(o)}`,"storageUrl"),l={copy:n(async(t,o)=>{const p=await(await e("/storage/copy",{sourceKey:t,destinationKey:o})).json();if(!p.data)throw new Error("Tego host API returned no copied object");return p.data},"copy"),getStream:n(async t=>{const o=await fetch(d("stream",t),{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage stream failed: ${o.status}`);return o.body},"getStream"),putStream:n(async(t,o,r)=>{const p={method:"POST",duplex:"half",body:o,headers:{authorization:`Bearer ${a.hostApiToken}`,"content-length":String(r.sizeBytes),"content-type":r.contentType??"application/octet-stream"}},g=await fetch(d("stream",t),p);if(!g.ok)throw new Error(`Tego storage stream write failed: ${g.status}`)},"putStream"),put:n(async(t,o,r)=>{const p=await fetch(d("put",t),{method:"POST",headers:{authorization:`Bearer ${a.hostApiToken}`,"content-type":r??"application/octet-stream"},body:$(o)});if(!p.ok)throw new Error(`Tego storage put failed: ${p.status}`)},"put"),get:n(async(t,o)=>{const r=o?.firstBytes,p=d("get",t),g=await fetch(r===void 0?p:`${p}&bytes=${r}`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(g.status===404)return null;if(!g.ok)throw new Error(`Tego storage get failed: ${g.status}`);return new Uint8Array(await g.arrayBuffer())},"get"),head:n(async t=>{const o=await fetch(`${a.hostApiUrl}/storage/head`,{method:"POST",headers:{"content-type":"application/json",authorization:`Bearer ${a.hostApiToken}`},body:JSON.stringify({key:t})});if(o.status===404)return null;if(!o.ok)throw new Error(`Tego storage head failed: ${o.status}`);const r=await o.json();if(!r.data)throw new Error("Tego host API returned no object head");return r.data},"head"),delete:n(async t=>{await e("/storage/delete",{key:t})},"delete"),signedUrl:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.url;if(!g)throw new Error("Tego host API returned no signed url");return g},"signedUrl"),signedPath:n(async(t,o)=>{const g=(await(await e("/storage/signed-url",{key:t,ttlSeconds:o})).json()).data?.path;if(!g)throw new Error("Tego host API returned no signed path");return g},"signedPath"),managedPath:n(async(t,o,r)=>{const g=await(await e("/storage/signed-url",{key:t,policy:o,ttlSeconds:r})).json();if(!g.data?.path)throw new Error("Tego host API returned no managed path");return g.data.path},"managedPath"),uploadPath:n(async(t,o)=>{const p=await(await e("/storage/upload-url",{key:t,maxBytes:o?.maxBytes,ttlSeconds:o?.ttlSeconds})).json();if(!p.data?.path)throw new Error("Tego host API returned no upload path");return p.data},"uploadPath")},w={publish:n(async(t,o)=>{await e("/events",{name:t,payload:o})},"publish")},h={send:n(async t=>{const r=await(await e("/notifications",t)).json();if(!r.data?.id)throw new Error("Tego host API returned no notification id");return{id:r.data.id}},"send")},y={async emit(t){const r=await(await e("/proactive/emit",t)).json();if(!r.data)throw new Error("Tego proactive response is missing data");return r.data}},i=n(async(t,o)=>{const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego attention response is missing data");return p.data},"attentionStatus"),u={async request(t){const r=await(await e("/attention/requests",t)).json();if(!r.data?.itemId)throw new Error("Tego host API returned no attention item");return r.data},get:n(t=>i("/attention/requests/get",{itemId:t}),"get"),cancel:n(t=>i("/attention/requests/cancel",{itemId:t}),"cancel")},b={async send(t){const r=await(await e("/mail/send",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async status(t){const r=await(await e("/mail/status",{userId:t})).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data},async unsubscribes(t={}){const r=await(await e("/mail/unsubscribes",t)).json();if(!r.data)throw new Error("Tego mail response is missing data");return r.data}};let v={};const A={current:n(()=>v,"current"),refresh:n(async()=>{const t=await fetch(`${a.hostApiUrl}/config`,{headers:{authorization:`Bearer ${a.hostApiToken}`}});if(!t.ok)throw new Error(`Tego host API /config failed: ${t.status} ${await t.text()}`);return v=(await t.json()).data?.values??{},v},"refresh")},I={async read(t,o){return(await(await e("/sources/read",{id:t,...o})).json()).data},async latestUserMessage(t){return(await(await e("/sources/latest-user-message",t)).json()).data}},P={async list(t){const r=await(await e("/delegations/list",{userId:t})).json();if(!r.data)throw new Error("Tego delegation response is missing data");return r.data}},k={async verify(t){const r=await(await e("/knowledge/verify",t)).json();if(!r.data)throw new Error("Tego knowledge response is missing data");return r.data},collections:{ensure:n(t=>m("ensure",t),"ensure"),permissions:n(t=>m("permissions",t),"permissions"),move:n(t=>m("move",t),"move"),access:n(t=>m("access",t),"access"),import:n(t=>m("import",t),"import"),importFiles:n(t=>m("import-files",t),"importFiles"),status:n(t=>m("status",t),"status"),delete:n(t=>m("delete",t),"delete"),documentsStatus:n(t=>m("documents-status",t),"documentsStatus"),documentContent:n(t=>m("document-content",t),"documentContent"),search:n(t=>m("search",t),"search"),remove:n(t=>m("remove",t),"remove")}};async function m(t,o){const p=await(await e(`/knowledge/collections/${t}`,o)).json();if(!p.data)throw new Error("Tego knowledge collection response is missing data");return p.data}n(m,"collectionCall");const N={async identity(t){const r=await(await e("/directory/identity",{userId:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async validate(t){const r=await(await e("/directory/validate",{principals:t})).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async list(t){const r=await(await e("/directory/list",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data},async match(t){const r=await(await e("/directory/match",t)).json();if(!r.data)throw new Error("Tego directory response is missing data");return r.data}},G={provisionUser:n(t=>E("/accounts/provision",t),"provisionUser"),resetPassword:n(t=>E("/accounts/password/reset",t),"resetPassword"),inviteUser:n(t=>E("/accounts/invite",t),"inviteUser"),getInvitation:n(t=>E("/accounts/get",{invitationId:t}),"getInvitation"),resendInvitation:n(t=>E("/accounts/resend",{invitationId:t}),"resendInvitation")};async function E(t,o){const p=await(await e(t,o)).json();if(!p.data)throw new Error("Tego account response is missing data");return p.data}return n(E,"collectionEnvelope"),{accounts:G,log:s,storage:l,diagrams:{status:n(async()=>{const o=await(await e("/diagrams/status",{})).json();if(!o.data)throw new Error("Tego host API returned no renderer status");return o.data},"status"),render:n(async t=>{const r=await(await e("/diagrams/render",t)).json();if(!r.data?.key)throw new Error("Tego host API returned no diagram artifact");return r.data},"render")},events:w,notifications:h,proactive:y,attention:u,mail:b,config:A,sources:I,directory:N,knowledge:k,knowledgeAdmin:{listManageableBases:n(t=>E("/knowledge/admin/list",t),"listManageableBases"),previewCreateBase:n(t=>E("/knowledge/admin/create-preview",t),"previewCreateBase"),createApprovedBase:n(t=>E("/knowledge/admin/create",t),"createApprovedBase"),prepareDocumentContent:n(t=>E("/knowledge/admin/prepare",t),"prepareDocumentContent"),previewDocumentBatch:n(t=>E("/knowledge/admin/preview",t),"previewDocumentBatch"),stageApprovedDocumentBatch:n(t=>E("/knowledge/admin/import",t),"stageApprovedDocumentBatch"),getTask:n(t=>E("/knowledge/admin/task",t),"getTask")},delegations:P}}n(W,"createHostClient");var K=5e3,J=15e3;function x(a){let e=null;async function s(){if(e)return e;const c=await import("pg"),d=c.default?.Pool??c.Pool;if(!d)throw new Error('The "pg" module resolved without a Pool constructor. The plugin runtime expects the driver the runner image provides.');return e=new d({connectionString:a,connectionTimeoutMillis:K}),e}return n(s,"ensurePool"),{query:n(async(c,d)=>(await(await s()).query(c,d)).rows,"query"),transaction:n(async c=>{const l=await(await s()).connect();let w=!0,h=!1;const y={query:n(async(i,u)=>{if(h)throw new Error("This transaction has already ended; its `tx` cannot be used afterwards.");return(await l.query(i,u)).rows},"query")};try{await l.query("BEGIN"),await l.query(`SET LOCAL idle_in_transaction_session_timeout = ${J}`);const i=await c(y);return await l.query("COMMIT"),i}catch(i){try{await l.query("ROLLBACK")}catch{w=!1}throw i}finally{h=!0,l.release(w?void 0:!0)}},"transaction")}}n(x,"createScopedDb");function S(a,e){const s=`http://localhost${a.url??"/"}`,c=new Headers;for(const[l,w]of Object.entries(a.headers))w!==void 0&&c.set(l,Array.isArray(w)?w.join(", "):w);const d=a.method??"GET";return new Request(s,{method:d,headers:c,...d==="GET"||d==="HEAD"?{}:{body:e}})}n(S,"toWebRequest");async function _(a,e){const s={};e.headers.forEach((c,d)=>{s[d]=c}),a.writeHead(e.status,s),a.end(Buffer.from(await e.arrayBuffer()))}n(_,"writeWebResponse");function j(a,e){return new Promise((s,c)=>{const d=[];let l=0;a.on("data",w=>{if(l+=w.length,e!==void 0&&l>e){c(new Error("Policy request body too large")),a.destroy();return}d.push(w)}),a.on("end",()=>{s($(Buffer.concat(d)))}),a.on("error",c)})}n(j,"readBody");function Y(a){const e=z(process.env),s={pluginId:e.pluginId,tenantId:e.tenantId,db:x(e.databaseUrl),...W(e)},c=D((i,u)=>{(async()=>{try{const b=(i.url??"/").split("?")[0];if(b===e.healthPath){u.writeHead(200,{"content-type":"application/json"}),u.end('{"status":"ok"}');return}if(i.headers["x-tego-plugin-storage-policy"]==="1"){const I=await j(i,16384),P=n(m=>typeof i.headers[m]=="string"?i.headers[m]:"","header"),k={installId:P("x-tego-plugin-install-id"),tenantId:P("x-tego-plugin-tenant-id"),issuedAt:P("x-tego-plugin-issued-at"),bodyHash:P("x-tego-plugin-body-hash")};if(b!==C||i.method!=="POST"||!k.installId||!k.tenantId||!R({context:k,signature:P("x-tego-plugin-signature"),key:e.gatewayKey,nowMs:Date.now(),body:Buffer.from(I).toString("utf8")})){u.writeHead(401),u.end();return}if(!a.authorizeStorage){u.writeHead(404),u.end();return}await _(u,await a.authorizeStorage(S(i,I),k,s));return}if(i.headers[T.public]==="1"){const I=O(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!I){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}if(!a.fetchPublic){u.writeHead(404,{"content-type":"application/json"}),u.end('{"error":"not found"}');return}const P=await j(i);await _(u,await a.fetchPublic(S(i,P),I,s));return}const v=U(i.headers,{key:e.gatewayKey,nowMs:Date.now()});if(!v){u.writeHead(401,{"content-type":"application/json"}),u.end('{"error":"missing or unverifiable tego plugin context"}');return}const f=await j(i),A=await a.fetch(S(i,f),v,s);await _(u,A)}catch(b){s.log.error("Unhandled error in plugin backend",{error:b instanceof Error?b.message:String(b)}),u.headersSent?u.end():(u.writeHead(500,{"content-type":"application/json"}),u.end('{"error":"plugin backend failed"}'))}})()});let d=!1,l=!1,w;const h=n(()=>(w??=Promise.resolve().then(()=>a.stop?.()),w),"stopModule"),y=(async()=>{const i=await F(s,e);if(i)throw new Error(i);d||(l=!0,await a.start?.(s),!d&&c.listen(e.port,()=>{s.log.info(`Plugin backend listening on ${e.port}`)}))})();y.catch(async i=>{console.error("Plugin backend startup failed",i);try{l&&await h()}catch(u){console.error("Plugin backend shutdown failed",u)}process.exit(1)}),process.on("SIGTERM",()=>{d||(d=!0,Promise.all([new Promise(i=>c.close(()=>i())),y.then(async()=>{l&&await h()})]).then(()=>process.exit(0)).catch(i=>{console.error("Plugin backend shutdown failed",i),process.exit(1)}))})}n(Y,"serveBackend");async function F(a,e){const s=await B(a.db,e.databaseUrl);if(s)return s;try{await a.config.refresh()}catch(c){return`Plugin backend cannot read its configuration from the host API: ${c instanceof Error?c.message:String(c)}`}return null}n(F,"startUp");async function B(a,e){try{return await a.query("select 1"),null}catch(s){return`Plugin backend cannot reach its database at ${Q(e)}: ${s instanceof Error?s.message:String(s)}`}}n(B,"checkDatabaseReachable");function Q(a){try{const e=new URL(a);return`${e.host}${e.pathname}`}catch{return"the address in DATABASE_URL"}}n(Q,"describeDatabaseTarget");function X(a,e={}){const s=e.intervalMs??3e4,c=[];let d,l,w=!0;const h=n(i=>{w||(d&&clearTimeout(d),d=setTimeout(()=>void y(),i))},"schedule"),y=n(async()=>{if(d=void 0,l)return h(s);l=(async()=>{for(const i of c){if(w)break;try{await i.run()}catch(u){a.log.error(`maintenance step ${i.name} failed`,{error:u instanceof Error?u.message:String(u)})}}})(),await l,l=void 0,h(s)},"tick");return{step(i,u){c.push({name:i,run:u})},start(){w&&(w=!1,h(0))},wake(){h(0)},async stop(){w=!0,d&&clearTimeout(d),d=void 0,await l}}}n(X,"createMaintenance");export{B as checkDatabaseReachable,X as createMaintenance,x as createScopedDb,O as readPublicContext,U as readUserContext,Y as serveBackend};
|
package/dist/server.cjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";var r=Object.defineProperty;var e=(t,n)=>r(t,"name",{value:n,configurable:!0});var
|
|
1
|
+
"use strict";var r=Object.defineProperty;var e=(t,n)=>r(t,"name",{value:n,configurable:!0});var chunkSR5V7ZC2_cjs=require("./chunk-SR5V7ZC2.cjs"),chunk66LDWN4T_cjs=require("./chunk-66LDWN4T.cjs");Object.defineProperty(exports,"PLUGIN_COLLECTION_CONTENT_PAGE_MAX",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.PLUGIN_COLLECTION_CONTENT_PAGE_MAX},"get")}),Object.defineProperty(exports,"PLUGIN_COLLECTION_IMPORT_MAX",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.PLUGIN_COLLECTION_IMPORT_MAX},"get")}),Object.defineProperty(exports,"PLUGIN_CONTEXT_HEADERS",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.PLUGIN_CONTEXT_HEADERS},"get")}),Object.defineProperty(exports,"accountInvitationSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.accountInvitationSchema},"get")}),Object.defineProperty(exports,"accountInviteSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.accountInviteSchema},"get")}),Object.defineProperty(exports,"accountPasswordResetSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.accountPasswordResetSchema},"get")}),Object.defineProperty(exports,"accountProvisionSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.accountProvisionSchema},"get")}),Object.defineProperty(exports,"definePluginBackend",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.definePluginBackend},"get")}),Object.defineProperty(exports,"directoryIdentitySchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.directoryIdentitySchema},"get")}),Object.defineProperty(exports,"directoryListSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.directoryListSchema},"get")}),Object.defineProperty(exports,"directoryMatchSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.directoryMatchSchema},"get")}),Object.defineProperty(exports,"directoryPrincipalSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.directoryPrincipalSchema},"get")}),Object.defineProperty(exports,"directoryValidateSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.directoryValidateSchema},"get")}),Object.defineProperty(exports,"pluginAdminActionSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginAdminActionSchema},"get")}),Object.defineProperty(exports,"pluginAdminProofSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginAdminProofSchema},"get")}),Object.defineProperty(exports,"pluginApprovalDigestSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginApprovalDigestSchema},"get")}),Object.defineProperty(exports,"pluginApprovedSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginApprovedSchema},"get")}),Object.defineProperty(exports,"pluginCollectionAccessSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionAccessSchema},"get")}),Object.defineProperty(exports,"pluginCollectionDeleteSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionDeleteSchema},"get")}),Object.defineProperty(exports,"pluginCollectionDocumentContentSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionDocumentContentSchema},"get")}),Object.defineProperty(exports,"pluginCollectionDocumentsStatusSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionDocumentsStatusSchema},"get")}),Object.defineProperty(exports,"pluginCollectionEnsureSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionEnsureSchema},"get")}),Object.defineProperty(exports,"pluginCollectionImportFilesSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionImportFilesSchema},"get")}),Object.defineProperty(exports,"pluginCollectionImportSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionImportSchema},"get")}),Object.defineProperty(exports,"pluginCollectionMoveSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionMoveSchema},"get")}),Object.defineProperty(exports,"pluginCollectionPermissionsSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionPermissionsSchema},"get")}),Object.defineProperty(exports,"pluginCollectionRemoveSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionRemoveSchema},"get")}),Object.defineProperty(exports,"pluginCollectionSearchSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionSearchSchema},"get")}),Object.defineProperty(exports,"pluginCollectionStatusSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginCollectionStatusSchema},"get")}),Object.defineProperty(exports,"pluginDiagramSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginDiagramSchema},"get")}),Object.defineProperty(exports,"pluginDocumentBatchInputSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginDocumentBatchInputSchema},"get")}),Object.defineProperty(exports,"pluginDocumentBatchItemSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginDocumentBatchItemSchema},"get")}),Object.defineProperty(exports,"pluginDocumentContentInputSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginDocumentContentInputSchema},"get")}),Object.defineProperty(exports,"pluginKnowledgeBaseInputSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginKnowledgeBaseInputSchema},"get")}),Object.defineProperty(exports,"pluginKnowledgeListInputSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginKnowledgeListInputSchema},"get")}),Object.defineProperty(exports,"pluginKnowledgeReferenceSchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginKnowledgeReferenceSchema},"get")}),Object.defineProperty(exports,"pluginKnowledgeVerifySchema",{enumerable:!0,get:e(function(){return chunkSR5V7ZC2_cjs.pluginKnowledgeVerifySchema},"get")}),Object.defineProperty(exports,"DECISION_CARD_FALLBACKS",{enumerable:!0,get:e(function(){return chunk66LDWN4T_cjs.DECISION_CARD_FALLBACKS},"get")}),Object.defineProperty(exports,"decisionCardPath",{enumerable:!0,get:e(function(){return chunk66LDWN4T_cjs.decisionCardPath},"get")}),Object.defineProperty(exports,"isDecisionCardBlock",{enumerable:!0,get:e(function(){return chunk66LDWN4T_cjs.isDecisionCardBlock},"get")}),Object.defineProperty(exports,"splitDecisionCardBlocks",{enumerable:!0,get:e(function(){return chunk66LDWN4T_cjs.splitDecisionCardBlocks},"get")}),Object.defineProperty(exports,"stripDecisionCardFallback",{enumerable:!0,get:e(function(){return chunk66LDWN4T_cjs.stripDecisionCardFallback},"get")});
|
package/dist/server.d.cts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
2
|
import { PluginUserContext } from './frontend.cjs';
|
|
3
|
+
export { n as DECISION_CARD_FALLBACKS, D as DecisionCard, a as DecisionCardBlock, b as DecisionCardButton, c as DecisionCardButtonId, d as DecisionCardChoice, e as DecisionCardCommit, f as DecisionCardField, g as DecisionCardGroup, h as DecisionCardItem, i as DecisionCardItemResult, j as DecisionCardSource, k as DecisionCardState, l as DecisionItemStatus, m as decisionCardPath, o as isDecisionCardBlock, s as splitDecisionCardBlocks, p as stripDecisionCardFallback } from './decision-card-IF2c4wvM.cjs';
|
|
3
4
|
|
|
4
5
|
/** Invitation requests never accept platform roles or tenant overrides. */
|
|
5
6
|
declare const accountInviteSchema: z.ZodEffects<z.ZodObject<{
|
|
@@ -1548,6 +1549,25 @@ interface PluginHostApi {
|
|
|
1548
1549
|
}): Promise<{
|
|
1549
1550
|
source: unknown;
|
|
1550
1551
|
}>;
|
|
1552
|
+
/**
|
|
1553
|
+
* Host API 1.39, requires `messages.latest_user`. The person's newest message in a
|
|
1554
|
+
* topic shared with this employee. `origin` is written by the host: `typed` or
|
|
1555
|
+
* `voice` are the person's own words; anything else, or null, is not. A long message
|
|
1556
|
+
* comes back with empty `content`: an answer is short, and this does not read history.
|
|
1557
|
+
*/
|
|
1558
|
+
latestUserMessage(input: {
|
|
1559
|
+
topicId: string;
|
|
1560
|
+
userId: string;
|
|
1561
|
+
avatarId: string;
|
|
1562
|
+
}): Promise<{
|
|
1563
|
+
message: {
|
|
1564
|
+
id: string;
|
|
1565
|
+
topicId: string;
|
|
1566
|
+
origin: string | null;
|
|
1567
|
+
content: string;
|
|
1568
|
+
createdAt: string;
|
|
1569
|
+
} | null;
|
|
1570
|
+
}>;
|
|
1551
1571
|
};
|
|
1552
1572
|
/**
|
|
1553
1573
|
* A person's live work delegations, as the host holds them.
|
|
@@ -1678,6 +1698,11 @@ interface PluginAttentionReceipt {
|
|
|
1678
1698
|
}
|
|
1679
1699
|
interface PluginAttentionStatus {
|
|
1680
1700
|
itemId: string;
|
|
1701
|
+
/**
|
|
1702
|
+
* Host API 1.40. Who actually holds it: a person away may have named a delegate, and
|
|
1703
|
+
* the host then sends a colleague's request to them instead of who was asked.
|
|
1704
|
+
*/
|
|
1705
|
+
recipientUserId?: string;
|
|
1681
1706
|
state: 'pending' | 'seen' | 'answered' | 'declined' | 'expired' | 'cancelled';
|
|
1682
1707
|
recordRef: string | null;
|
|
1683
1708
|
response: {
|