loopable-cli 0.2.0 → 0.2.1

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.
Files changed (65) hide show
  1. package/.output/nitro.json +1 -1
  2. package/.output/public/assets/_connectorId-CkygNLny.js +1 -0
  3. package/.output/public/assets/_loopId-Cshlc5Ja.js +1 -0
  4. package/.output/public/assets/_taskId-BKDIJ_Fg.js +1 -0
  5. package/.output/public/assets/connector-icon-BUoK6Cru.js +1 -0
  6. package/.output/public/assets/connectors-CeLBtEtg.js +1 -0
  7. package/.output/public/assets/gaps-BtFoD7mF.js +1 -0
  8. package/.output/public/assets/{inbox-CLEXUXCI.js → inbox-BYNjkNDJ.js} +1 -1
  9. package/.output/public/assets/index-0yP3Jn_G.js +18 -0
  10. package/.output/public/assets/loop-form-DnSJNc1k.js +1 -0
  11. package/.output/public/assets/loops-1CvbqO6m.js +1 -0
  12. package/.output/public/assets/{new-DPEaXKAY.js → new-m5NlqYQT.js} +1 -1
  13. package/.output/public/assets/refresh-cw-C3xBnKfy.js +1 -0
  14. package/.output/public/assets/{runners-BVBggS5B.js → runners-D8QVl-Y6.js} +1 -1
  15. package/.output/public/assets/{setting-fields-BT1naVJX.js → setting-fields-bJ_gTG7Q.js} +1 -1
  16. package/.output/public/assets/styles-ClTGaXU0.css +2 -0
  17. package/.output/public/assets/{task-list-CrptnI1N.js → task-list-BAxjcVgr.js} +1 -1
  18. package/.output/server/{_connectorId-DcSnoRjk.mjs → _connectorId-C9yydJrC.mjs} +90 -9
  19. package/.output/server/{_loopId-G_TAkYtS.mjs → _loopId-B0VG-eBC.mjs} +42 -13
  20. package/.output/server/_ssr/{callback-D20cVD2w.mjs → access-DTttr563.mjs} +37 -20
  21. package/.output/server/_ssr/{agents-Dms_6TBF.mjs → agents-C7B6RJ6-.mjs} +3 -3
  22. package/.output/server/_ssr/{agents-CrUmIQpi.mjs → agents-DG643yoJ.mjs} +2 -2
  23. package/.output/server/_ssr/alert-DQvzE7bu.mjs +1 -1
  24. package/.output/server/_ssr/connection-status-BZr3Y-IC.mjs +1 -1
  25. package/.output/server/_ssr/{connections-ypex3qUd.mjs → connections-Df-aDpfJ.mjs} +814 -15
  26. package/.output/server/_ssr/connector-icon-WvxwZ5TF.mjs +56 -0
  27. package/.output/server/_ssr/{connectors-4yzKb0KG.mjs → connectors-BU0IiRge.mjs} +6 -5
  28. package/.output/server/_ssr/{connectors-BZly0yGF.mjs → connectors-e0mf2pMs.mjs} +14 -3
  29. package/.output/server/_ssr/{gaps-D2Zh8sEo.mjs → gaps-Cz76ZicM.mjs} +6 -6
  30. package/.output/server/_ssr/{inbox-C2VBGLa5.mjs → inbox-CAUBa1I3.mjs} +3 -3
  31. package/.output/server/_ssr/{loop-form-D-U-kU4k.mjs → loop-form-FqSaXiHl.mjs} +5 -5
  32. package/.output/server/_ssr/{loops-Og_G3KyZ.mjs → loops-D8WuK7Ke.mjs} +199 -6
  33. package/.output/server/_ssr/{loops-D0XJ8eBb.mjs → loops-Dqoebe8q.mjs} +6 -6
  34. package/.output/server/_ssr/{new-CajvgIog.mjs → new-bBsVaWD6.mjs} +5 -5
  35. package/.output/server/_ssr/{router-BbrBz36P.mjs → router-54IDWTVz.mjs} +24 -19
  36. package/.output/server/_ssr/{runners-B_WuF8UJ.mjs → runners-Cj6z9Mqh.mjs} +26 -3
  37. package/.output/server/_ssr/{runners-D-0_lfiq.mjs → runners-D2UAdLyj.mjs} +1 -1
  38. package/.output/server/_ssr/{runners-zqF_zbEc.mjs → runners-DGWaVvWi.mjs} +2 -2
  39. package/.output/server/_ssr/{setting-fields-mpXfGftI.mjs → setting-fields-DzBlslan.mjs} +2 -2
  40. package/.output/server/_ssr/ssr.mjs +42 -34
  41. package/.output/server/_ssr/{start-BgTj-h_C.mjs → start-Vq3Oan3v.mjs} +2 -3
  42. package/.output/server/_ssr/switch-1pnd_bPJ.mjs +1 -1
  43. package/.output/server/_ssr/{task-list-BnQJ94Dk.mjs → task-list-_qgBS9LU.mjs} +5 -5
  44. package/.output/server/_ssr/{tasks-B_QmDFVs.mjs → tasks-BDqznm57.mjs} +16 -5
  45. package/.output/server/_ssr/{tasks-LIi-W4cy.mjs → tasks-Qtml5TlK.mjs} +3 -3
  46. package/.output/server/_ssr/textarea-CHJTKtsJ.mjs +1 -1
  47. package/.output/server/{_tanstack-start-manifest_v-BCHAazE8.mjs → _tanstack-start-manifest_v-CvheE7ZF.mjs} +25 -23
  48. package/.output/server/{_taskId-CIv0ajIx.mjs → _taskId-V4QLBO2N.mjs} +4 -4
  49. package/.output/server/index.mjs +139 -132
  50. package/README.md +24 -19
  51. package/dist/cli.mjs +24 -59
  52. package/dist/dispatcher.mjs +811 -31
  53. package/package.json +21 -17
  54. package/.output/public/assets/_connectorId-m67WbiJ8.js +0 -1
  55. package/.output/public/assets/_loopId-Bf4K5sdd.js +0 -1
  56. package/.output/public/assets/_taskId-eCKkcVOx.js +0 -1
  57. package/.output/public/assets/connector-icon-qGpNsPgH.js +0 -1
  58. package/.output/public/assets/connectors-DxXlc9zF.js +0 -1
  59. package/.output/public/assets/gaps-CoTA-PzA.js +0 -1
  60. package/.output/public/assets/index-Cndsw84p.js +0 -16
  61. package/.output/public/assets/loop-form-BvizlZdR.js +0 -1
  62. package/.output/public/assets/loops-Dbe_mf5T.js +0 -1
  63. package/.output/public/assets/styles-D3sonCfX.css +0 -2
  64. package/.output/server/_ssr/access-B7TcOZ7F.mjs +0 -42
  65. package/.output/server/_ssr/connector-icon-CFrrHjzR.mjs +0 -37
@@ -1,5 +1,4 @@
1
- import { networkInterfaces } from "node:os";
2
- //#region node_modules/.nitro/vite/services/ssr/assets/callback-D20cVD2w.js
1
+ //#region node_modules/.nitro/vite/services/ssr/assets/access-DTttr563.js
3
2
  function configuredOrigin() {
4
3
  return process.env.LOOPABLE_BASE_URL?.replace(/\/$/, "") || null;
5
4
  }
@@ -55,25 +54,43 @@ function registrableCallbackUrl(connectorId) {
55
54
  if (hosted) return `${hosted}/api/connectors/${connectorId}/callback`;
56
55
  return `http://127.0.0.1/api/connectors/${connectorId}/callback`;
57
56
  }
58
- /** First non-internal IPv4, preferring typical LAN ranges. */
59
- function lanIPv4(nics = networkInterfaces()) {
60
- const found = [];
61
- for (const addrs of Object.values(nics)) for (const addr of addrs ?? []) {
62
- if (addr.internal) continue;
63
- if (!["IPv4", "4"].includes(String(addr.family))) continue;
64
- found.push(addr.address);
57
+ var APP_ACCESS_COOKIE = "loopable_access";
58
+ function bearer(request) {
59
+ const header = request.headers.get("authorization") ?? "";
60
+ return /^Bearer\s+(.+)$/i.exec(header)?.[1]?.trim() ?? "";
61
+ }
62
+ function cookieValue(header, name) {
63
+ if (!header) return null;
64
+ for (const part of header.split(";")) {
65
+ const [rawName, ...rest] = part.trim().split("=");
66
+ if (rawName === name) return decodeURIComponent(rest.join("="));
65
67
  }
66
- return found.find((ip) => ip.startsWith("192.168.")) ?? found.find((ip) => ip.startsWith("10.")) ?? found.find((ip) => {
67
- const b = Number(ip.split(".")[1]);
68
- return ip.startsWith("172.") && b >= 16 && b <= 31;
69
- }) ?? found[0] ?? null;
68
+ return null;
69
+ }
70
+ function readAppToken(request) {
71
+ const fromBearer = bearer(request);
72
+ if (fromBearer) return fromBearer;
73
+ const fromQuery = new URL(request.url).searchParams.get("token")?.trim();
74
+ if (fromQuery) return fromQuery;
75
+ return cookieValue(request.headers.get("cookie"), APP_ACCESS_COOKIE);
76
+ }
77
+ function appAccessCookie(token) {
78
+ const secure = process.env.LOOPABLE_BASE_URL?.startsWith("https:") ? "; Secure" : "";
79
+ return `${APP_ACCESS_COOKIE}=${encodeURIComponent(token)}; Path=/; HttpOnly; SameSite=Lax${secure}`;
80
+ }
81
+ /**
82
+ * Loopback stays open. Anything else needs LOOPABLE_APP_TOKEN, or the UI is
83
+ * on the network with no door.
84
+ */
85
+ function assertAppAccess(request) {
86
+ if (isLoopbackHost(new URL(request.url).hostname)) return;
87
+ const expected = process.env.LOOPABLE_APP_TOKEN;
88
+ if (!expected) throw new Error("Set LOOPABLE_APP_TOKEN before exposing Loopable off loopback.");
89
+ if (readAppToken(request) !== expected) throw new Error("This Loopable is not open to you.");
70
90
  }
71
- /** Where runners should address this Loopable. A LAN IP when one exists. */
72
- function loopableOrigin(nics = networkInterfaces()) {
73
- const configured = configuredOrigin();
74
- if (configured) return configured;
75
- const port = process.env.PORT ?? process.env.NITRO_PORT ?? "4321";
76
- return `http://${lanIPv4(nics) ?? "127.0.0.1"}:${port}`;
91
+ /** Runner pull and OAuth callbacks have their own tokens. */
92
+ function isPublicApiPath(pathname) {
93
+ return pathname.startsWith("/api/runners/") || pathname.startsWith("/api/connectors/");
77
94
  }
78
95
  //#endregion
79
- export { registrableCallbackUrl as a, loopableOrigin as i, callbackUrl as n, isLoopbackHost as r, appOrigin as t };
96
+ export { callbackUrl as a, readAppToken as c, bearer as i, registrableCallbackUrl as l, appOrigin as n, isLoopbackHost as o, assertAppAccess as r, isPublicApiPath as s, appAccessCookie as t };
@@ -1,8 +1,8 @@
1
1
  import { n as createServerFn } from "./ssr.mjs";
2
- import { a as setDefaultAgent, i as saveAgentSettings, r as listAgents, s as testAgent } from "./agents-CrUmIQpi.mjs";
3
- import { c as listRunners, t as availableAgentIds } from "./runners-D-0_lfiq.mjs";
2
+ import { a as saveAgentSettings, c as testAgent, i as listAgents, o as setDefaultAgent } from "./agents-DG643yoJ.mjs";
3
+ import { c as listRunners, t as availableAgentIds } from "./runners-D2UAdLyj.mjs";
4
4
  import { t as createServerRpc } from "./createServerRpc-DPDrnFdH.mjs";
5
- //#region node_modules/.nitro/vite/services/ssr/assets/agents-Dms_6TBF.js
5
+ //#region node_modules/.nitro/vite/services/ssr/assets/agents-C7B6RJ6-.js
6
6
  async function withRunners(agents) {
7
7
  const runners = await listRunners();
8
8
  const available = await availableAgentIds();
@@ -6,7 +6,7 @@ import { join } from "node:path";
6
6
  import { homedir, tmpdir } from "node:os";
7
7
  import { execFile, spawn } from "node:child_process";
8
8
  import { promisify } from "node:util";
9
- //#region node_modules/.nitro/vite/services/ssr/assets/agents-CrUmIQpi.js
9
+ //#region node_modules/.nitro/vite/services/ssr/assets/agents-DG643yoJ.js
10
10
  function defineAgentManifest(manifest) {
11
11
  return manifest;
12
12
  }
@@ -654,4 +654,4 @@ async function testAgent(agentId) {
654
654
  };
655
655
  }
656
656
  //#endregion
657
- export { setDefaultAgent as a, saveAgentSettings as i, agentManifest as n, settingsFor as o, listAgents as r, testAgent as s, AGENT_MANIFESTS as t };
657
+ export { saveAgentSettings as a, testAgent as c, listAgents as i, agentManifest as n, setDefaultAgent as o, agentRuntime as r, settingsFor as s, AGENT_MANIFESTS as t };
@@ -1,7 +1,7 @@
1
1
  import "../_runtime.mjs";
2
2
  import { U as require_jsx_runtime, W as require_react } from "../_libs/@base-ui/react+[...].mjs";
3
3
  import { t as cva } from "../_libs/class-variance-authority+clsx.mjs";
4
- import { H as cn } from "./router-BbrBz36P.mjs";
4
+ import { W as cn } from "./router-54IDWTVz.mjs";
5
5
  require_react();
6
6
  var import_jsx_runtime = require_jsx_runtime();
7
7
  var alertVariants = cva("group/alert relative grid w-full gap-0.5 rounded-lg border px-2.5 py-2 text-left text-sm has-data-[slot=alert-action]:relative has-data-[slot=alert-action]:pr-18 has-[>svg]:grid-cols-[auto_1fr] has-[>svg]:gap-x-2 *:[svg]:row-span-2 *:[svg]:translate-y-0.5 *:[svg]:text-current *:[svg:not([class*='size-'])]:size-4", {
@@ -1,5 +1,5 @@
1
1
  import { U as require_jsx_runtime } from "../_libs/@base-ui/react+[...].mjs";
2
- import { I as Badge } from "./router-BbrBz36P.mjs";
2
+ import { R as Badge } from "./router-54IDWTVz.mjs";
3
3
  //#region node_modules/.nitro/vite/services/ssr/assets/connection-status-BZr3Y-IC.js
4
4
  var import_jsx_runtime = require_jsx_runtime();
5
5
  var LABELS = {