@eventcatalog/cli 0.3.3 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +134 -31
- package/dist/cli/index.js +69 -10
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/index.mjs +69 -10
- package/dist/cli/index.mjs.map +1 -1
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
## @eventcatalog/cli
|
|
2
2
|
|
|
3
|
-
Command-line interface for [EventCatalog](https://eventcatalog.dev).
|
|
3
|
+
Command-line interface for [EventCatalog](https://eventcatalog.dev). Import and export catalogs using the [EventCatalog DSL](https://www.eventcatalog.dev/docs/development/dsl/introduction), run SDK functions directly from your terminal, and automate your EventCatalog workflows.
|
|
4
4
|
|
|
5
5
|
### Installation
|
|
6
6
|
|
|
@@ -11,7 +11,7 @@ npm i @eventcatalog/cli
|
|
|
11
11
|
### Running with npx (no installation required)
|
|
12
12
|
|
|
13
13
|
```bash
|
|
14
|
-
npx @eventcatalog/cli --dir <catalog-path> <
|
|
14
|
+
npx @eventcatalog/cli --dir <catalog-path> <command> [args...]
|
|
15
15
|
```
|
|
16
16
|
|
|
17
17
|
### Running after installation
|
|
@@ -19,77 +19,180 @@ npx @eventcatalog/cli --dir <catalog-path> <function-name> [args...]
|
|
|
19
19
|
If you've installed the package, the `eventcatalog` command is available:
|
|
20
20
|
|
|
21
21
|
```bash
|
|
22
|
-
eventcatalog --dir <catalog-path> <
|
|
22
|
+
eventcatalog --dir <catalog-path> <command> [args...]
|
|
23
23
|
```
|
|
24
24
|
|
|
25
|
-
###
|
|
25
|
+
### Global Options
|
|
26
26
|
|
|
27
|
-
|
|
27
|
+
| Option | Description | Default |
|
|
28
|
+
| ------------------ | ------------------------------ | ----------------------- |
|
|
29
|
+
| `-d, --dir <path>` | Path to your catalog directory | `.` (current directory) |
|
|
30
|
+
|
|
31
|
+
---
|
|
32
|
+
|
|
33
|
+
### Commands
|
|
34
|
+
|
|
35
|
+
#### `import` — Import DSL files into your catalog
|
|
36
|
+
|
|
37
|
+
Parse `.ec` (EventCatalog DSL) files and write them as catalog resources (markdown + frontmatter).
|
|
28
38
|
|
|
29
39
|
```bash
|
|
30
|
-
|
|
40
|
+
eventcatalog import [files...] [options]
|
|
31
41
|
```
|
|
32
42
|
|
|
33
|
-
**
|
|
43
|
+
**Options:**
|
|
44
|
+
|
|
45
|
+
| Option | Description |
|
|
46
|
+
| ----------- | ------------------------------------------------------------ |
|
|
47
|
+
| `--stdin` | Read DSL from stdin instead of files |
|
|
48
|
+
| `--dry-run` | Preview changes without writing to disk |
|
|
49
|
+
| `--flat` | Write all resources at the top level (no nested directories) |
|
|
50
|
+
| `--no-init` | Skip the interactive catalog scaffolding prompt |
|
|
51
|
+
|
|
52
|
+
**Examples:**
|
|
34
53
|
|
|
35
54
|
```bash
|
|
36
|
-
|
|
37
|
-
|
|
55
|
+
# Import a single DSL file
|
|
56
|
+
eventcatalog import architecture.ec
|
|
57
|
+
|
|
58
|
+
# Import multiple files
|
|
59
|
+
eventcatalog import services.ec events.ec domains.ec
|
|
60
|
+
|
|
61
|
+
# Pipe DSL from another tool
|
|
62
|
+
cat architecture.ec | eventcatalog import --stdin
|
|
63
|
+
|
|
64
|
+
# Preview what would change
|
|
65
|
+
eventcatalog import architecture.ec --dry-run
|
|
66
|
+
|
|
67
|
+
# Import without nesting services inside domains
|
|
68
|
+
eventcatalog import architecture.ec --flat
|
|
38
69
|
```
|
|
39
70
|
|
|
40
|
-
**
|
|
71
|
+
**Behaviors:**
|
|
72
|
+
|
|
73
|
+
- If no `eventcatalog.config.js` exists, you'll be prompted to scaffold a new catalog (skip with `--no-init`).
|
|
74
|
+
- Importing a newer version of an existing resource automatically versions the old one.
|
|
75
|
+
- Re-importing the same version overwrites the existing resource.
|
|
76
|
+
- Referenced resources that aren't defined in the DSL (e.g., `sends event OrderCreated` without an inline body) are created as stubs at version `0.0.1`.
|
|
77
|
+
- Existing resource locations are preserved — updates go to where the resource already lives.
|
|
78
|
+
|
|
79
|
+
---
|
|
80
|
+
|
|
81
|
+
#### `export` — Export catalog resources to DSL
|
|
82
|
+
|
|
83
|
+
Convert catalog resources back into EventCatalog DSL (`.ec`) format.
|
|
41
84
|
|
|
42
85
|
```bash
|
|
43
|
-
|
|
44
|
-
npx @eventcatalog/cli --dir ./my-catalog getEvents '{"latestOnly":true}'
|
|
86
|
+
eventcatalog export [options]
|
|
45
87
|
```
|
|
46
88
|
|
|
47
|
-
**
|
|
89
|
+
**Options:**
|
|
90
|
+
|
|
91
|
+
| Option | Description |
|
|
92
|
+
| --------------------- | -------------------------------------------------------------------------------------------- |
|
|
93
|
+
| `--all` | Export the entire catalog |
|
|
94
|
+
| `--resource <type>` | Resource type to export (`event`, `command`, `query`, `service`, `domain`, `channel`) |
|
|
95
|
+
| `--id <id>` | Export a specific resource by ID (requires `--resource`) |
|
|
96
|
+
| `--version <version>` | Export a specific version (requires `--resource` and `--id`) |
|
|
97
|
+
| `--hydrate` | Include referenced resources (e.g., messages referenced by a service) |
|
|
98
|
+
| `--stdout` | Print to stdout instead of writing a file |
|
|
99
|
+
| `--playground` | Open the exported DSL in the [EventCatalog Playground](https://playground.eventcatalog.dev/) |
|
|
100
|
+
| `--output <path>` | Custom output file path |
|
|
101
|
+
|
|
102
|
+
**Examples:**
|
|
48
103
|
|
|
49
104
|
```bash
|
|
50
|
-
|
|
105
|
+
# Export a single event
|
|
106
|
+
eventcatalog export --resource event --id OrderCreated --stdout
|
|
107
|
+
|
|
108
|
+
# Export all services with their referenced messages
|
|
109
|
+
eventcatalog export --resource service --hydrate --stdout
|
|
110
|
+
|
|
111
|
+
# Export the entire catalog to a file
|
|
112
|
+
eventcatalog export --all --output catalog.ec
|
|
113
|
+
|
|
114
|
+
# Export and open in the playground
|
|
115
|
+
eventcatalog export --all --playground
|
|
51
116
|
```
|
|
52
117
|
|
|
53
|
-
|
|
118
|
+
---
|
|
119
|
+
|
|
120
|
+
#### `list` — List available SDK functions
|
|
121
|
+
|
|
122
|
+
Display all SDK functions organized by category (Events, Commands, Queries, Services, Domains, etc.).
|
|
54
123
|
|
|
55
124
|
```bash
|
|
56
|
-
|
|
125
|
+
eventcatalog list
|
|
57
126
|
```
|
|
58
127
|
|
|
59
|
-
|
|
128
|
+
---
|
|
129
|
+
|
|
130
|
+
#### `<function>` — Run any SDK function
|
|
131
|
+
|
|
132
|
+
Any unrecognized command is treated as an SDK function call. Output is JSON.
|
|
60
133
|
|
|
61
134
|
```bash
|
|
62
|
-
|
|
135
|
+
eventcatalog <function-name> [args...]
|
|
63
136
|
```
|
|
64
137
|
|
|
65
|
-
|
|
138
|
+
**Examples:**
|
|
139
|
+
|
|
140
|
+
```bash
|
|
141
|
+
# Get an event (latest version)
|
|
142
|
+
eventcatalog --dir ./my-catalog getEvent "OrderCreated"
|
|
143
|
+
|
|
144
|
+
# Get a specific version
|
|
145
|
+
eventcatalog --dir ./my-catalog getEvent "OrderCreated" "1.0.0"
|
|
146
|
+
|
|
147
|
+
# Get all events with options
|
|
148
|
+
eventcatalog --dir ./my-catalog getEvents '{"latestOnly":true}'
|
|
66
149
|
|
|
67
|
-
|
|
150
|
+
# Write an event
|
|
151
|
+
eventcatalog --dir ./my-catalog writeEvent '{"id":"OrderCreated","name":"Order Created","version":"1.0.0","markdown":"# Order Created"}'
|
|
152
|
+
|
|
153
|
+
# Get a service
|
|
154
|
+
eventcatalog --dir ./my-catalog getService "InventoryService"
|
|
155
|
+
|
|
156
|
+
# Add an event to a service
|
|
157
|
+
eventcatalog --dir ./my-catalog addEventToService "InventoryService" "sends" '{"id":"OrderCreated","version":"1.0.0"}'
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
Run `eventcatalog list` to see all available functions.
|
|
161
|
+
|
|
162
|
+
---
|
|
163
|
+
|
|
164
|
+
### Piping and Composing
|
|
165
|
+
|
|
166
|
+
Output from SDK functions is JSON, making it easy to pipe to tools like `jq`:
|
|
68
167
|
|
|
69
168
|
```bash
|
|
70
|
-
#
|
|
71
|
-
|
|
169
|
+
# Filter events by version
|
|
170
|
+
eventcatalog --dir ./my-catalog getEvents | jq '.[] | select(.version == "1.0.0")'
|
|
72
171
|
|
|
73
172
|
# Count total events
|
|
74
|
-
|
|
173
|
+
eventcatalog --dir ./my-catalog getEvents | jq 'length'
|
|
75
174
|
|
|
76
175
|
# Extract event IDs
|
|
77
|
-
|
|
176
|
+
eventcatalog --dir ./my-catalog getEvents | jq '.[].id'
|
|
78
177
|
```
|
|
79
178
|
|
|
80
179
|
### Arguments Format
|
|
81
180
|
|
|
82
181
|
Arguments are automatically parsed:
|
|
83
182
|
|
|
84
|
-
- **JSON objects:** `'{"key":"value"}'`
|
|
85
|
-
- **JSON arrays:** `'["item1","item2"]'`
|
|
86
|
-
- **Booleans:** `true` or `false`
|
|
87
|
-
- **Numbers:** `42` or `3.14`
|
|
88
|
-
- **Strings:** anything else
|
|
183
|
+
- **JSON objects:** `'{"key":"value"}'` — parsed as object
|
|
184
|
+
- **JSON arrays:** `'["item1","item2"]'` — parsed as array
|
|
185
|
+
- **Booleans:** `true` or `false` — parsed as boolean
|
|
186
|
+
- **Numbers:** `42` or `3.14` — parsed as number
|
|
187
|
+
- **Strings:** anything else — kept as string
|
|
188
|
+
|
|
189
|
+
### Documentation
|
|
89
190
|
|
|
90
|
-
|
|
191
|
+
- [EventCatalog DSL](https://www.eventcatalog.dev/docs/development/dsl/introduction)
|
|
192
|
+
- [SDK reference](https://www.eventcatalog.dev/docs/sdk)
|
|
193
|
+
- [CLI documentation](https://www.eventcatalog.dev/docs/development/cli)
|
|
91
194
|
|
|
92
|
-
|
|
195
|
+
## Enterprise support
|
|
93
196
|
|
|
94
197
|
Interested in collaborating with us? Our offerings include dedicated support, priority assistance, feature development, custom integrations, and more.
|
|
95
198
|
|
package/dist/cli/index.js
CHANGED
|
@@ -250,19 +250,45 @@ ${items.join("\n\n")}`);
|
|
|
250
250
|
}
|
|
251
251
|
return sections.join("\n\n");
|
|
252
252
|
}
|
|
253
|
-
function
|
|
254
|
-
const
|
|
255
|
-
const
|
|
256
|
-
for (
|
|
257
|
-
const trimmed =
|
|
253
|
+
function extractResourceDefinitions(dsl, filterTypes) {
|
|
254
|
+
const results = [];
|
|
255
|
+
const lines = dsl.split("\n");
|
|
256
|
+
for (let i = 0; i < lines.length; i++) {
|
|
257
|
+
const trimmed = lines[i].trimStart();
|
|
258
258
|
const parts = trimmed.split(/\s/);
|
|
259
259
|
const keyword = parts[0];
|
|
260
260
|
const id = parts[1];
|
|
261
|
-
if (!
|
|
261
|
+
if (!filterTypes.includes(keyword)) continue;
|
|
262
262
|
if (!id || !trimmed.endsWith("{")) continue;
|
|
263
|
-
|
|
263
|
+
let version2;
|
|
264
|
+
for (let j = i + 1; j < lines.length; j++) {
|
|
265
|
+
const inner = lines[j].trim();
|
|
266
|
+
if (inner === "}") break;
|
|
267
|
+
const vMatch = inner.match(/^version\s+(.+)$/);
|
|
268
|
+
if (vMatch) {
|
|
269
|
+
version2 = vMatch[1];
|
|
270
|
+
break;
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
results.push({ keyword, id, version: version2 });
|
|
274
|
+
}
|
|
275
|
+
return results;
|
|
276
|
+
}
|
|
277
|
+
function buildVisualizerBlock(dsl, name, filterTypes) {
|
|
278
|
+
const types = Array.isArray(filterTypes) ? filterTypes : [filterTypes];
|
|
279
|
+
const definitions = extractResourceDefinitions(dsl, types);
|
|
280
|
+
if (definitions.length === 0) return "";
|
|
281
|
+
const counts = /* @__PURE__ */ new Map();
|
|
282
|
+
for (const def of definitions) {
|
|
283
|
+
const key = `${def.keyword}:${def.id}`;
|
|
284
|
+
counts.set(key, (counts.get(key) || 0) + 1);
|
|
264
285
|
}
|
|
265
|
-
|
|
286
|
+
const entries = definitions.map((def) => {
|
|
287
|
+
const key = `${def.keyword}:${def.id}`;
|
|
288
|
+
const needsVersion = (counts.get(key) || 0) > 1 && def.version;
|
|
289
|
+
const ref = needsVersion ? `${def.id}@${def.version}` : def.id;
|
|
290
|
+
return ` ${def.keyword} ${ref}`;
|
|
291
|
+
});
|
|
266
292
|
return `
|
|
267
293
|
visualizer main {
|
|
268
294
|
name "${name}"
|
|
@@ -356,7 +382,8 @@ async function exportResource(options) {
|
|
|
356
382
|
}
|
|
357
383
|
const rawDsl = await sdk.toDSL(data, { type, hydrate });
|
|
358
384
|
const grouped = hydrate ? groupDSLBlocks(rawDsl) : rawDsl;
|
|
359
|
-
const
|
|
385
|
+
const vizTypes = hydrate ? [...RESOURCE_TYPES] : [type];
|
|
386
|
+
const vizBlock = buildVisualizerBlock(grouped, `View of ${id}`, vizTypes);
|
|
360
387
|
const dsl = vizBlock ? `${grouped}
|
|
361
388
|
${vizBlock}` : grouped;
|
|
362
389
|
if (stdout) {
|
|
@@ -385,6 +412,17 @@ var import_node_crypto = require("crypto");
|
|
|
385
412
|
var import_node_readline = require("readline");
|
|
386
413
|
var import_gray_matter = __toESM(require("gray-matter"));
|
|
387
414
|
var import_sdk4 = __toESM(require("@eventcatalog/sdk"));
|
|
415
|
+
|
|
416
|
+
// src/cli/dsl-managed-keys.ts
|
|
417
|
+
var MESSAGE_MANAGED_KEYS = /* @__PURE__ */ new Set(["id", "name", "version", "owners", "deprecated", "draft", "summary"]);
|
|
418
|
+
var DSL_MANAGED_KEYS_BY_TYPE = {
|
|
419
|
+
domain: /* @__PURE__ */ new Set(["id", "name", "version", "owners", "deprecated", "draft", "summary", "services", "domains"]),
|
|
420
|
+
event: MESSAGE_MANAGED_KEYS,
|
|
421
|
+
command: MESSAGE_MANAGED_KEYS,
|
|
422
|
+
query: MESSAGE_MANAGED_KEYS
|
|
423
|
+
};
|
|
424
|
+
|
|
425
|
+
// src/cli/import.ts
|
|
388
426
|
function normalizeImportedFrontmatter(type, frontmatter) {
|
|
389
427
|
const normalized = { ...frontmatter };
|
|
390
428
|
if (type === "container") {
|
|
@@ -399,6 +437,27 @@ function normalizeImportedFrontmatter(type, frontmatter) {
|
|
|
399
437
|
}
|
|
400
438
|
return normalized;
|
|
401
439
|
}
|
|
440
|
+
function toFrontmatter(resource) {
|
|
441
|
+
if (!resource || typeof resource !== "object") return {};
|
|
442
|
+
const { markdown: _markdown, ...frontmatter } = resource;
|
|
443
|
+
return frontmatter;
|
|
444
|
+
}
|
|
445
|
+
function mergeImportedFrontmatter(type, incomingFrontmatter, existing, latest) {
|
|
446
|
+
const normalizedIncoming = normalizeImportedFrontmatter(type, incomingFrontmatter);
|
|
447
|
+
const managedKeys = DSL_MANAGED_KEYS_BY_TYPE[type];
|
|
448
|
+
if (!managedKeys) {
|
|
449
|
+
return normalizedIncoming;
|
|
450
|
+
}
|
|
451
|
+
const baseFrontmatter = toFrontmatter(existing ?? latest);
|
|
452
|
+
const preservedFrontmatter = { ...baseFrontmatter };
|
|
453
|
+
for (const key of managedKeys) {
|
|
454
|
+
delete preservedFrontmatter[key];
|
|
455
|
+
}
|
|
456
|
+
return {
|
|
457
|
+
...preservedFrontmatter,
|
|
458
|
+
...normalizedIncoming
|
|
459
|
+
};
|
|
460
|
+
}
|
|
402
461
|
var RESOURCE_TYPE_FROM_FOLDER = {
|
|
403
462
|
events: "event",
|
|
404
463
|
commands: "command",
|
|
@@ -945,7 +1004,7 @@ async function importDSL(options) {
|
|
|
945
1004
|
}
|
|
946
1005
|
}
|
|
947
1006
|
const resourceData = {
|
|
948
|
-
...
|
|
1007
|
+
...mergeImportedFrontmatter(resource.type, resource.frontmatter, existing, latest),
|
|
949
1008
|
markdown
|
|
950
1009
|
};
|
|
951
1010
|
const writeOptions = {
|