zinkee 0.1.41 → 0.1.43
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/AGENTS.md +1 -0
- package/README.md +31 -2
- package/dist/index.js +506 -192
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/api/displays.ts +14 -2
- package/src/api/formulas.test.ts +65 -0
- package/src/api/formulas.ts +67 -0
- package/src/api/schemas.ts +3 -0
- package/src/command-registry.ts +21 -0
- package/src/commands/displays.test.ts +99 -0
- package/src/commands/displays.ts +19 -3
- package/src/commands/formulas.test.ts +194 -0
- package/src/commands/formulas.ts +243 -0
- package/src/commands/schemas.test.ts +89 -0
- package/src/commands/schemas.ts +13 -1
- package/src/program.ts +2 -0
- package/src/utils/examples.ts +110 -5
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
import type { Writable } from "node:stream";
|
|
2
|
+
|
|
3
|
+
import { Command, InvalidArgumentError } from "commander";
|
|
4
|
+
|
|
5
|
+
import {
|
|
6
|
+
FormulasApi,
|
|
7
|
+
type FormulaRecomputeInput,
|
|
8
|
+
type FormulaRecomputeResponse,
|
|
9
|
+
} from "../api/formulas.js";
|
|
10
|
+
import { ApiClient } from "../client.js";
|
|
11
|
+
import { defaultConfigPath, readRuntimeConfig } from "../config.js";
|
|
12
|
+
import {
|
|
13
|
+
normalizeUuidOrSlug,
|
|
14
|
+
type NormalizedUuidOrSlug,
|
|
15
|
+
} from "../parsers/selectors.js";
|
|
16
|
+
import { resolveRuntimeContext } from "../runtime-context.js";
|
|
17
|
+
import type { RuntimeOverrides } from "../types.js";
|
|
18
|
+
import { CliError } from "../utils/errors.js";
|
|
19
|
+
import { buildJsonSuccess } from "../utils/output.js";
|
|
20
|
+
|
|
21
|
+
interface CommandIo {
|
|
22
|
+
write(chunk: string): unknown;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export interface RegisterFormulasCommandsOptions {
|
|
26
|
+
configPath?: string;
|
|
27
|
+
stdout?: CommandIo;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
interface GlobalOptions extends RuntimeOverrides {}
|
|
31
|
+
|
|
32
|
+
interface ConfirmedCommandOptions {
|
|
33
|
+
yes?: boolean;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
function getCommandIo(stdout: CommandIo | undefined): CommandIo {
|
|
37
|
+
return stdout ?? (process.stdout as Writable);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
function writeLine(stdout: CommandIo, value: string): void {
|
|
41
|
+
stdout.write(`${value}\n`);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
function getGlobalOptions(command: Command): GlobalOptions {
|
|
45
|
+
return command.optsWithGlobals<GlobalOptions>();
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
function toConfigurationError(filePath: string, error: unknown): never {
|
|
49
|
+
if (error instanceof CliError) {
|
|
50
|
+
throw error;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
if (
|
|
54
|
+
typeof error === "object" &&
|
|
55
|
+
error !== null &&
|
|
56
|
+
"code" in error &&
|
|
57
|
+
error.code === "ENOENT"
|
|
58
|
+
) {
|
|
59
|
+
throw new CliError("configuration_error", `Config file not found at ${filePath}.`);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
if (error instanceof Error) {
|
|
63
|
+
throw new CliError("configuration_error", error.message);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
throw error;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
function createFormulasApi(
|
|
70
|
+
command: Command,
|
|
71
|
+
filePath: string,
|
|
72
|
+
): { api: FormulasApi; json: boolean; readOnly: boolean } {
|
|
73
|
+
try {
|
|
74
|
+
const config = readRuntimeConfig(filePath);
|
|
75
|
+
const runtime = resolveRuntimeContext(config, getGlobalOptions(command));
|
|
76
|
+
|
|
77
|
+
if (!runtime.baseUrl) {
|
|
78
|
+
throw new CliError(
|
|
79
|
+
"configuration_error",
|
|
80
|
+
`Resolved profile "${runtime.profile}" is missing a base URL.`,
|
|
81
|
+
);
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
return {
|
|
85
|
+
api: new FormulasApi(
|
|
86
|
+
new ApiClient({
|
|
87
|
+
baseUrl: runtime.baseUrl,
|
|
88
|
+
apiKey: runtime.apiKey,
|
|
89
|
+
}),
|
|
90
|
+
),
|
|
91
|
+
json: runtime.json,
|
|
92
|
+
readOnly: runtime.readOnly,
|
|
93
|
+
};
|
|
94
|
+
} catch (error) {
|
|
95
|
+
toConfigurationError(filePath, error);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
function ensureWritable(commandName: string, readOnly: boolean): void {
|
|
100
|
+
if (readOnly) {
|
|
101
|
+
throw new CliError(
|
|
102
|
+
"command_not_allowed_in_read_only_mode",
|
|
103
|
+
`Command "${commandName}" is not allowed in read-only mode.`,
|
|
104
|
+
{
|
|
105
|
+
commandMode: "write",
|
|
106
|
+
executionMode: "read-only",
|
|
107
|
+
},
|
|
108
|
+
);
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
function ensureConfirmed(commandName: string, confirmed: boolean | undefined): void {
|
|
113
|
+
if (!confirmed) {
|
|
114
|
+
throw new CliError(
|
|
115
|
+
"invalid_cli_usage",
|
|
116
|
+
`Command "${commandName}" requires --yes because it may enqueue a large recalculation.`,
|
|
117
|
+
);
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
function parseUuidOrSlugSelector(input: string): NormalizedUuidOrSlug {
|
|
122
|
+
try {
|
|
123
|
+
return normalizeUuidOrSlug(input);
|
|
124
|
+
} catch (error) {
|
|
125
|
+
const message = error instanceof Error ? error.message : "Invalid selector.";
|
|
126
|
+
throw new InvalidArgumentError(message);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
function emitResult(
|
|
131
|
+
stdout: CommandIo,
|
|
132
|
+
commandName: string,
|
|
133
|
+
result: FormulaRecomputeResponse,
|
|
134
|
+
configPath: string,
|
|
135
|
+
json: boolean,
|
|
136
|
+
): void {
|
|
137
|
+
if (json) {
|
|
138
|
+
writeLine(
|
|
139
|
+
stdout,
|
|
140
|
+
JSON.stringify(buildJsonSuccess(result, { command: commandName, configPath })),
|
|
141
|
+
);
|
|
142
|
+
return;
|
|
143
|
+
}
|
|
144
|
+
|
|
145
|
+
writeLine(
|
|
146
|
+
stdout,
|
|
147
|
+
`Queued ${result.eventsQueued} formula recalculation event(s) for ${result.scope.toLowerCase()} scope (request ${result.requestId}).`,
|
|
148
|
+
);
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
async function recompute(
|
|
152
|
+
command: Command,
|
|
153
|
+
commandName: string,
|
|
154
|
+
input: FormulaRecomputeInput,
|
|
155
|
+
options: RegisterFormulasCommandsOptions,
|
|
156
|
+
requireConfirmation: boolean,
|
|
157
|
+
confirmed?: boolean,
|
|
158
|
+
): Promise<void> {
|
|
159
|
+
const configPath = options.configPath ?? defaultConfigPath;
|
|
160
|
+
const stdout = getCommandIo(options.stdout);
|
|
161
|
+
const { api, json, readOnly } = createFormulasApi(command, configPath);
|
|
162
|
+
|
|
163
|
+
ensureWritable(commandName, readOnly);
|
|
164
|
+
if (requireConfirmation) {
|
|
165
|
+
ensureConfirmed(commandName, confirmed);
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
const result = await api.recompute(input);
|
|
169
|
+
emitResult(stdout, commandName, result, configPath, json);
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
export function registerFormulasCommands(
|
|
173
|
+
program: Command,
|
|
174
|
+
options: RegisterFormulasCommandsOptions = {},
|
|
175
|
+
): void {
|
|
176
|
+
const formulas = program
|
|
177
|
+
.command("formulas")
|
|
178
|
+
.description("Recalculate formula values");
|
|
179
|
+
const recomputeCommand = formulas
|
|
180
|
+
.command("recompute")
|
|
181
|
+
.description("Queue a full formula recalculation");
|
|
182
|
+
|
|
183
|
+
recomputeCommand
|
|
184
|
+
.command("field")
|
|
185
|
+
.description("Queue recalculation of one formula column")
|
|
186
|
+
.argument("<schema>", "schema UUID or slug", parseUuidOrSlugSelector)
|
|
187
|
+
.argument("<field>", "formula field UUID or slug", parseUuidOrSlugSelector)
|
|
188
|
+
.action(
|
|
189
|
+
async function action(
|
|
190
|
+
this: Command,
|
|
191
|
+
schema: NormalizedUuidOrSlug,
|
|
192
|
+
field: NormalizedUuidOrSlug,
|
|
193
|
+
) {
|
|
194
|
+
await recompute(
|
|
195
|
+
this,
|
|
196
|
+
"formulas recompute field",
|
|
197
|
+
{ scope: "FIELD", schema, field },
|
|
198
|
+
options,
|
|
199
|
+
false,
|
|
200
|
+
);
|
|
201
|
+
},
|
|
202
|
+
);
|
|
203
|
+
|
|
204
|
+
recomputeCommand
|
|
205
|
+
.command("schema")
|
|
206
|
+
.description("Queue recalculation of all active formulas in one schema")
|
|
207
|
+
.argument("<schema>", "schema UUID or slug", parseUuidOrSlugSelector)
|
|
208
|
+
.option("--yes", "confirm the potentially expensive recalculation")
|
|
209
|
+
.action(
|
|
210
|
+
async function action(
|
|
211
|
+
this: Command,
|
|
212
|
+
schema: NormalizedUuidOrSlug,
|
|
213
|
+
commandOptions: ConfirmedCommandOptions,
|
|
214
|
+
) {
|
|
215
|
+
await recompute(
|
|
216
|
+
this,
|
|
217
|
+
"formulas recompute schema",
|
|
218
|
+
{ scope: "SCHEMA", schema },
|
|
219
|
+
options,
|
|
220
|
+
true,
|
|
221
|
+
commandOptions.yes,
|
|
222
|
+
);
|
|
223
|
+
},
|
|
224
|
+
);
|
|
225
|
+
|
|
226
|
+
recomputeCommand
|
|
227
|
+
.command("workspace")
|
|
228
|
+
.description("Queue recalculation of all active formulas in the workspace")
|
|
229
|
+
.option("--yes", "confirm the potentially expensive recalculation")
|
|
230
|
+
.action(async function action(
|
|
231
|
+
this: Command,
|
|
232
|
+
commandOptions: ConfirmedCommandOptions,
|
|
233
|
+
) {
|
|
234
|
+
await recompute(
|
|
235
|
+
this,
|
|
236
|
+
"formulas recompute workspace",
|
|
237
|
+
{ scope: "WORKSPACE" },
|
|
238
|
+
options,
|
|
239
|
+
true,
|
|
240
|
+
commandOptions.yes,
|
|
241
|
+
);
|
|
242
|
+
});
|
|
243
|
+
}
|
|
@@ -381,6 +381,48 @@ describe("schemas commands", () => {
|
|
|
381
381
|
});
|
|
382
382
|
});
|
|
383
383
|
|
|
384
|
+
it("creates fields with a description from the dedicated flag", async () => {
|
|
385
|
+
const configPath = createApiConfig();
|
|
386
|
+
const output = createStdoutBuffer();
|
|
387
|
+
const fetchMock = createFetchMock();
|
|
388
|
+
mockSchemaLookup(fetchMock);
|
|
389
|
+
fetchMock.mockResolvedValueOnce(
|
|
390
|
+
jsonResponse({
|
|
391
|
+
id: "field-1",
|
|
392
|
+
type: "TextField",
|
|
393
|
+
slug: "email",
|
|
394
|
+
label: "Email",
|
|
395
|
+
description: "Primary contact email",
|
|
396
|
+
}),
|
|
397
|
+
);
|
|
398
|
+
const program = buildProgram({ configPath, stdout: output.stdout });
|
|
399
|
+
|
|
400
|
+
await program.parseAsync([
|
|
401
|
+
"node",
|
|
402
|
+
"zinkee",
|
|
403
|
+
"--json",
|
|
404
|
+
"schemas",
|
|
405
|
+
"fields",
|
|
406
|
+
"create",
|
|
407
|
+
"contacts",
|
|
408
|
+
"--type",
|
|
409
|
+
"text",
|
|
410
|
+
"--slug",
|
|
411
|
+
"email",
|
|
412
|
+
"--label",
|
|
413
|
+
"Email",
|
|
414
|
+
"--description",
|
|
415
|
+
"Primary contact email",
|
|
416
|
+
]);
|
|
417
|
+
|
|
418
|
+
expect(JSON.parse(String(fetchMock.mock.calls[1]?.[1]?.body))).toEqual({
|
|
419
|
+
type: "TextField",
|
|
420
|
+
slug: "email",
|
|
421
|
+
label: "Email",
|
|
422
|
+
description: "Primary contact email",
|
|
423
|
+
});
|
|
424
|
+
});
|
|
425
|
+
|
|
384
426
|
it("creates fields with a default value flag", async () => {
|
|
385
427
|
const configPath = createApiConfig();
|
|
386
428
|
const output = createStdoutBuffer();
|
|
@@ -589,6 +631,53 @@ describe("schemas commands", () => {
|
|
|
589
631
|
});
|
|
590
632
|
});
|
|
591
633
|
|
|
634
|
+
it.each([
|
|
635
|
+
["sets", "Shown in customer notifications"],
|
|
636
|
+
["clears", ""],
|
|
637
|
+
])("%s a field description without another metadata change", async (_action, description) => {
|
|
638
|
+
const configPath = createApiConfig();
|
|
639
|
+
const output = createStdoutBuffer();
|
|
640
|
+
const fetchMock = createFetchMock();
|
|
641
|
+
mockSchemaLookup(fetchMock);
|
|
642
|
+
fetchMock.mockResolvedValueOnce(
|
|
643
|
+
jsonResponse({
|
|
644
|
+
id: "550e8400-e29b-41d4-a716-446655440003",
|
|
645
|
+
type: "TextField",
|
|
646
|
+
slug: "notes",
|
|
647
|
+
label: "Notes",
|
|
648
|
+
required: false,
|
|
649
|
+
}),
|
|
650
|
+
);
|
|
651
|
+
fetchMock.mockResolvedValueOnce(
|
|
652
|
+
jsonResponse({
|
|
653
|
+
id: "550e8400-e29b-41d4-a716-446655440003",
|
|
654
|
+
type: "TextField",
|
|
655
|
+
slug: "notes",
|
|
656
|
+
label: "Notes",
|
|
657
|
+
description,
|
|
658
|
+
}),
|
|
659
|
+
);
|
|
660
|
+
const program = buildProgram({ configPath, stdout: output.stdout });
|
|
661
|
+
|
|
662
|
+
await program.parseAsync([
|
|
663
|
+
"node",
|
|
664
|
+
"zinkee",
|
|
665
|
+
"--json",
|
|
666
|
+
"schemas",
|
|
667
|
+
"fields",
|
|
668
|
+
"update",
|
|
669
|
+
"contacts",
|
|
670
|
+
"550E8400-E29B-41D4-A716-446655440003",
|
|
671
|
+
"--description",
|
|
672
|
+
description,
|
|
673
|
+
]);
|
|
674
|
+
|
|
675
|
+
expect(JSON.parse(String(fetchMock.mock.calls[2]?.[1]?.body))).toEqual({
|
|
676
|
+
type: "TextField",
|
|
677
|
+
description,
|
|
678
|
+
});
|
|
679
|
+
});
|
|
680
|
+
|
|
592
681
|
it("strips formula status from update payloads", async () => {
|
|
593
682
|
const configPath = createApiConfig();
|
|
594
683
|
const output = createStdoutBuffer();
|
package/src/commands/schemas.ts
CHANGED
|
@@ -78,6 +78,7 @@ interface FieldCreateCommandOptions {
|
|
|
78
78
|
type?: string;
|
|
79
79
|
slug?: string;
|
|
80
80
|
label?: string;
|
|
81
|
+
description?: string;
|
|
81
82
|
required?: boolean;
|
|
82
83
|
default?: string;
|
|
83
84
|
raw?: string;
|
|
@@ -86,6 +87,7 @@ interface FieldCreateCommandOptions {
|
|
|
86
87
|
|
|
87
88
|
interface FieldUpdateCommandOptions {
|
|
88
89
|
label?: string;
|
|
90
|
+
description?: string;
|
|
89
91
|
required?: boolean;
|
|
90
92
|
default?: string;
|
|
91
93
|
raw?: string;
|
|
@@ -386,6 +388,10 @@ function buildFieldCreateInput(
|
|
|
386
388
|
input.required = options.required;
|
|
387
389
|
}
|
|
388
390
|
|
|
391
|
+
if (options.description !== undefined) {
|
|
392
|
+
input.description = options.description;
|
|
393
|
+
}
|
|
394
|
+
|
|
389
395
|
applyFieldDefaultValue(input, options.default);
|
|
390
396
|
|
|
391
397
|
if ("config" in input && isJsonObject(input.config) && isEmptyObject(input.config)) {
|
|
@@ -462,6 +468,10 @@ function buildFieldUpdateInput(
|
|
|
462
468
|
input.required = options.required;
|
|
463
469
|
}
|
|
464
470
|
|
|
471
|
+
if (options.description !== undefined) {
|
|
472
|
+
input.description = options.description;
|
|
473
|
+
}
|
|
474
|
+
|
|
465
475
|
applyFieldDefaultValue(input, options.default);
|
|
466
476
|
|
|
467
477
|
return input;
|
|
@@ -769,6 +779,7 @@ export function registerSchemasCommands(
|
|
|
769
779
|
.option("--type <type>", `field type (${formatSchemaFieldTypes()})`)
|
|
770
780
|
.option("--slug <slug>", "field slug")
|
|
771
781
|
.option("--label <label>", "field label")
|
|
782
|
+
.option("--description <text>", "field description")
|
|
772
783
|
.option("--required <bool>", "required flag", parseBooleanFlag)
|
|
773
784
|
.option("--default <value>", "default field value")
|
|
774
785
|
.option("--raw <json>", 'raw JSON object payload (see type-specific shapes in --help)')
|
|
@@ -803,6 +814,7 @@ export function registerSchemasCommands(
|
|
|
803
814
|
.argument("<schema>", "schema uuid or slug", parseUuidOrSlugSelector)
|
|
804
815
|
.argument("<field>", "field uuid or slug", parseUuidOrSlugSelector)
|
|
805
816
|
.option("--label <label>", "field label")
|
|
817
|
+
.option("--description <text>", 'field description (use "" to clear)')
|
|
806
818
|
.option("--required <bool>", "required flag", parseBooleanFlag)
|
|
807
819
|
.option("--default <value>", "default field value")
|
|
808
820
|
.option("--raw <json>", "raw JSON object payload")
|
|
@@ -832,7 +844,7 @@ export function registerSchemasCommands(
|
|
|
832
844
|
if (isEmptyObject(input)) {
|
|
833
845
|
throw new CliError(
|
|
834
846
|
"invalid_cli_usage",
|
|
835
|
-
'Provide at least one field update via "--label", "--required", "--raw", or "--raw-file".',
|
|
847
|
+
'Provide at least one field update via "--label", "--description", "--required", "--default", "--raw", or "--raw-file".',
|
|
836
848
|
);
|
|
837
849
|
}
|
|
838
850
|
|
package/src/program.ts
CHANGED
|
@@ -8,6 +8,7 @@ import { registerCommentsCommands } from "./commands/comments.js";
|
|
|
8
8
|
import { registerDisplaysCommands } from "./commands/displays.js";
|
|
9
9
|
import { registerDocumentTemplatesCommands } from "./commands/document-templates.js";
|
|
10
10
|
import { registerFilesCommands } from "./commands/files.js";
|
|
11
|
+
import { registerFormulasCommands } from "./commands/formulas.js";
|
|
11
12
|
import { registerLogsCommands } from "./commands/logs.js";
|
|
12
13
|
import { registerNavigationCommands } from "./commands/navigation.js";
|
|
13
14
|
import { registerProfilesCommands } from "./commands/profiles.js";
|
|
@@ -51,6 +52,7 @@ export function buildProgram(options: BuildProgramOptions = {}): Command {
|
|
|
51
52
|
registerDisplaysCommands(program, options);
|
|
52
53
|
registerDocumentTemplatesCommands(program, options);
|
|
53
54
|
registerFilesCommands(program, options);
|
|
55
|
+
registerFormulasCommands(program, options);
|
|
54
56
|
registerNavigationCommands(program, options);
|
|
55
57
|
registerSchemasCommands(program, options);
|
|
56
58
|
registerRecordsCommands(program, options);
|
package/src/utils/examples.ts
CHANGED
|
@@ -27,6 +27,60 @@ export function buildCommandExamples(examples: readonly CommandExample[]): reado
|
|
|
27
27
|
const SAMPLE_UUID = "550e8400-e29b-41d4-a716-446655440001";
|
|
28
28
|
|
|
29
29
|
const specificExamples: Record<string, readonly CommandExample[]> = {
|
|
30
|
+
"formulas recompute field": buildCommandExamples([
|
|
31
|
+
{
|
|
32
|
+
description: "Queue a full recalculation of one formula column.",
|
|
33
|
+
command: "zinkee --json formulas recompute field invoices total",
|
|
34
|
+
raw: `{
|
|
35
|
+
"scope": "FIELD",
|
|
36
|
+
"schema": "invoices",
|
|
37
|
+
"field": "total"
|
|
38
|
+
}`,
|
|
39
|
+
response: `{
|
|
40
|
+
"requestId": "02ab5d47-cb5f-4eb2-afb8-e9a3a9eb34d4",
|
|
41
|
+
"scope": "FIELD",
|
|
42
|
+
"formulaCount": 1,
|
|
43
|
+
"skippedFormulaCount": 0,
|
|
44
|
+
"eventsQueued": 1,
|
|
45
|
+
"status": "QUEUED"
|
|
46
|
+
}`,
|
|
47
|
+
},
|
|
48
|
+
]),
|
|
49
|
+
"formulas recompute schema": buildCommandExamples([
|
|
50
|
+
{
|
|
51
|
+
description: "Queue recalculation of every active formula in one schema.",
|
|
52
|
+
command: "zinkee --json formulas recompute schema invoices --yes",
|
|
53
|
+
raw: `{
|
|
54
|
+
"scope": "SCHEMA",
|
|
55
|
+
"schema": "invoices"
|
|
56
|
+
}`,
|
|
57
|
+
response: `{
|
|
58
|
+
"requestId": "02ab5d47-cb5f-4eb2-afb8-e9a3a9eb34d4",
|
|
59
|
+
"scope": "SCHEMA",
|
|
60
|
+
"formulaCount": 8,
|
|
61
|
+
"skippedFormulaCount": 1,
|
|
62
|
+
"eventsQueued": 8,
|
|
63
|
+
"status": "QUEUED"
|
|
64
|
+
}`,
|
|
65
|
+
},
|
|
66
|
+
]),
|
|
67
|
+
"formulas recompute workspace": buildCommandExamples([
|
|
68
|
+
{
|
|
69
|
+
description: "Queue recalculation of every active formula in the workspace.",
|
|
70
|
+
command: "zinkee --json formulas recompute workspace --yes",
|
|
71
|
+
raw: `{
|
|
72
|
+
"scope": "WORKSPACE"
|
|
73
|
+
}`,
|
|
74
|
+
response: `{
|
|
75
|
+
"requestId": "02ab5d47-cb5f-4eb2-afb8-e9a3a9eb34d4",
|
|
76
|
+
"scope": "WORKSPACE",
|
|
77
|
+
"formulaCount": 24,
|
|
78
|
+
"skippedFormulaCount": 2,
|
|
79
|
+
"eventsQueued": 24,
|
|
80
|
+
"status": "QUEUED"
|
|
81
|
+
}`,
|
|
82
|
+
},
|
|
83
|
+
]),
|
|
30
84
|
"profiles list": buildCommandExamples([
|
|
31
85
|
{
|
|
32
86
|
description:
|
|
@@ -350,6 +404,22 @@ const specificExamples: Record<string, readonly CommandExample[]> = {
|
|
|
350
404
|
},
|
|
351
405
|
]),
|
|
352
406
|
"schemas fields update": buildCommandExamples([
|
|
407
|
+
{
|
|
408
|
+
description: "Set the field description without changing its label or configuration.",
|
|
409
|
+
command:
|
|
410
|
+
'zinkee --json schemas fields update contacts contact-name --description "Primary name shown for the customer"',
|
|
411
|
+
raw: `{
|
|
412
|
+
"description": "Primary name shown for the customer"
|
|
413
|
+
}`,
|
|
414
|
+
},
|
|
415
|
+
{
|
|
416
|
+
description: "Clear the field description.",
|
|
417
|
+
command:
|
|
418
|
+
'zinkee --json schemas fields update contacts contact-name --description ""',
|
|
419
|
+
raw: `{
|
|
420
|
+
"description": ""
|
|
421
|
+
}`,
|
|
422
|
+
},
|
|
353
423
|
{
|
|
354
424
|
description: "Rename slug and label.",
|
|
355
425
|
command:
|
|
@@ -1175,11 +1245,12 @@ const specificExamples: Record<string, readonly CommandExample[]> = {
|
|
|
1175
1245
|
"displays create": buildCommandExamples([
|
|
1176
1246
|
{
|
|
1177
1247
|
description:
|
|
1178
|
-
"Create a freeform display with an initial widget layout. Freeform layouts travel through --freeform-layouts.",
|
|
1248
|
+
"Create a described freeform display with an initial widget layout. Freeform layouts travel through --freeform-layouts.",
|
|
1179
1249
|
command:
|
|
1180
|
-
`zinkee --json displays create --name "Control Proyecto Freeform" --template freeform --freeform-layouts '{"lg":[{"i":"widget-1","x":0,"y":0,"w":6,"h":5}]}'`,
|
|
1250
|
+
`zinkee --json displays create --name "Control Proyecto Freeform" --description "Project delivery overview" --template freeform --freeform-layouts '{"lg":[{"i":"widget-1","x":0,"y":0,"w":6,"h":5}]}'`,
|
|
1181
1251
|
raw: `{
|
|
1182
1252
|
"name": "Control Proyecto Freeform",
|
|
1253
|
+
"description": "Project delivery overview",
|
|
1183
1254
|
"layout": {
|
|
1184
1255
|
"template": "freeform",
|
|
1185
1256
|
"freeformLayouts": {
|
|
@@ -3081,6 +3152,22 @@ const specificExamples: Record<string, readonly CommandExample[]> = {
|
|
|
3081
3152
|
},
|
|
3082
3153
|
]),
|
|
3083
3154
|
"displays update": buildCommandExamples([
|
|
3155
|
+
{
|
|
3156
|
+
description: "Update only the display description.",
|
|
3157
|
+
command:
|
|
3158
|
+
'zinkee --json displays update 0f6f062f-1478-4df2-96a1-c495d037d260 --description "Sales pipeline overview"',
|
|
3159
|
+
raw: `{
|
|
3160
|
+
"description": "Sales pipeline overview"
|
|
3161
|
+
}`,
|
|
3162
|
+
},
|
|
3163
|
+
{
|
|
3164
|
+
description: "Clear the display description.",
|
|
3165
|
+
command:
|
|
3166
|
+
'zinkee --json displays update 0f6f062f-1478-4df2-96a1-c495d037d260 --description ""',
|
|
3167
|
+
raw: `{
|
|
3168
|
+
"description": ""
|
|
3169
|
+
}`,
|
|
3170
|
+
},
|
|
3084
3171
|
{
|
|
3085
3172
|
description: "Rename a display (patch of top-level metadata only).",
|
|
3086
3173
|
command:
|
|
@@ -4463,8 +4550,26 @@ function buildSchemaFieldCreateExamples(type?: string): readonly CommandExample[
|
|
|
4463
4550
|
definition.examplePayloads.map((example) => ({ definition, example })),
|
|
4464
4551
|
);
|
|
4465
4552
|
|
|
4466
|
-
|
|
4467
|
-
|
|
4553
|
+
const flagExamples: CommandExample[] =
|
|
4554
|
+
selectedDefinition === undefined || selectedDefinition.key === "text"
|
|
4555
|
+
? [
|
|
4556
|
+
{
|
|
4557
|
+
description: "Text field with a description.",
|
|
4558
|
+
command:
|
|
4559
|
+
'zinkee --json schemas fields create contacts --type text --slug customer-name --label "Customer Name" --description "Primary name shown for the customer"',
|
|
4560
|
+
raw: `{
|
|
4561
|
+
"type": "TextField",
|
|
4562
|
+
"slug": "customer-name",
|
|
4563
|
+
"label": "Customer Name",
|
|
4564
|
+
"description": "Primary name shown for the customer"
|
|
4565
|
+
}`,
|
|
4566
|
+
},
|
|
4567
|
+
]
|
|
4568
|
+
: [];
|
|
4569
|
+
|
|
4570
|
+
return buildCommandExamples([
|
|
4571
|
+
...flagExamples,
|
|
4572
|
+
...flat.map(({ example }, index) => {
|
|
4468
4573
|
const slug =
|
|
4469
4574
|
typeof example.payload.slug === "string" ? example.payload.slug : "field";
|
|
4470
4575
|
const command = `zinkee --json schemas fields create contacts --raw '${JSON.stringify(example.payload)}'`;
|
|
@@ -4486,7 +4591,7 @@ function buildSchemaFieldCreateExamples(type?: string): readonly CommandExample[
|
|
|
4486
4591
|
command,
|
|
4487
4592
|
};
|
|
4488
4593
|
}),
|
|
4489
|
-
);
|
|
4594
|
+
]);
|
|
4490
4595
|
}
|
|
4491
4596
|
|
|
4492
4597
|
export function getCommandExamples(
|