dataiku-sdk 3.3.0 → 3.5.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.
Files changed (126) hide show
  1. package/README.md +6 -4
  2. package/dist/build-metadata.json +1 -1
  3. package/dist/src/cli/command-syntax.json +14524 -0
  4. package/dist/src/cli/commands/analysis.js +6 -9
  5. package/dist/src/cli/commands/api-deployer.js +15 -33
  6. package/dist/src/cli/commands/api-service.js +17 -27
  7. package/dist/src/cli/commands/app.js +22 -39
  8. package/dist/src/cli/commands/bundle.js +15 -24
  9. package/dist/src/cli/commands/business-app.js +10 -17
  10. package/dist/src/cli/commands/code-env.js +23 -36
  11. package/dist/src/cli/commands/code.js +5 -5
  12. package/dist/src/cli/commands/connection.js +12 -22
  13. package/dist/src/cli/commands/continuous-activity.js +6 -9
  14. package/dist/src/cli/commands/dashboard.js +8 -13
  15. package/dist/src/cli/commands/data-collection.js +9 -16
  16. package/dist/src/cli/commands/data-quality.js +14 -26
  17. package/dist/src/cli/commands/dataset.js +28 -51
  18. package/dist/src/cli/commands/discussion.js +7 -10
  19. package/dist/src/cli/commands/doctor.js +3 -3
  20. package/dist/src/cli/commands/flow-zone.js +8 -17
  21. package/dist/src/cli/commands/folder.js +12 -20
  22. package/dist/src/cli/commands/future.js +7 -10
  23. package/dist/src/cli/commands/group.js +7 -11
  24. package/dist/src/cli/commands/insight.js +7 -11
  25. package/dist/src/cli/commands/job.js +17 -25
  26. package/dist/src/cli/commands/knowledge-bank.js +5 -6
  27. package/dist/src/cli/commands/llm.js +5 -8
  28. package/dist/src/cli/commands/macro.js +11 -18
  29. package/dist/src/cli/commands/meaning.js +7 -11
  30. package/dist/src/cli/commands/metrics.js +7 -10
  31. package/dist/src/cli/commands/ml-task.js +12 -20
  32. package/dist/src/cli/commands/model-evaluation-store.js +7 -11
  33. package/dist/src/cli/commands/notebook.js +15 -27
  34. package/dist/src/cli/commands/plugin.js +35 -68
  35. package/dist/src/cli/commands/project-deployer.js +10 -22
  36. package/dist/src/cli/commands/project-folder.js +10 -17
  37. package/dist/src/cli/commands/project-git.js +39 -71
  38. package/dist/src/cli/commands/project-library.js +15 -23
  39. package/dist/src/cli/commands/project.js +9 -26
  40. package/dist/src/cli/commands/recipe.d.ts +16 -0
  41. package/dist/src/cli/commands/recipe.js +83 -94
  42. package/dist/src/cli/commands/saved-model.js +23 -39
  43. package/dist/src/cli/commands/scenario.js +21 -35
  44. package/dist/src/cli/commands/sql.js +4 -4
  45. package/dist/src/cli/commands/statistics.js +11 -18
  46. package/dist/src/cli/commands/streaming-endpoint.js +7 -11
  47. package/dist/src/cli/commands/user.js +11 -22
  48. package/dist/src/cli/commands/variable.js +3 -4
  49. package/dist/src/cli/commands/webapp.js +10 -16
  50. package/dist/src/cli/commands/wiki.js +9 -13
  51. package/dist/src/cli/commands/workspace.js +8 -14
  52. package/dist/src/cli/contract.d.ts +5 -15
  53. package/dist/src/cli/contract.js +179 -461
  54. package/dist/src/cli/doctor.js +1 -0
  55. package/dist/src/cli/env.d.ts +2 -0
  56. package/dist/src/cli/env.js +15 -1
  57. package/dist/src/cli/helpers/app-permissions.js +2 -1
  58. package/dist/src/cli/helpers/flow-zone.js +2 -1
  59. package/dist/src/cli/helpers/recipe.js +2 -1
  60. package/dist/src/cli/output-schemas.d.ts +24 -0
  61. package/dist/src/cli/output-schemas.js +233 -0
  62. package/dist/src/cli/syntax.d.ts +83 -0
  63. package/dist/src/cli/syntax.js +217 -0
  64. package/dist/src/cli/types.d.ts +3 -0
  65. package/dist/src/cli/usage.d.ts +1 -1
  66. package/dist/src/cli/usage.js +4 -2
  67. package/dist/src/cli/version.js +2 -0
  68. package/dist/src/cli.js +37 -64
  69. package/dist/src/client.d.ts +10 -1
  70. package/dist/src/client.js +27 -11
  71. package/dist/src/errors.d.ts +12 -1
  72. package/dist/src/errors.js +34 -7
  73. package/dist/src/generated/action-output-schemas.json +1735 -0
  74. package/dist/src/index.d.ts +1 -3
  75. package/dist/src/index.js +2 -2
  76. package/dist/src/resources/api-services.js +2 -3
  77. package/dist/src/resources/applications.js +2 -4
  78. package/dist/src/resources/code-envs.js +2 -2
  79. package/dist/src/resources/data-quality.js +4 -3
  80. package/dist/src/resources/datasets.d.ts +13 -0
  81. package/dist/src/resources/datasets.js +42 -8
  82. package/dist/src/resources/flow-zones.d.ts +6 -2
  83. package/dist/src/resources/flow-zones.js +10 -5
  84. package/dist/src/resources/folders.js +4 -2
  85. package/dist/src/resources/futures.d.ts +2 -0
  86. package/dist/src/resources/futures.js +39 -27
  87. package/dist/src/resources/insights.js +3 -2
  88. package/dist/src/resources/jobs.js +41 -31
  89. package/dist/src/resources/macros.js +2 -4
  90. package/dist/src/resources/ml-tasks.js +28 -19
  91. package/dist/src/resources/notebooks.js +2 -3
  92. package/dist/src/resources/plugins.d.ts +0 -2
  93. package/dist/src/resources/plugins.js +0 -3
  94. package/dist/src/resources/project-git.d.ts +6 -12
  95. package/dist/src/resources/project-git.js +31 -58
  96. package/dist/src/resources/project-library.d.ts +0 -2
  97. package/dist/src/resources/project-library.js +2 -7
  98. package/dist/src/resources/projects.d.ts +4 -2
  99. package/dist/src/resources/projects.js +37 -36
  100. package/dist/src/resources/recipes.d.ts +28 -0
  101. package/dist/src/resources/recipes.js +116 -84
  102. package/dist/src/resources/sql.js +8 -3
  103. package/dist/src/resources/statistics.js +2 -1
  104. package/dist/src/resources/variables.js +2 -1
  105. package/dist/src/resources/webapps.js +2 -3
  106. package/dist/src/schemas.d.ts +1 -2
  107. package/dist/src/schemas.js +1 -1
  108. package/dist/src/skill.js +6 -7
  109. package/dist/src/utils/cleanup-ledger.js +9 -8
  110. package/dist/src/utils/git-reference.d.ts +12 -0
  111. package/dist/src/utils/git-reference.js +38 -0
  112. package/dist/src/utils/polling.d.ts +3 -0
  113. package/dist/src/utils/polling.js +3 -0
  114. package/dist/src/utils/project-archive.js +2 -2
  115. package/dist/src/utils/stable-hash.d.ts +3 -1
  116. package/dist/src/utils/stable-hash.js +2 -0
  117. package/package.json +8 -8
  118. package/plugin.json +1 -1
  119. package/skills/dataiku-dss/SKILL.md +3 -2
  120. package/skills/dataiku-dss/references/app-releases.md +2 -3
  121. package/skills/dataiku-dss/references/authentication.md +7 -7
  122. package/skills/dataiku-dss/references/coding.md +1 -1
  123. package/skills/dataiku-dss/references/mutations.md +1 -1
  124. package/skills/dataiku-dss/references/troubleshooting.md +2 -2
  125. package/dist/src/utils/pagination.d.ts +0 -8
  126. package/dist/src/utils/pagination.js +0 -23
@@ -1,26 +1,25 @@
1
1
  import { requiredStringFlag, } from "../coerce.js";
2
2
  import { executionMode, } from "../flags.js";
3
3
  import { readIfExists, skipResult, } from "../output.js";
4
+ import { commandUsage, withUsage, } from "../syntax.js";
4
5
  import { requireArgs, } from "../usage.js";
5
- export const analysisCommands = {
6
+ export const analysisCommands = withUsage("analysis", {
6
7
  list: {
7
8
  handler: (c, _a, f) => c.analyses.list(f["project-key"]),
8
- usage: "dss analysis list [--project-key KEY]",
9
9
  description: "List Visual ML analyses in a project.",
10
10
  examples: ["dss analysis list --project-key PROJECT",],
11
11
  },
12
12
  get: {
13
13
  handler: (c, a, f) => {
14
- requireArgs(a, 1, "dss analysis get <analysisId> [--project-key KEY]");
14
+ requireArgs(a, 1, commandUsage("analysis", "get"));
15
15
  return c.analyses.get(a[0], f["project-key"]);
16
16
  },
17
- usage: "dss analysis get <analysisId> [--project-key KEY]",
18
17
  description: "Get a Visual ML analysis.",
19
18
  examples: ["dss analysis get ANALYSIS_ID --project-key PROJECT",],
20
19
  },
21
20
  create: {
22
21
  handler: async (c, _a, f) => {
23
- const usage = "dss analysis create --input-dataset DS [--dry-run] [--project-key KEY]";
22
+ const usage = commandUsage("analysis", "create");
24
23
  const inputDataset = requiredStringFlag(f, "input-dataset", usage);
25
24
  const projectKey = f["project-key"];
26
25
  const options = { inputDataset, projectKey, };
@@ -35,7 +34,6 @@ export const analysisCommands = {
35
34
  const created = await c.analyses.create(options);
36
35
  return { created: created.id, resource: "analysis", ...created, };
37
36
  },
38
- usage: "dss analysis create --input-dataset DS [--dry-run] [--project-key KEY]",
39
37
  description: "Create a Visual ML analysis for an input dataset.",
40
38
  examples: [
41
39
  "dss analysis create --input-dataset customers --project-key PROJECT",
@@ -44,7 +42,7 @@ export const analysisCommands = {
44
42
  },
45
43
  delete: {
46
44
  handler: async (c, a, f) => {
47
- requireArgs(a, 1, "dss analysis delete <analysisId> [--if-exists] [--dry-run] [--project-key KEY]");
45
+ requireArgs(a, 1, commandUsage("analysis", "delete"));
48
46
  const projectKey = f["project-key"];
49
47
  if (executionMode(f).dryRun || f["if-exists"] === true) {
50
48
  const current = await readIfExists(() => c.analyses.get(a[0], projectKey));
@@ -57,11 +55,10 @@ export const analysisCommands = {
57
55
  await c.analyses.delete(a[0], projectKey);
58
56
  return { deleted: a[0], resource: "analysis", };
59
57
  },
60
- usage: "dss analysis delete <analysisId> [--if-exists] [--dry-run] [--project-key KEY]",
61
58
  description: "Delete a Visual ML analysis.",
62
59
  examples: [
63
60
  "dss analysis delete ANALYSIS_ID --if-exists --project-key PROJECT",
64
61
  "dss analysis delete ANALYSIS_ID --dry-run --project-key PROJECT",
65
62
  ],
66
63
  },
67
- };
64
+ });
@@ -1,9 +1,9 @@
1
1
  import { requiredJsonInput, } from "../coerce.js";
2
+ import { commandUsage, withUsage, } from "../syntax.js";
2
3
  import { requireArgs, } from "../usage.js";
3
- export const apiDeployerCommands = {
4
+ export const apiDeployerCommands = withUsage("api-deployer", {
4
5
  "list-infras": {
5
6
  handler: (c) => c.apiDeployer.listInfras(),
6
- usage: "dss api-deployer list-infras",
7
7
  description: "List API Deployer infrastructures.",
8
8
  examples: ["dss api-deployer list-infras",],
9
9
  },
@@ -12,38 +12,33 @@ export const apiDeployerCommands = {
12
12
  const body = requiredJsonInput(f, "--data, --data-file, or --stdin is required (infra settings).");
13
13
  return c.apiDeployer.createInfra(body);
14
14
  },
15
- usage: "dss api-deployer create-infra (--data JSON|--data-file PATH|--stdin)",
16
15
  description: "Create an API Deployer infrastructure.",
17
16
  examples: ["dss api-deployer create-infra --data-file infra.json",],
18
17
  },
19
18
  "get-infra": {
20
19
  handler: (c, a) => {
21
- requireArgs(a, 1, "dss api-deployer get-infra <infraId>");
20
+ requireArgs(a, 1, commandUsage("api-deployer", "get-infra"));
22
21
  return c.apiDeployer.getInfra(a[0]);
23
22
  },
24
- usage: "dss api-deployer get-infra <infraId>",
25
23
  description: "Get an API Deployer infrastructure status.",
26
24
  examples: ["dss api-deployer get-infra prod-infra",],
27
25
  },
28
26
  "delete-infra": {
29
27
  handler: async (c, a) => {
30
- requireArgs(a, 1, "dss api-deployer delete-infra <infraId>");
28
+ requireArgs(a, 1, commandUsage("api-deployer", "delete-infra"));
31
29
  await c.apiDeployer.deleteInfra(a[0]);
32
30
  return { deleted: true, };
33
31
  },
34
- usage: "dss api-deployer delete-infra <infraId>",
35
32
  description: "Delete an API Deployer infrastructure.",
36
33
  examples: ["dss api-deployer delete-infra prod-infra",],
37
34
  },
38
35
  "list-stages": {
39
36
  handler: (c) => c.apiDeployer.listStages(),
40
- usage: "dss api-deployer list-stages",
41
37
  description: "List API Deployer lifecycle stages.",
42
38
  examples: ["dss api-deployer list-stages",],
43
39
  },
44
40
  "list-services": {
45
41
  handler: (c) => c.apiDeployer.listServices(),
46
- usage: "dss api-deployer list-services",
47
42
  description: "List published API Deployer services.",
48
43
  examples: ["dss api-deployer list-services",],
49
44
  },
@@ -52,52 +47,46 @@ export const apiDeployerCommands = {
52
47
  const body = requiredJsonInput(f, "--data, --data-file, or --stdin is required (service definition).");
53
48
  return c.apiDeployer.createService(body);
54
49
  },
55
- usage: "dss api-deployer create-service (--data JSON|--data-file PATH|--stdin)",
56
50
  description: "Create a published API Deployer service.",
57
51
  examples: ['dss api-deployer create-service --data \'{"id":"my-service"}\'',],
58
52
  },
59
53
  "get-service": {
60
54
  handler: (c, a) => {
61
- requireArgs(a, 1, "dss api-deployer get-service <serviceId>");
55
+ requireArgs(a, 1, commandUsage("api-deployer", "get-service"));
62
56
  return c.apiDeployer.getService(a[0]);
63
57
  },
64
- usage: "dss api-deployer get-service <serviceId>",
65
58
  description: "Get a published service's status (versions + deployments).",
66
59
  examples: ["dss api-deployer get-service my-service",],
67
60
  },
68
61
  "delete-service": {
69
62
  handler: async (c, a) => {
70
- requireArgs(a, 1, "dss api-deployer delete-service <serviceId>");
63
+ requireArgs(a, 1, commandUsage("api-deployer", "delete-service"));
71
64
  await c.apiDeployer.deleteService(a[0]);
72
65
  return { deleted: true, };
73
66
  },
74
- usage: "dss api-deployer delete-service <serviceId>",
75
67
  description: "Delete a published API Deployer service.",
76
68
  examples: ["dss api-deployer delete-service my-service",],
77
69
  },
78
70
  "publish-version": {
79
71
  handler: async (c, a) => {
80
- requireArgs(a, 2, "dss api-deployer publish-version <serviceId> <archive.zip>");
72
+ requireArgs(a, 2, commandUsage("api-deployer", "publish-version"));
81
73
  await c.apiDeployer.publishServiceVersion(a[0], a[1]);
82
74
  return { published: true, };
83
75
  },
84
- usage: "dss api-deployer publish-version <serviceId> <archive.zip>",
85
76
  description: "Publish (upload) a service version package to the API Deployer.",
86
77
  examples: ["dss api-deployer publish-version my-service ./pkg.zip",],
87
78
  },
88
79
  "delete-version": {
89
80
  handler: async (c, a) => {
90
- requireArgs(a, 2, "dss api-deployer delete-version <serviceId> <version>");
81
+ requireArgs(a, 2, commandUsage("api-deployer", "delete-version"));
91
82
  await c.apiDeployer.deleteServiceVersion(a[0], a[1]);
92
83
  return { deleted: true, };
93
84
  },
94
- usage: "dss api-deployer delete-version <serviceId> <version>",
95
85
  description: "Delete a published service version.",
96
86
  examples: ["dss api-deployer delete-version my-service v1",],
97
87
  },
98
88
  "list-deployments": {
99
89
  handler: (c) => c.apiDeployer.listDeployments(),
100
- usage: "dss api-deployer list-deployments",
101
90
  description: "List API Deployer deployments.",
102
91
  examples: ["dss api-deployer list-deployments",],
103
92
  },
@@ -106,65 +95,58 @@ export const apiDeployerCommands = {
106
95
  const body = requiredJsonInput(f, "--data, --data-file, or --stdin is required (deployment settings).");
107
96
  return c.apiDeployer.createDeployment(body);
108
97
  },
109
- usage: "dss api-deployer create-deployment (--data JSON|--data-file PATH|--stdin)",
110
98
  description: "Create an API Deployer deployment (maps a service version to an infra).",
111
99
  examples: ["dss api-deployer create-deployment --data-file deployment.json",],
112
100
  },
113
101
  "get-deployment": {
114
102
  handler: (c, a) => {
115
- requireArgs(a, 1, "dss api-deployer get-deployment <deploymentId>");
103
+ requireArgs(a, 1, commandUsage("api-deployer", "get-deployment"));
116
104
  return c.apiDeployer.getDeployment(a[0]);
117
105
  },
118
- usage: "dss api-deployer get-deployment <deploymentId>",
119
106
  description: "Get an API Deployer deployment.",
120
107
  examples: ["dss api-deployer get-deployment my-deployment",],
121
108
  },
122
109
  "deployment-status": {
123
110
  handler: (c, a) => {
124
- requireArgs(a, 1, "dss api-deployer deployment-status <deploymentId>");
111
+ requireArgs(a, 1, commandUsage("api-deployer", "deployment-status"));
125
112
  return c.apiDeployer.getDeploymentStatus(a[0]);
126
113
  },
127
- usage: "dss api-deployer deployment-status <deploymentId>",
128
114
  description: "Get an API Deployer deployment's full health/status.",
129
115
  examples: ["dss api-deployer deployment-status my-deployment",],
130
116
  },
131
117
  "deployment-settings": {
132
118
  handler: (c, a) => {
133
- requireArgs(a, 1, "dss api-deployer deployment-settings <deploymentId>");
119
+ requireArgs(a, 1, commandUsage("api-deployer", "deployment-settings"));
134
120
  return c.apiDeployer.getDeploymentSettings(a[0]);
135
121
  },
136
- usage: "dss api-deployer deployment-settings <deploymentId>",
137
122
  description: "Get an API Deployer deployment's settings.",
138
123
  examples: ["dss api-deployer deployment-settings my-deployment",],
139
124
  },
140
125
  "save-deployment-settings": {
141
126
  handler: async (c, a, f) => {
142
- requireArgs(a, 1, "dss api-deployer save-deployment-settings <deploymentId> (--data JSON|--data-file PATH|--stdin)");
127
+ requireArgs(a, 1, commandUsage("api-deployer", "save-deployment-settings"));
143
128
  const body = requiredJsonInput(f, "--data, --data-file, or --stdin is required (deployment settings).");
144
129
  await c.apiDeployer.saveDeploymentSettings(a[0], body);
145
130
  return { saved: true, };
146
131
  },
147
- usage: "dss api-deployer save-deployment-settings <deploymentId> (--data JSON|--data-file PATH|--stdin)",
148
132
  description: "Save an API Deployer deployment's settings.",
149
133
  examples: ["dss api-deployer save-deployment-settings my-deployment --data-file settings.json",],
150
134
  },
151
135
  deploy: {
152
136
  handler: (c, a) => {
153
- requireArgs(a, 1, "dss api-deployer deploy <deploymentId>");
137
+ requireArgs(a, 1, commandUsage("api-deployer", "deploy"));
154
138
  return c.apiDeployer.startDeploymentUpdate(a[0]);
155
139
  },
156
- usage: "dss api-deployer deploy <deploymentId>",
157
140
  description: "Apply a deployment's settings to its infrastructure (start update).",
158
141
  examples: ["dss api-deployer deploy my-deployment",],
159
142
  },
160
143
  "delete-deployment": {
161
144
  handler: async (c, a) => {
162
- requireArgs(a, 1, "dss api-deployer delete-deployment <deploymentId>");
145
+ requireArgs(a, 1, commandUsage("api-deployer", "delete-deployment"));
163
146
  await c.apiDeployer.deleteDeployment(a[0]);
164
147
  return { deleted: true, };
165
148
  },
166
- usage: "dss api-deployer delete-deployment <deploymentId>",
167
149
  description: "Delete an API Deployer deployment.",
168
150
  examples: ["dss api-deployer delete-deployment my-deployment",],
169
151
  },
170
- };
152
+ });
@@ -1,45 +1,43 @@
1
- import { ClientValidationError, } from "../../errors.js";
1
+ import { ClientValidationError, unexpectedResponseError, } from "../../errors.js";
2
2
  import { writeResponseToFile, } from "../../utils/response-file.js";
3
- import { stableHash, } from "../../utils/stable-hash.js";
3
+ import { SHA256_HEX_PATTERN, stableHash, } from "../../utils/stable-hash.js";
4
4
  import { requiredJsonInput, } from "../coerce.js";
5
5
  import { executionMode, } from "../flags.js";
6
+ import { commandUsage, withUsage, } from "../syntax.js";
6
7
  import { requireArgs, UsageError, } from "../usage.js";
7
8
  function validateExpectHash(value) {
8
9
  if (value === undefined || value === false)
9
10
  return undefined;
10
- if (typeof value !== "string" || !/^[0-9a-fA-F]{64}$/.test(value)) {
11
+ if (typeof value !== "string" || !SHA256_HEX_PATTERN.test(value)) {
11
12
  throw new ClientValidationError("Expected API service settings hash must be a 64-character SHA-256 hex digest.", "validation_failed", "Run this update with --dry-run and capture currentHash before retrying.");
12
13
  }
13
14
  return value;
14
15
  }
15
- export const apiServiceCommands = {
16
+ export const apiServiceCommands = withUsage("api-service", {
16
17
  list: {
17
18
  handler: (c, _a, f) => c.apiServices.list(f["project-key"]),
18
- usage: "dss api-service list [--project-key KEY]",
19
19
  description: "List API services in a project.",
20
20
  examples: ["dss api-service list",],
21
21
  },
22
22
  create: {
23
23
  handler: (c, a, f) => {
24
- requireArgs(a, 1, "dss api-service create <serviceId> [--project-key KEY]");
24
+ requireArgs(a, 1, commandUsage("api-service", "create"));
25
25
  return c.apiServices.create(a[0], f["project-key"]);
26
26
  },
27
- usage: "dss api-service create <serviceId> [--project-key KEY]",
28
27
  description: "Create an empty API service.",
29
28
  examples: ["dss api-service create my-service",],
30
29
  },
31
30
  "get-settings": {
32
31
  handler: (c, a, f) => {
33
- requireArgs(a, 1, "dss api-service get-settings <serviceId> [--project-key KEY]");
32
+ requireArgs(a, 1, commandUsage("api-service", "get-settings"));
34
33
  return c.apiServices.getSettings(a[0], f["project-key"]);
35
34
  },
36
- usage: "dss api-service get-settings <serviceId> [--project-key KEY]",
37
35
  description: "Get an API service's settings (endpoint definitions).",
38
36
  examples: ["dss api-service get-settings my-service",],
39
37
  },
40
38
  "save-settings": {
41
39
  handler: async (c, a, f) => {
42
- const usage = "dss api-service save-settings <serviceId> (--data JSON|--data-file PATH|--stdin) [--expect-hash SHA256] [--dry-run] [--project-key KEY]";
40
+ const usage = commandUsage("api-service", "save-settings");
43
41
  requireArgs(a, 1, usage);
44
42
  const body = requiredJsonInput(f, "--data, --data-file, or --stdin is required (service settings).");
45
43
  const projectKey = f["project-key"];
@@ -71,13 +69,12 @@ export const apiServiceCommands = {
71
69
  const saved = await c.apiServices.saveSettings(a[0], body, projectKey, { expectHash, });
72
70
  return { saved: a[0], ...saved, };
73
71
  },
74
- usage: "dss api-service save-settings <serviceId> (--data JSON|--data-file PATH|--stdin) [--expect-hash SHA256] [--dry-run] [--project-key KEY]",
75
72
  description: "Replace an API service's settings wholesale (explicit replacement: the supplied object is PUT as-is, so fetch get-settings first). --expect-hash refuses the write when the stored settings changed since they were fetched; --dry-run reports current, next, and both hashes without writing.",
76
73
  examples: ["dss api-service save-settings my-service --data-file service.json --dry-run",],
77
74
  },
78
75
  "add-prediction-endpoint": {
79
76
  handler: async (c, a, f) => {
80
- requireArgs(a, 3, "dss api-service add-prediction-endpoint <serviceId> <endpointId> <savedModelId> [--dry-run] [--project-key KEY]");
77
+ requireArgs(a, 3, commandUsage("api-service", "add-prediction-endpoint"));
81
78
  const endpoint = {
82
79
  id: a[1],
83
80
  type: "STD_PREDICTION",
@@ -87,7 +84,6 @@ export const apiServiceCommands = {
87
84
  return endpoint;
88
85
  return c.apiServices.addPredictionEndpoint(a[0], a[1], a[2], f["project-key"]);
89
86
  },
90
- usage: "dss api-service add-prediction-endpoint <serviceId> <endpointId> <savedModelId> [--dry-run] [--project-key KEY]",
91
87
  description: "Add a saved-model prediction endpoint to an API service.",
92
88
  examples: [
93
89
  "dss api-service add-prediction-endpoint my-service predict churn-model",
@@ -96,29 +92,26 @@ export const apiServiceCommands = {
96
92
  },
97
93
  "list-packages": {
98
94
  handler: async (c, a, f) => {
99
- requireArgs(a, 1, "dss api-service list-packages <serviceId> [--project-key KEY]");
95
+ requireArgs(a, 1, commandUsage("api-service", "list-packages"));
100
96
  const projectKey = f["project-key"];
101
97
  return c.apiServices.listPackages(a[0], projectKey);
102
98
  },
103
- usage: "dss api-service list-packages <serviceId> [--project-key KEY]",
104
99
  description: "List deployable packages of an API service.",
105
100
  examples: ["dss api-service list-packages my-service",],
106
101
  },
107
102
  "package-summary": {
108
103
  handler: (c, a, f) => {
109
- requireArgs(a, 2, "dss api-service package-summary <serviceId> <packageId> [--project-key KEY]");
104
+ requireArgs(a, 2, commandUsage("api-service", "package-summary"));
110
105
  return c.apiServices.getPackageSummary(a[0], a[1], f["project-key"]);
111
106
  },
112
- usage: "dss api-service package-summary <serviceId> <packageId> [--project-key KEY]",
113
107
  description: "Get a package summary.",
114
108
  examples: ["dss api-service package-summary my-service v1",],
115
109
  },
116
110
  "create-package": {
117
111
  handler: (c, a, f) => {
118
- requireArgs(a, 2, "dss api-service create-package <serviceId> <packageId> [--release-notes TEXT] [--project-key KEY]");
112
+ requireArgs(a, 2, commandUsage("api-service", "create-package"));
119
113
  return c.apiServices.createPackage(a[0], a[1], f["project-key"], typeof f["release-notes"] === "string" ? { releaseNotes: f["release-notes"], } : {});
120
114
  },
121
- usage: "dss api-service create-package <serviceId> <packageId> [--release-notes TEXT] [--project-key KEY]",
122
115
  description: "Build a deployable package from the current service state; --release-notes forwards the documented releaseNotes query parameter.",
123
116
  examples: [
124
117
  "dss api-service create-package my-service v1",
@@ -127,43 +120,40 @@ export const apiServiceCommands = {
127
120
  },
128
121
  "delete-package": {
129
122
  handler: async (c, a, f) => {
130
- requireArgs(a, 2, "dss api-service delete-package <serviceId> <packageId> [--project-key KEY]");
123
+ requireArgs(a, 2, commandUsage("api-service", "delete-package"));
131
124
  await c.apiServices.deletePackage(a[0], a[1], f["project-key"]);
132
125
  return { deleted: true, };
133
126
  },
134
- usage: "dss api-service delete-package <serviceId> <packageId> [--project-key KEY]",
135
127
  description: "Delete an API service package.",
136
128
  examples: ["dss api-service delete-package my-service v1",],
137
129
  },
138
130
  "download-package": {
139
131
  handler: async (c, a, f) => {
140
- requireArgs(a, 2, "dss api-service download-package <serviceId> <packageId> --output PATH [--project-key KEY]");
132
+ requireArgs(a, 2, commandUsage("api-service", "download-package"));
141
133
  const out = f["output"];
142
134
  if (!out)
143
135
  throw new UsageError("--output PATH is required.", "missing_required_flag");
144
136
  const res = await c.apiServices.downloadPackageArchive(a[0], a[1], f["project-key"]);
145
137
  if (!res.body) {
146
- throw new Error("apiServices.downloadPackageArchive response did not include a body");
138
+ throw unexpectedResponseError("apiServices.downloadPackageArchive response did not include a body");
147
139
  }
148
140
  const bytes = await writeResponseToFile(out, res);
149
141
  return { path: out, bytes, };
150
142
  },
151
- usage: "dss api-service download-package <serviceId> <packageId> --output PATH [--project-key KEY]",
152
143
  description: "Download an API service package archive to a local file.",
153
144
  examples: ["dss api-service download-package my-service v1 --output ./pkg.zip",],
154
145
  },
155
146
  "publish-package": {
156
147
  handler: (c, a, f) => {
157
- requireArgs(a, 2, "dss api-service publish-package <serviceId> <packageId> [--published-service-id ID] [--project-key KEY]");
148
+ requireArgs(a, 2, commandUsage("api-service", "publish-package"));
158
149
  return c.apiServices.publishPackage(a[0], a[1], f["project-key"], typeof f["published-service-id"] === "string"
159
150
  ? { publishedServiceId: f["published-service-id"], }
160
151
  : {});
161
152
  },
162
- usage: "dss api-service publish-package <serviceId> <packageId> [--published-service-id ID] [--project-key KEY]",
163
153
  description: "Publish a package to the API Deployer; --published-service-id forwards the documented publishedServiceId query parameter (a new published service is created when no match exists; the service's own id is the server-side default).",
164
154
  examples: [
165
155
  "dss api-service publish-package my-service v1",
166
156
  "dss api-service publish-package my-service v1 --published-service-id=prod-churn",
167
157
  ],
168
158
  },
169
- };
159
+ });
@@ -5,15 +5,16 @@ import { executionMode, } from "../flags.js";
5
5
  import { appPermissionsHash, appPermissionsVerificationError, assertAppPermissionsSnapshotBinding, buildAppPermissionsSnapshot, diffAppPermissions, readAppPermissionsSnapshot, writeAppPermissionsSnapshot, } from "../helpers/app-permissions.js";
6
6
  import { createSuccessorInstance, futureTargetIdentity, generatedInstanceKey, isDefinitiveRejection, preflightSuccessorInstance, requireAbsentProjectTarget, safeErrorSummary, verifyAppInstance, VISUAL_UI_GATE, } from "../helpers/app-successor.js";
7
7
  import { CommandResultFailure, } from "../output.js";
8
+ import { commandUsage, withUsage, } from "../syntax.js";
8
9
  import { requireArgs, requireNoArgs, UsageError, } from "../usage.js";
9
- const CREATE_INSTANCE_USAGE = "dss app create-instance <appId> (--data JSON|--data-file PATH|--stdin) [--wait] [--timeout MS] [--poll-interval MS]";
10
- const MANIFEST_VERSION_USAGE = "dss app manifest-version [--project-key KEY]";
11
- const SET_MANIFEST_VERSION_USAGE = "dss app set-manifest-version (--manifest-version V|--version-notes NOTES) [--expect-hash SHA256] [--dry-run] [--project-key KEY]";
12
- const CREATE_SUCCESSOR_USAGE = "dss app create-successor-instance <appId> --from KEY [--to KEY] [--name NAME] [--copy-permissions] [--timeout MS] [--poll-interval MS] [--dry-run] [--record-cleanup PATH]";
13
- const SUCCESSOR_PREFLIGHT_USAGE = "dss app successor-preflight <appId> --from KEY [--to KEY] [--name NAME] [--copy-permissions]";
14
- const VERIFY_INSTANCE_USAGE = "dss app verify-instance <appId> --project-key KEY [--expect-version V]";
15
- const DELETE_INSTANCE_USAGE = "dss app delete-instance --project-key KEY [--future-id ID] [--expect-project-incarnation SHA256] [--unconfirmed-creation] [--timeout MS] [--poll-interval MS]";
16
- const CREATE_INSTANCE_INDETERMINATE_REMEDIATION = "DSS may have accepted the creation, but no future ID or project incarnation authorizes cleanup. Inspect `dss app instances <appId>` and DSS task history; delete only after creation is known terminal and the target identity is verified.";
10
+ const CREATE_INSTANCE_USAGE = commandUsage("app", "create-instance");
11
+ const MANIFEST_VERSION_USAGE = commandUsage("app", "manifest-version");
12
+ const SET_MANIFEST_VERSION_USAGE = commandUsage("app", "set-manifest-version");
13
+ const CREATE_SUCCESSOR_USAGE = commandUsage("app", "create-successor-instance");
14
+ const SUCCESSOR_PREFLIGHT_USAGE = commandUsage("app", "successor-preflight");
15
+ const VERIFY_INSTANCE_USAGE = commandUsage("app", "verify-instance");
16
+ const DELETE_INSTANCE_USAGE = commandUsage("app", "delete-instance");
17
+ const CREATE_INSTANCE_INDETERMINATE_REMEDIATION = `DSS may have accepted the creation, but no future ID or project incarnation authorizes cleanup. Inspect \`${commandUsage("app", "instances")}\` and DSS task history; delete only after creation is known terminal and the target identity is verified.`;
17
18
  const CREATE_INSTANCE_REJECTED_REMEDIATION = "DSS refused the creation request, so no instance project was created: fix the reported problem and retry. If the target key itself is the problem, rerun create-instance with targetProjectKey omitted to generate a fresh random key (the generated key is a new key, never the rejected one).";
18
19
  const DELETE_INSTANCE_FUTURE_REMEDIATION = "The supplied creation future could not authorize deletion. Inspect that future and the target project, then retry only with a future whose terminal result reports this project.";
19
20
  const DELETE_INSTANCE_UNCONFIRMED_REMEDIATION = "Creation may still be running and DSS returned no future ID. Inspect the app's instances and wait until creation is known terminal before running delete-instance without --unconfirmed-creation.";
@@ -67,28 +68,25 @@ function optionalSuccessorTarget(flags, usage) {
67
68
  }
68
69
  return value.trim();
69
70
  }
70
- export const appCommands = {
71
+ export const appCommands = withUsage("app", {
71
72
  list: {
72
73
  handler: (c) => c.applications.listApps(),
73
- usage: "dss app list",
74
74
  description: "List all Dataiku App templates.",
75
75
  examples: ["dss app list",],
76
76
  },
77
77
  manifest: {
78
78
  handler: (c, a) => {
79
- requireArgs(a, 1, "dss app manifest <appId>");
79
+ requireArgs(a, 1, commandUsage("app", "manifest"));
80
80
  return c.applications.getAppManifest(a[0]);
81
81
  },
82
- usage: "dss app manifest <appId>",
83
82
  description: "Get the manifest of a Dataiku App template.",
84
83
  examples: ["dss app manifest my-app",],
85
84
  },
86
85
  instances: {
87
86
  handler: (c, a) => {
88
- requireArgs(a, 1, "dss app instances <appId>");
87
+ requireArgs(a, 1, commandUsage("app", "instances"));
89
88
  return c.applications.listInstances(a[0]);
90
89
  },
91
- usage: "dss app instances <appId>",
92
90
  description: "List instances created from a Dataiku App template.",
93
91
  examples: ["dss app instances my-app",],
94
92
  },
@@ -97,7 +95,6 @@ export const appCommands = {
97
95
  requireNoArgs(a, MANIFEST_VERSION_USAGE);
98
96
  return c.applications.getManifestVersion(f["project-key"]);
99
97
  },
100
- usage: MANIFEST_VERSION_USAGE,
101
98
  description: "Read the app-manifest version of a Dataiku App template or app-instance project: the raw persisted string only, never a synthesized default.",
102
99
  examples: ["dss app manifest-version --project-key MYAPP_TEMPLATE",],
103
100
  },
@@ -117,7 +114,6 @@ export const appCommands = {
117
114
  requiredExternalGates: [VISUAL_UI_GATE,],
118
115
  };
119
116
  },
120
- usage: VERIFY_INSTANCE_USAGE,
121
117
  description: "Read-only API readiness check for an app instance: project type, registration under the app, authoritative raw manifest version, and manifest reference validation. The visual UI remains an explicit external SSO gate.",
122
118
  examples: [
123
119
  "dss app verify-instance my-app --project-key RELEASE_INSTANCE",
@@ -388,7 +384,6 @@ export const appCommands = {
388
384
  : {}),
389
385
  };
390
386
  },
391
- usage: CREATE_INSTANCE_USAGE,
392
387
  description: "Create an app instance from a Dataiku App template, optionally waiting for the creation future. Omit targetProjectKey to generate a random APP_ key (the default display name); explicit keys are trimmed and must be absent.",
393
388
  examples: [
394
389
  'dss app create-instance my-app --data \'{"targetProjectKey":"NEWPROJ"}\'',
@@ -409,7 +404,6 @@ export const appCommands = {
409
404
  dryRun: true,
410
405
  }, SUCCESSOR_PREFLIGHT_USAGE);
411
406
  },
412
- usage: SUCCESSOR_PREFLIGHT_USAGE,
413
407
  description: "Run every read-only successor gate before changing the template version: validate the template, verify the predecessor, prove an explicit --to target absent, and optionally snapshot the predecessor ACL. Omit --to to preflight generated-key mode, where no target exists yet and nothing is probed or allocated.",
414
408
  examples: [
415
409
  "dss app successor-preflight my-app --from OLD_INSTANCE --to NEW_INSTANCE",
@@ -432,7 +426,6 @@ export const appCommands = {
432
426
  pollIntervalMs: num(f["poll-interval"], "--poll-interval"),
433
427
  }, CREATE_SUCCESSOR_USAGE);
434
428
  },
435
- usage: CREATE_SUCCESSOR_USAGE,
436
429
  description: "Create a new app instance from the current template version alongside an existing instance. An explicit --to keeps the strict caller-chosen-key contract (proven absent before the single POST); omit --to to generate the successor key once during apply and let the terminal future name it. The predecessor is never modified and is retired separately and deliberately; the creation future is always awaited.",
437
430
  examples: [
438
431
  "dss app create-successor-instance my-app --from OLD_INSTANCE --to NEW_INSTANCE",
@@ -442,20 +435,18 @@ export const appCommands = {
442
435
  },
443
436
  "instance-manifest": {
444
437
  handler: (c, a, f) => {
445
- requireNoArgs(a, "dss app instance-manifest [--project-key KEY]");
438
+ requireNoArgs(a, commandUsage("app", "instance-manifest"));
446
439
  return c.applications.getInstanceManifest(f["project-key"]);
447
440
  },
448
- usage: "dss app instance-manifest [--project-key KEY]",
449
441
  description: "Get the app manifest of a Dataiku App template or app-instance project.",
450
442
  examples: ["dss app instance-manifest --project-key MYINSTANCE",],
451
443
  },
452
444
  "save-instance-manifest": {
453
445
  handler: (c, a, f) => {
454
- requireNoArgs(a, "dss app save-instance-manifest (--data JSON|--data-file PATH|--stdin) [--project-key KEY]");
446
+ requireNoArgs(a, commandUsage("app", "save-instance-manifest"));
455
447
  const manifest = requiredJsonInput(f, "--data, --data-file, or --stdin is required (manifest JSON).");
456
448
  return c.applications.saveInstanceManifest(manifest, f["project-key"]);
457
449
  },
458
- usage: "dss app save-instance-manifest (--data JSON|--data-file PATH|--stdin) [--project-key KEY]",
459
450
  description: "Save the app manifest of a Dataiku App template project (homepage sections, use-as-recipe settings). Classic app-instance project manifests are read-only through this endpoint.",
460
451
  examples: [
461
452
  "dss app save-instance-manifest --data-file manifest.json --project-key MYAPP_TEMPLATE",
@@ -506,7 +497,6 @@ export const appCommands = {
506
497
  uiPublicationVerified: false,
507
498
  };
508
499
  },
509
- usage: SET_MANIFEST_VERSION_USAGE,
510
500
  description: "Set the raw app-manifest version and/or version notes of a Dataiku App template through the public app-manifest endpoint. This is not a publish transaction: the persisted string becomes the template version that new instances inherit, and the visual UI remains an external gate.",
511
501
  examples: [
512
502
  "dss app set-manifest-version --manifest-version 2.0.0 --project-key MYAPP_TEMPLATE",
@@ -515,7 +505,7 @@ export const appCommands = {
515
505
  },
516
506
  "validate-manifest": {
517
507
  handler: async (c, a, f) => {
518
- requireNoArgs(a, "dss app validate-manifest [--data JSON|--data-file PATH|--stdin] [--project-key KEY]");
508
+ requireNoArgs(a, commandUsage("app", "validate-manifest"));
519
509
  const payload = jsonInput(f);
520
510
  const manifest = payload ?? await c.applications.getInstanceManifest(f["project-key"]);
521
511
  const result = await c.applications.validateAppManifest(manifest, f["project-key"]);
@@ -524,7 +514,6 @@ export const appCommands = {
524
514
  }
525
515
  return result;
526
516
  },
527
- usage: "dss app validate-manifest [--data JSON|--data-file PATH|--stdin] [--project-key KEY]",
528
517
  description: "Validate an app manifest against source-verifiable reference data (scenario IDs, managed-folder IDs, variable names). Without a payload, reads the target project's app manifest.",
529
518
  examples: [
530
519
  "dss app validate-manifest --data-file manifest.json --project-key MYAPP_TEMPLATE",
@@ -533,11 +522,10 @@ export const appCommands = {
533
522
  },
534
523
  "compare-manifest": {
535
524
  handler: (c, a, f) => {
536
- requireArgs(a, 1, "dss app compare-manifest <appId> --project-key KEY");
537
- const projectKey = requiredStringFlag(f, "project-key", "dss app compare-manifest <appId> --project-key KEY");
525
+ requireArgs(a, 1, commandUsage("app", "compare-manifest"));
526
+ const projectKey = requiredStringFlag(f, "project-key", commandUsage("app", "compare-manifest"));
538
527
  return c.applications.compareAppManifest(a[0], projectKey);
539
528
  },
540
- usage: "dss app compare-manifest <appId> --project-key KEY",
541
529
  description: "Compare a Dataiku App template with the target app instance (normalized hashes and deterministic path-level differences; only project identity fields are omitted).",
542
530
  examples: ["dss app compare-manifest my-app --project-key MYINSTANCE",],
543
531
  },
@@ -720,7 +708,6 @@ export const appCommands = {
720
708
  pollCount: waited.pollCount,
721
709
  };
722
710
  },
723
- usage: DELETE_INSTANCE_USAGE,
724
711
  description: "Delete an app-instance project (destructive: removes the instance project). With --future-id, requires the recorded project-incarnation hash, waits without aborting, verifies that the terminal future reports this target, rechecks the incarnation, then deletes.",
725
712
  examples: [
726
713
  "dss app delete-instance --project-key MYINSTANCE",
@@ -729,16 +716,15 @@ export const appCommands = {
729
716
  },
730
717
  "business-app-instance-permissions": {
731
718
  handler: (c, a) => {
732
- requireArgs(a, 3, "dss app business-app-instance-permissions <businessAppId> <instanceProjectKey> <userLogin>");
719
+ requireArgs(a, 3, commandUsage("app", "business-app-instance-permissions"));
733
720
  return c.applications.getBusinessAppInstanceUserPermissions(a[0], a[1], a[2]);
734
721
  },
735
- usage: "dss app business-app-instance-permissions <businessAppId> <instanceProjectKey> <userLogin>",
736
722
  description: "Get a user's effective permissions on a Business App instance.",
737
723
  examples: ["dss app business-app-instance-permissions my-bapp INSTANCEPROJ alice",],
738
724
  },
739
725
  "permissions-snapshot": {
740
726
  handler: async (c, _a, f) => {
741
- const usage = "dss app permissions-snapshot --output PATH [--project-key KEY]";
727
+ const usage = commandUsage("app", "permissions-snapshot");
742
728
  requireNoArgs(_a, usage);
743
729
  const output = requiredStringFlag(f, "output", usage);
744
730
  const projectKey = c.resolveProjectKey(f["project-key"]);
@@ -757,7 +743,6 @@ export const appCommands = {
757
743
  capturedAt: snapshot.capturedAt,
758
744
  };
759
745
  },
760
- usage: "dss app permissions-snapshot --output PATH [--project-key KEY]",
761
746
  description: "Snapshot a project's access-control permissions to a local owner-only JSON file with a canonical integrity hash; commit it only when repository policy permits.",
762
747
  examples: [
763
748
  "dss app permissions-snapshot --output app-permissions.json --project-key MYINSTANCE",
@@ -765,7 +750,7 @@ export const appCommands = {
765
750
  },
766
751
  "permissions-diff": {
767
752
  handler: async (c, _a, f) => {
768
- const usage = "dss app permissions-diff --file PATH [--project-key KEY]";
753
+ const usage = commandUsage("app", "permissions-diff");
769
754
  requireNoArgs(_a, usage);
770
755
  const file = requiredStringFlag(f, "file", usage);
771
756
  const snapshot = readAppPermissionsSnapshot(file);
@@ -785,13 +770,12 @@ export const appCommands = {
785
770
  differences: diff.differences,
786
771
  };
787
772
  },
788
- usage: "dss app permissions-diff --file PATH [--project-key KEY]",
789
773
  description: "Compare a permission snapshot file against the live project permissions, returning deterministic path-level differences.",
790
774
  examples: ["dss app permissions-diff --file app-permissions.json --project-key MYINSTANCE",],
791
775
  },
792
776
  "permissions-restore": {
793
777
  handler: async (c, _a, f) => {
794
- const usage = "dss app permissions-restore --file PATH [--project-key KEY] [--dry-run]";
778
+ const usage = commandUsage("app", "permissions-restore");
795
779
  requireNoArgs(_a, usage);
796
780
  const file = requiredStringFlag(f, "file", usage);
797
781
  const snapshot = readAppPermissionsSnapshot(file);
@@ -840,10 +824,9 @@ export const appCommands = {
840
824
  applied: true,
841
825
  };
842
826
  },
843
- usage: "dss app permissions-restore --file PATH [--project-key KEY] [--dry-run]",
844
827
  description: "Restore a project's permissions from a snapshot file: hash-verifies the file, refuses cross-project restores, reads before writing, only PUTs when changed, and refetches to verify the result.",
845
828
  examples: [
846
829
  "dss app permissions-restore --file app-permissions.json --project-key MYINSTANCE --dry-run",
847
830
  ],
848
831
  },
849
- };
832
+ });