@keystrokehq/cli 0.0.38 → 0.0.39

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 CHANGED
@@ -210,6 +210,9 @@ keystroke search "put object"
210
210
  keystroke search "slack" --type integrations
211
211
  keystroke search "oauth" --type credentials --integration keystroke:slack
212
212
 
213
+ # --integration is valid for operations and credentials only (not --type integrations)
214
+ keystroke search "put" --integration aws-s3 --full
215
+
213
216
  keystroke operations list --integration aws-s3
214
217
  keystroke operations show aws-s3.put-object
215
218
  keystroke operations show aws-s3.put-object --schema --json
@@ -224,7 +227,8 @@ keystroke credentials definitions show keystroke:aws-s3
224
227
  Flags shared across discovery commands:
225
228
 
226
229
  - `--json` — machine-readable output (field names match shared-types schemas).
227
- - `--full` on `search`, `operations list`, and `credentials definitions list` — pass `include=full` for schemas and extended fields in one round-trip.
230
+ - `--full` on `search`, `operations list`, and `credentials definitions list` — pass `include=full` for schemas and extended fields in one round-trip. On `search`, `--full` adds operation schemas/safety flags and credential auth fields; for integrations it returns extended catalog fields (use `integrations show` for nested operation lists).
231
+ - `search --integration <id>` — restrict operations or credential-definition results to one integration; not valid with `--type integrations`.
228
232
 
229
233
  `keystroke credentials list` lists **your organization's credential sets**, not catalog definitions.
230
234
 
@@ -521,7 +521,7 @@ const logger = {
521
521
  };
522
522
  //#endregion
523
523
  //#region package.json
524
- var version = "0.0.38";
524
+ var version = "0.0.39";
525
525
  //#endregion
526
526
  //#region src/command-registry.ts
527
527
  const ROOT_OPTIONS_WITH_VALUES$1 = new Set([
@@ -598,7 +598,7 @@ const lazyCommandDefinitions = [
598
598
  },
599
599
  {
600
600
  name: "search",
601
- loadCommand: async () => (await import("./search-CQMgdp51.mjs")).createSearchCommand()
601
+ loadCommand: async () => (await import("./search-DdJpxHEs.mjs")).createSearchCommand()
602
602
  },
603
603
  {
604
604
  name: "skills",
@@ -3,7 +3,8 @@
3
3
  import { n as JsonOptionSchema, t as JSON_OPTION_CONFIG } from "./output-BPydP5tG.mjs";
4
4
  import { t as createTypedCommand } from "./commander-B_8QwPpe.mjs";
5
5
  import { z } from "zod";
6
- //#region src/commands/search/search.command.ts
6
+ //#region src/commands/search/search.schema.ts
7
+ const SEARCH_INTEGRATION_FILTER_ERROR = "--integration applies to operations and credentials search only.";
7
8
  const SearchTypeValues = [
8
9
  "operations",
9
10
  "integrations",
@@ -15,7 +16,15 @@ const SearchOptionsSchema = JsonOptionSchema.extend({
15
16
  integration: z.string().optional(),
16
17
  limit: z.coerce.number().int().positive().max(50).optional(),
17
18
  full: z.boolean().optional()
19
+ }).superRefine((value, ctx) => {
20
+ if (value.integration && value.type === "integrations") ctx.addIssue({
21
+ code: z.ZodIssueCode.custom,
22
+ path: ["integration"],
23
+ message: SEARCH_INTEGRATION_FILTER_ERROR
24
+ });
18
25
  });
26
+ //#endregion
27
+ //#region src/commands/search/search.command.ts
19
28
  const SEARCH_OPTIONS_CONFIG = {
20
29
  ...JSON_OPTION_CONFIG,
21
30
  type: {
@@ -24,7 +33,7 @@ const SEARCH_OPTIONS_CONFIG = {
24
33
  },
25
34
  integration: {
26
35
  flag: "--integration <id>",
27
- description: "Restrict to one integration (operations and credentials only)"
36
+ description: "Restrict to one integration (operations and credentials search only; not valid with --type integrations)"
28
37
  },
29
38
  limit: {
30
39
  flag: "--limit <n>",
@@ -32,7 +41,7 @@ const SEARCH_OPTIONS_CONFIG = {
32
41
  },
33
42
  full: {
34
43
  flag: "--full",
35
- description: "Include extended fields (schemas, safety flags, nested operations) without a follow-up show"
44
+ description: "Extended fields in one round-trip: operation schemas and safety flags; credential auth fields; integration catalog details (use integrations show for operation lists)"
36
45
  }
37
46
  };
38
47
  function createSearchCommand() {
@@ -46,7 +55,7 @@ function createSearchCommand() {
46
55
  description: "Search query (matches name and related fields per --type)",
47
56
  key: "query"
48
57
  },
49
- loadHandler: async () => (await import("./search.handler-Dn5jjyF-.mjs")).handleSearch
58
+ loadHandler: async () => (await import("./search.handler-dsvkAHFo.mjs")).handleSearch
50
59
  });
51
60
  }
52
61
  //#endregion
@@ -0,0 +1,112 @@
1
+ #!/usr/bin/env node
2
+
3
+ import { p as ui } from "./keystroke.mjs";
4
+ import { i as writeJson } from "./output-BPydP5tG.mjs";
5
+ import { i as requireClient } from "./context-Brc9VGV9.mjs";
6
+ import { t as renderCredential } from "./render-credential-D-H1ECDt.mjs";
7
+ import { i as formatPackageInstallCommand, r as detectPackageManager } from "./package-manager-BwJ6muas.mjs";
8
+ import { t as renderOperation } from "./render-operation-iF7Wblv2.mjs";
9
+ //#region src/lib/render-integration.ts
10
+ function renderIntegration(i, { full = false, packageManager } = {}) {
11
+ ui.br();
12
+ ui.text(i.publicId);
13
+ ui.text(` ${i.name}`);
14
+ if (i.description) ui.text(` ${i.description}`);
15
+ if (i.score !== void 0) ui.text(` score: ${i.score.toFixed(2)}`);
16
+ const npmPackageName = i.npmPackageName ?? `@keystrokehq/${i.publicId}`;
17
+ ui.text(` install: ${formatPackageInstallCommand(npmPackageName, { packageManager })}`);
18
+ if (full) {
19
+ const withOps = i;
20
+ if (Array.isArray(withOps.operations) && withOps.operations.length > 0) {
21
+ ui.text(` operations (${withOps.operations.length}):`);
22
+ for (const op of withOps.operations) ui.text(` ${op.id} — ${op.name}`);
23
+ }
24
+ }
25
+ }
26
+ //#endregion
27
+ //#region src/commands/search/search.params.ts
28
+ function buildSearchParams(type, options) {
29
+ const base = {
30
+ q: options.query,
31
+ ...options.limit !== void 0 ? { limit: options.limit } : {},
32
+ ...options.full ? { include: "full" } : {}
33
+ };
34
+ if (type === "integrations") return base;
35
+ return {
36
+ ...base,
37
+ ...options.integration ? { integrationId: options.integration } : {}
38
+ };
39
+ }
40
+ //#endregion
41
+ //#region src/commands/search/search.presentation.ts
42
+ function integrationFilterSuffix(integration, style) {
43
+ if (!integration) return "";
44
+ if (style === "empty") return ` (integration=${integration})`;
45
+ return ` · integration=${integration}`;
46
+ }
47
+ function typeLabel(type, count) {
48
+ if (type === "operations") return count === 1 ? "operation" : "operations";
49
+ if (type === "integrations") return count === 1 ? "integration" : "integrations";
50
+ return count === 1 ? "credential definition" : "credential definitions";
51
+ }
52
+ function browseCommand(type) {
53
+ if (type === "operations") return "operations list";
54
+ if (type === "integrations") return "integrations list";
55
+ return "credentials definitions list";
56
+ }
57
+ function filteredBrowseHint(type, integration) {
58
+ if (type === "operations") return `Or run \`keystroke operations list --integration ${integration}\` to browse that integration.`;
59
+ if (type === "credentials") return `Or run \`keystroke credentials definitions list --integration ${integration}\` to browse that integration.`;
60
+ return null;
61
+ }
62
+ function renderSearchEmptyState(type, options) {
63
+ ui.hint(`No ${typeLabel(type, 2)} matched "${options.query}"${integrationFilterSuffix(options.integration, "empty")}.`);
64
+ ui.hint(`Try a different query, or run \`keystroke ${browseCommand(type)}\` to browse.`);
65
+ if (options.integration) {
66
+ const filteredHint = filteredBrowseHint(type, options.integration);
67
+ if (filteredHint) ui.hint(filteredHint);
68
+ }
69
+ }
70
+ function formatSearchResultCountHint(type, options, count) {
71
+ return `\n${count} ${typeLabel(type, count)} matched "${options.query}"${integrationFilterSuffix(options.integration, "count")}`;
72
+ }
73
+ //#endregion
74
+ //#region src/commands/search/search.handler.ts
75
+ async function handleSearch(options, ctx) {
76
+ const type = options.type ?? "operations";
77
+ const result = await dispatchSearch(requireClient(ctx), type, buildSearchParams(type, options));
78
+ if (ctx.jsonMode) {
79
+ writeJson(result);
80
+ return;
81
+ }
82
+ if (result.results.length === 0) {
83
+ renderSearchEmptyState(type, options);
84
+ return;
85
+ }
86
+ const packageManager = detectPackageManager();
87
+ for (const hit of result.results) renderHit(type, hit, {
88
+ full: Boolean(options.full),
89
+ packageManager
90
+ });
91
+ ui.hint(formatSearchResultCountHint(type, options, result.results.length));
92
+ }
93
+ function dispatchSearch(client, type, params) {
94
+ if (type === "operations") return client.search.operations(params);
95
+ if (type === "integrations") return client.search.integrations(params);
96
+ if (type === "credentials") return client.search.credentials(params);
97
+ throw new Error(`Unsupported search type: ${type}`);
98
+ }
99
+ function renderHit(type, hit, { full, packageManager }) {
100
+ if (type === "operations") renderOperation(hit, {
101
+ showSchemas: full,
102
+ packageManager
103
+ });
104
+ else if (type === "integrations") renderIntegration(hit, {
105
+ full,
106
+ packageManager
107
+ });
108
+ else if (type === "credentials") renderCredential(hit, { full });
109
+ else throw new Error(`Unsupported search type: ${type}`);
110
+ }
111
+ //#endregion
112
+ export { handleSearch };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@keystrokehq/cli",
3
- "version": "0.0.38",
3
+ "version": "0.0.39",
4
4
  "private": false,
5
5
  "description": "Command-line interface for creating, managing, and deploying Keystroke automations.",
6
6
  "type": "module",
@@ -40,18 +40,18 @@
40
40
  "vitest": "^4.1.5",
41
41
  "@keystroke/env-utils": "0.0.0",
42
42
  "@keystroke/local-memory": "0.0.2",
43
- "@keystrokehq/config": "0.0.2",
43
+ "@keystroke/shared-types": "0.0.13",
44
44
  "@keystroke/test-utils": "0.0.7",
45
45
  "@keystroke/typescript-config": "0.0.0",
46
46
  "@keystroke/utils": "0.0.0",
47
- "@keystroke/shared-types": "0.0.12",
47
+ "@keystroke/workflow-builder": "0.0.18",
48
+ "@keystrokehq/core": "0.0.11",
48
49
  "@keystrokehq/runtime": "0.0.8",
49
50
  "@keystrokehq/workflow-build-contracts": "0.0.7",
50
- "@keystroke/workflow-builder": "0.0.17",
51
51
  "@keystrokehq/testing": "0.2.6",
52
- "@keystroke/workflow-deploy": "0.0.14",
53
- "@keystroke/workflow-sdk": "0.0.12",
54
- "@keystrokehq/core": "0.0.11"
52
+ "@keystroke/workflow-deploy": "0.0.15",
53
+ "@keystroke/workflow-sdk": "0.0.13",
54
+ "@keystrokehq/config": "0.0.2"
55
55
  },
56
56
  "keywords": [
57
57
  "automation",
@@ -1,79 +0,0 @@
1
- #!/usr/bin/env node
2
-
3
- import { p as ui } from "./keystroke.mjs";
4
- import { i as writeJson } from "./output-BPydP5tG.mjs";
5
- import { i as requireClient } from "./context-Brc9VGV9.mjs";
6
- import { t as renderCredential } from "./render-credential-D-H1ECDt.mjs";
7
- import { i as formatPackageInstallCommand, r as detectPackageManager } from "./package-manager-BwJ6muas.mjs";
8
- import { t as renderOperation } from "./render-operation-iF7Wblv2.mjs";
9
- //#region src/lib/render-integration.ts
10
- function renderIntegration(i, { full = false, packageManager } = {}) {
11
- ui.br();
12
- ui.text(i.publicId);
13
- ui.text(` ${i.name}`);
14
- if (i.description) ui.text(` ${i.description}`);
15
- if (i.score !== void 0) ui.text(` score: ${i.score.toFixed(2)}`);
16
- const npmPackageName = i.npmPackageName ?? `@keystrokehq/${i.publicId}`;
17
- ui.text(` install: ${formatPackageInstallCommand(npmPackageName, { packageManager })}`);
18
- if (full) {
19
- const withOps = i;
20
- if (Array.isArray(withOps.operations) && withOps.operations.length > 0) {
21
- ui.text(` operations (${withOps.operations.length}):`);
22
- for (const op of withOps.operations) ui.text(` ${op.id} — ${op.name}`);
23
- }
24
- }
25
- }
26
- //#endregion
27
- //#region src/commands/search/search.handler.ts
28
- async function handleSearch(options, ctx) {
29
- const type = options.type ?? "operations";
30
- const result = await dispatchSearch(requireClient(ctx), type, {
31
- q: options.query,
32
- integrationId: options.integration,
33
- limit: options.limit,
34
- ...options.full ? { include: "full" } : {}
35
- });
36
- if (ctx.jsonMode) {
37
- writeJson(result);
38
- return;
39
- }
40
- if (result.results.length === 0) {
41
- ui.hint(`No ${type} matched "${options.query}".`);
42
- ui.hint(`Try a different query, or run \`keystroke ${browseCommand(type)}\` to browse.`);
43
- return;
44
- }
45
- const packageManager = detectPackageManager();
46
- for (const hit of result.results) renderHit(type, hit, {
47
- full: Boolean(options.full),
48
- packageManager
49
- });
50
- }
51
- function browseCommand(type) {
52
- if (type === "operations") return "operations list";
53
- if (type === "integrations") return "integrations list";
54
- return "credentials definitions list";
55
- }
56
- function dispatchSearch(client, type, params) {
57
- if (type === "operations") return client.search.operations(params);
58
- if (type === "integrations") return client.search.integrations(params);
59
- return client.search.credentials(params);
60
- }
61
- function renderHit(type, hit, { full, packageManager }) {
62
- if (type === "operations") {
63
- renderOperation(hit, {
64
- showSchemas: full,
65
- packageManager
66
- });
67
- return;
68
- }
69
- if (type === "integrations") {
70
- renderIntegration(hit, {
71
- full,
72
- packageManager
73
- });
74
- return;
75
- }
76
- renderCredential(hit, { full });
77
- }
78
- //#endregion
79
- export { handleSearch };