@sanity/runtime-cli 10.11.0 → 10.11.2
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 +17 -17
- package/dist/actions/blueprints/blueprint.js +11 -1
- package/dist/actions/blueprints/config.d.ts +11 -2
- package/dist/actions/blueprints/config.js +34 -4
- package/dist/actions/blueprints/index.js +14 -5
- package/dist/actions/blueprints/stacks.d.ts +5 -4
- package/dist/actions/blueprints/stacks.js +10 -4
- package/dist/actions/sanity/projects.d.ts +4 -2
- package/dist/actions/sanity/projects.js +5 -2
- package/dist/cores/blueprints/config.js +11 -4
- package/dist/cores/blueprints/deploy.js +10 -6
- package/dist/cores/blueprints/destroy.js +2 -2
- package/dist/cores/blueprints/doctor.js +3 -3
- package/dist/cores/blueprints/init.js +17 -8
- package/dist/cores/blueprints/plan.js +4 -1
- package/dist/cores/blueprints/stacks.js +1 -1
- package/dist/cores/index.js +1 -1
- package/dist/utils/display/prompt.js +3 -2
- package/dist/utils/get-headers.d.ts +2 -2
- package/dist/utils/get-headers.js +5 -14
- package/dist/utils/types.d.ts +6 -3
- package/dist/utils/validate/resource.js +3 -3
- package/oclif.manifest.json +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -20,7 +20,7 @@ $ npm install -g @sanity/runtime-cli
|
|
|
20
20
|
$ sanity-run COMMAND
|
|
21
21
|
running command...
|
|
22
22
|
$ sanity-run (--version)
|
|
23
|
-
@sanity/runtime-cli/10.11.
|
|
23
|
+
@sanity/runtime-cli/10.11.2 linux-x64 node-v22.20.0
|
|
24
24
|
$ sanity-run --help [COMMAND]
|
|
25
25
|
USAGE
|
|
26
26
|
$ sanity-run COMMAND
|
|
@@ -89,7 +89,7 @@ EXAMPLES
|
|
|
89
89
|
$ sanity-run blueprints add function --name my-function --fn-type document-create --fn-type document-update --lang js
|
|
90
90
|
```
|
|
91
91
|
|
|
92
|
-
_See code: [src/commands/blueprints/add.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
92
|
+
_See code: [src/commands/blueprints/add.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/add.ts)_
|
|
93
93
|
|
|
94
94
|
## `sanity-run blueprints config`
|
|
95
95
|
|
|
@@ -120,7 +120,7 @@ EXAMPLES
|
|
|
120
120
|
$ sanity-run blueprints config --edit --project-id <projectId> --stack-id <stackId>
|
|
121
121
|
```
|
|
122
122
|
|
|
123
|
-
_See code: [src/commands/blueprints/config.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
123
|
+
_See code: [src/commands/blueprints/config.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/config.ts)_
|
|
124
124
|
|
|
125
125
|
## `sanity-run blueprints deploy`
|
|
126
126
|
|
|
@@ -142,7 +142,7 @@ EXAMPLES
|
|
|
142
142
|
$ sanity-run blueprints deploy --no-wait
|
|
143
143
|
```
|
|
144
144
|
|
|
145
|
-
_See code: [src/commands/blueprints/deploy.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
145
|
+
_See code: [src/commands/blueprints/deploy.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/deploy.ts)_
|
|
146
146
|
|
|
147
147
|
## `sanity-run blueprints destroy`
|
|
148
148
|
|
|
@@ -167,7 +167,7 @@ EXAMPLES
|
|
|
167
167
|
$ sanity-run blueprints destroy --stack-id <stackId> --project-id <projectId> --force --no-wait
|
|
168
168
|
```
|
|
169
169
|
|
|
170
|
-
_See code: [src/commands/blueprints/destroy.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
170
|
+
_See code: [src/commands/blueprints/destroy.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/destroy.ts)_
|
|
171
171
|
|
|
172
172
|
## `sanity-run blueprints doctor`
|
|
173
173
|
|
|
@@ -185,7 +185,7 @@ DESCRIPTION
|
|
|
185
185
|
Diagnose potential issues with Blueprint configuration
|
|
186
186
|
```
|
|
187
187
|
|
|
188
|
-
_See code: [src/commands/blueprints/doctor.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
188
|
+
_See code: [src/commands/blueprints/doctor.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/doctor.ts)_
|
|
189
189
|
|
|
190
190
|
## `sanity-run blueprints info`
|
|
191
191
|
|
|
@@ -207,7 +207,7 @@ EXAMPLES
|
|
|
207
207
|
$ sanity-run blueprints info --stack-id <stackId>
|
|
208
208
|
```
|
|
209
209
|
|
|
210
|
-
_See code: [src/commands/blueprints/info.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
210
|
+
_See code: [src/commands/blueprints/info.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/info.ts)_
|
|
211
211
|
|
|
212
212
|
## `sanity-run blueprints init [DIR]`
|
|
213
213
|
|
|
@@ -245,7 +245,7 @@ EXAMPLES
|
|
|
245
245
|
$ sanity-run blueprints init --blueprint-type <json|js|ts> --stack-name <stackName>
|
|
246
246
|
```
|
|
247
247
|
|
|
248
|
-
_See code: [src/commands/blueprints/init.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
248
|
+
_See code: [src/commands/blueprints/init.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/init.ts)_
|
|
249
249
|
|
|
250
250
|
## `sanity-run blueprints logs`
|
|
251
251
|
|
|
@@ -267,7 +267,7 @@ EXAMPLES
|
|
|
267
267
|
$ sanity-run blueprints logs --watch
|
|
268
268
|
```
|
|
269
269
|
|
|
270
|
-
_See code: [src/commands/blueprints/logs.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
270
|
+
_See code: [src/commands/blueprints/logs.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/logs.ts)_
|
|
271
271
|
|
|
272
272
|
## `sanity-run blueprints plan`
|
|
273
273
|
|
|
@@ -284,7 +284,7 @@ EXAMPLES
|
|
|
284
284
|
$ sanity-run blueprints plan
|
|
285
285
|
```
|
|
286
286
|
|
|
287
|
-
_See code: [src/commands/blueprints/plan.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
287
|
+
_See code: [src/commands/blueprints/plan.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/plan.ts)_
|
|
288
288
|
|
|
289
289
|
## `sanity-run blueprints stacks`
|
|
290
290
|
|
|
@@ -306,7 +306,7 @@ EXAMPLES
|
|
|
306
306
|
$ sanity-run blueprints stacks --project-id <projectId>
|
|
307
307
|
```
|
|
308
308
|
|
|
309
|
-
_See code: [src/commands/blueprints/stacks.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
309
|
+
_See code: [src/commands/blueprints/stacks.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/blueprints/stacks.ts)_
|
|
310
310
|
|
|
311
311
|
## `sanity-run functions dev`
|
|
312
312
|
|
|
@@ -328,7 +328,7 @@ EXAMPLES
|
|
|
328
328
|
$ sanity-run functions dev --port 8974
|
|
329
329
|
```
|
|
330
330
|
|
|
331
|
-
_See code: [src/commands/functions/dev.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
331
|
+
_See code: [src/commands/functions/dev.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/dev.ts)_
|
|
332
332
|
|
|
333
333
|
## `sanity-run functions env add NAME KEY VALUE`
|
|
334
334
|
|
|
@@ -350,7 +350,7 @@ EXAMPLES
|
|
|
350
350
|
$ sanity-run functions env add MyFunction API_URL https://api.example.com/
|
|
351
351
|
```
|
|
352
352
|
|
|
353
|
-
_See code: [src/commands/functions/env/add.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
353
|
+
_See code: [src/commands/functions/env/add.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/env/add.ts)_
|
|
354
354
|
|
|
355
355
|
## `sanity-run functions env list NAME`
|
|
356
356
|
|
|
@@ -370,7 +370,7 @@ EXAMPLES
|
|
|
370
370
|
$ sanity-run functions env list MyFunction
|
|
371
371
|
```
|
|
372
372
|
|
|
373
|
-
_See code: [src/commands/functions/env/list.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
373
|
+
_See code: [src/commands/functions/env/list.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/env/list.ts)_
|
|
374
374
|
|
|
375
375
|
## `sanity-run functions env remove NAME KEY`
|
|
376
376
|
|
|
@@ -391,7 +391,7 @@ EXAMPLES
|
|
|
391
391
|
$ sanity-run functions env remove MyFunction API_URL
|
|
392
392
|
```
|
|
393
393
|
|
|
394
|
-
_See code: [src/commands/functions/env/remove.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
394
|
+
_See code: [src/commands/functions/env/remove.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/env/remove.ts)_
|
|
395
395
|
|
|
396
396
|
## `sanity-run functions logs NAME`
|
|
397
397
|
|
|
@@ -425,7 +425,7 @@ EXAMPLES
|
|
|
425
425
|
$ sanity-run functions logs <name> --delete
|
|
426
426
|
```
|
|
427
427
|
|
|
428
|
-
_See code: [src/commands/functions/logs.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
428
|
+
_See code: [src/commands/functions/logs.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/logs.ts)_
|
|
429
429
|
|
|
430
430
|
## `sanity-run functions test NAME`
|
|
431
431
|
|
|
@@ -472,7 +472,7 @@ EXAMPLES
|
|
|
472
472
|
$ sanity-run functions test <name> --event update --data-before '{ "title": "before" }' --data-after '{ "title": "after" }'
|
|
473
473
|
```
|
|
474
474
|
|
|
475
|
-
_See code: [src/commands/functions/test.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.
|
|
475
|
+
_See code: [src/commands/functions/test.ts](https://github.com/sanity-io/runtime-cli/blob/v10.11.2/src/commands/functions/test.ts)_
|
|
476
476
|
|
|
477
477
|
## `sanity-run help [COMMAND]`
|
|
478
478
|
|
|
@@ -6,7 +6,7 @@ import { findUpSync } from 'find-up';
|
|
|
6
6
|
import { createJiti } from 'jiti';
|
|
7
7
|
import { isLocalFunctionResource } from '../../utils/types.js';
|
|
8
8
|
import { validateFunctionResource } from '../../utils/validate/resource.js';
|
|
9
|
-
import { readConfigFile } from './config.js';
|
|
9
|
+
import { backfillOrganizationId, readConfigFile } from './config.js';
|
|
10
10
|
const SUPPORTED_FILE_EXTENSIONS = ['.json', '.js', '.mjs', '.ts'];
|
|
11
11
|
let SUPPORTED_FILE_NAMES = SUPPORTED_FILE_EXTENSIONS.map((ext) => `blueprint${ext}`);
|
|
12
12
|
SUPPORTED_FILE_NAMES = [
|
|
@@ -132,6 +132,16 @@ export async function readLocalBlueprint(blueprintPath) {
|
|
|
132
132
|
const { SANITY_ORGANIZATION_ID: envOrganizationId, SANITY_PROJECT_ID: envProjectId, SANITY_BLUEPRINT_STACK_ID: envStackId, } = env;
|
|
133
133
|
const configIds = readConfigFile(foundFilePath);
|
|
134
134
|
const configPath = configIds?.configPath;
|
|
135
|
+
// passively heal config on disk by getting organizationId from projectId
|
|
136
|
+
if (configIds && !configIds.organizationId && configIds.projectId) {
|
|
137
|
+
try {
|
|
138
|
+
await backfillOrganizationId({
|
|
139
|
+
projectId: configIds.projectId,
|
|
140
|
+
blueprintFilePath: foundFilePath,
|
|
141
|
+
});
|
|
142
|
+
}
|
|
143
|
+
catch { }
|
|
144
|
+
}
|
|
135
145
|
let organizationId;
|
|
136
146
|
if (envOrganizationId)
|
|
137
147
|
organizationId = envOrganizationId;
|
|
@@ -10,8 +10,17 @@ export declare function writeConfigFile({ blueprintFilePath, organizationId, pro
|
|
|
10
10
|
stackId?: string;
|
|
11
11
|
} & ({
|
|
12
12
|
organizationId: string;
|
|
13
|
-
projectId?:
|
|
13
|
+
projectId?: string;
|
|
14
14
|
} | {
|
|
15
15
|
projectId: string;
|
|
16
|
-
organizationId?:
|
|
16
|
+
organizationId?: string;
|
|
17
17
|
})): void;
|
|
18
|
+
/**
|
|
19
|
+
* Find and write an organizationId to the config file by getting it from the projectId
|
|
20
|
+
* @throws {Error} if unable to fetch project
|
|
21
|
+
* @returns {Promise<string>} the discovered organizationId
|
|
22
|
+
*/
|
|
23
|
+
export declare function backfillOrganizationId({ blueprintFilePath, projectId, }: {
|
|
24
|
+
blueprintFilePath: string;
|
|
25
|
+
projectId: string;
|
|
26
|
+
}): Promise<string>;
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { existsSync, mkdirSync, readFileSync, writeFileSync } from 'node:fs';
|
|
2
2
|
import { dirname, join } from 'node:path';
|
|
3
3
|
import { cwd } from 'node:process';
|
|
4
|
-
import { BLUEPRINT_CONFIG_FILE, BLUEPRINT_CONFIG_VERSION, BLUEPRINT_DIR } from '../../config.js';
|
|
4
|
+
import config, { BLUEPRINT_CONFIG_FILE, BLUEPRINT_CONFIG_VERSION, BLUEPRINT_DIR, } from '../../config.js';
|
|
5
|
+
import { getProject } from '../sanity/projects.js';
|
|
5
6
|
export function readConfigFile(blueprintFilePath) {
|
|
6
7
|
const blueprintDir = blueprintFilePath ? dirname(blueprintFilePath) : cwd();
|
|
7
8
|
const configPath = join(blueprintDir, BLUEPRINT_DIR, BLUEPRINT_CONFIG_FILE);
|
|
@@ -32,10 +33,39 @@ export function writeConfigFile({ blueprintFilePath, organizationId, projectId,
|
|
|
32
33
|
// config broken, start fresh
|
|
33
34
|
}
|
|
34
35
|
}
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
36
|
+
if (organizationId)
|
|
37
|
+
config.organizationId = organizationId;
|
|
38
|
+
if (projectId)
|
|
39
|
+
config.projectId = projectId;
|
|
40
|
+
if (stackId)
|
|
41
|
+
config.stackId = stackId;
|
|
38
42
|
config.blueprintConfigVersion = BLUEPRINT_CONFIG_VERSION;
|
|
39
43
|
config.updatedAt = Date.now();
|
|
40
44
|
writeFileSync(configPath, JSON.stringify(config, null, 2));
|
|
41
45
|
}
|
|
46
|
+
/**
|
|
47
|
+
* Find and write an organizationId to the config file by getting it from the projectId
|
|
48
|
+
* @throws {Error} if unable to fetch project
|
|
49
|
+
* @returns {Promise<string>} the discovered organizationId
|
|
50
|
+
*/
|
|
51
|
+
export async function backfillOrganizationId({ blueprintFilePath, projectId, }) {
|
|
52
|
+
const token = config.token;
|
|
53
|
+
if (!token)
|
|
54
|
+
throw new Error('No token found');
|
|
55
|
+
let organizationId;
|
|
56
|
+
try {
|
|
57
|
+
const response = await getProject({ token, scopeType: 'project', scopeId: projectId });
|
|
58
|
+
if (!response.ok)
|
|
59
|
+
throw new Error('Failed to get project');
|
|
60
|
+
if (!response.project)
|
|
61
|
+
throw new Error('No project found');
|
|
62
|
+
organizationId = response.project.organizationId;
|
|
63
|
+
}
|
|
64
|
+
catch (error) {
|
|
65
|
+
throw new Error('Failed to backfill organizationId', { cause: error });
|
|
66
|
+
}
|
|
67
|
+
if (!organizationId)
|
|
68
|
+
throw new Error('No organizationId found');
|
|
69
|
+
writeConfigFile({ blueprintFilePath, organizationId });
|
|
70
|
+
return organizationId;
|
|
71
|
+
}
|
|
@@ -33,11 +33,20 @@ export async function getBlueprintAndStack({ token, blueprintPath, }) {
|
|
|
33
33
|
issues.push({ code: 'NO_STACK_ID', message: 'Stack ID not found' });
|
|
34
34
|
return { localBlueprint, issues };
|
|
35
35
|
}
|
|
36
|
-
const
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
36
|
+
const stackResponse = await getStack({
|
|
37
|
+
stackId,
|
|
38
|
+
auth: {
|
|
39
|
+
scopeType: 'project',
|
|
40
|
+
scopeId: projectId,
|
|
41
|
+
token,
|
|
42
|
+
},
|
|
43
|
+
});
|
|
44
|
+
if (!stackResponse.ok) {
|
|
45
|
+
issues.push({ code: 'NO_STACK', message: stackResponse.error || 'Unknown error' });
|
|
40
46
|
return { localBlueprint, issues };
|
|
41
47
|
}
|
|
42
|
-
return {
|
|
48
|
+
return {
|
|
49
|
+
localBlueprint: localBlueprint,
|
|
50
|
+
deployedStack: stackResponse.stack,
|
|
51
|
+
};
|
|
43
52
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { AuthParams, Stack, StackMutation } from '../../utils/types.js';
|
|
1
|
+
import type { AuthParams, ScopeType, Stack, StackMutation } from '../../utils/types.js';
|
|
2
2
|
export declare const stacksUrl: string;
|
|
3
3
|
interface ListStacksResponse {
|
|
4
4
|
ok: boolean;
|
|
@@ -10,7 +10,7 @@ interface GetStackResponse {
|
|
|
10
10
|
ok: boolean;
|
|
11
11
|
error: string | null;
|
|
12
12
|
stack: Stack;
|
|
13
|
-
response
|
|
13
|
+
response?: Response;
|
|
14
14
|
}
|
|
15
15
|
export declare function getStack({ stackId, auth, }: {
|
|
16
16
|
stackId: string;
|
|
@@ -25,9 +25,10 @@ export declare function createStack({ stackMutation, auth, }: {
|
|
|
25
25
|
stackMutation: StackMutation;
|
|
26
26
|
auth: AuthParams;
|
|
27
27
|
}): Promise<CreateStackResponse>;
|
|
28
|
-
export declare function createEmptyStack({ token,
|
|
28
|
+
export declare function createEmptyStack({ token, scopeType, scopeId, name, projectBased, }: {
|
|
29
29
|
token: string;
|
|
30
|
-
|
|
30
|
+
scopeType: ScopeType;
|
|
31
|
+
scopeId: string;
|
|
31
32
|
name: string;
|
|
32
33
|
projectBased?: boolean;
|
|
33
34
|
}): Promise<Stack>;
|
|
@@ -2,6 +2,7 @@ import config from '../../config.js';
|
|
|
2
2
|
import getHeaders from '../../utils/get-headers.js';
|
|
3
3
|
const { apiUrl } = config;
|
|
4
4
|
export const stacksUrl = `${apiUrl}vX/blueprints/stacks`;
|
|
5
|
+
/** Discriminate between Resource and Resource with parameters */
|
|
5
6
|
function hasParameters(obj) {
|
|
6
7
|
return (typeof obj === 'object' &&
|
|
7
8
|
obj !== null &&
|
|
@@ -9,6 +10,7 @@ function hasParameters(obj) {
|
|
|
9
10
|
typeof obj.parameters === 'object' &&
|
|
10
11
|
obj.parameters !== null);
|
|
11
12
|
}
|
|
13
|
+
/** Flatten Resource with parameters */
|
|
12
14
|
function flattenResource(resource) {
|
|
13
15
|
if (hasParameters(resource)) {
|
|
14
16
|
const { parameters, ...rest } = resource;
|
|
@@ -16,6 +18,7 @@ function flattenResource(resource) {
|
|
|
16
18
|
}
|
|
17
19
|
return resource;
|
|
18
20
|
}
|
|
21
|
+
/** Flatten a Stack's resources */
|
|
19
22
|
function flattenStackResources(stack) {
|
|
20
23
|
if (stack && Array.isArray(stack.resources)) {
|
|
21
24
|
return {
|
|
@@ -63,15 +66,18 @@ export async function createStack({ stackMutation, auth, }) {
|
|
|
63
66
|
stack: response.ok ? flattenStackResources(data) : data,
|
|
64
67
|
};
|
|
65
68
|
}
|
|
66
|
-
export async function createEmptyStack({ token,
|
|
69
|
+
export async function createEmptyStack({ token, scopeType, scopeId, name, projectBased = true, }) {
|
|
67
70
|
const stackMutation = {
|
|
68
71
|
name,
|
|
69
|
-
|
|
72
|
+
scopeType,
|
|
73
|
+
scopeId,
|
|
70
74
|
useProjectBasedId: projectBased,
|
|
71
75
|
document: { resources: [] },
|
|
72
76
|
};
|
|
73
|
-
const
|
|
74
|
-
|
|
77
|
+
const response = await createStack({
|
|
78
|
+
stackMutation,
|
|
79
|
+
auth: { token, scopeType, scopeId },
|
|
80
|
+
});
|
|
75
81
|
if (!response.ok) {
|
|
76
82
|
throw new Error(response.error || 'Failed to create new Stack');
|
|
77
83
|
}
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { ScopeType } from '../../utils/types.js';
|
|
1
2
|
export declare const projectsApiPath: string;
|
|
2
3
|
export declare const orgsApiPath: string;
|
|
3
4
|
export interface Project {
|
|
@@ -40,8 +41,9 @@ interface GetProjectResponse {
|
|
|
40
41
|
error: string | null;
|
|
41
42
|
project: Project;
|
|
42
43
|
}
|
|
43
|
-
export declare function getProject({ token,
|
|
44
|
+
export declare function getProject({ token, scopeId, scopeType, }: {
|
|
44
45
|
token: string;
|
|
45
|
-
|
|
46
|
+
scopeId: string;
|
|
47
|
+
scopeType: ScopeType;
|
|
46
48
|
}): Promise<GetProjectResponse>;
|
|
47
49
|
export {};
|
|
@@ -48,8 +48,11 @@ export async function groupProjectsByOrganization({ token, }) {
|
|
|
48
48
|
organizations: orgsWithProjects,
|
|
49
49
|
};
|
|
50
50
|
}
|
|
51
|
-
export async function getProject({ token,
|
|
52
|
-
|
|
51
|
+
export async function getProject({ token, scopeId, scopeType, }) {
|
|
52
|
+
if (scopeType !== 'project') {
|
|
53
|
+
throw new Error('Scope type must be project');
|
|
54
|
+
}
|
|
55
|
+
const response = await fetch(`${projectsApiPath}/${scopeId}`, {
|
|
53
56
|
method: 'GET',
|
|
54
57
|
headers: { Authorization: `Bearer ${token}`, 'Content-Type': 'application/json' },
|
|
55
58
|
});
|
|
@@ -140,7 +140,7 @@ async function testConfigAndReport({ token, stackId, projectId, }) {
|
|
|
140
140
|
const spinner = ora('Testing the configuration...').start();
|
|
141
141
|
const { ok, error } = await getStack({
|
|
142
142
|
stackId,
|
|
143
|
-
auth: { token, projectId },
|
|
143
|
+
auth: { token, scopeType: 'project', scopeId: projectId },
|
|
144
144
|
});
|
|
145
145
|
if (!ok) {
|
|
146
146
|
spinner.fail('Configuration test failed.');
|
|
@@ -151,7 +151,7 @@ async function testConfigAndReport({ token, stackId, projectId, }) {
|
|
|
151
151
|
return { ok, error };
|
|
152
152
|
}
|
|
153
153
|
async function startReinitializeStack({ token, projectId, }) {
|
|
154
|
-
const auth = { token, projectId };
|
|
154
|
+
const auth = { token, scopeType: 'project', scopeId: projectId };
|
|
155
155
|
// stack id IS ST-${projectId} – it has already been checked and doesn't exist
|
|
156
156
|
const { confirm } = await inquirer.prompt([
|
|
157
157
|
{
|
|
@@ -170,8 +170,15 @@ async function startReinitializeStack({ token, projectId, }) {
|
|
|
170
170
|
};
|
|
171
171
|
}
|
|
172
172
|
const projectDisplayName = project.displayName;
|
|
173
|
-
const
|
|
174
|
-
|
|
173
|
+
const response = await createStack({
|
|
174
|
+
stackMutation: {
|
|
175
|
+
name: projectDisplayName,
|
|
176
|
+
scopeType: 'project',
|
|
177
|
+
scopeId: projectId,
|
|
178
|
+
document: { resources: [] },
|
|
179
|
+
},
|
|
180
|
+
auth,
|
|
181
|
+
});
|
|
175
182
|
if (!response.ok)
|
|
176
183
|
return { ok: false, error: response.error || 'Failed to create new Stack' };
|
|
177
184
|
return {
|
|
@@ -46,14 +46,18 @@ export async function blueprintDeployCore(options) {
|
|
|
46
46
|
}
|
|
47
47
|
}
|
|
48
48
|
}
|
|
49
|
-
const stackMutation = {
|
|
50
|
-
projectId,
|
|
51
|
-
name: deployedStack.name,
|
|
52
|
-
document: { resources: validResources },
|
|
53
|
-
};
|
|
54
49
|
const spinner = ora('Deploying...').start();
|
|
55
50
|
const isoNow = new Date().toISOString();
|
|
56
|
-
const { ok: deployOk, stack, error: deployError, } = await updateStack({
|
|
51
|
+
const { ok: deployOk, stack, error: deployError, } = await updateStack({
|
|
52
|
+
stackId,
|
|
53
|
+
stackMutation: {
|
|
54
|
+
scopeType: 'project',
|
|
55
|
+
scopeId: projectId,
|
|
56
|
+
name: deployedStack.name,
|
|
57
|
+
document: { resources: validResources },
|
|
58
|
+
},
|
|
59
|
+
auth,
|
|
60
|
+
});
|
|
57
61
|
if (!deployOk) {
|
|
58
62
|
spinner.fail(`${chalk.red('Failed')} to update deployment`);
|
|
59
63
|
return { success: false, error: deployError || 'Failed to update deployment' };
|
|
@@ -12,7 +12,7 @@ export async function blueprintDestroyCore(options) {
|
|
|
12
12
|
if (flagProjectId && flagStackId && force) {
|
|
13
13
|
const { ok, error, stack } = await destroyStack({
|
|
14
14
|
stackId: flagStackId,
|
|
15
|
-
auth: { token,
|
|
15
|
+
auth: { token, scopeType: 'project', scopeId: flagProjectId },
|
|
16
16
|
});
|
|
17
17
|
if (!ok)
|
|
18
18
|
return { success: false, error: error || 'Failed to destroy deployment' };
|
|
@@ -22,7 +22,7 @@ export async function blueprintDestroyCore(options) {
|
|
|
22
22
|
const { projectId, stackId } = blueprint;
|
|
23
23
|
if (!projectId)
|
|
24
24
|
return { success: false, error: 'Project ID is required' };
|
|
25
|
-
const auth = { token, projectId };
|
|
25
|
+
const auth = { token, scopeType: 'project', scopeId: projectId };
|
|
26
26
|
let stack;
|
|
27
27
|
try {
|
|
28
28
|
if (flagStackId) {
|
|
@@ -125,7 +125,7 @@ export async function blueprintDoctorCore(options) {
|
|
|
125
125
|
// STACK + ACCESS
|
|
126
126
|
if (diagnostics.online && diagnostics.tokenValid && token && stackId && projectId) {
|
|
127
127
|
const stackResponse = await getStack({
|
|
128
|
-
auth: { token, projectId },
|
|
128
|
+
auth: { token, scopeType: 'project', scopeId: projectId },
|
|
129
129
|
stackId,
|
|
130
130
|
});
|
|
131
131
|
if (stackResponse.ok) {
|
|
@@ -134,12 +134,12 @@ export async function blueprintDoctorCore(options) {
|
|
|
134
134
|
diagnostics.stackReady = true;
|
|
135
135
|
diagnostics.userHasAccess = true;
|
|
136
136
|
}
|
|
137
|
-
else if (stackResponse.response
|
|
137
|
+
else if (stackResponse.response?.status === 404) {
|
|
138
138
|
if (v)
|
|
139
139
|
yikes(`Deployment "Stack" <${stackId}> not found`);
|
|
140
140
|
diagnostics.stackReady = false;
|
|
141
141
|
}
|
|
142
|
-
else if (stackResponse.response
|
|
142
|
+
else if (stackResponse.response?.status === 403 || stackResponse.response?.status === 401) {
|
|
143
143
|
if (v)
|
|
144
144
|
yikes(`User does not have access to "Stack" <${stackId}>`);
|
|
145
145
|
diagnostics.userHasAccess = false;
|
|
@@ -38,7 +38,8 @@ export async function blueprintInitCore(options) {
|
|
|
38
38
|
// * 3. create empty stack with name from example name
|
|
39
39
|
const stack = await createEmptyStack({
|
|
40
40
|
token,
|
|
41
|
-
|
|
41
|
+
scopeType: 'project',
|
|
42
|
+
scopeId: projectId,
|
|
42
43
|
name: `example-${flagExample}`,
|
|
43
44
|
projectBased: false,
|
|
44
45
|
});
|
|
@@ -106,17 +107,17 @@ export async function blueprintInitCore(options) {
|
|
|
106
107
|
// using --stack-name gets around "LAUNCH LIMIT: 1 Stack per Project"
|
|
107
108
|
const stack = await createEmptyStack({
|
|
108
109
|
token,
|
|
109
|
-
|
|
110
|
+
scopeType: 'project',
|
|
111
|
+
scopeId: projectId,
|
|
110
112
|
name: flagStackName,
|
|
111
113
|
projectBased: false,
|
|
112
114
|
});
|
|
113
115
|
stackId = stack.id;
|
|
114
116
|
}
|
|
115
|
-
const auth = { token: token, projectId };
|
|
116
117
|
if (!stackId) {
|
|
117
118
|
// LAUNCH LIMIT: 1 Stack per Project - do not prompt for Stack, just create one
|
|
118
119
|
if (LAUNCH_LIMIT_STACK_PER_PROJECT) {
|
|
119
|
-
await createProjectBasedStack(
|
|
120
|
+
await createProjectBasedStack({ token, scopeType: 'project', scopeId: projectId }, log);
|
|
120
121
|
// do not set stackId, to avoid saving it to the config file
|
|
121
122
|
}
|
|
122
123
|
else {
|
|
@@ -175,10 +176,17 @@ async function promptForBlueprintType() {
|
|
|
175
176
|
return pickedBlueprintsType;
|
|
176
177
|
}
|
|
177
178
|
// LAUNCH LIMIT: 1 Stack per Project - create exclusive stack for project
|
|
178
|
-
async function createProjectBasedStack(auth,
|
|
179
|
-
|
|
179
|
+
async function createProjectBasedStack(auth, log) {
|
|
180
|
+
if (auth.scopeType !== 'project') {
|
|
181
|
+
throw new Error('Auth must be for a project');
|
|
182
|
+
}
|
|
183
|
+
const { scopeId: projectId, token } = auth;
|
|
180
184
|
// get project
|
|
181
|
-
const { ok: projectOk, project } = await getProject(
|
|
185
|
+
const { ok: projectOk, project } = await getProject({
|
|
186
|
+
token: auth.token,
|
|
187
|
+
scopeType: 'project',
|
|
188
|
+
scopeId: projectId,
|
|
189
|
+
});
|
|
182
190
|
if (!projectOk) {
|
|
183
191
|
throw new Error('Failed to find Project while creating Stack');
|
|
184
192
|
}
|
|
@@ -196,7 +204,8 @@ async function createProjectBasedStack(auth, token, log) {
|
|
|
196
204
|
// if not, create a stack
|
|
197
205
|
const stack = await createEmptyStack({
|
|
198
206
|
token,
|
|
199
|
-
|
|
207
|
+
scopeType: 'project',
|
|
208
|
+
scopeId: projectId,
|
|
200
209
|
name: projectDisplayName,
|
|
201
210
|
});
|
|
202
211
|
return stack;
|
|
@@ -7,7 +7,10 @@ export async function blueprintPlanCore(options) {
|
|
|
7
7
|
log(`${chalk.bold.blueBright('Blueprint Deployment Plan')} ${chalk.dim(`(${fileInfo.fileName})`)}`);
|
|
8
8
|
log(formatResourceTree(parsedBlueprint.resources));
|
|
9
9
|
if (token && projectId && stackId) {
|
|
10
|
-
const stackResponse = await getStack({
|
|
10
|
+
const stackResponse = await getStack({
|
|
11
|
+
auth: { token, scopeType: 'project', scopeId: projectId },
|
|
12
|
+
stackId,
|
|
13
|
+
});
|
|
11
14
|
if (!stackResponse.ok) {
|
|
12
15
|
log(chalk.dim('Unable to retrieve live deployment for comparison'));
|
|
13
16
|
}
|
|
@@ -11,7 +11,7 @@ export async function blueprintStacksCore(options) {
|
|
|
11
11
|
return { success: false, error: 'No Project ID provided' };
|
|
12
12
|
}
|
|
13
13
|
try {
|
|
14
|
-
const { ok, stacks, error } = await listStacks({ token, projectId });
|
|
14
|
+
const { ok, stacks, error } = await listStacks({ token, scopeType: 'project', scopeId: projectId });
|
|
15
15
|
if (!ok)
|
|
16
16
|
return { success: false, error: error || 'Failed to list stacks' };
|
|
17
17
|
if (!stacks || stacks.length === 0) {
|
package/dist/cores/index.js
CHANGED
|
@@ -48,7 +48,7 @@ export async function initDeployedBlueprintConfig(config) {
|
|
|
48
48
|
if (!stackId)
|
|
49
49
|
return { ok: false, error: 'Missing deployment configuration for Blueprint' };
|
|
50
50
|
}
|
|
51
|
-
const auth = { token: config.token, projectId };
|
|
51
|
+
const auth = { token: config.token, scopeType: 'project', scopeId: projectId };
|
|
52
52
|
const stackResponse = await getStack({ stackId, auth });
|
|
53
53
|
if (!stackResponse.ok) {
|
|
54
54
|
config.log(`Could not retrieve deployment info for ${niceId(stackId)}. Was it destroyed?`);
|
|
@@ -54,7 +54,7 @@ export async function promptForProject({ token, knownOrganizationId, knownProjec
|
|
|
54
54
|
return pickedProject;
|
|
55
55
|
}
|
|
56
56
|
export async function promptForStackId({ projectId, token, }) {
|
|
57
|
-
const { ok: stacksOk, error: stacksErr, stacks } = await listStacks({ token, projectId });
|
|
57
|
+
const { ok: stacksOk, error: stacksErr, stacks, } = await listStacks({ token, scopeType: 'project', scopeId: projectId });
|
|
58
58
|
if (!stacksOk) {
|
|
59
59
|
throw new Error(stacksErr || 'Failed to list Stacks');
|
|
60
60
|
}
|
|
@@ -87,7 +87,8 @@ export async function promptForStackId({ projectId, token, }) {
|
|
|
87
87
|
]);
|
|
88
88
|
const stack = await createEmptyStack({
|
|
89
89
|
token,
|
|
90
|
-
|
|
90
|
+
scopeType: 'project',
|
|
91
|
+
scopeId: projectId,
|
|
91
92
|
name: stackName,
|
|
92
93
|
});
|
|
93
94
|
return stack.id;
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import type { AuthParams } from './types.js';
|
|
2
|
-
export default function getHeaders({ token,
|
|
2
|
+
export default function getHeaders({ token, scopeId, scopeType }: AuthParams): {
|
|
3
3
|
Accept: string;
|
|
4
4
|
'Content-Type': string;
|
|
5
5
|
Authorization: string;
|
|
6
|
-
'X-Sanity-Scope-Type':
|
|
6
|
+
'X-Sanity-Scope-Type': import("./types.js").ScopeType;
|
|
7
7
|
'X-Sanity-Scope-Id': string;
|
|
8
8
|
'User-Agent': string;
|
|
9
9
|
};
|
|
@@ -1,21 +1,12 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
const pkg = await (await import('../../package.json', { with: { type: 'json' } })).default;
|
|
5
|
-
return `${pkg.name}@${pkg.version}`;
|
|
6
|
-
}
|
|
7
|
-
catch {
|
|
8
|
-
return 'unknown@0.0.0';
|
|
9
|
-
}
|
|
10
|
-
}
|
|
11
|
-
export default function getHeaders({ token, projectId }) {
|
|
12
|
-
// TODO: support organization scope type
|
|
1
|
+
import pkg from '../../package.json' with { type: 'json' };
|
|
2
|
+
const userAgent = `${pkg.name}@${pkg.version}`;
|
|
3
|
+
export default function getHeaders({ token, scopeId, scopeType }) {
|
|
13
4
|
return {
|
|
14
5
|
Accept: 'application/json',
|
|
15
6
|
'Content-Type': 'application/json',
|
|
16
7
|
Authorization: `Bearer ${token}`,
|
|
17
|
-
'X-Sanity-Scope-Type':
|
|
18
|
-
'X-Sanity-Scope-Id':
|
|
8
|
+
'X-Sanity-Scope-Type': scopeType,
|
|
9
|
+
'X-Sanity-Scope-Id': scopeId,
|
|
19
10
|
'User-Agent': userAgent,
|
|
20
11
|
};
|
|
21
12
|
}
|
package/dist/utils/types.d.ts
CHANGED
|
@@ -11,7 +11,8 @@ export type Result<T, E = string> = {
|
|
|
11
11
|
/** @internal */
|
|
12
12
|
export interface AuthParams {
|
|
13
13
|
token: string;
|
|
14
|
-
|
|
14
|
+
scopeType: ScopeType;
|
|
15
|
+
scopeId: string;
|
|
15
16
|
}
|
|
16
17
|
/** @internal */
|
|
17
18
|
export interface GroqRule {
|
|
@@ -55,7 +56,8 @@ export interface Stack {
|
|
|
55
56
|
id: string;
|
|
56
57
|
name: string;
|
|
57
58
|
displayName: string;
|
|
58
|
-
|
|
59
|
+
scopeType: ScopeType;
|
|
60
|
+
scopeId: string;
|
|
59
61
|
resources: Array<DeployedResource>;
|
|
60
62
|
createdAt?: string;
|
|
61
63
|
updatedAt?: string;
|
|
@@ -71,7 +73,8 @@ export interface StackOperation {
|
|
|
71
73
|
/** @internal */
|
|
72
74
|
export interface StackMutation {
|
|
73
75
|
name: string;
|
|
74
|
-
|
|
76
|
+
scopeType: ScopeType;
|
|
77
|
+
scopeId: string;
|
|
75
78
|
document: Blueprint;
|
|
76
79
|
useProjectBasedId?: boolean;
|
|
77
80
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { BlueprintParserErrorType } from '../types.js';
|
|
2
2
|
export function validateFunctionName(name) {
|
|
3
|
-
// must be
|
|
4
|
-
return /^[a-zA-Z0-9][a-zA-Z0-9_-]{
|
|
3
|
+
// must be 3+ characters, no special characters, no spaces, allow _ and -
|
|
4
|
+
return /^[a-zA-Z0-9][a-zA-Z0-9_-]{2,}$/.test(name);
|
|
5
5
|
}
|
|
6
6
|
const validFunctionEventNames = ['publish', 'create', 'update', 'delete'];
|
|
7
7
|
export function validateFunctionResource(resource) {
|
|
@@ -10,7 +10,7 @@ export function validateFunctionResource(resource) {
|
|
|
10
10
|
const errors = [];
|
|
11
11
|
if (!validateFunctionName(resource.name)) {
|
|
12
12
|
errors.push({
|
|
13
|
-
message: `${msgPrefix} Function name must be at least
|
|
13
|
+
message: `${msgPrefix} Function name must be at least 3 characters, start with a letter or number, and only contain letters, numbers, _ or -`,
|
|
14
14
|
type: BlueprintParserErrorType.InvalidProperty,
|
|
15
15
|
});
|
|
16
16
|
}
|
package/oclif.manifest.json
CHANGED