@crossdelta/cloudevents 0.6.2 → 0.6.4

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/dist/index.d.ts CHANGED
@@ -1,6 +1,8 @@
1
1
  import { Context } from 'hono';
2
2
  import { CloudEventV1 } from 'cloudevents';
3
3
  import { ZodTypeAny, z } from 'zod';
4
+ import { ChangeResult, FlowContext, FsContextMixin, GenerationContextMixin, FlowStep } from '@crossdelta/flowcore';
5
+ import { PfPlugin } from '@crossdelta/platform-sdk';
4
6
  import { ConsumerMessages, Subscription } from 'nats';
5
7
 
6
8
  /**
@@ -46,6 +48,355 @@ interface CloudEventParseResult {
46
48
  */
47
49
  declare const parseEventFromContext: (context: Context) => Promise<CloudEventParseResult>;
48
50
 
51
+ /**
52
+ * Domain Effects
53
+ *
54
+ * Effects are pure DATA describing side effects that need to happen.
55
+ * They are produced by domain flows and consumed by runtime handlers.
56
+ *
57
+ * This enables:
58
+ * - Clean separation between domain logic (cloudevents) and runtime integration (pf)
59
+ * - Testability: flows return data, no side effects
60
+ * - MCP compatibility: effects can be returned to AI agents
61
+ *
62
+ * Naming Convention:
63
+ * - Kind: `<noun>.<past-participle>` (e.g., `stream.wired`, `contract.created`)
64
+ * - Type: `<Noun><PastParticiple>Effect` (e.g., `StreamWiredEffect`)
65
+ * - Factory: `<noun><PastParticiple>` (e.g., `streamWired()`)
66
+ */
67
+ /**
68
+ * Effect: Stream was wired to a service
69
+ *
70
+ * Signals that a service should be configured to consume from a stream.
71
+ * Runtime handler will modify the service's entry point (index.ts/main.ts).
72
+ */
73
+ interface StreamWiredEffect {
74
+ readonly kind: 'stream.wired';
75
+ readonly stream: string;
76
+ readonly servicePath: string;
77
+ }
78
+ /**
79
+ * Effect: Contract was created
80
+ *
81
+ * Signals that a new contract file was created.
82
+ * Runtime may need to invalidate caches or trigger rebuilds.
83
+ */
84
+ interface ContractCreatedEffect {
85
+ readonly kind: 'contract.created';
86
+ readonly path: string;
87
+ readonly eventType: string;
88
+ }
89
+ /**
90
+ * Effect: Handler was created
91
+ *
92
+ * Signals that a new handler file was created.
93
+ * Runtime may need to update service configuration.
94
+ */
95
+ interface HandlerCreatedEffect {
96
+ readonly kind: 'handler.created';
97
+ readonly path: string;
98
+ readonly eventType: string;
99
+ readonly servicePath: string;
100
+ }
101
+ /**
102
+ * Union of all domain effects
103
+ *
104
+ * Add new effect types here as the system grows.
105
+ * Effects are a discriminated union on `kind`.
106
+ */
107
+ type DomainEffect = StreamWiredEffect | ContractCreatedEffect | HandlerCreatedEffect;
108
+ /**
109
+ * Create a stream.wired effect
110
+ */
111
+ declare const streamWired: (stream: string, servicePath: string) => StreamWiredEffect;
112
+ /**
113
+ * Create a contract.created effect
114
+ */
115
+ declare const contractCreated: (path: string, eventType: string) => ContractCreatedEffect;
116
+ /**
117
+ * Create a handler.created effect
118
+ */
119
+ declare const handlerCreated: (path: string, eventType: string, servicePath: string) => HandlerCreatedEffect;
120
+
121
+ /**
122
+ * Generator Types
123
+ *
124
+ * Interfaces for file system abstraction and generator options
125
+ */
126
+ /**
127
+ * File system abstraction for testing
128
+ */
129
+ interface FileSystem {
130
+ readFile(path: string): string | null;
131
+ writeFile(path: string, content: string): void;
132
+ exists(path: string): boolean;
133
+ mkdir(path: string): void;
134
+ }
135
+ /**
136
+ * In-memory file system for testing
137
+ */
138
+ declare const createMemoryFileSystem: (initialFiles?: Record<string, string>) => FileSystem & {
139
+ files: Record<string, string>;
140
+ };
141
+ /**
142
+ * Schema field definition for contract generation
143
+ */
144
+ interface SchemaField {
145
+ name: string;
146
+ type: 'string' | 'number' | 'boolean' | 'date' | 'datetime' | 'array' | 'object';
147
+ optional?: boolean;
148
+ }
149
+ /**
150
+ * Options for contract generation
151
+ */
152
+ interface GenerateContractOptions {
153
+ /** Event type (e.g., 'order.created') */
154
+ eventType: string;
155
+ /** Schema fields */
156
+ fields?: SchemaField[];
157
+ /** Base path for contracts (e.g., 'packages/contracts/src') */
158
+ basePath: string;
159
+ /** Package scope for imports (e.g., '@crossdelta') */
160
+ scope?: string;
161
+ /** Force overwrite existing files */
162
+ force?: boolean;
163
+ }
164
+ /**
165
+ * Options for event handler generation
166
+ */
167
+ interface GenerateEventHandlerOptions {
168
+ /** Event type (e.g., 'order.created') */
169
+ eventType: string;
170
+ /** Base path for service (e.g., 'services/orders/src') */
171
+ basePath: string;
172
+ /** Contract package name (e.g., '@crossdelta/contracts') */
173
+ contractsPackage?: string;
174
+ /** Force overwrite existing files */
175
+ force?: boolean;
176
+ }
177
+ /**
178
+ * Options for mock generation
179
+ */
180
+ interface GenerateMockOptions {
181
+ /** Event type (e.g., 'order.created') */
182
+ eventType: string;
183
+ /** Base path for mocks (e.g., 'packages/contracts/src/__mocks__') */
184
+ basePath: string;
185
+ /** Schema fields to generate mock data for */
186
+ fields?: SchemaField[];
187
+ /** Force overwrite existing files */
188
+ force?: boolean;
189
+ }
190
+
191
+ /**
192
+ * Contract Generator
193
+ *
194
+ * Pure function for generating event contract files
195
+ */
196
+
197
+ /**
198
+ * Generate contract file content
199
+ */
200
+ declare const generateContractContent: (options: GenerateContractOptions) => string;
201
+ /**
202
+ * Get the full path for a contract file
203
+ */
204
+ declare const getContractFilePath: (eventType: string, basePath: string) => string;
205
+ /**
206
+ * Generate a contract file
207
+ *
208
+ * Returns ChangeResult indicating if file was created, updated, or skipped.
209
+ *
210
+ * @example
211
+ * generateContract({
212
+ * eventType: 'order.created',
213
+ * basePath: 'packages/contracts/src',
214
+ * fields: [
215
+ * { name: 'orderId', type: 'string' },
216
+ * { name: 'total', type: 'number' },
217
+ * ],
218
+ * })
219
+ */
220
+ declare const generateContract: (options: GenerateContractOptions, fs?: FileSystem) => ChangeResult<string>;
221
+
222
+ /**
223
+ * Handler Generator
224
+ *
225
+ * Pure function for generating event handler files
226
+ */
227
+
228
+ /**
229
+ * Generate handler file content
230
+ */
231
+ declare const generateEventHandlerContent: (options: GenerateEventHandlerOptions) => string;
232
+ /**
233
+ * Get the full path for a handler file
234
+ */
235
+ declare const getHandlerFilePath: (eventType: string, basePath: string) => string;
236
+ /**
237
+ * Generate an event handler file
238
+ *
239
+ * @example
240
+ * generateEventHandler({
241
+ * eventType: 'order.created',
242
+ * basePath: 'services/orders/src',
243
+ * contractsPackage: '@my-org/contracts',
244
+ * })
245
+ */
246
+ declare const generateEventHandler: (options: GenerateEventHandlerOptions, fs?: FileSystem) => ChangeResult<string>;
247
+
248
+ /**
249
+ * Mock Generator
250
+ *
251
+ * Pure functions for generating event mock files (TypeScript and JSON formats).
252
+ * Supports optional @faker-js/faker for realistic mock data.
253
+ */
254
+
255
+ interface JsonMockData {
256
+ eventName: string;
257
+ description: string;
258
+ data: Record<string, unknown>;
259
+ faker?: Record<string, string>;
260
+ }
261
+ /**
262
+ * Initialize faker (call once at startup if you want faker support)
263
+ */
264
+ declare const initFaker: () => Promise<boolean>;
265
+ /**
266
+ * Generate mock file content
267
+ */
268
+ declare const generateMockContent: (options: GenerateMockOptions) => string;
269
+ /**
270
+ * Get the full path for a mock file
271
+ */
272
+ declare const getMockFilePath: (eventType: string, basePath: string) => string;
273
+ /**
274
+ * Generate a mock file
275
+ *
276
+ * @example
277
+ * generateMock({
278
+ * eventType: 'order.created',
279
+ * basePath: 'packages/contracts/src/__mocks__',
280
+ * fields: [
281
+ * { name: 'orderId', type: 'string' },
282
+ * { name: 'total', type: 'number' },
283
+ * ],
284
+ * })
285
+ */
286
+ declare const generateMock: (options: GenerateMockOptions, fs?: FileSystem) => ChangeResult<string>;
287
+ /**
288
+ * Get the JSON mock file path for an event type
289
+ */
290
+ declare const getJsonMockPath: (eventType: string, contractsPath: string) => string;
291
+ /**
292
+ * Check if a JSON mock file exists
293
+ */
294
+ declare const jsonMockExists: (eventType: string, contractsPath: string, fs?: FileSystem) => boolean;
295
+ /**
296
+ * Load JSON mock data for an event type
297
+ */
298
+ declare const loadJsonMock: (eventType: string, contractsPath: string, fs?: FileSystem) => JsonMockData | null;
299
+ /**
300
+ * Generate and save a JSON mock file for an event type
301
+ */
302
+ declare const generateJsonMock: (options: {
303
+ eventType: string;
304
+ contractsPath: string;
305
+ fields?: SchemaField[];
306
+ force?: boolean;
307
+ /** Use @faker-js/faker for realistic data */
308
+ useFaker?: boolean;
309
+ }, fs?: FileSystem) => ChangeResult<string>;
310
+ /**
311
+ * Generate JSON mock from existing contract file
312
+ */
313
+ declare const generateJsonMockFromContract: (eventType: string, contractsPath: string, options?: {
314
+ useFaker?: boolean;
315
+ }, fs?: FileSystem) => ChangeResult<string> | null;
316
+
317
+ /**
318
+ * Simple options for creating an event
319
+ */
320
+ interface CreateEventOptions {
321
+ /** Schema fields as string (e.g., 'orderId:string,total:number') or array */
322
+ fields?: string | SchemaField[];
323
+ /** Service path for handler (e.g., 'services/orders') */
324
+ service?: string;
325
+ /** Base path for contracts (default: 'packages/contracts/src') */
326
+ contractsPath?: string;
327
+ /** Base path for mocks (optional) */
328
+ mocksPath?: string;
329
+ /** Overwrite existing files */
330
+ force?: boolean;
331
+ }
332
+ /**
333
+ * Create an event contract (and optionally handler + mock)
334
+ *
335
+ * @example
336
+ * ```typescript
337
+ * import { createEvent } from '@crossdelta/cloudevents'
338
+ *
339
+ * // Simple: just the event type (interactive)
340
+ * await createEvent('order.created')
341
+ *
342
+ * // With fields
343
+ * await createEvent('order.created', {
344
+ * fields: 'orderId:string,total:number,customerId:string'
345
+ * })
346
+ *
347
+ * // With handler
348
+ * await createEvent('order.created', {
349
+ * fields: 'orderId:string,total:number',
350
+ * service: 'services/orders'
351
+ * })
352
+ * ```
353
+ */
354
+ declare const createEvent: (eventType: string, options?: CreateEventOptions) => Promise<{
355
+ created: string[];
356
+ skipped: string[];
357
+ effects: DomainEffect[];
358
+ }>;
359
+ /**
360
+ * List all event types in the workspace
361
+ *
362
+ * @example
363
+ * ```typescript
364
+ * import { listEvents } from '@crossdelta/cloudevents'
365
+ *
366
+ * // List all
367
+ * const events = await listEvents()
368
+ * // ['order.created', 'order.updated', 'customer.created']
369
+ *
370
+ * // Filter by pattern
371
+ * const orderEvents = await listEvents({ pattern: 'order' })
372
+ * // ['order.created', 'order.updated']
373
+ * ```
374
+ */
375
+ declare const listEvents: (options?: {
376
+ pattern?: string;
377
+ contractsPath?: string;
378
+ }) => Promise<string[]>;
379
+ /**
380
+ * Publish an event to NATS
381
+ *
382
+ * @example
383
+ * ```typescript
384
+ * import { publishEvent } from '@crossdelta/cloudevents'
385
+ *
386
+ * await publishEvent('order.created', {
387
+ * orderId: 'ord_123',
388
+ * total: 99.99,
389
+ * customerId: 'cus_456'
390
+ * })
391
+ * ```
392
+ */
393
+ declare const publishEvent: (eventType: string, data: Record<string, unknown>, options?: {
394
+ natsUrl?: string;
395
+ contractsPath?: string;
396
+ }) => Promise<{
397
+ success: boolean;
398
+ }>;
399
+
49
400
  /**
50
401
  * Domain Types
51
402
  *
@@ -254,6 +605,185 @@ declare function eventSchema<T extends Record<string, ZodTypeAny>>(schema: T & {
254
605
  type: ZodTypeAny;
255
606
  } extends infer T_1 ? { -readonly [P in keyof T_1]: T_1[P]; } : never, z.core.$strip>;
256
607
 
608
+ /**
609
+ * Pluralization Utilities
610
+ *
611
+ * Re-exports from the 'pluralize' library for consistent pluralization.
612
+ * Used by both cloudevents (subject derivation) and platform-sdk (contract generation).
613
+ */
614
+ /**
615
+ * Convert singular word to plural
616
+ *
617
+ * @example pluralize('order') => 'orders'
618
+ * @example pluralize('policy') => 'policies'
619
+ * @example pluralize('max') => 'maxes'
620
+ * @example pluralize('batch') => 'batches'
621
+ * @example pluralize('bus') => 'buses'
622
+ * @example pluralize('products') => 'products' (already plural)
623
+ */
624
+ declare const pluralize: (word: string) => string;
625
+ /**
626
+ * Convert plural word to singular
627
+ *
628
+ * @example singularize('orders') => 'order'
629
+ * @example singularize('policies') => 'policy'
630
+ * @example singularize('maxes') => 'max'
631
+ * @example singularize('batches') => 'batch'
632
+ */
633
+ declare const singularize: (word: string) => string;
634
+
635
+ /**
636
+ * Event Naming Domain
637
+ *
638
+ * Central authority for all event naming conventions:
639
+ * - Event type format and validation
640
+ * - Pluralization rules for streams/domains
641
+ * - Name derivation (schema, contract, handler, etc.)
642
+ * - Path structure for contracts and handlers
643
+ */
644
+
645
+ /**
646
+ * Derived names from an event type
647
+ */
648
+ interface EventNames {
649
+ /** Original event type (e.g., 'order.created') */
650
+ eventType: string;
651
+ /** Event type in kebab-case (e.g., 'order-created') */
652
+ kebab: string;
653
+ /** Event type in PascalCase (e.g., 'OrderCreated') */
654
+ pascal: string;
655
+ /** Schema name - singular PascalCase (e.g., 'OrderCreatedSchema') */
656
+ schemaName: string;
657
+ /** Type name - singular PascalCase (e.g., 'OrderCreatedData') */
658
+ typeName: string;
659
+ /** Contract name - plural PascalCase (e.g., 'OrdersCreatedContract') */
660
+ contractName: string;
661
+ /** Handler filename (e.g., 'order-created.handler.ts') */
662
+ handlerFile: string;
663
+ /** Stream name - uppercase plural (e.g., 'ORDERS') */
664
+ streamName: string;
665
+ /** Domain folder - lowercase plural (e.g., 'customers') */
666
+ domain: string;
667
+ /** Event action part (e.g., 'created' from 'order.created') */
668
+ action: string;
669
+ /** Namespace part - singular (e.g., 'order' from 'order.created') */
670
+ namespace: string;
671
+ }
672
+ /**
673
+ * Event type validation result
674
+ */
675
+ interface EventTypeValidation {
676
+ valid: boolean;
677
+ errors: string[];
678
+ }
679
+ /**
680
+ * Contract file path structure
681
+ */
682
+ interface ContractPaths {
683
+ /** Relative path from contracts root (e.g., 'events/orders/created.ts') */
684
+ relativePath: string;
685
+ /** Domain folder (e.g., 'orders') */
686
+ folder: string;
687
+ /** Filename without extension (e.g., 'created') */
688
+ filename: string;
689
+ }
690
+ /**
691
+ * Convert string to kebab-case
692
+ * Handles dots as separators
693
+ */
694
+ declare const toKebabCase: (str: string) => string;
695
+ /**
696
+ * Convert string to PascalCase
697
+ * Handles dots and dashes as word separators
698
+ */
699
+ declare const toPascalCase: (str: string) => string;
700
+ /**
701
+ * Validate an event type string
702
+ *
703
+ * Rules:
704
+ * - Must contain at least one dot (namespace.action)
705
+ * - Must be lowercase
706
+ * - Must not start/end with dots
707
+ * - Namespace must be singular (will be pluralized for domain)
708
+ */
709
+ declare const validateEventType: (eventType: string) => EventTypeValidation;
710
+ /**
711
+ * Check if an event type is valid
712
+ */
713
+ declare const isValidEventType: (eventType: string) => boolean;
714
+ /**
715
+ * Derive all names from an event type
716
+ *
717
+ * @example
718
+ * deriveEventNames('order.created')
719
+ * // {
720
+ * // eventType: 'order.created',
721
+ * // kebab: 'order-created',
722
+ * // pascal: 'OrderCreated',
723
+ * // schemaName: 'OrderCreatedSchema',
724
+ * // typeName: 'OrderCreatedData',
725
+ * // contractName: 'OrdersCreatedContract',
726
+ * // handlerFile: 'order-created.handler.ts',
727
+ * // streamName: 'ORDERS',
728
+ * // domain: 'orders',
729
+ * // action: 'created',
730
+ * // namespace: 'order',
731
+ * // }
732
+ */
733
+ declare const deriveEventNames: (eventType: string) => EventNames;
734
+ /**
735
+ * Get contract file paths from an event type
736
+ *
737
+ * @example
738
+ * getContractPaths('order.created')
739
+ * // {
740
+ * // relativePath: 'events/orders/created.ts',
741
+ * // folder: 'orders',
742
+ * // filename: 'created',
743
+ * // }
744
+ */
745
+ declare const getContractPaths: (eventType: string) => ContractPaths;
746
+ /**
747
+ * Get handler file path from an event type
748
+ *
749
+ * @example
750
+ * getHandlerPath('order.created')
751
+ * // 'events/order-created.handler.ts'
752
+ */
753
+ declare const getHandlerPath: (eventType: string) => string;
754
+ /**
755
+ * Get stream name from an event type
756
+ *
757
+ * @example
758
+ * getStreamName('order.created') // 'ORDERS'
759
+ * getStreamName('customer.updated') // 'CUSTOMERS'
760
+ */
761
+ declare const getStreamName: (eventType: string) => string;
762
+ /**
763
+ * Parse an event type from a handler filename
764
+ *
765
+ * @example
766
+ * parseEventTypeFromHandler('order-created.handler.ts') // 'order.created'
767
+ * parseEventTypeFromHandler('customer-profile-updated.handler.ts') // 'customer-profile.updated'
768
+ */
769
+ declare const parseEventTypeFromHandler: (filename: string) => string | null;
770
+ /**
771
+ * Parse an event type from a contract filename
772
+ *
773
+ * @example
774
+ * parseEventTypeFromContract('orders/created.ts') // 'order.created'
775
+ * parseEventTypeFromContract('customers/profile-updated.ts') // 'customer.profile-updated'
776
+ */
777
+ declare const parseEventTypeFromContract: (path: string) => string | null;
778
+ /**
779
+ * Normalize subject from event type
780
+ * Used for NATS subject derivation
781
+ *
782
+ * @example
783
+ * normalizeSubject('order.created') // 'orders.created'
784
+ */
785
+ declare const normalizeSubject: (eventType: string) => string;
786
+
257
787
  /**
258
788
  * Domain Validation
259
789
  *
@@ -269,6 +799,150 @@ declare function eventSchema<T extends Record<string, ZodTypeAny>>(schema: T & {
269
799
  */
270
800
  declare const extractTypeFromSchema: (schema: ZodTypeAny) => string | undefined;
271
801
 
802
+ /**
803
+ * Create Event Flow
804
+ *
805
+ * Interactive flow for creating event contracts, handlers, and mocks
806
+ */
807
+
808
+ /**
809
+ * Configuration for event flows
810
+ */
811
+ interface FlowConfig$2 {
812
+ /** Base path for contracts (e.g., 'packages/contracts/src') */
813
+ contractsPath: string;
814
+ /** Base path for mocks (e.g., 'packages/contracts/src/__mocks__') */
815
+ mocksPath?: string;
816
+ /** Contracts package name (e.g., '@my-platform/contracts') */
817
+ contractsPackage?: string;
818
+ /** File system abstraction (defaults to node fs) */
819
+ fs?: FileSystem;
820
+ }
821
+ /**
822
+ * Context for create event flow
823
+ *
824
+ * Flow-specific fields (user-provided):
825
+ * - eventType: Event name like "order.created"
826
+ * - servicePath: Optional service for handler creation
827
+ * - fieldsInput: Raw input string from user (internal)
828
+ * - fields: Parsed schema fields
829
+ * - availableServices: Services available for handler creation
830
+ * - force: Overwrite existing files
831
+ * - config: Flow configuration (paths, fs)
832
+ *
833
+ * Infrastructure fields (auto-initialized by ensure() steps):
834
+ * - _fs: Filesystem abstraction (lazy-init via flow.ensure())
835
+ * - _generation: Generation tracker (lazy-init via flow.ensure())
836
+ *
837
+ * @see FsContextMixin for _fs details
838
+ * @see GenerationContextMixin for _generation details
839
+ */
840
+ interface CreateEventContext extends FlowContext, FsContextMixin, GenerationContextMixin<DomainEffect> {
841
+ /** Event type (e.g., 'order.created') */
842
+ eventType: string;
843
+ /** Service path for handler generation */
844
+ servicePath?: string;
845
+ /** Schema fields as comma-separated string */
846
+ fieldsInput?: string;
847
+ /** Parsed schema fields */
848
+ fields?: Array<{
849
+ name: string;
850
+ type: string;
851
+ optional?: boolean;
852
+ }>;
853
+ /** Available services for selection */
854
+ availableServices?: string[];
855
+ /** Force overwrite existing files */
856
+ force?: boolean;
857
+ /** Flow configuration */
858
+ config: FlowConfig$2;
859
+ /** Internal filesystem (lazy-initialized) */
860
+ _fs?: FileSystem;
861
+ }
862
+ declare const parseFieldsInput: (input: string) => SchemaField[];
863
+ /**
864
+ * Complete flow for creating event contracts
865
+ *
866
+ * Steps:
867
+ * 1. Initialize infrastructure (_fs, _generation)
868
+ * 2. Get event type (e.g., "order.created")
869
+ * 3. Get schema fields (optional)
870
+ * 4. Select service for handler (optional)
871
+ * 5. Generate files (contract, mock, handler, exports)
872
+ * 6. Print summary
873
+ */
874
+ declare const createEventFlowSteps: FlowStep<CreateEventContext>[];
875
+
876
+ /**
877
+ * List Events Flow
878
+ *
879
+ * Flow for discovering and listing event types in the workspace
880
+ */
881
+
882
+ /**
883
+ * Configuration for event flows
884
+ */
885
+ interface FlowConfig$1 {
886
+ /** Base path for contracts (e.g., 'packages/contracts/src') */
887
+ contractsPath: string;
888
+ /** Base path for mocks (e.g., 'packages/contracts/src/__mocks__') */
889
+ mocksPath?: string;
890
+ /** Contracts package name (e.g., '@my-platform/contracts') */
891
+ contractsPackage?: string;
892
+ }
893
+ /**
894
+ * Context for list events flow
895
+ */
896
+ interface ListEventsContext extends FlowContext {
897
+ /** Filter pattern for event types */
898
+ pattern?: string;
899
+ /** Discovered event types */
900
+ eventTypes?: string[];
901
+ /** Flow configuration */
902
+ config: FlowConfig$1;
903
+ }
904
+ declare const discoverEventTypes: (contractsPath: string, pattern?: string) => string[];
905
+ declare const listEventsFlowSteps: FlowStep<ListEventsContext>[];
906
+
907
+ /**
908
+ * Publish Event Flow
909
+ *
910
+ * Flow for publishing events to NATS
911
+ */
912
+
913
+ /**
914
+ * Configuration for event flows
915
+ */
916
+ interface FlowConfig {
917
+ /** Base path for contracts (e.g., 'packages/contracts/src') */
918
+ contractsPath: string;
919
+ /** NATS connection URL */
920
+ natsUrl?: string;
921
+ }
922
+ /**
923
+ * Context for publish event flow
924
+ */
925
+ interface PublishEventContext extends FlowContext {
926
+ /** Event type to publish */
927
+ eventType: string;
928
+ /** Event data as JSON string */
929
+ dataInput?: string;
930
+ /** Parsed event data */
931
+ data?: Record<string, unknown>;
932
+ /** NATS connection URL */
933
+ natsUrl?: string;
934
+ /** Whether publish was successful */
935
+ published?: boolean;
936
+ /** Whether mock data was used */
937
+ usedMock?: boolean;
938
+ /** Flow configuration */
939
+ config: FlowConfig & {
940
+ natsUrl?: string;
941
+ };
942
+ }
943
+ declare const parseDataInput: (input: string) => Record<string, unknown> | null;
944
+ declare const publishEventFlowSteps: FlowStep<PublishEventContext>[];
945
+
272
946
  /**
273
947
  * Handler Cache Management
274
948
  * Immutable cache operations for CloudEvents handlers
@@ -502,12 +1176,42 @@ interface CloudEventsOptions {
502
1176
  */
503
1177
  declare function cloudEvents(options?: CloudEventsOptions): (ctx: Context, next: () => Promise<void>) => Promise<void | Response>;
504
1178
 
1179
+ /**
1180
+ * PfPlugin Adapter
1181
+ *
1182
+ * Exposes cloudevents functionality as a pf plugin.
1183
+ * Architectural rules:
1184
+ * - cloudevents IMPORTS Pf* interfaces from platform-sdk
1185
+ * - Uses flows for all commands (CLI + MCP)
1186
+ * - Returns effects for workspace mutations
1187
+ */
1188
+
1189
+ interface CloudEventsPfPluginOptions {
1190
+ contractsPath?: string;
1191
+ contractsPackage?: string;
1192
+ mocksPath?: string;
1193
+ availableServices?: string[];
1194
+ natsUrl?: string;
1195
+ }
1196
+ declare const createPfPlugin: (options?: CloudEventsPfPluginOptions) => PfPlugin;
1197
+
505
1198
  interface PublishNatsEventOptions {
506
1199
  servers?: string;
507
1200
  source?: string;
508
1201
  subject?: string;
509
1202
  tenantId?: string;
1203
+ /** Close connection after publishing (for CLI tools) */
1204
+ closeAfterPublish?: boolean;
510
1205
  }
1206
+ /**
1207
+ * Close the NATS connection and reset state
1208
+ */
1209
+ declare const closeConnection: () => Promise<void>;
1210
+ /**
1211
+ * Reset publisher state (for testing only)
1212
+ * @internal
1213
+ */
1214
+ declare const __resetNatsPublisher: () => Promise<void>;
511
1215
  declare const deriveSubjectFromType: (eventType: string, config?: RoutingConfig) => string;
512
1216
  declare const deriveStreamFromType: (eventType: string, config?: RoutingConfig) => string | undefined;
513
1217
  declare const publishNatsRawEvent: (subjectName: string, eventType: string, eventData: unknown, options?: PublishNatsEventOptions) => Promise<string>;
@@ -518,7 +1222,6 @@ declare const publish: (eventTypeOrContract: string | {
518
1222
  subject?: string;
519
1223
  };
520
1224
  }, eventData: unknown, options?: PublishNatsEventOptions) => Promise<string>;
521
- declare const __resetNatsPublisher: () => void;
522
1225
 
523
1226
  interface PublishEventOptions {
524
1227
  projectId?: string;
@@ -527,26 +1230,6 @@ interface PublishEventOptions {
527
1230
  subject?: string;
528
1231
  attributes?: Record<string, string>;
529
1232
  }
530
- /**
531
- * Publishes an event using a Zod schema for validation and type extraction.
532
- * Automatically extracts the event type from the schema and creates a CloudEvent.
533
- *
534
- * @param topicName - PubSub topic name
535
- * @param schema - Zod schema that defines the event structure and type
536
- * @param eventData - Event data that must match the schema
537
- * @param options - Optional PubSub configuration
538
- * @returns Promise resolving to the published message ID
539
- *
540
- * @example
541
- * ```typescript
542
- * await publishEvent(
543
- * 'customer-events',
544
- * CustomerCreatedSchema,
545
- * { customer: { id: '123', email: 'test@example.com' } }
546
- * )
547
- * ```
548
- */
549
- declare function publishEvent<T extends ZodTypeAny>(topicName: string, schema: T, eventData: unknown, options?: PublishEventOptions): Promise<string>;
550
1233
  /**
551
1234
  * Raw event publisher - bypasses schema validation.
552
1235
  * Use this when you need direct control over the event type and data.
@@ -809,34 +1492,4 @@ interface NatsConsumerOptions extends Pick<CloudEventsOptions, 'quarantineTopic'
809
1492
  */
810
1493
  declare function consumeNatsEvents(options: NatsConsumerOptions): Promise<Subscription>;
811
1494
 
812
- /**
813
- * Pluralization Utilities
814
- *
815
- * Central place for English pluralization rules.
816
- * Used by both cloudevents (subject derivation) and platform-sdk (contract generation).
817
- *
818
- * Rules follow standard English grammar:
819
- * - consonant + y → ies (policy → policies)
820
- * - s, sh, ch, x → +es (max → maxes, batch → batches)
821
- * - all other → +s (order → orders)
822
- */
823
- /**
824
- * Convert singular word to plural
825
- *
826
- * @example pluralize('order') => 'orders'
827
- * @example pluralize('policy') => 'policies'
828
- * @example pluralize('max') => 'maxes'
829
- * @example pluralize('batch') => 'batches'
830
- */
831
- declare const pluralize: (word: string) => string;
832
- /**
833
- * Convert plural word to singular (inverse of pluralize)
834
- *
835
- * @example singularize('orders') => 'order'
836
- * @example singularize('policies') => 'policy'
837
- * @example singularize('maxes') => 'max'
838
- * @example singularize('batches') => 'batch'
839
- */
840
- declare const singularize: (word: string) => string;
841
-
842
- export { type ChannelConfig, type ChannelMetadata, type EnrichedEvent, type EventContext, type HandleEventOptions, type IdempotencyStore, type InferEventData, type JetStreamConsumerOptions, type JetStreamStreamOptions, type JetStreamStreamsConsumerOptions, type JetStreamStreamsOptions, type PublishEventOptions, type PublishNatsEventOptions, type RoutingConfig, type StreamConfig, type StreamDefinition, __resetNatsPublisher, checkAndMarkProcessed, clearHandlerCache, cloudEvents, consumeJetStreamEvents, consumeJetStreamStreams, consumeJetStreams, consumeNatsEvents, createContract, createInMemoryIdempotencyStore, deriveStreamFromType, deriveSubjectFromType, ensureJetStreamStream, ensureJetStreamStreams, ensureJetStreams, eventSchema, extractTypeFromSchema, getDefaultIdempotencyStore, handleEvent, parseEventFromContext, pluralize, publish, publishEvent, publishNatsEvent, publishNatsRawEvent, publishRawEvent, resetDefaultIdempotencyStore, singularize };
1495
+ export { type ChannelConfig, type ChannelMetadata, type CloudEventsPfPluginOptions, type ContractCreatedEffect, type ContractPaths, type CreateEventContext, type CreateEventOptions, type DomainEffect, type EnrichedEvent, type EventContext, type EventNames, type EventTypeValidation, type FileSystem, type HandleEventOptions, type HandlerCreatedEffect, type IdempotencyStore, type InferEventData, type JetStreamConsumerOptions, type JetStreamStreamOptions, type JetStreamStreamsConsumerOptions, type JetStreamStreamsOptions, type ListEventsContext, type PublishEventContext, type PublishEventOptions, type PublishNatsEventOptions, type RoutingConfig, type SchemaField, type StreamConfig, type StreamDefinition, type StreamWiredEffect, __resetNatsPublisher, checkAndMarkProcessed, clearHandlerCache, closeConnection, cloudEvents, consumeJetStreamEvents, consumeJetStreamStreams, consumeJetStreams, consumeNatsEvents, contractCreated, createContract, createEvent, createEventFlowSteps, createInMemoryIdempotencyStore, createMemoryFileSystem, createPfPlugin, deriveEventNames, deriveStreamFromType, deriveSubjectFromType, discoverEventTypes, ensureJetStreamStream, ensureJetStreamStreams, ensureJetStreams, eventSchema, extractTypeFromSchema, generateContract, generateContractContent, generateEventHandler, generateEventHandlerContent, generateJsonMock, generateJsonMockFromContract, generateMock, generateMockContent, getContractFilePath, getContractPaths, getDefaultIdempotencyStore, getHandlerFilePath, getHandlerPath, getJsonMockPath, getMockFilePath, getStreamName, handleEvent, handlerCreated, initFaker, isValidEventType, jsonMockExists, listEvents, listEventsFlowSteps, loadJsonMock, normalizeSubject, parseDataInput, parseEventFromContext, parseEventTypeFromContract, parseEventTypeFromHandler, parseFieldsInput, pluralize, publish, publishEvent, publishEventFlowSteps, publishNatsEvent, publishNatsRawEvent, publishRawEvent, resetDefaultIdempotencyStore, singularize, streamWired, toKebabCase, toPascalCase, validateEventType };