@drawcall/design 0.12.3 → 0.12.5
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 +10 -6
- package/dist/browser.d.ts +2 -1
- package/dist/browser.js +1 -0
- package/dist/command/context.d.ts +38 -0
- package/dist/command/filesystem.js +9 -2
- package/dist/command/frame.js +39 -0
- package/dist/command/image.js +1 -0
- package/dist/command/imports.d.ts +5 -0
- package/dist/command/imports.js +34 -0
- package/dist/frame-image.d.ts +2 -1
- package/dist/frame-image.js +2 -6
- package/dist/frame-preview.d.ts +1 -0
- package/dist/frame-preview.js +6 -0
- package/dist/mcp/file.js +21 -6
- package/dist/mcp/frame.js +46 -25
- package/dist/mcp/schema.d.ts +9 -0
- package/dist/mcp/schema.js +34 -1
- package/dist/skill.generated.d.ts +2 -2
- package/dist/skill.generated.js +2 -2
- package/dist/v1/contract.d.ts +38 -0
- package/dist/v1/contract.js +6 -2
- package/dist/v1/schemas.d.ts +34 -0
- package/dist/v1/schemas.js +29 -0
- package/package.json +1 -1
- package/skills/drawcall-design/SKILL.md +39 -6
package/README.md
CHANGED
|
@@ -10,7 +10,7 @@ const projects = await design.project.list();
|
|
|
10
10
|
```
|
|
11
11
|
|
|
12
12
|
Projects and frames have immutable 14-character lowercase IDs. A project is a hosted filesystem at `https://<project-id>.design.drawcallcontent.com/`; every frame owns `/<frame-id>/` within it.
|
|
13
|
-
|
|
13
|
+
Every GLTS, Markdown, image, or Market frame includes a canonical `previewUrl` at
|
|
14
14
|
`https://<project-id>.design.drawcallcontent.com/<frame-id>.webp`.
|
|
15
15
|
|
|
16
16
|
```sh
|
|
@@ -19,13 +19,17 @@ npx drawcall design project create showroom
|
|
|
19
19
|
# `project list` prints: <project-id> <name>
|
|
20
20
|
|
|
21
21
|
npx drawcall design -p r6z2n9k4x8m1qc frame create racecar \
|
|
22
|
-
--type glts --size 800x800
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
22
|
+
--type glts --size 800x800 \
|
|
23
|
+
--import ./parts/wheel.glts=-0.5,0,-0.5:0.5,1,0.5 \
|
|
24
|
+
--text 'import * as THREE from "three"; import Wheel from "./parts/wheel.glts"; export default class Racecar extends THREE.Group { constructor() { super(); this.add(new Wheel()); } }'
|
|
25
|
+
# `frame create` prints its frame ID and /<frame-id>/ path. `--text -` reads stdin.
|
|
26
|
+
# Each `--import` box becomes a placeholder file until the real part is written.
|
|
27
|
+
|
|
28
|
+
npx drawcall design -p r6z2n9k4x8m1qc write /a4z8m2q7v9kcde/parts/wheel.glts \
|
|
29
|
+
'import * as THREE from "three"; export default class Wheel extends THREE.Group {}'
|
|
27
30
|
npx drawcall design -p r6z2n9k4x8m1qc ls /
|
|
28
31
|
npx drawcall design -p r6z2n9k4x8m1qc read /a4z8m2q7v9kcde/index.glts
|
|
32
|
+
npx drawcall design -p r6z2n9k4x8m1qc frame preview a4z8m2q7v9kcde
|
|
29
33
|
npx drawcall design -p r6z2n9k4x8m1qc frame screenshot a4z8m2q7v9kcde
|
|
30
34
|
|
|
31
35
|
npx drawcall design -p r6z2n9k4x8m1qc frame create release-notes \
|
package/dist/browser.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
export * as v1 from "./v1/index.js";
|
|
2
2
|
export { frameImageUrl } from "./frame-image.js";
|
|
3
|
+
export { framePreviewUrl } from "./frame-preview.js";
|
|
3
4
|
export { registerDesignTools, type DesignMcpOptions, type DesignMcpServer, type DesignMcpToolResult, } from "./mcp/index.js";
|
|
4
5
|
export { cliDesignSkill, mcpDesignSkill } from "./skill.generated.js";
|
|
5
6
|
export { frameCreationCapabilities, type FrameCreationCapability, type FrameCreationCapabilityId, type FrameCreationInput, } from "./v1/capabilities.js";
|
|
@@ -7,4 +8,4 @@ export { cameraPoseSchema, commentBodySchema, commentPositionInputSchema, commen
|
|
|
7
8
|
export { parseFrameSize } from "./target.js";
|
|
8
9
|
export { projectFrameLayoutSchema, projectCommentsChangedServerMessageSchema, projectFrameRecordSchema, projectGltsFrameRecordSchema, projectImageFrameRecordSchema, projectMarkdownFrameRecordSchema, projectMarketFileSchema, projectMarketFrameRecordSchema, projectPresenceClientMessageSchema, projectPresenceServerMessageSchema, projectStateSchema, type ProjectFrameLayout, type ProjectCommentsChangedServerMessage, type ProjectFrameRecord, type ProjectGltsFrameRecord, type ProjectImageFrameRecord, type ProjectMarkdownFrameRecord, type ProjectMarketFile, type ProjectMarketFrameRecord, type ProjectPresenceClientMessage, type ProjectPresenceServerMessage, type ProjectState, } from "./project-state.js";
|
|
9
10
|
export { cameraCaptureCommandSchema, cameraCaptureResultSchema, cameraMessageTypes, cameraSetCommandSchema, commentActionMessageSchema, commentActionResultSchema, commentPickCommandSchema, commentPickResultSchema, commentRuntimeMessageTypes, commentSelectionMessageSchema, commentStateCommandSchema, frameNavigationMessageSchema, frameNavigationMessageTypes, frameNavigationV2MessageSchema, frameNavigationV2MessageTypes, frameInteractionMessageSchema, frameInteractionMessageTypes, framePointerMessageSchema, framePointerMessageTypes, frameZoomMessageSchema, frameZoomMessageTypes, frameRenderResultSchema, gltsExportCancelCommandSchema, gltsExportCancelledResultSchema, gltsExportCommandSchema, gltsExportFrameMessageSchema, gltsExportMessageTypes, gltsExportParentMessageSchema, gltsExportResultSchema, gltsRuntimeExportFormatSchema, immersiveCommandSchema, immersiveFrameMessageSchema, immersiveMessageTypes, immersiveModeSchema, inspectionCommandSchema, inspectionFrameMessageSchema, inspectionMessageTypes, posterMessageTypes, posterPagePath, posterPageUrl, posterRenderCommandSchema, posterRenderResultSchema, previewConfigureCommandSchema, previewLoadCommandSchema, previewLoadResultSchema, previewMessageTypes, previewPagePath, previewPageUrl, previewPixelRatioMax, previewSessionEventSchema, projectSyncUrl, sourceFileChangeSchema, sourceFileMessageTypes, sourceFileReloadResultSchema, sourceFilesChangedMessageSchema, type GltsExportCancelCommand, type GltsExportCancelledResult, type GltsExportCommand, type GltsExportFrameMessage, type GltsExportParentMessage, type GltsExportResult, type GltsRuntimeExportFormat, type CameraCaptureCommand, type CameraSetCommand, type CameraCaptureFailure, type CameraCaptureResult, type CommentActionMessage, type CommentActionResult, type CommentPickCommand, type CommentPickResult, type CommentSelectionMessage, type CommentStateCommand, type FrameRenderResult, type FramePointerMessage, type FrameZoomMessage, type InspectionAppliedMessage, type InspectionCommand, type InspectionFrameMessage, type PosterRenderCommand, type PosterRenderResult, type PreviewLoadCommand, type PreviewLoadResult, type ImmersiveCommand, type ImmersiveFrameMessage, type ImmersiveMode, type SourceFileChange, type SourceFileReloadResult, type SourceFilesChangedMessage, } from "./protocol.js";
|
|
10
|
-
export type { BinaryFile, CameraPose, Comment, CommentAuthor, CommentPosition, CommentPositionInput, CommentReply, CommentResolution, CreateComment, CreateFrame, CreateProjectFromBrief, CreateGltsFrame, CreateImageFrame, CreateMarkdownFrame, CreateMarketFrame, GenerateImage, GenerateImageUrl, DesignFile, FileList, FileMutation, FrameExport, Frame, GltsFrame, GltsFrameExport, ImageFrame, ImageFrameExport, ImageGenerationOperation, ImageGenerationProvenance, ImageGenerationResult, ImageInput, ImageInputProvenance, MarketFrame, MarketFrameExport, MarkdownFrame, MarkdownFrameExport, Project, ProjectDerivationStatus, Screenshot, TextFile, User, } from "./v1/schemas.js";
|
|
11
|
+
export type { BinaryFile, BoundingBox, CameraPose, Imports, Comment, CommentAuthor, CommentPosition, CommentPositionInput, CommentReply, CommentResolution, CreateComment, CreateFrame, CreateProjectFromBrief, CreateGltsFrame, CreateImageFrame, CreateMarkdownFrame, CreateMarketFrame, GenerateImage, GenerateImageUrl, DesignFile, FileList, FileMutation, FrameExport, Frame, GltsFrame, GltsFrameExport, ImageFrame, ImageFrameExport, ImageGenerationOperation, ImageGenerationProvenance, ImageGenerationResult, ImageInput, ImageInputProvenance, MarketFrame, MarketFrameExport, MarkdownFrame, MarkdownFrameExport, Project, ProjectDerivationStatus, Screenshot, TextFile, User, } from "./v1/schemas.js";
|
package/dist/browser.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
export * as v1 from "./v1/index.js";
|
|
2
2
|
export { frameImageUrl } from "./frame-image.js";
|
|
3
|
+
export { framePreviewUrl } from "./frame-preview.js";
|
|
3
4
|
export { registerDesignTools, } from "./mcp/index.js";
|
|
4
5
|
export { cliDesignSkill, mcpDesignSkill } from "./skill.generated.js";
|
|
5
6
|
export { frameCreationCapabilities, } from "./v1/capabilities.js";
|
|
@@ -112,6 +112,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
112
112
|
width: import("zod").ZodNumber;
|
|
113
113
|
height: import("zod").ZodNumber;
|
|
114
114
|
viewUrl: import("zod").ZodString;
|
|
115
|
+
previewUrl: import("zod").ZodString;
|
|
115
116
|
createdAt: import("zod").ZodString;
|
|
116
117
|
updatedAt: import("zod").ZodString;
|
|
117
118
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -138,6 +139,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
138
139
|
width: import("zod").ZodNumber;
|
|
139
140
|
height: import("zod").ZodNumber;
|
|
140
141
|
viewUrl: import("zod").ZodString;
|
|
142
|
+
previewUrl: import("zod").ZodString;
|
|
141
143
|
createdAt: import("zod").ZodString;
|
|
142
144
|
updatedAt: import("zod").ZodString;
|
|
143
145
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -151,6 +153,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
151
153
|
width: import("zod").ZodNumber;
|
|
152
154
|
height: import("zod").ZodNumber;
|
|
153
155
|
viewUrl: import("zod").ZodString;
|
|
156
|
+
previewUrl: import("zod").ZodString;
|
|
154
157
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
155
158
|
createdAt: import("zod").ZodString;
|
|
156
159
|
updatedAt: import("zod").ZodString;
|
|
@@ -188,6 +191,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
188
191
|
width: import("zod").ZodNumber;
|
|
189
192
|
height: import("zod").ZodNumber;
|
|
190
193
|
viewUrl: import("zod").ZodString;
|
|
194
|
+
previewUrl: import("zod").ZodString;
|
|
191
195
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
192
196
|
createdAt: import("zod").ZodString;
|
|
193
197
|
updatedAt: import("zod").ZodString;
|
|
@@ -202,6 +206,11 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
202
206
|
type: import("zod").ZodLiteral<"glts">;
|
|
203
207
|
width: import("zod").ZodNumber;
|
|
204
208
|
height: import("zod").ZodNumber;
|
|
209
|
+
text: import("zod").ZodOptional<import("zod").ZodString>;
|
|
210
|
+
imports: import("zod").ZodOptional<import("zod").ZodRecord<import("zod").ZodString, import("zod").ZodObject<{
|
|
211
|
+
min: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
212
|
+
max: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
213
|
+
}, import("zod/v4/core").$strict>>>;
|
|
205
214
|
}, import("zod/v4/core").$strict>, import("zod").ZodObject<{
|
|
206
215
|
project: import("zod").ZodString;
|
|
207
216
|
name: import("zod").ZodString;
|
|
@@ -210,6 +219,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
210
219
|
type: import("zod").ZodLiteral<"markdown">;
|
|
211
220
|
width: import("zod").ZodNumber;
|
|
212
221
|
height: import("zod").ZodNumber;
|
|
222
|
+
text: import("zod").ZodOptional<import("zod").ZodString>;
|
|
213
223
|
}, import("zod/v4/core").$strict>, import("zod").ZodObject<{
|
|
214
224
|
project: import("zod").ZodString;
|
|
215
225
|
name: import("zod").ZodString;
|
|
@@ -233,6 +243,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
233
243
|
width: import("zod").ZodNumber;
|
|
234
244
|
height: import("zod").ZodNumber;
|
|
235
245
|
viewUrl: import("zod").ZodString;
|
|
246
|
+
previewUrl: import("zod").ZodString;
|
|
236
247
|
createdAt: import("zod").ZodString;
|
|
237
248
|
updatedAt: import("zod").ZodString;
|
|
238
249
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -259,6 +270,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
259
270
|
width: import("zod").ZodNumber;
|
|
260
271
|
height: import("zod").ZodNumber;
|
|
261
272
|
viewUrl: import("zod").ZodString;
|
|
273
|
+
previewUrl: import("zod").ZodString;
|
|
262
274
|
createdAt: import("zod").ZodString;
|
|
263
275
|
updatedAt: import("zod").ZodString;
|
|
264
276
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -272,6 +284,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
272
284
|
width: import("zod").ZodNumber;
|
|
273
285
|
height: import("zod").ZodNumber;
|
|
274
286
|
viewUrl: import("zod").ZodString;
|
|
287
|
+
previewUrl: import("zod").ZodString;
|
|
275
288
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
276
289
|
createdAt: import("zod").ZodString;
|
|
277
290
|
updatedAt: import("zod").ZodString;
|
|
@@ -309,6 +322,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
309
322
|
width: import("zod").ZodNumber;
|
|
310
323
|
height: import("zod").ZodNumber;
|
|
311
324
|
viewUrl: import("zod").ZodString;
|
|
325
|
+
previewUrl: import("zod").ZodString;
|
|
312
326
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
313
327
|
createdAt: import("zod").ZodString;
|
|
314
328
|
updatedAt: import("zod").ZodString;
|
|
@@ -353,6 +367,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
353
367
|
width: import("zod").ZodNumber;
|
|
354
368
|
height: import("zod").ZodNumber;
|
|
355
369
|
viewUrl: import("zod").ZodString;
|
|
370
|
+
previewUrl: import("zod").ZodString;
|
|
356
371
|
createdAt: import("zod").ZodString;
|
|
357
372
|
updatedAt: import("zod").ZodString;
|
|
358
373
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -379,6 +394,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
379
394
|
width: import("zod").ZodNumber;
|
|
380
395
|
height: import("zod").ZodNumber;
|
|
381
396
|
viewUrl: import("zod").ZodString;
|
|
397
|
+
previewUrl: import("zod").ZodString;
|
|
382
398
|
createdAt: import("zod").ZodString;
|
|
383
399
|
updatedAt: import("zod").ZodString;
|
|
384
400
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -392,6 +408,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
392
408
|
width: import("zod").ZodNumber;
|
|
393
409
|
height: import("zod").ZodNumber;
|
|
394
410
|
viewUrl: import("zod").ZodString;
|
|
411
|
+
previewUrl: import("zod").ZodString;
|
|
395
412
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
396
413
|
createdAt: import("zod").ZodString;
|
|
397
414
|
updatedAt: import("zod").ZodString;
|
|
@@ -429,6 +446,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
429
446
|
width: import("zod").ZodNumber;
|
|
430
447
|
height: import("zod").ZodNumber;
|
|
431
448
|
viewUrl: import("zod").ZodString;
|
|
449
|
+
previewUrl: import("zod").ZodString;
|
|
432
450
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
433
451
|
createdAt: import("zod").ZodString;
|
|
434
452
|
updatedAt: import("zod").ZodString;
|
|
@@ -448,6 +466,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
448
466
|
width: import("zod").ZodNumber;
|
|
449
467
|
height: import("zod").ZodNumber;
|
|
450
468
|
viewUrl: import("zod").ZodString;
|
|
469
|
+
previewUrl: import("zod").ZodString;
|
|
451
470
|
createdAt: import("zod").ZodString;
|
|
452
471
|
updatedAt: import("zod").ZodString;
|
|
453
472
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -474,6 +493,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
474
493
|
width: import("zod").ZodNumber;
|
|
475
494
|
height: import("zod").ZodNumber;
|
|
476
495
|
viewUrl: import("zod").ZodString;
|
|
496
|
+
previewUrl: import("zod").ZodString;
|
|
477
497
|
createdAt: import("zod").ZodString;
|
|
478
498
|
updatedAt: import("zod").ZodString;
|
|
479
499
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -487,6 +507,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
487
507
|
width: import("zod").ZodNumber;
|
|
488
508
|
height: import("zod").ZodNumber;
|
|
489
509
|
viewUrl: import("zod").ZodString;
|
|
510
|
+
previewUrl: import("zod").ZodString;
|
|
490
511
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
491
512
|
createdAt: import("zod").ZodString;
|
|
492
513
|
updatedAt: import("zod").ZodString;
|
|
@@ -524,6 +545,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
524
545
|
width: import("zod").ZodNumber;
|
|
525
546
|
height: import("zod").ZodNumber;
|
|
526
547
|
viewUrl: import("zod").ZodString;
|
|
548
|
+
previewUrl: import("zod").ZodString;
|
|
527
549
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
528
550
|
createdAt: import("zod").ZodString;
|
|
529
551
|
updatedAt: import("zod").ZodString;
|
|
@@ -557,6 +579,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
557
579
|
width: import("zod").ZodNumber;
|
|
558
580
|
height: import("zod").ZodNumber;
|
|
559
581
|
viewUrl: import("zod").ZodString;
|
|
582
|
+
previewUrl: import("zod").ZodString;
|
|
560
583
|
createdAt: import("zod").ZodString;
|
|
561
584
|
updatedAt: import("zod").ZodString;
|
|
562
585
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -583,6 +606,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
583
606
|
width: import("zod").ZodNumber;
|
|
584
607
|
height: import("zod").ZodNumber;
|
|
585
608
|
viewUrl: import("zod").ZodString;
|
|
609
|
+
previewUrl: import("zod").ZodString;
|
|
586
610
|
createdAt: import("zod").ZodString;
|
|
587
611
|
updatedAt: import("zod").ZodString;
|
|
588
612
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -596,6 +620,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
596
620
|
width: import("zod").ZodNumber;
|
|
597
621
|
height: import("zod").ZodNumber;
|
|
598
622
|
viewUrl: import("zod").ZodString;
|
|
623
|
+
previewUrl: import("zod").ZodString;
|
|
599
624
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
600
625
|
createdAt: import("zod").ZodString;
|
|
601
626
|
updatedAt: import("zod").ZodString;
|
|
@@ -633,6 +658,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
633
658
|
width: import("zod").ZodNumber;
|
|
634
659
|
height: import("zod").ZodNumber;
|
|
635
660
|
viewUrl: import("zod").ZodString;
|
|
661
|
+
previewUrl: import("zod").ZodString;
|
|
636
662
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
637
663
|
createdAt: import("zod").ZodString;
|
|
638
664
|
updatedAt: import("zod").ZodString;
|
|
@@ -655,6 +681,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
655
681
|
width: import("zod").ZodNumber;
|
|
656
682
|
height: import("zod").ZodNumber;
|
|
657
683
|
viewUrl: import("zod").ZodString;
|
|
684
|
+
previewUrl: import("zod").ZodString;
|
|
658
685
|
createdAt: import("zod").ZodString;
|
|
659
686
|
updatedAt: import("zod").ZodString;
|
|
660
687
|
type: import("zod").ZodLiteral<"glts">;
|
|
@@ -681,6 +708,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
681
708
|
width: import("zod").ZodNumber;
|
|
682
709
|
height: import("zod").ZodNumber;
|
|
683
710
|
viewUrl: import("zod").ZodString;
|
|
711
|
+
previewUrl: import("zod").ZodString;
|
|
684
712
|
createdAt: import("zod").ZodString;
|
|
685
713
|
updatedAt: import("zod").ZodString;
|
|
686
714
|
type: import("zod").ZodLiteral<"markdown">;
|
|
@@ -694,6 +722,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
694
722
|
width: import("zod").ZodNumber;
|
|
695
723
|
height: import("zod").ZodNumber;
|
|
696
724
|
viewUrl: import("zod").ZodString;
|
|
725
|
+
previewUrl: import("zod").ZodString;
|
|
697
726
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
698
727
|
createdAt: import("zod").ZodString;
|
|
699
728
|
updatedAt: import("zod").ZodString;
|
|
@@ -731,6 +760,7 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
731
760
|
width: import("zod").ZodNumber;
|
|
732
761
|
height: import("zod").ZodNumber;
|
|
733
762
|
viewUrl: import("zod").ZodString;
|
|
763
|
+
previewUrl: import("zod").ZodString;
|
|
734
764
|
contentRevision: import("zod").ZodOptional<import("zod").ZodNumber>;
|
|
735
765
|
createdAt: import("zod").ZodString;
|
|
736
766
|
updatedAt: import("zod").ZodString;
|
|
@@ -1109,6 +1139,10 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
1109
1139
|
project: import("zod").ZodString;
|
|
1110
1140
|
path: import("zod").ZodString;
|
|
1111
1141
|
text: import("zod").ZodString;
|
|
1142
|
+
imports: import("zod").ZodOptional<import("zod").ZodRecord<import("zod").ZodString, import("zod").ZodObject<{
|
|
1143
|
+
min: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
1144
|
+
max: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
1145
|
+
}, import("zod/v4/core").$strict>>>;
|
|
1112
1146
|
}, import("zod/v4/core").$strip>, import("zod").ZodObject<{
|
|
1113
1147
|
paths: import("zod").ZodArray<import("zod").ZodString>;
|
|
1114
1148
|
}, import("zod/v4/core").$strip>, Record<never, never>>;
|
|
@@ -1117,6 +1151,10 @@ export declare function clientFor(command: Command): Promise<{
|
|
|
1117
1151
|
path: import("zod").ZodString;
|
|
1118
1152
|
oldText: import("zod").ZodString;
|
|
1119
1153
|
newText: import("zod").ZodString;
|
|
1154
|
+
imports: import("zod").ZodOptional<import("zod").ZodRecord<import("zod").ZodString, import("zod").ZodObject<{
|
|
1155
|
+
min: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
1156
|
+
max: import("zod").ZodTuple<[import("zod").ZodNumber, import("zod").ZodNumber, import("zod").ZodNumber], null>;
|
|
1157
|
+
}, import("zod/v4/core").$strict>>>;
|
|
1120
1158
|
}, import("zod/v4/core").$strip>, import("zod").ZodObject<{
|
|
1121
1159
|
paths: import("zod").ZodArray<import("zod").ZodString>;
|
|
1122
1160
|
}, import("zod/v4/core").$strip>, Record<never, never>>;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { clientFor, projectId, requireConfirmation } from "./context.js";
|
|
2
|
+
import { importOption, parseImports } from "./imports.js";
|
|
2
3
|
import { textArgument } from "./input.js";
|
|
3
4
|
export function registerFilesystemCommands(program) {
|
|
4
5
|
program
|
|
@@ -35,12 +36,15 @@ export function registerFilesystemCommands(program) {
|
|
|
35
36
|
.description("Create or overwrite a text project file")
|
|
36
37
|
.argument("<path>", "Absolute project path")
|
|
37
38
|
.argument("[text]", "Inline text; omit or use - to read stdin")
|
|
38
|
-
.
|
|
39
|
+
.addOption(importOption)
|
|
40
|
+
.action(async (path, text, options, command) => {
|
|
39
41
|
const client = await clientFor(command);
|
|
42
|
+
const imports = parseImports(options.import);
|
|
40
43
|
await client.filesystem.write({
|
|
41
44
|
project: projectId(command),
|
|
42
45
|
path,
|
|
43
46
|
text: await textArgument(text),
|
|
47
|
+
...(imports === undefined ? {} : { imports }),
|
|
44
48
|
});
|
|
45
49
|
console.log(`Wrote ${path}.`);
|
|
46
50
|
});
|
|
@@ -50,13 +54,16 @@ export function registerFilesystemCommands(program) {
|
|
|
50
54
|
.argument("<path>", "Absolute project path")
|
|
51
55
|
.argument("<old-text>", "Text that must occur exactly once")
|
|
52
56
|
.argument("<new-text>", "Replacement text")
|
|
53
|
-
.
|
|
57
|
+
.addOption(importOption)
|
|
58
|
+
.action(async (path, oldText, newText, options, command) => {
|
|
54
59
|
const client = await clientFor(command);
|
|
60
|
+
const imports = parseImports(options.import);
|
|
55
61
|
await client.filesystem.edit({
|
|
56
62
|
project: projectId(command),
|
|
57
63
|
path,
|
|
58
64
|
oldText,
|
|
59
65
|
newText,
|
|
66
|
+
...(imports === undefined ? {} : { imports }),
|
|
60
67
|
});
|
|
61
68
|
console.log(`Edited ${path}.`);
|
|
62
69
|
});
|
package/dist/command/frame.js
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import { readImageInput } from "../image.js";
|
|
2
2
|
import { parseFrameSize } from "../target.js";
|
|
3
|
+
import { importOption, parseImports } from "./imports.js";
|
|
4
|
+
import { textArgument } from "./input.js";
|
|
3
5
|
import { designIdSchema, marketAssetSchema, } from "../v1/schemas.js";
|
|
4
6
|
import { clientFor, projectId, requireConfirmation } from "./context.js";
|
|
5
7
|
import { registerImageCommands } from "./image.js";
|
|
@@ -27,6 +29,8 @@ export function registerFrameCommands(program) {
|
|
|
27
29
|
.option("-s, --size <width>x<height>", "GLTS or Markdown viewport size")
|
|
28
30
|
.option("--image <url-or-path>", "Image URL or local PNG, JPEG, or WebP")
|
|
29
31
|
.option("--asset <name@version>", "Exact public Market asset version")
|
|
32
|
+
.option("--text <text>", "Initial index.glts or index.md content; use - to read stdin")
|
|
33
|
+
.addOption(importOption)
|
|
30
34
|
.action(async (name, options, command) => {
|
|
31
35
|
const project = projectId(command);
|
|
32
36
|
const input = await createFrameInput(project, name, options);
|
|
@@ -65,6 +69,22 @@ export function registerFrameCommands(program) {
|
|
|
65
69
|
console.log(`Deleted ${id}.`);
|
|
66
70
|
}
|
|
67
71
|
});
|
|
72
|
+
frame
|
|
73
|
+
.command("preview")
|
|
74
|
+
.description("Print frames' current WebP preview URLs")
|
|
75
|
+
.argument("<frame-id...>", "Frame IDs")
|
|
76
|
+
.action(async (frameIds, _options, command) => {
|
|
77
|
+
const project = projectId(command);
|
|
78
|
+
const client = await clientFor(command);
|
|
79
|
+
const frames = await client.frame.list({ project });
|
|
80
|
+
for (const frameId of frameIds) {
|
|
81
|
+
const id = designIdSchema.parse(frameId);
|
|
82
|
+
const target = frames.find((item) => item.id === id);
|
|
83
|
+
if (!target)
|
|
84
|
+
throw new Error(`Frame ${id} does not exist.`);
|
|
85
|
+
console.log(`${id}\t${target.previewUrl}`);
|
|
86
|
+
}
|
|
87
|
+
});
|
|
68
88
|
frame
|
|
69
89
|
.command("screenshot")
|
|
70
90
|
.description("Render frames and print their screenshot URLs")
|
|
@@ -81,6 +101,9 @@ export function registerFrameCommands(program) {
|
|
|
81
101
|
registerImageCommands(frame);
|
|
82
102
|
}
|
|
83
103
|
async function createFrameInput(project, name, options) {
|
|
104
|
+
if (options.import !== undefined && options.type !== "glts") {
|
|
105
|
+
throw new Error("Only GLTS frames accept --import");
|
|
106
|
+
}
|
|
84
107
|
if (options.type === "glts") {
|
|
85
108
|
if (options.image !== undefined || options.asset !== undefined) {
|
|
86
109
|
throw new Error("GLTS frames do not accept --image or --asset");
|
|
@@ -88,17 +111,26 @@ async function createFrameInput(project, name, options) {
|
|
|
88
111
|
if (options.size === undefined) {
|
|
89
112
|
throw new Error("GLTS frames require --size <width>x<height>");
|
|
90
113
|
}
|
|
114
|
+
const imports = parseImports(options.import);
|
|
115
|
+
const text = options.text === undefined
|
|
116
|
+
? {}
|
|
117
|
+
: { text: await textArgument(options.text) };
|
|
91
118
|
return {
|
|
92
119
|
project,
|
|
93
120
|
name,
|
|
94
121
|
type: "glts",
|
|
95
122
|
...parseFrameSize(options.size),
|
|
123
|
+
...text,
|
|
124
|
+
...(imports === undefined ? {} : { imports }),
|
|
96
125
|
};
|
|
97
126
|
}
|
|
98
127
|
if (options.type === "image") {
|
|
99
128
|
if (options.size !== undefined || options.asset !== undefined) {
|
|
100
129
|
throw new Error("Image frames do not accept --size or --asset");
|
|
101
130
|
}
|
|
131
|
+
if (options.text !== undefined) {
|
|
132
|
+
throw new Error("Image frames do not accept --text");
|
|
133
|
+
}
|
|
102
134
|
if (options.image === undefined) {
|
|
103
135
|
throw new Error("Image frames require --image");
|
|
104
136
|
}
|
|
@@ -116,17 +148,24 @@ async function createFrameInput(project, name, options) {
|
|
|
116
148
|
if (options.size === undefined) {
|
|
117
149
|
throw new Error("Markdown frames require --size <width>x<height>");
|
|
118
150
|
}
|
|
151
|
+
const text = options.text === undefined
|
|
152
|
+
? {}
|
|
153
|
+
: { text: await textArgument(options.text) };
|
|
119
154
|
return {
|
|
120
155
|
project,
|
|
121
156
|
name,
|
|
122
157
|
type: "markdown",
|
|
123
158
|
...parseFrameSize(options.size),
|
|
159
|
+
...text,
|
|
124
160
|
};
|
|
125
161
|
}
|
|
126
162
|
if (options.type === "market") {
|
|
127
163
|
if (options.size !== undefined || options.image !== undefined) {
|
|
128
164
|
throw new Error("Market frames do not accept --size or --image");
|
|
129
165
|
}
|
|
166
|
+
if (options.text !== undefined) {
|
|
167
|
+
throw new Error("Market frames do not accept --text");
|
|
168
|
+
}
|
|
130
169
|
if (options.asset === undefined) {
|
|
131
170
|
throw new Error("Market frames require --asset");
|
|
132
171
|
}
|
package/dist/command/image.js
CHANGED
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { Option } from "commander";
|
|
2
|
+
import { type Imports } from "../v1/schemas.js";
|
|
3
|
+
/** `--import <specifier>=<minx,miny,minz>:<maxx,maxy,maxz>`, repeatable. */
|
|
4
|
+
export declare const importOption: Option;
|
|
5
|
+
export declare function parseImports(values: string[] | undefined): Imports | undefined;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { Option } from "commander";
|
|
2
|
+
import { boundingBoxSchema } from "../v1/schemas.js";
|
|
3
|
+
/** `--import <specifier>=<minx,miny,minz>:<maxx,maxy,maxz>`, repeatable. */
|
|
4
|
+
export const importOption = new Option("--import <specifier=min:max>", "Bounding box for an imported .glts file that does not exist yet, as x,y,z:x,y,z").argParser((value, previous = []) => [...previous, value]);
|
|
5
|
+
export function parseImports(values) {
|
|
6
|
+
if (values === undefined)
|
|
7
|
+
return undefined;
|
|
8
|
+
const imports = {};
|
|
9
|
+
for (const value of values) {
|
|
10
|
+
const separator = value.indexOf("=");
|
|
11
|
+
if (separator === -1)
|
|
12
|
+
throw new Error(`--import needs <specifier>=<min>:<max>, got ${value}`);
|
|
13
|
+
const specifier = value.slice(0, separator);
|
|
14
|
+
const [min, max, ...rest] = value.slice(separator + 1).split(":");
|
|
15
|
+
if (min === undefined || max === undefined || rest.length > 0) {
|
|
16
|
+
throw new Error(`--import ${specifier} needs <minx,miny,minz>:<maxx,maxy,maxz>`);
|
|
17
|
+
}
|
|
18
|
+
imports[specifier] = boundingBoxSchema.parse({
|
|
19
|
+
min: corner(min),
|
|
20
|
+
max: corner(max),
|
|
21
|
+
});
|
|
22
|
+
}
|
|
23
|
+
return imports;
|
|
24
|
+
}
|
|
25
|
+
function corner(value) {
|
|
26
|
+
const coordinates = value.split(",");
|
|
27
|
+
const numbers = coordinates.map(Number);
|
|
28
|
+
if (coordinates.length !== 3 ||
|
|
29
|
+
coordinates.some((coordinate) => coordinate.trim() === "") ||
|
|
30
|
+
numbers.some((number) => !Number.isFinite(number))) {
|
|
31
|
+
throw new Error(`Bounding box corners are three comma-separated numbers, got ${value}`);
|
|
32
|
+
}
|
|
33
|
+
return numbers;
|
|
34
|
+
}
|
package/dist/frame-image.d.ts
CHANGED
|
@@ -1 +1,2 @@
|
|
|
1
|
-
|
|
1
|
+
/** @deprecated Use framePreviewUrl. */
|
|
2
|
+
export { framePreviewUrl as frameImageUrl } from "./frame-preview.js";
|
package/dist/frame-image.js
CHANGED
|
@@ -1,6 +1,2 @@
|
|
|
1
|
-
|
|
2
|
-
export
|
|
3
|
-
const view = new URL(httpUrlSchema.parse(viewUrl));
|
|
4
|
-
const id = designIdSchema.parse(frameId);
|
|
5
|
-
return new URL(`/${id}.webp`, view.origin).href;
|
|
6
|
-
}
|
|
1
|
+
/** @deprecated Use framePreviewUrl. */
|
|
2
|
+
export { framePreviewUrl as frameImageUrl } from "./frame-preview.js";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function framePreviewUrl(viewUrl: string, frameId: string): string;
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import { designIdSchema, httpUrlSchema } from "./v1/schemas.js";
|
|
2
|
+
export function framePreviewUrl(viewUrl, frameId) {
|
|
3
|
+
const view = new URL(httpUrlSchema.parse(viewUrl));
|
|
4
|
+
const id = designIdSchema.parse(frameId);
|
|
5
|
+
return new URL(`/${id}.webp`, view.origin).href;
|
|
6
|
+
}
|
package/dist/mcp/file.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { fileTextSchema } from "../v1/schemas.js";
|
|
2
2
|
import { fileResult, result } from "./result.js";
|
|
3
|
-
import { directoryPathSchema, fileInput, projectInput } from "./schema.js";
|
|
3
|
+
import { directoryPathSchema, fileInput, importsInput, projectInput, } from "./schema.js";
|
|
4
4
|
export function registerFileTools(server, client) {
|
|
5
5
|
server.registerTool("list_design_files", {
|
|
6
6
|
title: "List Design files",
|
|
@@ -34,27 +34,42 @@ export function registerFileTools(server, client) {
|
|
|
34
34
|
});
|
|
35
35
|
server.registerTool("write_design_file", {
|
|
36
36
|
title: "Write Design file",
|
|
37
|
-
description: "Create or replace one .glts file at a canonical project-absolute path. The path includes the frame ID; this tool does not accept a frame argument.",
|
|
38
|
-
inputSchema: fileInput.extend({
|
|
37
|
+
description: "Create or replace one .glts or .md file at a canonical project-absolute path. Every .glts file it imports must exist or be given a bounding box in imports, which creates a placeholder file to replace later. The path includes the frame ID; this tool does not accept a frame argument.",
|
|
38
|
+
inputSchema: fileInput.extend({
|
|
39
|
+
text: fileTextSchema,
|
|
40
|
+
imports: importsInput.optional(),
|
|
41
|
+
}),
|
|
39
42
|
annotations: {
|
|
40
43
|
readOnlyHint: false,
|
|
41
44
|
destructiveHint: true,
|
|
42
45
|
openWorldHint: true,
|
|
43
46
|
},
|
|
44
|
-
}, async ({ project, path, text }) => result(await client.filesystem.write({
|
|
47
|
+
}, async ({ project, path, text, imports }) => result(await client.filesystem.write({
|
|
48
|
+
project,
|
|
49
|
+
path,
|
|
50
|
+
text,
|
|
51
|
+
...(imports === undefined ? {} : { imports }),
|
|
52
|
+
})));
|
|
45
53
|
server.registerTool("edit_design_file", {
|
|
46
54
|
title: "Edit Design file",
|
|
47
|
-
description: "Replace oldText when it occurs exactly once at a canonical project-absolute .glts path. The path includes the frame ID; this tool does not accept a frame argument.",
|
|
55
|
+
description: "Replace oldText when it occurs exactly once at a canonical project-absolute .glts or .md path. A newly imported .glts file that does not exist needs a bounding box in imports. The path includes the frame ID; this tool does not accept a frame argument.",
|
|
48
56
|
inputSchema: fileInput.extend({
|
|
49
57
|
oldText: fileTextSchema.min(1),
|
|
50
58
|
newText: fileTextSchema,
|
|
59
|
+
imports: importsInput.optional(),
|
|
51
60
|
}),
|
|
52
61
|
annotations: {
|
|
53
62
|
readOnlyHint: false,
|
|
54
63
|
destructiveHint: true,
|
|
55
64
|
openWorldHint: true,
|
|
56
65
|
},
|
|
57
|
-
}, async ({ project, path, oldText, newText }) => result(await client.filesystem.edit({
|
|
66
|
+
}, async ({ project, path, oldText, newText, imports }) => result(await client.filesystem.edit({
|
|
67
|
+
project,
|
|
68
|
+
path,
|
|
69
|
+
oldText,
|
|
70
|
+
newText,
|
|
71
|
+
...(imports === undefined ? {} : { imports }),
|
|
72
|
+
})));
|
|
58
73
|
server.registerTool("delete_design_file", {
|
|
59
74
|
title: "Delete Design file",
|
|
60
75
|
description: "Permanently delete one .glts file at a canonical project-absolute path. The path includes the frame ID; this tool does not accept a frame argument.",
|