@walkeros/server-destination-gcp 4.7.0-next-1790722899482 → 4.7.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/CHANGELOG.md CHANGED
@@ -1,9 +1,14 @@
1
1
  # @walkeros/server-destination-gcp
2
2
 
3
- ## 4.7.0-next-1790722899482
3
+ ## 4.7.0
4
4
 
5
5
  ### Minor Changes
6
6
 
7
+ - 64b06de: Packages with several exports, such as the GCP and AWS sources and
8
+ destinations, now publish a settings schema per export. `walkeros validate`
9
+ and MCP `package_get` use the schema of the export a step imports. Pub/Sub,
10
+ BigQuery, SNS and SQS steps pinned to this release or later are checked
11
+ instead of skipped; older pins still report a skip.
7
12
  - 74821ed: Simulate records every vendor call through one recorder, `observeEnv`
8
13
  from `@walkeros/core`, and runs offline: BigQuery, Data Manager and the
9
14
  Sheets, GCS and S3 stores reach the network through `env`. Client and `Env`
@@ -21,6 +26,8 @@
21
26
  - Updated dependencies [74821ed]
22
27
  - Updated dependencies [06b498a]
23
28
  - Updated dependencies [74821ed]
29
+ - Updated dependencies [64b06de]
30
+ - Updated dependencies [4b4937f]
24
31
  - Updated dependencies [74821ed]
25
32
  - Updated dependencies [74821ed]
26
33
  - Updated dependencies [74821ed]
@@ -30,10 +37,12 @@
30
37
  - Updated dependencies [74821ed]
31
38
  - Updated dependencies [74821ed]
32
39
  - Updated dependencies [74821ed]
40
+ - Updated dependencies [e860006]
33
41
  - Updated dependencies [74821ed]
34
42
  - Updated dependencies [74821ed]
35
- - @walkeros/core@4.7.0-next-1790722899482
36
- - @walkeros/server-core@4.7.0-next-1790722899482
43
+ - Updated dependencies [4f89234]
44
+ - @walkeros/core@4.7.0
45
+ - @walkeros/server-core@4.7.0
37
46
 
38
47
  ## 4.6.1
39
48
 
package/dist/dev.d.mts CHANGED
@@ -5,17 +5,6 @@ import { managedwriter } from '@google-cloud/bigquery-storage';
5
5
  import { Flow, Hint } from '@walkeros/core';
6
6
  import { ClientConfig } from '@google-cloud/pubsub';
7
7
 
8
- declare const settings$1: _walkeros_core_dev.JSONSchema;
9
- declare const mapping$1: _walkeros_core_dev.JSONSchema;
10
-
11
- declare const settings: _walkeros_core_dev.JSONSchema;
12
- declare const mapping: _walkeros_core_dev.JSONSchema;
13
- declare const setup: _walkeros_core_dev.JSONSchema;
14
-
15
- declare namespace schemas {
16
- export { mapping$1 as mapping, mapping as pubsubMapping, settings as pubsubSettings, setup as pubsubSetup, settings$1 as settings };
17
- }
18
-
19
8
  type CallOptions = NonNullable<Parameters<managedwriter.WriterClient['getWriteStream']>[1]>;
20
9
  type ClientOptions = NonNullable<ConstructorParameters<typeof managedwriter.WriterClient>[0]>;
21
10
  type WriteStreamRequest = Parameters<managedwriter.WriterClient['getWriteStream']>[0];
@@ -248,6 +237,17 @@ declare namespace pubsubExamplesNs {
248
237
  export { pubsubExamplesNs_env as env, pubsubExamplesNs_step as step };
249
238
  }
250
239
 
240
+ declare const settings$1: _walkeros_core_dev.JSONSchema;
241
+ declare const mapping$1: _walkeros_core_dev.JSONSchema;
242
+
243
+ declare const settings: _walkeros_core_dev.JSONSchema;
244
+ declare const mapping: _walkeros_core_dev.JSONSchema;
245
+ declare const setup: _walkeros_core_dev.JSONSchema;
246
+
247
+ declare namespace schemas {
248
+ export { mapping$1 as mapping, mapping as pubsubMapping, settings as pubsubSettings, setup as pubsubSetup, settings$1 as settings };
249
+ }
250
+
251
251
  declare const hints: Hint.Hints;
252
252
 
253
253
  /** Dev examples per export, keyed by the export names in package.json. */
@@ -255,5 +255,17 @@ declare const exportExamples: {
255
255
  destinationBigQuery: typeof bigqueryExamplesNs;
256
256
  destinationPubSub: typeof pubsubExamplesNs;
257
257
  };
258
+ /** Schemas per export, keyed by the export names in package.json. */
259
+ declare const exportSchemas: {
260
+ destinationBigQuery: {
261
+ settings: _walkeros_core_dev.JSONSchema;
262
+ mapping: _walkeros_core_dev.JSONSchema;
263
+ };
264
+ destinationPubSub: {
265
+ settings: _walkeros_core_dev.JSONSchema;
266
+ mapping: _walkeros_core_dev.JSONSchema;
267
+ setup: _walkeros_core_dev.JSONSchema;
268
+ };
269
+ };
258
270
 
259
- export { bigqueryExamplesNs as examples, exportExamples, hints, pubsubExamplesNs as pubsubExamples, schemas };
271
+ export { bigqueryExamplesNs as examples, exportExamples, exportSchemas, hints, pubsubExamplesNs as pubsubExamples, schemas };
package/dist/dev.d.ts CHANGED
@@ -5,17 +5,6 @@ import { managedwriter } from '@google-cloud/bigquery-storage';
5
5
  import { Flow, Hint } from '@walkeros/core';
6
6
  import { ClientConfig } from '@google-cloud/pubsub';
7
7
 
8
- declare const settings$1: _walkeros_core_dev.JSONSchema;
9
- declare const mapping$1: _walkeros_core_dev.JSONSchema;
10
-
11
- declare const settings: _walkeros_core_dev.JSONSchema;
12
- declare const mapping: _walkeros_core_dev.JSONSchema;
13
- declare const setup: _walkeros_core_dev.JSONSchema;
14
-
15
- declare namespace schemas {
16
- export { mapping$1 as mapping, mapping as pubsubMapping, settings as pubsubSettings, setup as pubsubSetup, settings$1 as settings };
17
- }
18
-
19
8
  type CallOptions = NonNullable<Parameters<managedwriter.WriterClient['getWriteStream']>[1]>;
20
9
  type ClientOptions = NonNullable<ConstructorParameters<typeof managedwriter.WriterClient>[0]>;
21
10
  type WriteStreamRequest = Parameters<managedwriter.WriterClient['getWriteStream']>[0];
@@ -248,6 +237,17 @@ declare namespace pubsubExamplesNs {
248
237
  export { pubsubExamplesNs_env as env, pubsubExamplesNs_step as step };
249
238
  }
250
239
 
240
+ declare const settings$1: _walkeros_core_dev.JSONSchema;
241
+ declare const mapping$1: _walkeros_core_dev.JSONSchema;
242
+
243
+ declare const settings: _walkeros_core_dev.JSONSchema;
244
+ declare const mapping: _walkeros_core_dev.JSONSchema;
245
+ declare const setup: _walkeros_core_dev.JSONSchema;
246
+
247
+ declare namespace schemas {
248
+ export { mapping$1 as mapping, mapping as pubsubMapping, settings as pubsubSettings, setup as pubsubSetup, settings$1 as settings };
249
+ }
250
+
251
251
  declare const hints: Hint.Hints;
252
252
 
253
253
  /** Dev examples per export, keyed by the export names in package.json. */
@@ -255,5 +255,17 @@ declare const exportExamples: {
255
255
  destinationBigQuery: typeof bigqueryExamplesNs;
256
256
  destinationPubSub: typeof pubsubExamplesNs;
257
257
  };
258
+ /** Schemas per export, keyed by the export names in package.json. */
259
+ declare const exportSchemas: {
260
+ destinationBigQuery: {
261
+ settings: _walkeros_core_dev.JSONSchema;
262
+ mapping: _walkeros_core_dev.JSONSchema;
263
+ };
264
+ destinationPubSub: {
265
+ settings: _walkeros_core_dev.JSONSchema;
266
+ mapping: _walkeros_core_dev.JSONSchema;
267
+ setup: _walkeros_core_dev.JSONSchema;
268
+ };
269
+ };
258
270
 
259
- export { bigqueryExamplesNs as examples, exportExamples, hints, pubsubExamplesNs as pubsubExamples, schemas };
271
+ export { bigqueryExamplesNs as examples, exportExamples, exportSchemas, hints, pubsubExamplesNs as pubsubExamples, schemas };
package/dist/dev.js CHANGED
@@ -1 +1 @@
1
- "use strict";var e,t=Object.defineProperty,r=Object.getOwnPropertyDescriptor,s=Object.getOwnPropertyNames,o=Object.prototype.hasOwnProperty,i=(e,r)=>{for(var s in r)t(e,s,{get:r[s],enumerable:!0})},a={};i(a,{examples:()=>O,exportExamples:()=>ue,hints:()=>ce,pubsubExamples:()=>L,schemas:()=>n}),module.exports=(e=a,((e,i,a,n)=>{if(i&&"object"==typeof i||"function"==typeof i)for(let l of s(i))o.call(e,l)||l===a||t(e,l,{get:()=>i[l],enumerable:!(n=r(i,l))||n.enumerable});return e})(t({},"__esModule",{value:!0}),e));var n={};i(n,{mapping:()=>g,pubsubMapping:()=>k,pubsubSettings:()=>w,pubsubSetup:()=>j,settings:()=>p});var l=require("@walkeros/core/dev"),c=require("@walkeros/core/dev"),u=c.z.object({client:c.z.any().describe("Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))").optional(),projectId:c.z.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),datasetId:c.z.string().min(1).default("walkerOS").describe("BigQuery dataset ID where events will be stored (like walker_events)"),tableId:c.z.string().min(1).default("events").describe("BigQuery table ID for event storage (like events)"),location:c.z.string().default("EU").describe("Geographic location for the BigQuery dataset (like US)"),bigquery:c.z.any().describe('Additional BigQuery client configuration options (like { keyFilename: "path/to/key.json" })').optional()}),d=require("@walkeros/core/dev").z.object({}),p=(0,l.zodToSchema)(u),g=(0,l.zodToSchema)(d),m=require("@walkeros/core/dev"),b=require("@walkeros/core/dev"),h=b.z.object({client:b.z.any().describe("Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))").optional(),projectId:b.z.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),topic:b.z.string().min(1).describe("Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK."),credentials:b.z.any().describe("Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)").optional(),apiEndpoint:b.z.string().describe("Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).").optional(),orderingKey:b.z.any().describe("Mapping value resolved per-event. Truthy enables per-key ordering for the publish.").optional(),attributes:b.z.any().describe("Default per-event attribute map merged into every published message. Mapping.Map shape.").optional()}),y=require("@walkeros/core/dev"),v=y.z.object({topic:y.z.string().describe("Per-rule topic override. Falls back to settings.topic if absent.").optional(),orderingKey:y.z.any().describe("Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.").optional(),attributes:y.z.any().describe("Per-rule attribute Mapping.Map merged on top of settings.attributes.").optional()}),f=require("@walkeros/core/dev"),S=f.z.object({messageStoragePolicy:f.z.object({allowedPersistenceRegions:f.z.array(f.z.string()).describe("Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).")}).describe("Topic-level message storage policy.").optional(),messageRetentionDuration:f.z.object({seconds:f.z.number().describe("Retention window in seconds. Default: project default.")}).describe("Topic-level retention configuration.").optional(),kmsKeyName:f.z.string().describe("Customer-managed encryption key (CMEK) resource name. Optional.").optional(),labels:f.z.record(f.z.string(),f.z.string()).describe("Topic labels for organization and billing.").optional()}),w=(0,m.zodToSchema)(h),k=(0,m.zodToSchema)(v),j=(0,m.zodToSchema)(S),O={};i(O,{env:()=>z,step:()=>B});var z={};i(z,{push:()=>q,simulation:()=>J});var P=require("events"),A=[],E=null,C=null,D=null,T=null,I=class extends P.EventEmitter{streamId;constructor(e){super(),this.streamId=e}getStreamId(){return this.streamId}onConnectionError(e){return A.push({method:"onConnectionError",args:[]}),this.on("error",e),{off:()=>{this.off("error",e)}}}__emitConnectionError(e){this.emit("error",e)}},x=[],N={convertStorageSchemaToProto2Descriptor:(e,t)=>(A.push({method:"adapt.convertStorageSchemaToProto2Descriptor",args:[e,t]}),{name:"root",field:[]})},R=class{constructor(e){A.push({method:"WriterClient.ctor",args:[e]})}async createStreamConnection(e,t){if("DEFAULT"!==e.streamId)throw new Error(`mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(e)}`);A.push({method:"createStreamConnection",args:[e,t]});const r=T;if(null!==r)throw T=null,r;const s=new I(`${e.destinationTable}/streams/_default`);return x.push(s),s}async getWriteStream(e,t){return A.push({method:"getWriteStream",args:[e,t]}),{tableSchema:{fields:[]}}}close(){A.push({method:"WriterClient.close",args:[]})}},M=class{constructor(e){A.push({method:"JSONWriter.ctor",args:[e]})}appendRows(e,t){A.push({method:"appendRows",args:[e,t]});const r=C;if(null!==r)throw C=null,r;const s=E;E=null;const o=D;return D=null,{getResult:async()=>{if(null!==o)throw o;return{appendResult:{offset:{value:"0"}},rowErrors:s??[],writeStream:"projects/p/datasets/d/tables/t/streams/_default"}}}}close(){A.push({method:"JSONWriter.close",args:[]})}};var q={get BigQuery(){return class{calls;options;constructor(e){this.options=e,this.calls=[]}dataset(e){return this.calls.push({method:"dataset",args:[e]}),this}table(e){return this.calls.push({method:"table",args:[e]}),this}async exists(){return this.calls.push({method:"exists",args:[]}),[!0]}async create(e){this.calls.push({method:"create",args:[e]})}async getMetadata(){return this.calls.push({method:"getMetadata",args:[]}),[{}]}}},get WriterClient(){return R},get JSONWriter(){return M},get adapt(){return N}},J=["call:JSONWriter.appendRows"],B={};i(B,{pageView:()=>U,purchase:()=>G});var _=require("@walkeros/core");function Q(e){return null==e?null:"object"==typeof e?Array.isArray(e)&&0===e.length?null:Array.isArray(e)||0!==Object.keys(e).length?JSON.stringify(e):null:JSON.stringify(e)}function W(e){return function(e){return{name:e.name,data:Q(e.data),context:Q(e.context),globals:Q(e.globals),custom:Q(e.custom),user:Q(e.user),nested:Q(e.nested),consent:Q(e.consent),id:e.id,trigger:e.trigger,entity:e.entity,action:e.action,timestamp:1e3*new Date(e.timestamp).getTime(),timing:e.timing,source:Q(e.source)}}(e)}var K=(0,_.getEvent)("page view",{timestamp:1700001100,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server"}}),U={title:"Page view",description:"A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.",in:K,mapping:void 0,out:[["appendRows",[W(K)]]]},F=(0,_.getEvent)("order complete",{timestamp:1700001101,data:{id:"ORD-500",total:199.99,items:[{sku:"SKU-1",qty:2}]},source:{type:"express",platform:"server"}}),G={title:"Purchase",description:"An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().",in:F,mapping:void 0,out:[["appendRows",[W(F)]]]},L={};i(L,{env:()=>V,step:()=>Y});var V={};i(V,{push:()=>X,simulation:()=>H});var $=class{constructor(e){this.name=e}name;publishMessage(e){return Promise.resolve("mock-message-id")}resumePublishing(e){}},X={PubSub:class{constructor(e){this.options=e}options;topic(e){return new $(e)}close(){return Promise.resolve()}}},H=["call:PubSub.topic.publishMessage"],Y={};i(Y,{defaultPush:()=>se,mappedAttributes:()=>ae,mappedData:()=>ne,mappedOrderingKey:()=>ie,mappedTopic:()=>oe,pageView:()=>le});var Z=require("@walkeros/core"),ee=(0,Z.getEvent)("order complete",{timestamp:1700001100,data:{id:"ORD-500",total:199.99,currency:"EUR"},user:{id:"usr-789"},source:{type:"express",platform:"server",trace:"1a2b3c4d5e6f70819a2b3c4d5e6f7081",count:1}}),te=(0,Z.getEvent)("page view",{timestamp:1700001101,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server",trace:"9f8e7d6c5b4a39281706f5e4d3c2b1a0",count:1}});function re(e){const t=e.source.platform??"default",r={...e,source:{...e.source,release:{[t]:"4.7.0-next-1790722899482"}}};return Buffer.from(JSON.stringify(r))}var se={title:"Default publish",description:"An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.",in:ee,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:re(ee)}]]},oe={title:"Topic override",description:"A mapping rule overrides the destination default topic so order events are published to a dedicated topic.",in:ee,mapping:{settings:{topic:"orders"}},out:[["topic","orders",{messageOrdering:!1}],["publishMessage","orders",{data:re(ee)}]]},ie={title:"Ordering key from user",description:"A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.",in:ee,mapping:{settings:{orderingKey:"user.id"}},out:[["topic","events",{messageOrdering:!0}],["publishMessage","events",{data:re(ee),orderingKey:"usr-789"}]]},ae={title:"Mapped attributes",description:"A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.",in:ee,mapping:{settings:{attributes:{entity:"entity",action:"action"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:re(ee),attributes:{entity:"order",action:"complete"}}]]},ne={title:"Mapped payload",description:"A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.",in:ee,mapping:{data:{map:{order_id:"data.id",revenue:"data.total",currency:"data.currency"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Buffer.from(JSON.stringify({order_id:"ORD-500",revenue:199.99,currency:"EUR"}))}]]},le={title:"Page view",description:"A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.",in:te,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:re(te)}]]},ce={"auth-methods":{text:'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: "./sa.json" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',code:[{lang:"json",code:'{ "settings": { "projectId": "my-project", "bigquery": { "keyFilename": "./sa.json" } } }'},{lang:"json",code:'{ "settings": { "projectId": "my-project" } }'}]},"storage-format":{text:'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset "walkeros", table "events", location "EU" — all overridable via settings.'},"query-json-columns":{text:"Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.",code:[{lang:"sql",code:"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'"}]},"troubleshoot-empty-table":{text:"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK."}},ue={destinationBigQuery:O,destinationPubSub:L};//# sourceMappingURL=dev.js.map
1
+ "use strict";var e,t=Object.defineProperty,r=Object.getOwnPropertyDescriptor,s=Object.getOwnPropertyNames,i=Object.prototype.hasOwnProperty,o=(e,r)=>{for(var s in r)t(e,s,{get:r[s],enumerable:!0})},a={};o(a,{examples:()=>n,exportExamples:()=>ue,exportSchemas:()=>pe,hints:()=>ce,pubsubExamples:()=>D,schemas:()=>le}),module.exports=(e=a,((e,o,a,n)=>{if(o&&"object"==typeof o||"function"==typeof o)for(let l of s(o))i.call(e,l)||l===a||t(e,l,{get:()=>o[l],enumerable:!(n=r(o,l))||n.enumerable});return e})(t({},"__esModule",{value:!0}),e));var n={};o(n,{env:()=>l,step:()=>k});var l={};o(l,{push:()=>S,simulation:()=>w});var c=require("events"),u=[],p=null,d=null,g=null,m=null,b=class extends c.EventEmitter{streamId;constructor(e){super(),this.streamId=e}getStreamId(){return this.streamId}onConnectionError(e){return u.push({method:"onConnectionError",args:[]}),this.on("error",e),{off:()=>{this.off("error",e)}}}__emitConnectionError(e){this.emit("error",e)}},h=[],y={convertStorageSchemaToProto2Descriptor:(e,t)=>(u.push({method:"adapt.convertStorageSchemaToProto2Descriptor",args:[e,t]}),{name:"root",field:[]})},v=class{constructor(e){u.push({method:"WriterClient.ctor",args:[e]})}async createStreamConnection(e,t){if("DEFAULT"!==e.streamId)throw new Error(`mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(e)}`);u.push({method:"createStreamConnection",args:[e,t]});const r=m;if(null!==r)throw m=null,r;const s=new b(`${e.destinationTable}/streams/_default`);return h.push(s),s}async getWriteStream(e,t){return u.push({method:"getWriteStream",args:[e,t]}),{tableSchema:{fields:[]}}}close(){u.push({method:"WriterClient.close",args:[]})}},f=class{constructor(e){u.push({method:"JSONWriter.ctor",args:[e]})}appendRows(e,t){u.push({method:"appendRows",args:[e,t]});const r=d;if(null!==r)throw d=null,r;const s=p;p=null;const i=g;return g=null,{getResult:async()=>{if(null!==i)throw i;return{appendResult:{offset:{value:"0"}},rowErrors:s??[],writeStream:"projects/p/datasets/d/tables/t/streams/_default"}}}}close(){u.push({method:"JSONWriter.close",args:[]})}};var S={get BigQuery(){return class{calls;options;constructor(e){this.options=e,this.calls=[]}dataset(e){return this.calls.push({method:"dataset",args:[e]}),this}table(e){return this.calls.push({method:"table",args:[e]}),this}async exists(){return this.calls.push({method:"exists",args:[]}),[!0]}async create(e){this.calls.push({method:"create",args:[e]})}async getMetadata(){return this.calls.push({method:"getMetadata",args:[]}),[{}]}}},get WriterClient(){return v},get JSONWriter(){return f},get adapt(){return y}},w=["call:JSONWriter.appendRows"],k={};o(k,{pageView:()=>A,purchase:()=>C});var j=require("@walkeros/core");function O(e){return null==e?null:"object"==typeof e?Array.isArray(e)&&0===e.length?null:Array.isArray(e)||0!==Object.keys(e).length?JSON.stringify(e):null:JSON.stringify(e)}function z(e){return function(e){return{name:e.name,data:O(e.data),context:O(e.context),globals:O(e.globals),custom:O(e.custom),user:O(e.user),nested:O(e.nested),consent:O(e.consent),id:e.id,trigger:e.trigger,entity:e.entity,action:e.action,timestamp:1e3*new Date(e.timestamp).getTime(),timing:e.timing,source:O(e.source)}}(e)}var P=(0,j.getEvent)("page view",{timestamp:1700001100,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server"}}),A={title:"Page view",description:"A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.",in:P,mapping:void 0,out:[["appendRows",[z(P)]]]},E=(0,j.getEvent)("order complete",{timestamp:1700001101,data:{id:"ORD-500",total:199.99,items:[{sku:"SKU-1",qty:2}]},source:{type:"express",platform:"server"}}),C={title:"Purchase",description:"An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().",in:E,mapping:void 0,out:[["appendRows",[z(E)]]]},D={};o(D,{env:()=>T,step:()=>R});var T={};o(T,{push:()=>x,simulation:()=>N});var I=class{constructor(e){this.name=e}name;publishMessage(e){return Promise.resolve("mock-message-id")}resumePublishing(e){}},x={PubSub:class{constructor(e){this.options=e}options;topic(e){return new I(e)}close(){return Promise.resolve()}}},N=["call:PubSub.topic.publishMessage"],R={};o(R,{defaultPush:()=>_,mappedAttributes:()=>K,mappedData:()=>U,mappedOrderingKey:()=>W,mappedTopic:()=>Q,pageView:()=>F});var M=require("@walkeros/core"),q=(0,M.getEvent)("order complete",{timestamp:1700001100,data:{id:"ORD-500",total:199.99,currency:"EUR"},user:{id:"usr-789"},source:{type:"express",platform:"server",trace:"1a2b3c4d5e6f70819a2b3c4d5e6f7081",count:1}}),J=(0,M.getEvent)("page view",{timestamp:1700001101,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server",trace:"9f8e7d6c5b4a39281706f5e4d3c2b1a0",count:1}});function B(e){const t=e.source.platform??"default",r={...e,source:{...e.source,release:{[t]:"4.7.0"}}};return Buffer.from(JSON.stringify(r))}var _={title:"Default publish",description:"An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.",in:q,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:B(q)}]]},Q={title:"Topic override",description:"A mapping rule overrides the destination default topic so order events are published to a dedicated topic.",in:q,mapping:{settings:{topic:"orders"}},out:[["topic","orders",{messageOrdering:!1}],["publishMessage","orders",{data:B(q)}]]},W={title:"Ordering key from user",description:"A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.",in:q,mapping:{settings:{orderingKey:"user.id"}},out:[["topic","events",{messageOrdering:!0}],["publishMessage","events",{data:B(q),orderingKey:"usr-789"}]]},K={title:"Mapped attributes",description:"A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.",in:q,mapping:{settings:{attributes:{entity:"entity",action:"action"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:B(q),attributes:{entity:"order",action:"complete"}}]]},U={title:"Mapped payload",description:"A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.",in:q,mapping:{data:{map:{order_id:"data.id",revenue:"data.total",currency:"data.currency"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Buffer.from(JSON.stringify({order_id:"ORD-500",revenue:199.99,currency:"EUR"}))}]]},F={title:"Page view",description:"A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.",in:J,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:B(J)}]]},G=require("@walkeros/core/dev"),L=require("@walkeros/core/dev"),V=L.z.object({client:L.z.any().describe("Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))").optional(),projectId:L.z.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),datasetId:L.z.string().min(1).default("walkerOS").describe("BigQuery dataset ID where events will be stored (like walker_events)"),tableId:L.z.string().min(1).default("events").describe("BigQuery table ID for event storage (like events)"),location:L.z.string().default("EU").describe("Geographic location for the BigQuery dataset (like US)"),bigquery:L.z.any().describe('Additional BigQuery client configuration options (like { keyFilename: "path/to/key.json" })').optional()}),$=require("@walkeros/core/dev").z.object({}),X=(0,G.zodToSchema)(V),H=(0,G.zodToSchema)($),Y=require("@walkeros/core/dev"),Z=require("@walkeros/core/dev"),ee=Z.z.object({client:Z.z.any().describe("Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))").optional(),projectId:Z.z.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),topic:Z.z.string().min(1).describe("Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK."),credentials:Z.z.any().describe("Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)").optional(),apiEndpoint:Z.z.string().describe("Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).").optional(),orderingKey:Z.z.any().describe("Mapping value resolved per-event. Truthy enables per-key ordering for the publish.").optional(),attributes:Z.z.any().describe("Default per-event attribute map merged into every published message. Mapping.Map shape.").optional()}),te=require("@walkeros/core/dev"),re=te.z.object({topic:te.z.string().describe("Per-rule topic override. Falls back to settings.topic if absent.").optional(),orderingKey:te.z.any().describe("Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.").optional(),attributes:te.z.any().describe("Per-rule attribute Mapping.Map merged on top of settings.attributes.").optional()}),se=require("@walkeros/core/dev"),ie=se.z.object({messageStoragePolicy:se.z.object({allowedPersistenceRegions:se.z.array(se.z.string()).describe("Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).")}).describe("Topic-level message storage policy.").optional(),messageRetentionDuration:se.z.object({seconds:se.z.number().describe("Retention window in seconds. Default: project default.")}).describe("Topic-level retention configuration.").optional(),kmsKeyName:se.z.string().describe("Customer-managed encryption key (CMEK) resource name. Optional.").optional(),labels:se.z.record(se.z.string(),se.z.string()).describe("Topic labels for organization and billing.").optional()}),oe=(0,Y.zodToSchema)(ee),ae=(0,Y.zodToSchema)(re),ne=(0,Y.zodToSchema)(ie),le={};o(le,{mapping:()=>H,pubsubMapping:()=>ae,pubsubSettings:()=>oe,pubsubSetup:()=>ne,settings:()=>X});var ce={"auth-methods":{text:'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: "./sa.json" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',code:[{lang:"json",code:'{ "settings": { "projectId": "my-project", "bigquery": { "keyFilename": "./sa.json" } } }'},{lang:"json",code:'{ "settings": { "projectId": "my-project" } }'}]},"storage-format":{text:'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset "walkeros", table "events", location "EU" — all overridable via settings.'},"query-json-columns":{text:"Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.",code:[{lang:"sql",code:"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'"}]},"troubleshoot-empty-table":{text:"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK."}},ue={destinationBigQuery:n,destinationPubSub:D},pe={destinationBigQuery:{settings:X,mapping:H},destinationPubSub:{settings:oe,mapping:ae,setup:ne}};//# sourceMappingURL=dev.js.map
package/dist/dev.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/dev.ts","../src/schemas.ts","../src/bigquery/schemas/index.ts","../src/bigquery/schemas/settings.ts","../src/bigquery/schemas/mapping.ts","../src/pubsub/schemas/index.ts","../src/pubsub/schemas/settings.ts","../src/pubsub/schemas/mapping.ts","../src/pubsub/schemas/setup.ts","../src/bigquery/examples/index.ts","../src/bigquery/examples/env.ts","../src/bigquery/__mocks__/@google-cloud/bigquery-storage.ts","../src/bigquery/examples/step.ts","../src/bigquery/eventToRow.ts","../src/pubsub/examples/index.ts","../src/pubsub/examples/env.ts","../src/pubsub/examples/step.ts","../src/hints.ts"],"sourcesContent":["export * as schemas from './schemas';\nexport * as examples from './bigquery/examples';\nexport * as pubsubExamples from './pubsub/examples';\nexport { hints } from './hints';\n\nimport * as bigqueryExamplesNs from './bigquery/examples';\nimport * as pubsubExamplesNs from './pubsub/examples';\n\n/** Dev examples per export, keyed by the export names in package.json. */\nexport const exportExamples = {\n destinationBigQuery: bigqueryExamplesNs,\n destinationPubSub: pubsubExamplesNs,\n};\n","// Browser-safe schema-only exports\n// This file exports ONLY schemas without any Node.js dependencies\nexport { settings, mapping } from './bigquery/schemas';\nexport {\n settings as pubsubSettings,\n mapping as pubsubMapping,\n setup as pubsubSetup,\n} from './pubsub/schemas';\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z.object({\n client: z\n .any()\n .describe(\n 'Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))',\n )\n .optional(),\n projectId: z\n .string()\n .min(1)\n .describe('Google Cloud Project ID (like my-gcp-project)'),\n datasetId: z\n .string()\n .min(1)\n .default('walkerOS')\n .describe(\n 'BigQuery dataset ID where events will be stored (like walker_events)',\n ),\n tableId: z\n .string()\n .min(1)\n .default('events')\n .describe('BigQuery table ID for event storage (like events)'),\n location: z\n .string()\n .default('EU')\n .describe('Geographic location for the BigQuery dataset (like US)'),\n bigquery: z\n .any()\n .describe(\n 'Additional BigQuery client configuration options (like { keyFilename: \"path/to/key.json\" })',\n )\n .optional(),\n});\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP BigQuery Mapping Schema\n * BigQuery has no event-level mapping configuration\n */\nexport const MappingSchema = z.object({});\n\n/**\n * Type inference from MappingSchema\n */\nexport type Mapping = z.infer<typeof MappingSchema>;\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\nimport { SetupSchema } from './setup';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\nexport { SetupSchema, type Setup } from './setup';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\nexport const setup = zodToSchema(SetupSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z.object({\n client: z\n .any()\n .describe(\n 'Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))',\n )\n .optional(),\n projectId: z\n .string()\n .min(1)\n .describe('Google Cloud Project ID (like my-gcp-project)'),\n topic: z\n .string()\n .min(1)\n .describe(\n 'Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK.',\n ),\n credentials: z\n .any()\n .describe(\n 'Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)',\n )\n .optional(),\n apiEndpoint: z\n .string()\n .describe(\n 'Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).',\n )\n .optional(),\n orderingKey: z\n .any()\n .describe(\n 'Mapping value resolved per-event. Truthy enables per-key ordering for the publish.',\n )\n .optional(),\n attributes: z\n .any()\n .describe(\n 'Default per-event attribute map merged into every published message. Mapping.Map shape.',\n )\n .optional(),\n});\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP Pub/Sub Mapping Schema\n *\n * Per-rule overrides for topic, orderingKey, and attributes.\n */\nexport const MappingSchema = z.object({\n topic: z\n .string()\n .describe(\n 'Per-rule topic override. Falls back to settings.topic if absent.',\n )\n .optional(),\n orderingKey: z\n .any()\n .describe(\n 'Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.',\n )\n .optional(),\n attributes: z\n .any()\n .describe(\n 'Per-rule attribute Mapping.Map merged on top of settings.attributes.',\n )\n .optional(),\n});\n\n/**\n * Type inference from MappingSchema\n */\nexport type Mapping = z.infer<typeof MappingSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP Pub/Sub Setup Schema\n *\n * Provisioning options for `walkeros setup destination.<id>`. Idempotent topic\n * creation. Subscription provisioning is owned by the source side.\n */\nexport const SetupSchema = z.object({\n messageStoragePolicy: z\n .object({\n allowedPersistenceRegions: z\n .array(z.string())\n .describe(\n 'Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).',\n ),\n })\n .describe('Topic-level message storage policy.')\n .optional(),\n messageRetentionDuration: z\n .object({\n seconds: z\n .number()\n .describe('Retention window in seconds. Default: project default.'),\n })\n .describe('Topic-level retention configuration.')\n .optional(),\n kmsKeyName: z\n .string()\n .describe('Customer-managed encryption key (CMEK) resource name. Optional.')\n .optional(),\n labels: z\n .record(z.string(), z.string())\n .describe('Topic labels for organization and billing.')\n .optional(),\n});\n\nexport type Setup = z.infer<typeof SetupSchema>;\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, QueryClient, TableMetadataShape } from '../types';\nimport {\n managedwriter as mockManagedwriter,\n adapt as mockAdapt,\n} from '../__mocks__/@google-cloud/bigquery-storage';\n\n/**\n * Example environment configurations for GCP BigQuery destination\n *\n * These environments provide standardized mock structures for testing\n * and development without requiring actual BigQuery SDK dependencies.\n *\n * The Storage Write API mocks (WriterClient, JSONWriter, adapt) are\n * re-exported from the package-local __mocks__ folder so example/test\n * code shares a single source of truth with the jest auto-mock.\n */\n\n/**\n * Mock BigQuery query client: dataset and table provisioning calls resolve as\n * if both already exist.\n */\nfunction createMockBigQuery() {\n return class MockBigQuery implements QueryClient {\n calls: Array<{ method: string; args: unknown[] }>;\n options: unknown;\n\n constructor(options?: unknown) {\n this.options = options;\n this.calls = [];\n }\n\n dataset(datasetId: string) {\n this.calls.push({ method: 'dataset', args: [datasetId] });\n return this;\n }\n\n table(tableId: string) {\n this.calls.push({ method: 'table', args: [tableId] });\n return this;\n }\n\n async exists(): Promise<[boolean]> {\n this.calls.push({ method: 'exists', args: [] });\n return [true];\n }\n\n async create(options: unknown): Promise<void> {\n this.calls.push({ method: 'create', args: [options] });\n }\n\n async getMetadata(): Promise<[TableMetadataShape]> {\n this.calls.push({ method: 'getMetadata', args: [] });\n return [{}];\n }\n };\n}\n\n/**\n * Standard mock environment for push operations\n *\n * Use this for testing BigQuery Storage Write appends without connecting\n * to actual GCP infrastructure.\n */\nexport const push: Env = {\n get BigQuery() {\n return createMockBigQuery();\n },\n get WriterClient() {\n return mockManagedwriter.WriterClient;\n },\n get JSONWriter() {\n return mockManagedwriter.JSONWriter;\n },\n get adapt() {\n return mockAdapt;\n },\n};\n\n/**\n * Every row goes through the writer's `appendRows`; the writer is built from\n * `JSONWriter` in init, so the path continues on the constructed instance.\n * Constructors are not recorded: their arguments carry credentials.\n */\nexport const simulation = ['call:JSONWriter.appendRows'];\n","import { EventEmitter } from 'events';\n\nconst calls: Array<{ method: string; args: unknown[] }> = [];\n\ninterface MockRowError {\n index: number;\n code: number;\n message: string;\n}\n\nlet nextAppendRowErrors: MockRowError[] | null = null;\nlet nextAppendThrow: unknown = null;\nlet nextGetResultReject: unknown = null;\nlet nextCreateStreamConnectionError: unknown = null;\n\n/**\n * Honest stand-in for the SDK's StreamConnection: a REAL Node EventEmitter so\n * `emit('error', …)` with no listener throws exactly like the real one (Node's\n * special-cased `'error'` event). `onConnectionError` mirrors the SDK surface:\n * it registers an `'error'` listener and returns an `{ off }` disposable.\n */\nclass MockStreamConnection extends EventEmitter {\n private readonly streamId: string;\n constructor(streamId: string) {\n super();\n this.streamId = streamId;\n }\n getStreamId(): string {\n return this.streamId;\n }\n onConnectionError(listener: (err: unknown) => void): { off: () => void } {\n calls.push({ method: 'onConnectionError', args: [] });\n this.on('error', listener);\n return {\n off: () => {\n this.off('error', listener);\n },\n };\n }\n /**\n * Test-only: literally `this.emit('error', err)` with NO internal\n * listener-count guard, so before a listener is attached this reproduces\n * Node's real \"throw if no 'error' listener\" behavior. A fake that silently\n * swallowed would mask the very crash this listener exists to contain.\n */\n __emitConnectionError(err: unknown): void {\n this.emit('error', err);\n }\n}\n\n// The most recently created connection, so tests can emit on it and assert the\n// listener was registered.\nlet lastConnection: MockStreamConnection | null = null;\n\n// Every connection ever created (this reset cycle), so tests can assert that a\n// concurrent re-open did not orphan a connection still carrying an 'error'\n// listener.\nconst allConnections: MockStreamConnection[] = [];\n\nclass MockJSONWriter {\n constructor(_args: { connection: unknown; protoDescriptor: unknown }) {\n calls.push({ method: 'JSONWriter.ctor', args: [_args] });\n }\n appendRows(rows: unknown[], offsetValue?: unknown) {\n calls.push({ method: 'appendRows', args: [rows, offsetValue] });\n const queuedThrow = nextAppendThrow;\n if (queuedThrow !== null) {\n nextAppendThrow = null;\n throw queuedThrow;\n }\n const queuedErrors = nextAppendRowErrors;\n nextAppendRowErrors = null;\n const queuedReject = nextGetResultReject;\n nextGetResultReject = null;\n return {\n getResult: async () => {\n // Models a gRPC deadline-exceeded (or any stream error): the append is\n // accepted but getResult() rejects when the stream's deadline fires.\n if (queuedReject !== null) throw queuedReject;\n return {\n appendResult: { offset: { value: '0' } },\n rowErrors: queuedErrors ?? [],\n writeStream: 'projects/p/datasets/d/tables/t/streams/_default',\n };\n },\n };\n }\n close(): void {\n calls.push({ method: 'JSONWriter.close', args: [] });\n }\n}\n\nclass MockWriterClient {\n constructor(args: {\n projectId?: string;\n keyFilename?: string;\n credentials?: unknown;\n scopes?: string | string[];\n }) {\n calls.push({ method: 'WriterClient.ctor', args: [args] });\n }\n async createStreamConnection(\n args: {\n destinationTable: string;\n streamId: string;\n },\n options?: unknown,\n ) {\n // Match the real SDK: callers must pass streamId=DefaultStream (not streamType)\n // for default-stream use. Passing streamType triggers a CreateWriteStream\n // call with type='DEFAULT', which BQ rejects as TYPE_UNSPECIFIED.\n if (args.streamId !== 'DEFAULT') {\n throw new Error(\n `mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(args)}`,\n );\n }\n // args[1] captures the gax CallOptions (e.g. { timeout }) so tests can\n // assert the request deadline is forwarded to the appendRows stream.\n calls.push({ method: 'createStreamConnection', args: [args, options] });\n const queuedError = nextCreateStreamConnectionError;\n if (queuedError !== null) {\n nextCreateStreamConnectionError = null;\n throw queuedError;\n }\n const connection = new MockStreamConnection(\n `${args.destinationTable}/streams/_default`,\n );\n lastConnection = connection;\n allConnections.push(connection);\n return connection;\n }\n async getWriteStream(\n args: { streamId: string; view?: number },\n options?: unknown,\n ) {\n // args[1] captures the gax CallOptions so tests can assert the deadline\n // is forwarded to the unary schema fetch.\n calls.push({ method: 'getWriteStream', args: [args, options] });\n // Minimal tableSchema shape consumed by adapt.convertStorageSchemaToProto2Descriptor\n return {\n tableSchema: { fields: [] },\n };\n }\n close(): void {\n calls.push({ method: 'WriterClient.close', args: [] });\n }\n}\n\nconst adapt = {\n convertStorageSchemaToProto2Descriptor: (_schema: unknown, _root: string) => {\n calls.push({\n method: 'adapt.convertStorageSchemaToProto2Descriptor',\n args: [_schema, _root],\n });\n return { name: 'root', field: [] };\n },\n};\n\nconst managedwriter = {\n WriterClient: MockWriterClient,\n JSONWriter: MockJSONWriter,\n DefaultStream: 'DEFAULT',\n};\n\nconst protos = {\n google: {\n cloud: {\n bigquery: {\n storage: {\n v1: {\n WriteStreamView: {\n WRITE_STREAM_VIEW_UNSPECIFIED: 0,\n BASIC: 1,\n FULL: 2,\n },\n },\n },\n },\n },\n },\n};\n\n// Test-only helper. Not part of the real SDK.\nfunction __getMockCalls() {\n return calls;\n}\n\nfunction __resetMockCalls() {\n calls.length = 0;\n nextAppendRowErrors = null;\n nextAppendThrow = null;\n nextGetResultReject = null;\n nextCreateStreamConnectionError = null;\n lastConnection = null;\n allConnections.length = 0;\n}\n\n/**\n * Test-only: the most recently created StreamConnection, so a test can emit an\n * out-of-band `'error'` on it (via `__emitConnectionError`) and assert the\n * destination attached a listener.\n */\nfunction __getLastConnection(): MockStreamConnection {\n if (!lastConnection) throw new Error('mock: no StreamConnection created yet');\n return lastConnection;\n}\n\n/**\n * Test-only: every StreamConnection created since the last reset, so a test can\n * assert that a concurrent re-open did not orphan a connection that still\n * carries an 'error' listener (a leak).\n */\nfunction __getAllConnections(): MockStreamConnection[] {\n return allConnections.slice();\n}\n\n/**\n * Test-only: queue rowErrors for the next appendRows().getResult() call.\n * Auto-resets after one use.\n */\nfunction __setNextAppendRowErrors(errors: MockRowError[]): void {\n nextAppendRowErrors = errors;\n}\n\n/**\n * Test-only: make the next appendRows() throw synchronously, simulating a\n * Storage Write API call failure. Auto-resets after one use.\n */\nfunction __setNextAppendThrow(err: unknown): void {\n nextAppendThrow = err;\n}\n\n/**\n * Test-only: make the next appendRows().getResult() reject, simulating a gRPC\n * deadline-exceeded (or any stream error) surfacing through the pending write.\n * Auto-resets after one use.\n */\nfunction __setNextGetResultReject(err: unknown): void {\n nextGetResultReject = err;\n}\n\n/**\n * Test-only: queue an error for the next createStreamConnection() call so\n * tests can simulate openWriter failures (NotFound, INVALID_ARGUMENT, etc.).\n * Auto-resets after one use.\n */\nfunction __setNextOpenWriterError(err: unknown): void {\n nextCreateStreamConnectionError = err;\n}\n\nexport {\n managedwriter,\n adapt,\n protos,\n MockStreamConnection,\n __getMockCalls,\n __resetMockCalls,\n __getLastConnection,\n __getAllConnections,\n __setNextAppendRowErrors,\n __setNextAppendThrow,\n __setNextGetResultReject,\n __setNextOpenWriterError,\n};\n","import type { Flow, WalkerOS } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport { eventToRow } from '../eventToRow';\n\n/**\n * Mirror of push.ts via eventToRow() -- produces a flat 15-column row\n * with nested object/array values JSON-stringified. Imported directly\n * from the runtime helper so the step examples stay in sync with what\n * push.ts actually emits to JSONWriter.appendRows.\n */\nfunction expectedRow(event: WalkerOS.Event) {\n return eventToRow(event);\n}\n\n/**\n * Page view -- one row appended through JSONWriter.appendRows([row]).\n * Captured as a single intent-level call: ['appendRows', [row]].\n */\nconst pageViewEvent = getEvent('page view', {\n timestamp: 1700001100,\n data: { title: 'Documentation', url: 'https://example.com/docs' },\n source: { type: 'express', platform: 'server' },\n});\n\nexport const pageView: Flow.StepExample = {\n title: 'Page view',\n description:\n 'A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.',\n in: pageViewEvent,\n mapping: undefined,\n out: [['appendRows', [expectedRow(pageViewEvent)]]],\n};\n\n/**\n * Purchase -- nested array in data.items is JSON.stringified into the\n * data column of the appended row.\n */\nconst purchaseEvent = getEvent('order complete', {\n timestamp: 1700001101,\n data: {\n id: 'ORD-500',\n total: 199.99,\n items: [{ sku: 'SKU-1', qty: 2 }],\n },\n source: { type: 'express', platform: 'server' },\n});\n\nexport const purchase: Flow.StepExample = {\n title: 'Purchase',\n description:\n 'An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().',\n in: purchaseEvent,\n mapping: undefined,\n out: [['appendRows', [expectedRow(purchaseEvent)]]],\n};\n","import type { WalkerOS } from '@walkeros/core';\n\n/** Row shape passed to JSONWriter.appendRows. Values are JSON-serializable scalars or strings. */\nexport interface BigQueryRow {\n [key: string]: string | number | null;\n name: string;\n data: string | null;\n context: string | null;\n globals: string | null;\n custom: string | null;\n user: string | null;\n nested: string | null;\n consent: string | null;\n id: string;\n trigger: string;\n entity: string;\n action: string;\n timestamp: number;\n timing: number;\n source: string | null;\n}\n\nfunction jsonOrNull(value: unknown): string | null {\n if (value === undefined || value === null) return null;\n if (typeof value === 'object') {\n if (Array.isArray(value) && value.length === 0) return null;\n if (!Array.isArray(value) && Object.keys(value).length === 0) return null;\n return JSON.stringify(value);\n }\n return JSON.stringify(value);\n}\n\n/** Convert a walkerOS Event v4 into a 15-column BigQuery row in canonical order.\n *\n * Note: BQ Storage Write API encodes TIMESTAMP fields as INT64 microseconds\n * since epoch (the SDK calls Long.fromString on the value). ISO strings fail\n * with \"interior hyphen\" because Long.fromString sees the date hyphens as\n * non-numeric. Pass microseconds directly.\n */\nexport function eventToRow(event: WalkerOS.Event): BigQueryRow {\n return {\n name: event.name,\n data: jsonOrNull(event.data),\n context: jsonOrNull(event.context),\n globals: jsonOrNull(event.globals),\n custom: jsonOrNull(event.custom),\n user: jsonOrNull(event.user),\n nested: jsonOrNull(event.nested),\n consent: jsonOrNull(event.consent),\n id: event.id,\n trigger: event.trigger,\n entity: event.entity,\n action: event.action,\n timestamp: new Date(event.timestamp).getTime() * 1000, // microseconds since epoch\n timing: event.timing,\n source: jsonOrNull(event.source),\n };\n}\n","export * as env from './env';\nexport * as step from './step';\n","import type {\n Env,\n PubSubPublisher,\n PublishMessage,\n TopicPublisher,\n} from '../types';\n\n/**\n * Example environment for the GCP Pub/Sub destination.\n *\n * `push` is the mock env simulate injects: `PubSub` builds a client whose\n * topics answer `publishMessage` locally, so nothing reaches GCP. Unit tests\n * still substitute the SDK module-wide via `jest.mock('@google-cloud/pubsub')`.\n */\n\nclass MockTopic implements TopicPublisher {\n constructor(public name: string) {}\n publishMessage(_message: PublishMessage): Promise<string> {\n return Promise.resolve('mock-message-id');\n }\n resumePublishing(_orderingKey: string): void {}\n}\n\nclass MockPubSub implements PubSubPublisher {\n constructor(public options?: object) {}\n topic(name: string): TopicPublisher {\n return new MockTopic(name);\n }\n close(): Promise<void> {\n return Promise.resolve();\n }\n}\n\nexport const push: Env = {\n PubSub: MockPubSub,\n};\n\n/** The publish carries the request; `args[0]` is the message. */\nexport const simulation = ['call:PubSub.topic.publishMessage'];\n","import type { Flow, WalkerOS } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\n\n// Build-time version define. The upstream collector stamps source.release with\n// this on push, so the expected payload must mirror it rather than a literal,\n// else it breaks whenever the fixed version group is bumped (release).\ndeclare const __VERSION__: string;\n\n/**\n * Pub/Sub step examples. Each example's `out` is the array of recorded mock\n * calls produced by `push()`. The recording shape is:\n * ['topic', topicName, topicOptions] // implicit topic-handle creation\n * ['publishMessage', topicName, messageOptions]\n * ['resumePublishing', topicName, orderingKey] // only on publish failure\n */\n\n// Events reaching a server destination arrive already enriched by the upstream\n// collector, so they carry the run trace and per-run count. The collector\n// preserves these (stamp-if-absent), keeping the example deterministic.\nconst orderEvent = getEvent('order complete', {\n timestamp: 1700001100,\n data: { id: 'ORD-500', total: 199.99, currency: 'EUR' },\n user: { id: 'usr-789' },\n source: {\n type: 'express',\n platform: 'server',\n trace: '1a2b3c4d5e6f70819a2b3c4d5e6f7081',\n count: 1,\n },\n});\n\nconst pageEvent = getEvent('page view', {\n timestamp: 1700001101,\n data: { title: 'Documentation', url: 'https://example.com/docs' },\n source: {\n type: 'express',\n platform: 'server',\n trace: '9f8e7d6c5b4a39281706f5e4d3c2b1a0',\n count: 1,\n },\n});\n\nfunction expectedPayload(event: WalkerOS.Event): Buffer {\n // The harness pushes the event through an unconfigured collector, which stamps\n // source.release = { [name ?? platform ?? 'default']: __VERSION__ }. With no\n // collector name, the key is the event's platform. Mirror that here so the\n // expected message body matches the published (post-collector) event.\n const releaseKey = event.source.platform ?? 'default';\n const stamped = {\n ...event,\n source: { ...event.source, release: { [releaseKey]: __VERSION__ } },\n };\n return Buffer.from(JSON.stringify(stamped));\n}\n\n/**\n * Default publish, no mapping. Settings.topic = 'events'. The destination\n * constructs a topic handle inline with messageOrdering=false (no ordering\n * key resolved) and publishes the full event JSON as the message body.\n */\nexport const defaultPush: Flow.StepExample = {\n title: 'Default publish',\n description:\n 'An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.',\n in: orderEvent,\n out: [\n ['topic', 'events', { messageOrdering: false }],\n ['publishMessage', 'events', { data: expectedPayload(orderEvent) }],\n ],\n};\n\n/**\n * Per-rule topic override. Mapping carries `settings.topic = 'orders'`\n * which routes this rule to a dedicated topic.\n */\nexport const mappedTopic: Flow.StepExample = {\n title: 'Topic override',\n description:\n 'A mapping rule overrides the destination default topic so order events are published to a dedicated topic.',\n in: orderEvent,\n mapping: {\n settings: {\n topic: 'orders',\n },\n },\n out: [\n ['topic', 'orders', { messageOrdering: false }],\n ['publishMessage', 'orders', { data: expectedPayload(orderEvent) }],\n ],\n};\n\n/**\n * Per-rule ordering key resolved from the event. `mapping.orderingKey =\n * 'user.id'` is a Mapping.Value that resolves to the event's user.id. The\n * topic handle is constructed with messageOrdering=true and the publish\n * carries the resolved orderingKey.\n */\nexport const mappedOrderingKey: Flow.StepExample = {\n title: 'Ordering key from user',\n description:\n 'A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.',\n in: orderEvent,\n mapping: {\n settings: {\n orderingKey: 'user.id',\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: true }],\n [\n 'publishMessage',\n 'events',\n {\n data: expectedPayload(orderEvent),\n orderingKey: 'usr-789',\n },\n ],\n ],\n};\n\n/**\n * Per-rule attributes. `mapping.attributes = { entity: 'entity', action:\n * 'action' }` is a Mapping.Map resolved per event. Each value is a path\n * resolved against the event.\n */\nexport const mappedAttributes: Flow.StepExample = {\n title: 'Mapped attributes',\n description:\n 'A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.',\n in: orderEvent,\n mapping: {\n settings: {\n attributes: {\n entity: 'entity',\n action: 'action',\n },\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: false }],\n [\n 'publishMessage',\n 'events',\n {\n data: expectedPayload(orderEvent),\n attributes: { entity: 'order', action: 'complete' },\n },\n ],\n ],\n};\n\n/**\n * Mapped data. `mapping.data` rewrites the publish body. The rewritten\n * object replaces the event as the message data.\n */\nexport const mappedData: Flow.StepExample = {\n title: 'Mapped payload',\n description:\n 'A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.',\n in: orderEvent,\n mapping: {\n data: {\n map: {\n order_id: 'data.id',\n revenue: 'data.total',\n currency: 'data.currency',\n },\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: false }],\n [\n 'publishMessage',\n 'events',\n {\n // Mapped-data publish: the body is the mapping result (no event\n // envelope, so no source.release), emitted verbatim.\n data: Buffer.from(\n JSON.stringify({\n order_id: 'ORD-500',\n revenue: 199.99,\n currency: 'EUR',\n }),\n ),\n },\n ],\n ],\n};\n\n/**\n * Page view, no rule. Verifies free-form publish on a non-ordered topic\n * for an event with no special mapping.\n */\nexport const pageView: Flow.StepExample = {\n title: 'Page view',\n description:\n 'A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.',\n in: pageEvent,\n out: [\n ['topic', 'events', { messageOrdering: false }],\n ['publishMessage', 'events', { data: expectedPayload(pageEvent) }],\n ],\n};\n","import type { Hint } from '@walkeros/core';\n\nexport const hints: Hint.Hints = {\n 'auth-methods': {\n text: 'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: \"./sa.json\" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',\n code: [\n {\n lang: 'json',\n code: '{ \"settings\": { \"projectId\": \"my-project\", \"bigquery\": { \"keyFilename\": \"./sa.json\" } } }',\n },\n {\n lang: 'json',\n code: '{ \"settings\": { \"projectId\": \"my-project\" } }',\n },\n ],\n },\n 'storage-format': {\n text: 'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset \"walkeros\", table \"events\", location \"EU\" — all overridable via settings.',\n },\n 'query-json-columns': {\n text: 'Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.',\n code: [\n {\n lang: 'sql',\n code: \"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'\",\n },\n ],\n },\n 'troubleshoot-empty-table': {\n text: \"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK.\",\n },\n};\n"],"mappings":"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","names":["examples_exports","mapping","settings","import_dev","import_dev","import_dev","import_dev","SettingsSchema","import_dev","MappingSchema","import_dev","settings","SettingsSchema","mapping","MappingSchema","examples_exports","env_exports","step_exports","env_exports","push","simulation","step_exports","pageView","import_core","examples_exports"]}
1
+ {"version":3,"sources":["../src/dev.ts","../src/bigquery/examples/index.ts","../src/bigquery/examples/env.ts","../src/bigquery/__mocks__/@google-cloud/bigquery-storage.ts","../src/bigquery/examples/step.ts","../src/bigquery/eventToRow.ts","../src/pubsub/examples/index.ts","../src/pubsub/examples/env.ts","../src/pubsub/examples/step.ts","../src/bigquery/schemas/index.ts","../src/bigquery/schemas/settings.ts","../src/bigquery/schemas/mapping.ts","../src/pubsub/schemas/index.ts","../src/pubsub/schemas/settings.ts","../src/pubsub/schemas/mapping.ts","../src/pubsub/schemas/setup.ts","../src/schemas.ts","../src/hints.ts"],"sourcesContent":["import * as bigqueryExamplesNs from './bigquery/examples';\nimport * as pubsubExamplesNs from './pubsub/examples';\nimport * as bigquerySchemasNs from './bigquery/schemas';\nimport * as pubsubSchemasNs from './pubsub/schemas';\n\nexport * as schemas from './schemas';\nexport * as examples from './bigquery/examples';\nexport * as pubsubExamples from './pubsub/examples';\nexport { hints } from './hints';\n\n/** Dev examples per export, keyed by the export names in package.json. */\nexport const exportExamples = {\n destinationBigQuery: bigqueryExamplesNs,\n destinationPubSub: pubsubExamplesNs,\n};\n\n/** Schemas per export, keyed by the export names in package.json. */\nexport const exportSchemas = {\n destinationBigQuery: {\n settings: bigquerySchemasNs.settings,\n mapping: bigquerySchemasNs.mapping,\n },\n destinationPubSub: {\n settings: pubsubSchemasNs.settings,\n mapping: pubsubSchemasNs.mapping,\n setup: pubsubSchemasNs.setup,\n },\n};\n","export * as env from './env';\nexport * as step from './step';\n","import type { Env, QueryClient, TableMetadataShape } from '../types';\nimport {\n managedwriter as mockManagedwriter,\n adapt as mockAdapt,\n} from '../__mocks__/@google-cloud/bigquery-storage';\n\n/**\n * Example environment configurations for GCP BigQuery destination\n *\n * These environments provide standardized mock structures for testing\n * and development without requiring actual BigQuery SDK dependencies.\n *\n * The Storage Write API mocks (WriterClient, JSONWriter, adapt) are\n * re-exported from the package-local __mocks__ folder so example/test\n * code shares a single source of truth with the jest auto-mock.\n */\n\n/**\n * Mock BigQuery query client: dataset and table provisioning calls resolve as\n * if both already exist.\n */\nfunction createMockBigQuery() {\n return class MockBigQuery implements QueryClient {\n calls: Array<{ method: string; args: unknown[] }>;\n options: unknown;\n\n constructor(options?: unknown) {\n this.options = options;\n this.calls = [];\n }\n\n dataset(datasetId: string) {\n this.calls.push({ method: 'dataset', args: [datasetId] });\n return this;\n }\n\n table(tableId: string) {\n this.calls.push({ method: 'table', args: [tableId] });\n return this;\n }\n\n async exists(): Promise<[boolean]> {\n this.calls.push({ method: 'exists', args: [] });\n return [true];\n }\n\n async create(options: unknown): Promise<void> {\n this.calls.push({ method: 'create', args: [options] });\n }\n\n async getMetadata(): Promise<[TableMetadataShape]> {\n this.calls.push({ method: 'getMetadata', args: [] });\n return [{}];\n }\n };\n}\n\n/**\n * Standard mock environment for push operations\n *\n * Use this for testing BigQuery Storage Write appends without connecting\n * to actual GCP infrastructure.\n */\nexport const push: Env = {\n get BigQuery() {\n return createMockBigQuery();\n },\n get WriterClient() {\n return mockManagedwriter.WriterClient;\n },\n get JSONWriter() {\n return mockManagedwriter.JSONWriter;\n },\n get adapt() {\n return mockAdapt;\n },\n};\n\n/**\n * Every row goes through the writer's `appendRows`; the writer is built from\n * `JSONWriter` in init, so the path continues on the constructed instance.\n * Constructors are not recorded: their arguments carry credentials.\n */\nexport const simulation = ['call:JSONWriter.appendRows'];\n","import { EventEmitter } from 'events';\n\nconst calls: Array<{ method: string; args: unknown[] }> = [];\n\ninterface MockRowError {\n index: number;\n code: number;\n message: string;\n}\n\nlet nextAppendRowErrors: MockRowError[] | null = null;\nlet nextAppendThrow: unknown = null;\nlet nextGetResultReject: unknown = null;\nlet nextCreateStreamConnectionError: unknown = null;\n\n/**\n * Honest stand-in for the SDK's StreamConnection: a REAL Node EventEmitter so\n * `emit('error', …)` with no listener throws exactly like the real one (Node's\n * special-cased `'error'` event). `onConnectionError` mirrors the SDK surface:\n * it registers an `'error'` listener and returns an `{ off }` disposable.\n */\nclass MockStreamConnection extends EventEmitter {\n private readonly streamId: string;\n constructor(streamId: string) {\n super();\n this.streamId = streamId;\n }\n getStreamId(): string {\n return this.streamId;\n }\n onConnectionError(listener: (err: unknown) => void): { off: () => void } {\n calls.push({ method: 'onConnectionError', args: [] });\n this.on('error', listener);\n return {\n off: () => {\n this.off('error', listener);\n },\n };\n }\n /**\n * Test-only: literally `this.emit('error', err)` with NO internal\n * listener-count guard, so before a listener is attached this reproduces\n * Node's real \"throw if no 'error' listener\" behavior. A fake that silently\n * swallowed would mask the very crash this listener exists to contain.\n */\n __emitConnectionError(err: unknown): void {\n this.emit('error', err);\n }\n}\n\n// The most recently created connection, so tests can emit on it and assert the\n// listener was registered.\nlet lastConnection: MockStreamConnection | null = null;\n\n// Every connection ever created (this reset cycle), so tests can assert that a\n// concurrent re-open did not orphan a connection still carrying an 'error'\n// listener.\nconst allConnections: MockStreamConnection[] = [];\n\nclass MockJSONWriter {\n constructor(_args: { connection: unknown; protoDescriptor: unknown }) {\n calls.push({ method: 'JSONWriter.ctor', args: [_args] });\n }\n appendRows(rows: unknown[], offsetValue?: unknown) {\n calls.push({ method: 'appendRows', args: [rows, offsetValue] });\n const queuedThrow = nextAppendThrow;\n if (queuedThrow !== null) {\n nextAppendThrow = null;\n throw queuedThrow;\n }\n const queuedErrors = nextAppendRowErrors;\n nextAppendRowErrors = null;\n const queuedReject = nextGetResultReject;\n nextGetResultReject = null;\n return {\n getResult: async () => {\n // Models a gRPC deadline-exceeded (or any stream error): the append is\n // accepted but getResult() rejects when the stream's deadline fires.\n if (queuedReject !== null) throw queuedReject;\n return {\n appendResult: { offset: { value: '0' } },\n rowErrors: queuedErrors ?? [],\n writeStream: 'projects/p/datasets/d/tables/t/streams/_default',\n };\n },\n };\n }\n close(): void {\n calls.push({ method: 'JSONWriter.close', args: [] });\n }\n}\n\nclass MockWriterClient {\n constructor(args: {\n projectId?: string;\n keyFilename?: string;\n credentials?: unknown;\n scopes?: string | string[];\n }) {\n calls.push({ method: 'WriterClient.ctor', args: [args] });\n }\n async createStreamConnection(\n args: {\n destinationTable: string;\n streamId: string;\n },\n options?: unknown,\n ) {\n // Match the real SDK: callers must pass streamId=DefaultStream (not streamType)\n // for default-stream use. Passing streamType triggers a CreateWriteStream\n // call with type='DEFAULT', which BQ rejects as TYPE_UNSPECIFIED.\n if (args.streamId !== 'DEFAULT') {\n throw new Error(\n `mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(args)}`,\n );\n }\n // args[1] captures the gax CallOptions (e.g. { timeout }) so tests can\n // assert the request deadline is forwarded to the appendRows stream.\n calls.push({ method: 'createStreamConnection', args: [args, options] });\n const queuedError = nextCreateStreamConnectionError;\n if (queuedError !== null) {\n nextCreateStreamConnectionError = null;\n throw queuedError;\n }\n const connection = new MockStreamConnection(\n `${args.destinationTable}/streams/_default`,\n );\n lastConnection = connection;\n allConnections.push(connection);\n return connection;\n }\n async getWriteStream(\n args: { streamId: string; view?: number },\n options?: unknown,\n ) {\n // args[1] captures the gax CallOptions so tests can assert the deadline\n // is forwarded to the unary schema fetch.\n calls.push({ method: 'getWriteStream', args: [args, options] });\n // Minimal tableSchema shape consumed by adapt.convertStorageSchemaToProto2Descriptor\n return {\n tableSchema: { fields: [] },\n };\n }\n close(): void {\n calls.push({ method: 'WriterClient.close', args: [] });\n }\n}\n\nconst adapt = {\n convertStorageSchemaToProto2Descriptor: (_schema: unknown, _root: string) => {\n calls.push({\n method: 'adapt.convertStorageSchemaToProto2Descriptor',\n args: [_schema, _root],\n });\n return { name: 'root', field: [] };\n },\n};\n\nconst managedwriter = {\n WriterClient: MockWriterClient,\n JSONWriter: MockJSONWriter,\n DefaultStream: 'DEFAULT',\n};\n\nconst protos = {\n google: {\n cloud: {\n bigquery: {\n storage: {\n v1: {\n WriteStreamView: {\n WRITE_STREAM_VIEW_UNSPECIFIED: 0,\n BASIC: 1,\n FULL: 2,\n },\n },\n },\n },\n },\n },\n};\n\n// Test-only helper. Not part of the real SDK.\nfunction __getMockCalls() {\n return calls;\n}\n\nfunction __resetMockCalls() {\n calls.length = 0;\n nextAppendRowErrors = null;\n nextAppendThrow = null;\n nextGetResultReject = null;\n nextCreateStreamConnectionError = null;\n lastConnection = null;\n allConnections.length = 0;\n}\n\n/**\n * Test-only: the most recently created StreamConnection, so a test can emit an\n * out-of-band `'error'` on it (via `__emitConnectionError`) and assert the\n * destination attached a listener.\n */\nfunction __getLastConnection(): MockStreamConnection {\n if (!lastConnection) throw new Error('mock: no StreamConnection created yet');\n return lastConnection;\n}\n\n/**\n * Test-only: every StreamConnection created since the last reset, so a test can\n * assert that a concurrent re-open did not orphan a connection that still\n * carries an 'error' listener (a leak).\n */\nfunction __getAllConnections(): MockStreamConnection[] {\n return allConnections.slice();\n}\n\n/**\n * Test-only: queue rowErrors for the next appendRows().getResult() call.\n * Auto-resets after one use.\n */\nfunction __setNextAppendRowErrors(errors: MockRowError[]): void {\n nextAppendRowErrors = errors;\n}\n\n/**\n * Test-only: make the next appendRows() throw synchronously, simulating a\n * Storage Write API call failure. Auto-resets after one use.\n */\nfunction __setNextAppendThrow(err: unknown): void {\n nextAppendThrow = err;\n}\n\n/**\n * Test-only: make the next appendRows().getResult() reject, simulating a gRPC\n * deadline-exceeded (or any stream error) surfacing through the pending write.\n * Auto-resets after one use.\n */\nfunction __setNextGetResultReject(err: unknown): void {\n nextGetResultReject = err;\n}\n\n/**\n * Test-only: queue an error for the next createStreamConnection() call so\n * tests can simulate openWriter failures (NotFound, INVALID_ARGUMENT, etc.).\n * Auto-resets after one use.\n */\nfunction __setNextOpenWriterError(err: unknown): void {\n nextCreateStreamConnectionError = err;\n}\n\nexport {\n managedwriter,\n adapt,\n protos,\n MockStreamConnection,\n __getMockCalls,\n __resetMockCalls,\n __getLastConnection,\n __getAllConnections,\n __setNextAppendRowErrors,\n __setNextAppendThrow,\n __setNextGetResultReject,\n __setNextOpenWriterError,\n};\n","import type { Flow, WalkerOS } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\nimport { eventToRow } from '../eventToRow';\n\n/**\n * Mirror of push.ts via eventToRow() -- produces a flat 15-column row\n * with nested object/array values JSON-stringified. Imported directly\n * from the runtime helper so the step examples stay in sync with what\n * push.ts actually emits to JSONWriter.appendRows.\n */\nfunction expectedRow(event: WalkerOS.Event) {\n return eventToRow(event);\n}\n\n/**\n * Page view -- one row appended through JSONWriter.appendRows([row]).\n * Captured as a single intent-level call: ['appendRows', [row]].\n */\nconst pageViewEvent = getEvent('page view', {\n timestamp: 1700001100,\n data: { title: 'Documentation', url: 'https://example.com/docs' },\n source: { type: 'express', platform: 'server' },\n});\n\nexport const pageView: Flow.StepExample = {\n title: 'Page view',\n description:\n 'A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.',\n in: pageViewEvent,\n mapping: undefined,\n out: [['appendRows', [expectedRow(pageViewEvent)]]],\n};\n\n/**\n * Purchase -- nested array in data.items is JSON.stringified into the\n * data column of the appended row.\n */\nconst purchaseEvent = getEvent('order complete', {\n timestamp: 1700001101,\n data: {\n id: 'ORD-500',\n total: 199.99,\n items: [{ sku: 'SKU-1', qty: 2 }],\n },\n source: { type: 'express', platform: 'server' },\n});\n\nexport const purchase: Flow.StepExample = {\n title: 'Purchase',\n description:\n 'An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().',\n in: purchaseEvent,\n mapping: undefined,\n out: [['appendRows', [expectedRow(purchaseEvent)]]],\n};\n","import type { WalkerOS } from '@walkeros/core';\n\n/** Row shape passed to JSONWriter.appendRows. Values are JSON-serializable scalars or strings. */\nexport interface BigQueryRow {\n [key: string]: string | number | null;\n name: string;\n data: string | null;\n context: string | null;\n globals: string | null;\n custom: string | null;\n user: string | null;\n nested: string | null;\n consent: string | null;\n id: string;\n trigger: string;\n entity: string;\n action: string;\n timestamp: number;\n timing: number;\n source: string | null;\n}\n\nfunction jsonOrNull(value: unknown): string | null {\n if (value === undefined || value === null) return null;\n if (typeof value === 'object') {\n if (Array.isArray(value) && value.length === 0) return null;\n if (!Array.isArray(value) && Object.keys(value).length === 0) return null;\n return JSON.stringify(value);\n }\n return JSON.stringify(value);\n}\n\n/** Convert a walkerOS Event v4 into a 15-column BigQuery row in canonical order.\n *\n * Note: BQ Storage Write API encodes TIMESTAMP fields as INT64 microseconds\n * since epoch (the SDK calls Long.fromString on the value). ISO strings fail\n * with \"interior hyphen\" because Long.fromString sees the date hyphens as\n * non-numeric. Pass microseconds directly.\n */\nexport function eventToRow(event: WalkerOS.Event): BigQueryRow {\n return {\n name: event.name,\n data: jsonOrNull(event.data),\n context: jsonOrNull(event.context),\n globals: jsonOrNull(event.globals),\n custom: jsonOrNull(event.custom),\n user: jsonOrNull(event.user),\n nested: jsonOrNull(event.nested),\n consent: jsonOrNull(event.consent),\n id: event.id,\n trigger: event.trigger,\n entity: event.entity,\n action: event.action,\n timestamp: new Date(event.timestamp).getTime() * 1000, // microseconds since epoch\n timing: event.timing,\n source: jsonOrNull(event.source),\n };\n}\n","export * as env from './env';\nexport * as step from './step';\n","import type {\n Env,\n PubSubPublisher,\n PublishMessage,\n TopicPublisher,\n} from '../types';\n\n/**\n * Example environment for the GCP Pub/Sub destination.\n *\n * `push` is the mock env simulate injects: `PubSub` builds a client whose\n * topics answer `publishMessage` locally, so nothing reaches GCP. Unit tests\n * still substitute the SDK module-wide via `jest.mock('@google-cloud/pubsub')`.\n */\n\nclass MockTopic implements TopicPublisher {\n constructor(public name: string) {}\n publishMessage(_message: PublishMessage): Promise<string> {\n return Promise.resolve('mock-message-id');\n }\n resumePublishing(_orderingKey: string): void {}\n}\n\nclass MockPubSub implements PubSubPublisher {\n constructor(public options?: object) {}\n topic(name: string): TopicPublisher {\n return new MockTopic(name);\n }\n close(): Promise<void> {\n return Promise.resolve();\n }\n}\n\nexport const push: Env = {\n PubSub: MockPubSub,\n};\n\n/** The publish carries the request; `args[0]` is the message. */\nexport const simulation = ['call:PubSub.topic.publishMessage'];\n","import type { Flow, WalkerOS } from '@walkeros/core';\nimport { getEvent } from '@walkeros/core';\n\n// Build-time version define. The upstream collector stamps source.release with\n// this on push, so the expected payload must mirror it rather than a literal,\n// else it breaks whenever the fixed version group is bumped (release).\ndeclare const __VERSION__: string;\n\n/**\n * Pub/Sub step examples. Each example's `out` is the array of recorded mock\n * calls produced by `push()`. The recording shape is:\n * ['topic', topicName, topicOptions] // implicit topic-handle creation\n * ['publishMessage', topicName, messageOptions]\n * ['resumePublishing', topicName, orderingKey] // only on publish failure\n */\n\n// Events reaching a server destination arrive already enriched by the upstream\n// collector, so they carry the run trace and per-run count. The collector\n// preserves these (stamp-if-absent), keeping the example deterministic.\nconst orderEvent = getEvent('order complete', {\n timestamp: 1700001100,\n data: { id: 'ORD-500', total: 199.99, currency: 'EUR' },\n user: { id: 'usr-789' },\n source: {\n type: 'express',\n platform: 'server',\n trace: '1a2b3c4d5e6f70819a2b3c4d5e6f7081',\n count: 1,\n },\n});\n\nconst pageEvent = getEvent('page view', {\n timestamp: 1700001101,\n data: { title: 'Documentation', url: 'https://example.com/docs' },\n source: {\n type: 'express',\n platform: 'server',\n trace: '9f8e7d6c5b4a39281706f5e4d3c2b1a0',\n count: 1,\n },\n});\n\nfunction expectedPayload(event: WalkerOS.Event): Buffer {\n // The harness pushes the event through an unconfigured collector, which stamps\n // source.release = { [name ?? platform ?? 'default']: __VERSION__ }. With no\n // collector name, the key is the event's platform. Mirror that here so the\n // expected message body matches the published (post-collector) event.\n const releaseKey = event.source.platform ?? 'default';\n const stamped = {\n ...event,\n source: { ...event.source, release: { [releaseKey]: __VERSION__ } },\n };\n return Buffer.from(JSON.stringify(stamped));\n}\n\n/**\n * Default publish, no mapping. Settings.topic = 'events'. The destination\n * constructs a topic handle inline with messageOrdering=false (no ordering\n * key resolved) and publishes the full event JSON as the message body.\n */\nexport const defaultPush: Flow.StepExample = {\n title: 'Default publish',\n description:\n 'An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.',\n in: orderEvent,\n out: [\n ['topic', 'events', { messageOrdering: false }],\n ['publishMessage', 'events', { data: expectedPayload(orderEvent) }],\n ],\n};\n\n/**\n * Per-rule topic override. Mapping carries `settings.topic = 'orders'`\n * which routes this rule to a dedicated topic.\n */\nexport const mappedTopic: Flow.StepExample = {\n title: 'Topic override',\n description:\n 'A mapping rule overrides the destination default topic so order events are published to a dedicated topic.',\n in: orderEvent,\n mapping: {\n settings: {\n topic: 'orders',\n },\n },\n out: [\n ['topic', 'orders', { messageOrdering: false }],\n ['publishMessage', 'orders', { data: expectedPayload(orderEvent) }],\n ],\n};\n\n/**\n * Per-rule ordering key resolved from the event. `mapping.orderingKey =\n * 'user.id'` is a Mapping.Value that resolves to the event's user.id. The\n * topic handle is constructed with messageOrdering=true and the publish\n * carries the resolved orderingKey.\n */\nexport const mappedOrderingKey: Flow.StepExample = {\n title: 'Ordering key from user',\n description:\n 'A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.',\n in: orderEvent,\n mapping: {\n settings: {\n orderingKey: 'user.id',\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: true }],\n [\n 'publishMessage',\n 'events',\n {\n data: expectedPayload(orderEvent),\n orderingKey: 'usr-789',\n },\n ],\n ],\n};\n\n/**\n * Per-rule attributes. `mapping.attributes = { entity: 'entity', action:\n * 'action' }` is a Mapping.Map resolved per event. Each value is a path\n * resolved against the event.\n */\nexport const mappedAttributes: Flow.StepExample = {\n title: 'Mapped attributes',\n description:\n 'A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.',\n in: orderEvent,\n mapping: {\n settings: {\n attributes: {\n entity: 'entity',\n action: 'action',\n },\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: false }],\n [\n 'publishMessage',\n 'events',\n {\n data: expectedPayload(orderEvent),\n attributes: { entity: 'order', action: 'complete' },\n },\n ],\n ],\n};\n\n/**\n * Mapped data. `mapping.data` rewrites the publish body. The rewritten\n * object replaces the event as the message data.\n */\nexport const mappedData: Flow.StepExample = {\n title: 'Mapped payload',\n description:\n 'A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.',\n in: orderEvent,\n mapping: {\n data: {\n map: {\n order_id: 'data.id',\n revenue: 'data.total',\n currency: 'data.currency',\n },\n },\n },\n out: [\n ['topic', 'events', { messageOrdering: false }],\n [\n 'publishMessage',\n 'events',\n {\n // Mapped-data publish: the body is the mapping result (no event\n // envelope, so no source.release), emitted verbatim.\n data: Buffer.from(\n JSON.stringify({\n order_id: 'ORD-500',\n revenue: 199.99,\n currency: 'EUR',\n }),\n ),\n },\n ],\n ],\n};\n\n/**\n * Page view, no rule. Verifies free-form publish on a non-ordered topic\n * for an event with no special mapping.\n */\nexport const pageView: Flow.StepExample = {\n title: 'Page view',\n description:\n 'A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.',\n in: pageEvent,\n out: [\n ['topic', 'events', { messageOrdering: false }],\n ['publishMessage', 'events', { data: expectedPayload(pageEvent) }],\n ],\n};\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z.object({\n client: z\n .any()\n .describe(\n 'Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))',\n )\n .optional(),\n projectId: z\n .string()\n .min(1)\n .describe('Google Cloud Project ID (like my-gcp-project)'),\n datasetId: z\n .string()\n .min(1)\n .default('walkerOS')\n .describe(\n 'BigQuery dataset ID where events will be stored (like walker_events)',\n ),\n tableId: z\n .string()\n .min(1)\n .default('events')\n .describe('BigQuery table ID for event storage (like events)'),\n location: z\n .string()\n .default('EU')\n .describe('Geographic location for the BigQuery dataset (like US)'),\n bigquery: z\n .any()\n .describe(\n 'Additional BigQuery client configuration options (like { keyFilename: \"path/to/key.json\" })',\n )\n .optional(),\n});\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP BigQuery Mapping Schema\n * BigQuery has no event-level mapping configuration\n */\nexport const MappingSchema = z.object({});\n\n/**\n * Type inference from MappingSchema\n */\nexport type Mapping = z.infer<typeof MappingSchema>;\n","import { zodToSchema } from '@walkeros/core/dev';\nimport { SettingsSchema } from './settings';\nimport { MappingSchema } from './mapping';\nimport { SetupSchema } from './setup';\n\nexport { SettingsSchema, type Settings } from './settings';\nexport { MappingSchema, type Mapping } from './mapping';\nexport { SetupSchema, type Setup } from './setup';\n\n// JSON Schema\nexport const settings = zodToSchema(SettingsSchema);\nexport const mapping = zodToSchema(MappingSchema);\nexport const setup = zodToSchema(SetupSchema);\n","import { z } from '@walkeros/core/dev';\n\nexport const SettingsSchema = z.object({\n client: z\n .any()\n .describe(\n 'Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))',\n )\n .optional(),\n projectId: z\n .string()\n .min(1)\n .describe('Google Cloud Project ID (like my-gcp-project)'),\n topic: z\n .string()\n .min(1)\n .describe(\n 'Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK.',\n ),\n credentials: z\n .any()\n .describe(\n 'Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)',\n )\n .optional(),\n apiEndpoint: z\n .string()\n .describe(\n 'Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).',\n )\n .optional(),\n orderingKey: z\n .any()\n .describe(\n 'Mapping value resolved per-event. Truthy enables per-key ordering for the publish.',\n )\n .optional(),\n attributes: z\n .any()\n .describe(\n 'Default per-event attribute map merged into every published message. Mapping.Map shape.',\n )\n .optional(),\n});\n\nexport type Settings = z.infer<typeof SettingsSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP Pub/Sub Mapping Schema\n *\n * Per-rule overrides for topic, orderingKey, and attributes.\n */\nexport const MappingSchema = z.object({\n topic: z\n .string()\n .describe(\n 'Per-rule topic override. Falls back to settings.topic if absent.',\n )\n .optional(),\n orderingKey: z\n .any()\n .describe(\n 'Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.',\n )\n .optional(),\n attributes: z\n .any()\n .describe(\n 'Per-rule attribute Mapping.Map merged on top of settings.attributes.',\n )\n .optional(),\n});\n\n/**\n * Type inference from MappingSchema\n */\nexport type Mapping = z.infer<typeof MappingSchema>;\n","import { z } from '@walkeros/core/dev';\n\n/**\n * GCP Pub/Sub Setup Schema\n *\n * Provisioning options for `walkeros setup destination.<id>`. Idempotent topic\n * creation. Subscription provisioning is owned by the source side.\n */\nexport const SetupSchema = z.object({\n messageStoragePolicy: z\n .object({\n allowedPersistenceRegions: z\n .array(z.string())\n .describe(\n 'Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).',\n ),\n })\n .describe('Topic-level message storage policy.')\n .optional(),\n messageRetentionDuration: z\n .object({\n seconds: z\n .number()\n .describe('Retention window in seconds. Default: project default.'),\n })\n .describe('Topic-level retention configuration.')\n .optional(),\n kmsKeyName: z\n .string()\n .describe('Customer-managed encryption key (CMEK) resource name. Optional.')\n .optional(),\n labels: z\n .record(z.string(), z.string())\n .describe('Topic labels for organization and billing.')\n .optional(),\n});\n\nexport type Setup = z.infer<typeof SetupSchema>;\n","// Browser-safe schema-only exports\n// This file exports ONLY schemas without any Node.js dependencies\nexport { settings, mapping } from './bigquery/schemas';\nexport {\n settings as pubsubSettings,\n mapping as pubsubMapping,\n setup as pubsubSetup,\n} from './pubsub/schemas';\n","import type { Hint } from '@walkeros/core';\n\nexport const hints: Hint.Hints = {\n 'auth-methods': {\n text: 'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: \"./sa.json\" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',\n code: [\n {\n lang: 'json',\n code: '{ \"settings\": { \"projectId\": \"my-project\", \"bigquery\": { \"keyFilename\": \"./sa.json\" } } }',\n },\n {\n lang: 'json',\n code: '{ \"settings\": { \"projectId\": \"my-project\" } }',\n },\n ],\n },\n 'storage-format': {\n text: 'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset \"walkeros\", table \"events\", location \"EU\" — all overridable via settings.',\n },\n 'query-json-columns': {\n text: 'Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.',\n code: [\n {\n lang: 'sql',\n code: \"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'\",\n },\n ],\n },\n 'troubleshoot-empty-table': {\n text: \"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK.\",\n },\n};\n"],"mappings":"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","names":["examples_exports","examples_exports","env_exports","step_exports","env_exports","push","simulation","step_exports","pageView","import_core","import_dev","import_dev","import_dev","import_dev","SettingsSchema","import_dev","MappingSchema","import_dev","settings","SettingsSchema","mapping","MappingSchema","mapping","settings","examples_exports","settings","mapping"]}
package/dist/dev.mjs CHANGED
@@ -1 +1 @@
1
- var e=Object.defineProperty,t=(t,r)=>{for(var s in r)e(t,s,{get:r[s],enumerable:!0})},r={};t(r,{mapping:()=>c,pubsubMapping:()=>f,pubsubSettings:()=>y,pubsubSetup:()=>v,settings:()=>l});import{zodToSchema as s}from"@walkeros/core/dev";import{z as o}from"@walkeros/core/dev";var i=o.object({client:o.any().describe("Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))").optional(),projectId:o.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),datasetId:o.string().min(1).default("walkerOS").describe("BigQuery dataset ID where events will be stored (like walker_events)"),tableId:o.string().min(1).default("events").describe("BigQuery table ID for event storage (like events)"),location:o.string().default("EU").describe("Geographic location for the BigQuery dataset (like US)"),bigquery:o.any().describe('Additional BigQuery client configuration options (like { keyFilename: "path/to/key.json" })').optional()});import{z as a}from"@walkeros/core/dev";var n=a.object({}),l=s(i),c=s(n);import{zodToSchema as p}from"@walkeros/core/dev";import{z as d}from"@walkeros/core/dev";var u=d.object({client:d.any().describe("Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))").optional(),projectId:d.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),topic:d.string().min(1).describe("Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK."),credentials:d.any().describe("Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)").optional(),apiEndpoint:d.string().describe("Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).").optional(),orderingKey:d.any().describe("Mapping value resolved per-event. Truthy enables per-key ordering for the publish.").optional(),attributes:d.any().describe("Default per-event attribute map merged into every published message. Mapping.Map shape.").optional()});import{z as g}from"@walkeros/core/dev";var m=g.object({topic:g.string().describe("Per-rule topic override. Falls back to settings.topic if absent.").optional(),orderingKey:g.any().describe("Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.").optional(),attributes:g.any().describe("Per-rule attribute Mapping.Map merged on top of settings.attributes.").optional()});import{z as b}from"@walkeros/core/dev";var h=b.object({messageStoragePolicy:b.object({allowedPersistenceRegions:b.array(b.string()).describe("Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).")}).describe("Topic-level message storage policy.").optional(),messageRetentionDuration:b.object({seconds:b.number().describe("Retention window in seconds. Default: project default.")}).describe("Topic-level retention configuration.").optional(),kmsKeyName:b.string().describe("Customer-managed encryption key (CMEK) resource name. Optional.").optional(),labels:b.record(b.string(),b.string()).describe("Topic labels for organization and billing.").optional()}),y=p(u),f=p(m),v=p(h),S={};t(S,{env:()=>w,step:()=>M});var w={};t(w,{push:()=>x,simulation:()=>N});import{EventEmitter as k}from"events";var j=[],O=null,P=null,A=null,C=null,D=class extends k{streamId;constructor(e){super(),this.streamId=e}getStreamId(){return this.streamId}onConnectionError(e){return j.push({method:"onConnectionError",args:[]}),this.on("error",e),{off:()=>{this.off("error",e)}}}__emitConnectionError(e){this.emit("error",e)}},I=[],E={convertStorageSchemaToProto2Descriptor:(e,t)=>(j.push({method:"adapt.convertStorageSchemaToProto2Descriptor",args:[e,t]}),{name:"root",field:[]})},R=class{constructor(e){j.push({method:"WriterClient.ctor",args:[e]})}async createStreamConnection(e,t){if("DEFAULT"!==e.streamId)throw new Error(`mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(e)}`);j.push({method:"createStreamConnection",args:[e,t]});const r=C;if(null!==r)throw C=null,r;const s=new D(`${e.destinationTable}/streams/_default`);return I.push(s),s}async getWriteStream(e,t){return j.push({method:"getWriteStream",args:[e,t]}),{tableSchema:{fields:[]}}}close(){j.push({method:"WriterClient.close",args:[]})}},T=class{constructor(e){j.push({method:"JSONWriter.ctor",args:[e]})}appendRows(e,t){j.push({method:"appendRows",args:[e,t]});const r=P;if(null!==r)throw P=null,r;const s=O;O=null;const o=A;return A=null,{getResult:async()=>{if(null!==o)throw o;return{appendResult:{offset:{value:"0"}},rowErrors:s??[],writeStream:"projects/p/datasets/d/tables/t/streams/_default"}}}}close(){j.push({method:"JSONWriter.close",args:[]})}};var x={get BigQuery(){return class{calls;options;constructor(e){this.options=e,this.calls=[]}dataset(e){return this.calls.push({method:"dataset",args:[e]}),this}table(e){return this.calls.push({method:"table",args:[e]}),this}async exists(){return this.calls.push({method:"exists",args:[]}),[!0]}async create(e){this.calls.push({method:"create",args:[e]})}async getMetadata(){return this.calls.push({method:"getMetadata",args:[]}),[{}]}}},get WriterClient(){return R},get JSONWriter(){return T},get adapt(){return E}},N=["call:JSONWriter.appendRows"],M={};t(M,{pageView:()=>_,purchase:()=>U});import{getEvent as J}from"@walkeros/core";function B(e){return null==e?null:"object"==typeof e?Array.isArray(e)&&0===e.length?null:Array.isArray(e)||0!==Object.keys(e).length?JSON.stringify(e):null:JSON.stringify(e)}function Q(e){return function(e){return{name:e.name,data:B(e.data),context:B(e.context),globals:B(e.globals),custom:B(e.custom),user:B(e.user),nested:B(e.nested),consent:B(e.consent),id:e.id,trigger:e.trigger,entity:e.entity,action:e.action,timestamp:1e3*new Date(e.timestamp).getTime(),timing:e.timing,source:B(e.source)}}(e)}var W=J("page view",{timestamp:1700001100,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server"}}),_={title:"Page view",description:"A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.",in:W,mapping:void 0,out:[["appendRows",[Q(W)]]]},K=J("order complete",{timestamp:1700001101,data:{id:"ORD-500",total:199.99,items:[{sku:"SKU-1",qty:2}]},source:{type:"express",platform:"server"}}),U={title:"Purchase",description:"An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().",in:K,mapping:void 0,out:[["appendRows",[Q(K)]]]},q={};t(q,{env:()=>F,step:()=>V});var F={};t(F,{push:()=>z,simulation:()=>L});var G=class{constructor(e){this.name=e}name;publishMessage(e){return Promise.resolve("mock-message-id")}resumePublishing(e){}},z={PubSub:class{constructor(e){this.options=e}options;topic(e){return new G(e)}close(){return Promise.resolve()}}},L=["call:PubSub.topic.publishMessage"],V={};t(V,{defaultPush:()=>Z,mappedAttributes:()=>re,mappedData:()=>se,mappedOrderingKey:()=>te,mappedTopic:()=>ee,pageView:()=>oe});import{getEvent as $}from"@walkeros/core";var X=$("order complete",{timestamp:1700001100,data:{id:"ORD-500",total:199.99,currency:"EUR"},user:{id:"usr-789"},source:{type:"express",platform:"server",trace:"1a2b3c4d5e6f70819a2b3c4d5e6f7081",count:1}}),H=$("page view",{timestamp:1700001101,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server",trace:"9f8e7d6c5b4a39281706f5e4d3c2b1a0",count:1}});function Y(e){const t=e.source.platform??"default",r={...e,source:{...e.source,release:{[t]:"4.7.0-next-1790722899482"}}};return Buffer.from(JSON.stringify(r))}var Z={title:"Default publish",description:"An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.",in:X,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Y(X)}]]},ee={title:"Topic override",description:"A mapping rule overrides the destination default topic so order events are published to a dedicated topic.",in:X,mapping:{settings:{topic:"orders"}},out:[["topic","orders",{messageOrdering:!1}],["publishMessage","orders",{data:Y(X)}]]},te={title:"Ordering key from user",description:"A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.",in:X,mapping:{settings:{orderingKey:"user.id"}},out:[["topic","events",{messageOrdering:!0}],["publishMessage","events",{data:Y(X),orderingKey:"usr-789"}]]},re={title:"Mapped attributes",description:"A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.",in:X,mapping:{settings:{attributes:{entity:"entity",action:"action"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Y(X),attributes:{entity:"order",action:"complete"}}]]},se={title:"Mapped payload",description:"A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.",in:X,mapping:{data:{map:{order_id:"data.id",revenue:"data.total",currency:"data.currency"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Buffer.from(JSON.stringify({order_id:"ORD-500",revenue:199.99,currency:"EUR"}))}]]},oe={title:"Page view",description:"A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.",in:H,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Y(H)}]]},ie={"auth-methods":{text:'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: "./sa.json" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',code:[{lang:"json",code:'{ "settings": { "projectId": "my-project", "bigquery": { "keyFilename": "./sa.json" } } }'},{lang:"json",code:'{ "settings": { "projectId": "my-project" } }'}]},"storage-format":{text:'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset "walkeros", table "events", location "EU" — all overridable via settings.'},"query-json-columns":{text:"Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.",code:[{lang:"sql",code:"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'"}]},"troubleshoot-empty-table":{text:"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK."}},ae={destinationBigQuery:S,destinationPubSub:q};export{S as examples,ae as exportExamples,ie as hints,q as pubsubExamples,r as schemas};//# sourceMappingURL=dev.mjs.map
1
+ var e=Object.defineProperty,t=(t,r)=>{for(var s in r)e(t,s,{get:r[s],enumerable:!0})},r={};t(r,{env:()=>s,step:()=>y});var s={};t(s,{push:()=>b,simulation:()=>h});import{EventEmitter as i}from"events";var o=[],a=null,n=null,l=null,c=null,p=class extends i{streamId;constructor(e){super(),this.streamId=e}getStreamId(){return this.streamId}onConnectionError(e){return o.push({method:"onConnectionError",args:[]}),this.on("error",e),{off:()=>{this.off("error",e)}}}__emitConnectionError(e){this.emit("error",e)}},d=[],u={convertStorageSchemaToProto2Descriptor:(e,t)=>(o.push({method:"adapt.convertStorageSchemaToProto2Descriptor",args:[e,t]}),{name:"root",field:[]})},g=class{constructor(e){o.push({method:"WriterClient.ctor",args:[e]})}async createStreamConnection(e,t){if("DEFAULT"!==e.streamId)throw new Error(`mock createStreamConnection: expected streamId='DEFAULT', got ${JSON.stringify(e)}`);o.push({method:"createStreamConnection",args:[e,t]});const r=c;if(null!==r)throw c=null,r;const s=new p(`${e.destinationTable}/streams/_default`);return d.push(s),s}async getWriteStream(e,t){return o.push({method:"getWriteStream",args:[e,t]}),{tableSchema:{fields:[]}}}close(){o.push({method:"WriterClient.close",args:[]})}},m=class{constructor(e){o.push({method:"JSONWriter.ctor",args:[e]})}appendRows(e,t){o.push({method:"appendRows",args:[e,t]});const r=n;if(null!==r)throw n=null,r;const s=a;a=null;const i=l;return l=null,{getResult:async()=>{if(null!==i)throw i;return{appendResult:{offset:{value:"0"}},rowErrors:s??[],writeStream:"projects/p/datasets/d/tables/t/streams/_default"}}}}close(){o.push({method:"JSONWriter.close",args:[]})}};var b={get BigQuery(){return class{calls;options;constructor(e){this.options=e,this.calls=[]}dataset(e){return this.calls.push({method:"dataset",args:[e]}),this}table(e){return this.calls.push({method:"table",args:[e]}),this}async exists(){return this.calls.push({method:"exists",args:[]}),[!0]}async create(e){this.calls.push({method:"create",args:[e]})}async getMetadata(){return this.calls.push({method:"getMetadata",args:[]}),[{}]}}},get WriterClient(){return g},get JSONWriter(){return m},get adapt(){return u}},h=["call:JSONWriter.appendRows"],y={};t(y,{pageView:()=>k,purchase:()=>O});import{getEvent as f}from"@walkeros/core";function v(e){return null==e?null:"object"==typeof e?Array.isArray(e)&&0===e.length?null:Array.isArray(e)||0!==Object.keys(e).length?JSON.stringify(e):null:JSON.stringify(e)}function S(e){return function(e){return{name:e.name,data:v(e.data),context:v(e.context),globals:v(e.globals),custom:v(e.custom),user:v(e.user),nested:v(e.nested),consent:v(e.consent),id:e.id,trigger:e.trigger,entity:e.entity,action:e.action,timestamp:1e3*new Date(e.timestamp).getTime(),timing:e.timing,source:v(e.source)}}(e)}var w=f("page view",{timestamp:1700001100,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server"}}),k={title:"Page view",description:"A page view is appended as one row through the BigQuery Storage Write API JSONWriter. Nested objects/arrays in data, source, etc. are JSON-stringified by eventToRow.",in:w,mapping:void 0,out:[["appendRows",[S(w)]]]},j=f("order complete",{timestamp:1700001101,data:{id:"ORD-500",total:199.99,items:[{sku:"SKU-1",qty:2}]},source:{type:"express",platform:"server"}}),O={title:"Purchase",description:"An order event is appended as a single row through JSONWriter.appendRows. The entire nested data object (including arrays like items) is JSON-stringified into the data column via eventToRow().",in:j,mapping:void 0,out:[["appendRows",[S(j)]]]},P={};t(P,{env:()=>A,step:()=>E});var A={};t(A,{push:()=>D,simulation:()=>I});var C=class{constructor(e){this.name=e}name;publishMessage(e){return Promise.resolve("mock-message-id")}resumePublishing(e){}},D={PubSub:class{constructor(e){this.options=e}options;topic(e){return new C(e)}close(){return Promise.resolve()}}},I=["call:PubSub.topic.publishMessage"],E={};t(E,{defaultPush:()=>M,mappedAttributes:()=>Q,mappedData:()=>W,mappedOrderingKey:()=>B,mappedTopic:()=>J,pageView:()=>_});import{getEvent as R}from"@walkeros/core";var T=R("order complete",{timestamp:1700001100,data:{id:"ORD-500",total:199.99,currency:"EUR"},user:{id:"usr-789"},source:{type:"express",platform:"server",trace:"1a2b3c4d5e6f70819a2b3c4d5e6f7081",count:1}}),N=R("page view",{timestamp:1700001101,data:{title:"Documentation",url:"https://example.com/docs"},source:{type:"express",platform:"server",trace:"9f8e7d6c5b4a39281706f5e4d3c2b1a0",count:1}});function x(e){const t=e.source.platform??"default",r={...e,source:{...e.source,release:{[t]:"4.7.0"}}};return Buffer.from(JSON.stringify(r))}var M={title:"Default publish",description:"An event is published to the configured Pub/Sub topic with the full JSON event as the message body and no ordering key.",in:T,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:x(T)}]]},J={title:"Topic override",description:"A mapping rule overrides the destination default topic so order events are published to a dedicated topic.",in:T,mapping:{settings:{topic:"orders"}},out:[["topic","orders",{messageOrdering:!1}],["publishMessage","orders",{data:x(T)}]]},B={title:"Ordering key from user",description:"A mapping resolves the ordering key from event.user.id, enabling per-user ordering for this publish.",in:T,mapping:{settings:{orderingKey:"user.id"}},out:[["topic","events",{messageOrdering:!0}],["publishMessage","events",{data:x(T),orderingKey:"usr-789"}]]},Q={title:"Mapped attributes",description:"A mapping resolves a per-event attribute map, here exposing entity and action as Pub/Sub attributes for routing in subscribers.",in:T,mapping:{settings:{attributes:{entity:"entity",action:"action"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:x(T),attributes:{entity:"order",action:"complete"}}]]},W={title:"Mapped payload",description:"A data mapping transforms the event payload before publish. The rewritten object becomes the Pub/Sub message body.",in:T,mapping:{data:{map:{order_id:"data.id",revenue:"data.total",currency:"data.currency"}}},out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:Buffer.from(JSON.stringify({order_id:"ORD-500",revenue:199.99,currency:"EUR"}))}]]},_={title:"Page view",description:"A page view is published to the default topic with no ordering key, demonstrating the simplest publish path.",in:N,out:[["topic","events",{messageOrdering:!1}],["publishMessage","events",{data:x(N)}]]};import{zodToSchema as K}from"@walkeros/core/dev";import{z as U}from"@walkeros/core/dev";var q=U.object({client:U.any().describe("Google Cloud BigQuery client instance (like new BigQuery({ projectId, keyFilename }))").optional(),projectId:U.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),datasetId:U.string().min(1).default("walkerOS").describe("BigQuery dataset ID where events will be stored (like walker_events)"),tableId:U.string().min(1).default("events").describe("BigQuery table ID for event storage (like events)"),location:U.string().default("EU").describe("Geographic location for the BigQuery dataset (like US)"),bigquery:U.any().describe('Additional BigQuery client configuration options (like { keyFilename: "path/to/key.json" })').optional()});import{z as F}from"@walkeros/core/dev";var G=F.object({}),z=K(q),L=K(G);import{zodToSchema as V}from"@walkeros/core/dev";import{z as $}from"@walkeros/core/dev";var X=$.object({client:$.any().describe("Google Cloud Pub/Sub client instance (like new PubSub({ projectId, keyFilename }))").optional(),projectId:$.string().min(1).describe("Google Cloud Project ID (like my-gcp-project)"),topic:$.string().min(1).describe("Pub/Sub topic short name (like events). The full resource name projects/<projectId>/topics/<topic> is built by the SDK."),credentials:$.any().describe("Service account credentials as a JSON string or an object with client_email and private_key. Default: Application Default Credentials (ADC). (deprecated: use config.credentials)").optional(),apiEndpoint:$.string().describe("Override Pub/Sub API endpoint. Useful for the local emulator (like localhost:8085).").optional(),orderingKey:$.any().describe("Mapping value resolved per-event. Truthy enables per-key ordering for the publish.").optional(),attributes:$.any().describe("Default per-event attribute map merged into every published message. Mapping.Map shape.").optional()});import{z as H}from"@walkeros/core/dev";var Y=H.object({topic:H.string().describe("Per-rule topic override. Falls back to settings.topic if absent.").optional(),orderingKey:H.any().describe("Per-rule ordering-key Mapping.Value. Overrides settings.orderingKey when set.").optional(),attributes:H.any().describe("Per-rule attribute Mapping.Map merged on top of settings.attributes.").optional()});import{z as Z}from"@walkeros/core/dev";var ee=Z.object({messageStoragePolicy:Z.object({allowedPersistenceRegions:Z.array(Z.string()).describe("Geographic regions for at-rest message storage. Default: EU multi-region (eu-west1, eu-west3, eu-west4).")}).describe("Topic-level message storage policy.").optional(),messageRetentionDuration:Z.object({seconds:Z.number().describe("Retention window in seconds. Default: project default.")}).describe("Topic-level retention configuration.").optional(),kmsKeyName:Z.string().describe("Customer-managed encryption key (CMEK) resource name. Optional.").optional(),labels:Z.record(Z.string(),Z.string()).describe("Topic labels for organization and billing.").optional()}),te=V(X),re=V(Y),se=V(ee),ie={};t(ie,{mapping:()=>L,pubsubMapping:()=>re,pubsubSettings:()=>te,pubsubSetup:()=>se,settings:()=>z});var oe={"auth-methods":{text:'Supports three auth methods: SA key file via bigquery options ({ bigquery: { keyFilename: "./sa.json" } }), Application Default Credentials (automatic on GCP infrastructure — just provide projectId), or a pre-configured BigQuery client instance (client option). See settings schema for all options.',code:[{lang:"json",code:'{ "settings": { "projectId": "my-project", "bigquery": { "keyFilename": "./sa.json" } } }'},{lang:"json",code:'{ "settings": { "projectId": "my-project" } }'}]},"storage-format":{text:'All events are stored in a single table. Scalar fields (strings, numbers, booleans) are stored as-is. Nested objects and arrays are JSON-stringified automatically. Defaults: dataset "walkeros", table "events", location "EU" — all overridable via settings.'},"query-json-columns":{text:"Nested event fields (data, context, globals, user) are stored as JSON strings. Use BigQuery JSON_EXTRACT_SCALAR to query them. Field paths follow the walkerOS event structure.",code:[{lang:"sql",code:"SELECT JSON_EXTRACT_SCALAR(data, '$.total') AS total FROM `project.walkeros.events` WHERE entity = 'order'"}]},"troubleshoot-empty-table":{text:"Events not appearing? Common causes: projectId doesn't match GCP project, dataset doesn't exist yet (create via BigQuery console or bq CLI before first push), or SA key lacks bigquery.dataEditor role. The destination validates client/datasetId/tableId at push time but GCP permission errors surface from the BigQuery SDK."}},ae={destinationBigQuery:r,destinationPubSub:P},ne={destinationBigQuery:{settings:z,mapping:L},destinationPubSub:{settings:te,mapping:re,setup:se}};export{r as examples,ae as exportExamples,ne as exportSchemas,oe as hints,P as pubsubExamples,ie as schemas};//# sourceMappingURL=dev.mjs.map