@loxtep/sdk 0.9.14 → 0.9.16

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 (52) hide show
  1. package/CHANGELOG.md +38 -0
  2. package/dist/authoring/types.d.ts +8 -0
  3. package/dist/authoring/types.d.ts.map +1 -1
  4. package/dist/cli/commands/deploy-cmd.d.ts.map +1 -1
  5. package/dist/cli/commands/deploy-cmd.js +30 -15
  6. package/dist/cli/commands/deploy-cmd.js.map +1 -1
  7. package/dist/cli/commands/init-cmd.d.ts.map +1 -1
  8. package/dist/cli/commands/init-cmd.js +54 -24
  9. package/dist/cli/commands/init-cmd.js.map +1 -1
  10. package/dist/cli/commands/setup-cmd.d.ts +31 -0
  11. package/dist/cli/commands/setup-cmd.d.ts.map +1 -0
  12. package/dist/cli/commands/setup-cmd.js +126 -0
  13. package/dist/cli/commands/setup-cmd.js.map +1 -0
  14. package/dist/cli/commands/test-cmd.d.ts +3 -0
  15. package/dist/cli/commands/test-cmd.d.ts.map +1 -1
  16. package/dist/cli/commands/test-cmd.js +60 -50
  17. package/dist/cli/commands/test-cmd.js.map +1 -1
  18. package/dist/cli/help.d.ts.map +1 -1
  19. package/dist/cli/help.js +7 -3
  20. package/dist/cli/help.js.map +1 -1
  21. package/dist/cli/index.d.ts.map +1 -1
  22. package/dist/cli/index.js +4 -0
  23. package/dist/cli/index.js.map +1 -1
  24. package/dist/cli/load-workflow-module.d.ts +30 -0
  25. package/dist/cli/load-workflow-module.d.ts.map +1 -0
  26. package/dist/cli/load-workflow-module.js +94 -0
  27. package/dist/cli/load-workflow-module.js.map +1 -0
  28. package/dist/cli/resolve-package-root.cjs +49 -0
  29. package/dist/cli/templates-materialize.d.ts +23 -0
  30. package/dist/cli/templates-materialize.d.ts.map +1 -0
  31. package/dist/cli/templates-materialize.js +127 -0
  32. package/dist/cli/templates-materialize.js.map +1 -0
  33. package/dist/client/data-products.d.ts.map +1 -1
  34. package/dist/client/data-products.js +24 -2
  35. package/dist/client/data-products.js.map +1 -1
  36. package/dist/client/loxtep-client.d.ts +11 -4
  37. package/dist/client/loxtep-client.d.ts.map +1 -1
  38. package/dist/client/loxtep-client.js +39 -11
  39. package/dist/client/loxtep-client.js.map +1 -1
  40. package/dist/rstreams/leo-runtime.d.ts +6 -1
  41. package/dist/rstreams/leo-runtime.d.ts.map +1 -1
  42. package/dist/rstreams/leo-runtime.js +15 -2
  43. package/dist/rstreams/leo-runtime.js.map +1 -1
  44. package/docs/code-first-cli.md +28 -12
  45. package/package.json +6 -4
  46. package/templates/shopify-orders/AGENTS.md +35 -0
  47. package/templates/shopify-orders/README.md +50 -0
  48. package/templates/shopify-orders/events/order-created.json +17 -0
  49. package/templates/shopify-orders/package.json +11 -0
  50. package/templates/shopify-orders/skills/shopify-orders.yaml +29 -0
  51. package/templates/shopify-orders/tsconfig.json +14 -0
  52. package/templates/shopify-orders/workflows/orders-enricher.ts +31 -0
@@ -7,7 +7,7 @@
7
7
  */
8
8
  import { createRequire } from 'node:module';
9
9
  const require = createRequire(import.meta.url);
10
- export function createRStreamsSdk(config) {
10
+ export function createRStreamsSdk(config, options) {
11
11
  // Lazy CJS require — only when a stream reader/writer is actually constructed.
12
12
  const StreamRuntime = require('leo-sdk');
13
13
  const defaultExport = StreamRuntime.default;
@@ -15,6 +15,19 @@ export function createRStreamsSdk(config) {
15
15
  if (!SDK || typeof SDK !== 'function') {
16
16
  throw new Error('Failed to resolve RStreamsSdk constructor from leo-sdk');
17
17
  }
18
- return new SDK(config);
18
+ const credentials = options?.credentials;
19
+ if (!credentials) {
20
+ return new SDK(config);
21
+ }
22
+ // Pin STS onto every AWS client the bus uses — default credential chain is the
23
+ // operator profile, which cannot write org/shared bus Kinesis streams.
24
+ const region = config.Region;
25
+ const clientCreds = { credentials, region };
26
+ return new SDK(config, {
27
+ kinesisConfig: clientCreds,
28
+ dynamodbConfig: clientCreds,
29
+ s3Config: clientCreds,
30
+ firehoseConfig: clientCreds,
31
+ });
19
32
  }
20
33
  //# sourceMappingURL=leo-runtime.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"leo-runtime.js","sourceRoot":"","sources":["../../src/rstreams/leo-runtime.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAG5C,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAE/C,MAAM,UAAU,iBAAiB,CAAC,MAA8B;IAC9D,+EAA+E;IAC/E,MAAM,aAAa,GAAG,OAAO,CAAC,SAAS,CAGtC,CAAC;IACF,MAAM,aAAa,GAAG,aAAa,CAAC,OAAO,CAAC;IAC5C,MAAM,GAAG,GAAG,CAAC,aAAa,CAAC,WAAW,IAAI,aAAa,EAAE,WAAW,CAEvD,CAAC;IACd,IAAI,CAAC,GAAG,IAAI,OAAO,GAAG,KAAK,UAAU,EAAE,CAAC;QACtC,MAAM,IAAI,KAAK,CAAC,wDAAwD,CAAC,CAAC;IAC5E,CAAC;IACD,OAAO,IAAI,GAAG,CAAC,MAAM,CAAC,CAAC;AACzB,CAAC"}
1
+ {"version":3,"file":"leo-runtime.js","sourceRoot":"","sources":["../../src/rstreams/leo-runtime.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAI5C,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAO/C,MAAM,UAAU,iBAAiB,CAC/B,MAA8B,EAC9B,OAAkC;IAElC,+EAA+E;IAC/E,MAAM,aAAa,GAAG,OAAO,CAAC,SAAS,CAMtC,CAAC;IACF,MAAM,aAAa,GAAG,aAAa,CAAC,OAAO,CAAC;IAC5C,MAAM,GAAG,GAAG,CAAC,aAAa,CAAC,WAAW,IAAI,aAAa,EAAE,WAAW,CAKvD,CAAC;IACd,IAAI,CAAC,GAAG,IAAI,OAAO,GAAG,KAAK,UAAU,EAAE,CAAC;QACtC,MAAM,IAAI,KAAK,CAAC,wDAAwD,CAAC,CAAC;IAC5E,CAAC;IAED,MAAM,WAAW,GAAG,OAAO,EAAE,WAAW,CAAC;IACzC,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,OAAO,IAAI,GAAG,CAAC,MAAM,CAAC,CAAC;IACzB,CAAC;IAED,+EAA+E;IAC/E,uEAAuE;IACvE,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC;IAC7B,MAAM,WAAW,GAAG,EAAE,WAAW,EAAE,MAAM,EAAE,CAAC;IAC5C,OAAO,IAAI,GAAG,CAAC,MAAM,EAAE;QACrB,aAAa,EAAE,WAAW;QAC1B,cAAc,EAAE,WAAW;QAC3B,QAAQ,EAAE,WAAW;QACrB,cAAc,EAAE,WAAW;KAC5B,CAAC,CAAC;AACL,CAAC"}
@@ -86,9 +86,10 @@ Scaffolds a **Loxtep workspace** in the current directory.
86
86
  | `workflows/` | Workflow modules you author and deploy |
87
87
  | `data-products/` | Data product definitions |
88
88
 
89
- With **`--template <slug>`**, init also materializes template content from the
90
- platform catalog, including **`AGENTS.md`** and a default skill at
91
- **`.loxtep/skills/<slug>.yaml`**.
89
+ With **`--template shopify-orders`**, init materializes the **bundled runnable
90
+ sample** (workflow, event fixture, AGENTS.md, skill, package/tsconfig). Other
91
+ slugs still write AGENTS.md + a default skill from catalog metadata when
92
+ available.
92
93
 
93
94
  ### Common flags
94
95
 
@@ -141,17 +142,18 @@ Import in workflow modules:
141
142
 
142
143
  ```typescript
143
144
  import { defineDataWorkflow, on } from '@loxtep/sdk';
144
- import { workspace } from './.loxtep/generated';
145
+ import { workspace } from '../.loxtep/generated/index.js';
145
146
 
146
147
  export default defineDataWorkflow({
147
148
  name: 'orders-enricher',
148
- triggers: [on.queueEvent(workspace.queues.orders_raw)],
149
+ triggers: [on.webhook('/shopify/orders')],
150
+ requireApproval: ['dataProducts.write'],
149
151
  async handler(ctx, event) {
150
- await ctx.toolbox.dataProducts.upsert({
151
- dataProduct: workspace.dataProducts.orders_enriched,
152
- domain: workspace.domains.commerce,
153
- record: event,
154
- });
152
+ const order = (event ?? {}) as Record<string, unknown>;
153
+ await ctx.toolbox!.dataProducts.write(
154
+ workspace.dataProducts.orders_enriched,
155
+ { ...order, enriched_at: new Date().toISOString(), source: 'orders-enricher' }
156
+ );
155
157
  },
156
158
  });
157
159
  ```
@@ -161,6 +163,19 @@ credentials without hand-wiring env vars.
161
163
 
162
164
  ---
163
165
 
166
+ ## `loxtep setup` (shopify-orders)
167
+
168
+ After attach, provision the sample data products (idempotent):
169
+
170
+ ```bash
171
+ pnpm exec loxtep setup
172
+ ```
173
+
174
+ Creates `orders_raw` and `orders_enriched` via `ingest create --deploy` when
175
+ missing. Requires an org domain.
176
+
177
+ ---
178
+
164
179
  ## `loxtep test` and `loxtep deploy`
165
180
 
166
181
  ```bash
@@ -168,8 +183,9 @@ pnpm exec loxtep test orders-enricher --event ./events/order-created.json
168
183
  pnpm exec loxtep deploy
169
184
  ```
170
185
 
171
- - **`test`** — runs one workflow module locally against the attached instance and
172
- prints an action trace.
186
+ - **`test`** — runs one workflow module **locally with live instance I/O** and
187
+ prints an action trace. Guarded ops (`requireApproval`) prompt; reject/timeout
188
+ and handler errors exit **nonzero**.
173
189
  - **`deploy`** — compiles modules into the platform workflow graph and deploys to
174
190
  the attached instance.
175
191
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@loxtep/sdk",
3
- "version": "0.9.14",
3
+ "version": "0.9.16",
4
4
  "description": "Loxtep SDK for Node.js — the Enterprise Context Layer: data products, workflows, projects, queues, and machine-usable context for AI",
5
5
  "author": "Loxtep <engineering@loxtep.io>",
6
6
  "homepage": "https://loxtep.io",
@@ -34,17 +34,19 @@
34
34
  "dist",
35
35
  "docs",
36
36
  "schemas",
37
+ "templates",
37
38
  "CHANGELOG.md"
38
39
  ],
39
40
  "scripts": {
40
- "build": "tsc && mkdir -p dist/lib/entity-json-schemas && cp src/lib/entity-json-schemas/ajv-loader.cjs dist/lib/entity-json-schemas/ajv-loader.cjs",
41
+ "build": "tsc && mkdir -p dist/lib/entity-json-schemas && cp src/lib/entity-json-schemas/ajv-loader.cjs dist/lib/entity-json-schemas/ajv-loader.cjs && cp src/cli/resolve-package-root.cjs dist/cli/resolve-package-root.cjs",
41
42
  "prepublishOnly": "npm run build",
42
43
  "test": "jest --config jest.config.cjs",
43
44
  "lint": "eslint src --ext .ts",
44
45
  "sync:entity-schemas": "node scripts/sync-entity-schemas.mjs",
45
46
  "generate:api-types": "tsx scripts/generate-api-types.ts",
46
47
  "docs": "typedoc",
47
- "test:e2e:cli": "bash scripts/cli-e2e.sh"
48
+ "test:e2e:cli": "bash scripts/cli-e2e.sh",
49
+ "test:e2e:try-it": "bash scripts/try-it-onboarding-e2e.sh"
48
50
  },
49
51
  "publishConfig": {
50
52
  "access": "public",
@@ -89,6 +91,7 @@
89
91
  "ajv-formats": "^3.0.1",
90
92
  "js-yaml": "^4.3.0",
91
93
  "leo-sdk": "7.1.21",
94
+ "tsx": "^4.22.0",
92
95
  "zod": "^4.4.3"
93
96
  },
94
97
  "devDependencies": {
@@ -97,7 +100,6 @@
97
100
  "fast-check": "^4.8.0",
98
101
  "jest": "^30.4.2",
99
102
  "ts-jest": "^29.4.9",
100
- "tsx": "^4.22.0",
101
103
  "typedoc": "^0.28.19",
102
104
  "typescript": "^6.0.3",
103
105
  "zod-to-ts": "^2.0.0"
@@ -0,0 +1,35 @@
1
+ # AGENTS.md — shopify-orders
2
+
3
+ This project was scaffolded from the `shopify-orders` template (Try it sample).
4
+
5
+ ## MCP tools
6
+
7
+ ```json
8
+ { "mcpServers": { "loxtep": { "url": "https://mcp.loxtep.io/ai/mcp/stream" } } }
9
+ ```
10
+
11
+ Dev MCP host: `https://mcpdev.loxtep.io/ai/mcp/stream`.
12
+
13
+ ## Lifecycle
14
+
15
+ ```bash
16
+ loxtep login
17
+ loxtep attach --instance <non-prod-instance-id>
18
+ loxtep setup
19
+ loxtep generate
20
+ loxtep test orders-enricher --event ./events/order-created.json
21
+ loxtep deploy
22
+ ```
23
+
24
+ `loxtep test` runs the handler locally with **live** instance I/O. Approve
25
+ `dataProducts.write` when prompted.
26
+
27
+ ## SDK methods
28
+
29
+ - `LoxtepClient.fromWorkspace()` — configure from `.loxtep/project.json`
30
+ - `defineDataWorkflow({ name, triggers, handler, requireApproval })`
31
+ - `workspace.dataProducts.*` — typed constants after `loxtep generate`
32
+
33
+ ## Skill scope
34
+
35
+ Default skill: `.loxtep/skills/shopify-orders.yaml`
@@ -0,0 +1,50 @@
1
+ # Shopify orders sample (`shopify-orders`)
2
+
3
+ Minimal code-first Loxtep workspace used by [Try it](https://loxtep.io/try-it).
4
+
5
+ ## Prerequisites
6
+
7
+ | Requirement | Notes |
8
+ | --- | --- |
9
+ | **Node.js 22+** | `node --version` |
10
+ | **Loxtep account** | [app.loxtep.io](https://app.loxtep.io) |
11
+ | **Auth** | `loxtep login` (writes `./.loxtep/credentials.json`) |
12
+ | **Instance** | Non-production preferred — `loxtep instances list` then `loxtep attach` |
13
+ | **Domain** | Org must have at least one domain (create in UI if none) |
14
+
15
+ `loxtep test` executes your handler **locally with live instance I/O** (stream writes).
16
+ It is not an offline simulator. Sample writes require terminal approval
17
+ (`requireApproval: ['dataProducts.write']`).
18
+
19
+ ## Lifecycle (empty directory → deploy)
20
+
21
+ ```bash
22
+ mkdir shopify-orders-demo && cd shopify-orders-demo
23
+ npm init -y
24
+ npm install @loxtep/sdk@^0.9.16
25
+ npx loxtep login
26
+ npx loxtep init --template shopify-orders
27
+ npx loxtep attach --instance <non-prod-instance-id>
28
+ npx loxtep setup # provisions orders_raw + orders_enriched (idempotent)
29
+ npx loxtep generate
30
+ npx loxtep test orders-enricher --event ./events/order-created.json
31
+ # Approve dataProducts.write when prompted (y)
32
+ npx loxtep deploy
33
+ ```
34
+
35
+ Re-running `setup` is safe: existing data products are reused.
36
+
37
+ ## What this template scaffolds
38
+
39
+ | Path | Purpose |
40
+ | --- | --- |
41
+ | `workflows/orders-enricher.ts` | Sample module (webhook → enrich → write) |
42
+ | `events/order-created.json` | Fixture for `loxtep test` |
43
+ | `AGENTS.md` / `.loxtep/skills/` | Agent + skill scope |
44
+ | `package.json` / `tsconfig.json` | Node 22 + typed workflows |
45
+
46
+ ## Approval / failure behavior
47
+
48
+ - Reject or timeout on a guarded write → operation skipped, **nonzero exit**
49
+ - Handler or toolbox errors → recorded in the action trace, **nonzero exit**
50
+ - Success → exit 0 and a trace with `handler.start` → `dataProducts.write` → `handler.complete`
@@ -0,0 +1,17 @@
1
+ {
2
+ "id": "gid://shopify/Order/5678901234",
3
+ "name": "#1001",
4
+ "email": "customer@example.com",
5
+ "created_at": "2026-09-22T12:00:00Z",
6
+ "currency": "USD",
7
+ "total_price": "129.99",
8
+ "financial_status": "paid",
9
+ "line_items": [
10
+ {
11
+ "id": 1,
12
+ "title": "Sample Widget",
13
+ "quantity": 1,
14
+ "price": "129.99"
15
+ }
16
+ ]
17
+ }
@@ -0,0 +1,11 @@
1
+ {
2
+ "name": "loxtep-shopify-orders-sample",
3
+ "private": true,
4
+ "type": "module",
5
+ "engines": {
6
+ "node": ">=22"
7
+ },
8
+ "dependencies": {
9
+ "@loxtep/sdk": "^0.9.16"
10
+ }
11
+ }
@@ -0,0 +1,29 @@
1
+ # Default skill for the shopify-orders template.
2
+ # Scoped to the sample resources provisioned by `loxtep setup`.
3
+ name: shopify-orders
4
+ description: Shopify orders enricher sample — orders_raw ingest and orders_enriched write target
5
+ scope:
6
+ # workflows left empty until after first `loxtep deploy` of orders-enricher
7
+ # (generate validates skill refs against the live workspace).
8
+ data_products:
9
+ - orders_raw
10
+ - orders_enriched
11
+ connectors: []
12
+ workflows: []
13
+ domains: []
14
+ queues: []
15
+ permissions:
16
+ data_products:
17
+ - read
18
+ - write
19
+ connectors:
20
+ - read
21
+ workflows:
22
+ - read
23
+ - write
24
+ - create
25
+ domains:
26
+ - read
27
+ queues:
28
+ - read
29
+ - write
@@ -0,0 +1,14 @@
1
+ {
2
+ "compilerOptions": {
3
+ "target": "ES2022",
4
+ "module": "NodeNext",
5
+ "moduleResolution": "NodeNext",
6
+ "strict": true,
7
+ "esModuleInterop": true,
8
+ "skipLibCheck": true,
9
+ "resolveJsonModule": true,
10
+ "noEmit": true,
11
+ "types": ["node"]
12
+ },
13
+ "include": ["workflows/**/*.ts", ".loxtep/generated/**/*.ts"]
14
+ }
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Sample: enrich an inbound Shopify order and write it to `orders_enriched`.
3
+ *
4
+ * Prerequisites (see README / `loxtep setup`):
5
+ * - attached non-production instance
6
+ * - `orders_enriched` data product provisioned and deployed
7
+ * - `loxtep generate` so `.loxtep/generated` exists
8
+ *
9
+ * `loxtep test` runs this handler locally against the attached instance
10
+ * (live stream I/O — not an offline simulation). `dataProducts.write` is
11
+ * gated by `requireApproval` so sample writes cannot silently hit the bus.
12
+ */
13
+ import { defineDataWorkflow, on } from '@loxtep/sdk';
14
+ import { workspace } from '../.loxtep/generated/index.js';
15
+
16
+ export default defineDataWorkflow({
17
+ name: 'orders-enricher',
18
+ // Webhook trigger avoids depending on a friendly observe queue name.
19
+ // After `loxtep setup`, you can switch to on.queueEvent(workspace.queues.*)
20
+ // once a matching queue appears in `loxtep generate` output.
21
+ triggers: [on.webhook('/shopify/orders')],
22
+ requireApproval: ['dataProducts.write'],
23
+ async handler(ctx, event) {
24
+ const order = (event ?? {}) as Record<string, unknown>;
25
+ await ctx.toolbox.dataProducts.write(workspace.dataProducts.orders_enriched, {
26
+ ...order,
27
+ enriched_at: new Date().toISOString(),
28
+ source: 'orders-enricher',
29
+ });
30
+ },
31
+ });