assistant-ui 0.0.91 → 0.0.93
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 +32 -108
- package/dist/codemods/utils/createTransformer.d.ts +17 -13
- package/dist/codemods/utils/createTransformer.d.ts.map +1 -1
- package/dist/codemods/utils/createTransformer.js +18 -15
- package/dist/codemods/utils/createTransformer.js.map +1 -1
- package/dist/codemods/v0-11/content-part-to-message-part.d.ts +3 -1
- package/dist/codemods/v0-11/content-part-to-message-part.d.ts.map +1 -1
- package/dist/codemods/v0-11/content-part-to-message-part.js +98 -135
- package/dist/codemods/v0-11/content-part-to-message-part.js.map +1 -1
- package/dist/codemods/v0-12/assistant-api-to-aui.d.ts +3 -1
- package/dist/codemods/v0-12/assistant-api-to-aui.d.ts.map +1 -1
- package/dist/codemods/v0-12/assistant-api-to-aui.js +126 -213
- package/dist/codemods/v0-12/assistant-api-to-aui.js.map +1 -1
- package/dist/codemods/v0-12/event-names-to-camelcase.d.ts +3 -1
- package/dist/codemods/v0-12/event-names-to-camelcase.d.ts.map +1 -1
- package/dist/codemods/v0-12/event-names-to-camelcase.js +33 -38
- package/dist/codemods/v0-12/event-names-to-camelcase.js.map +1 -1
- package/dist/codemods/v0-12/primitive-if-to-aui-if.d.ts +3 -1
- package/dist/codemods/v0-12/primitive-if-to-aui-if.d.ts.map +1 -1
- package/dist/codemods/v0-12/primitive-if-to-aui-if.js +212 -297
- package/dist/codemods/v0-12/primitive-if-to-aui-if.js.map +1 -1
- package/dist/codemods/v0-8/ui-package-split.d.ts +3 -1
- package/dist/codemods/v0-8/ui-package-split.d.ts.map +1 -1
- package/dist/codemods/v0-8/ui-package-split.js +121 -164
- package/dist/codemods/v0-8/ui-package-split.js.map +1 -1
- package/dist/codemods/v0-9/edge-package-split.d.ts +3 -1
- package/dist/codemods/v0-9/edge-package-split.d.ts.map +1 -1
- package/dist/codemods/v0-9/edge-package-split.js +96 -140
- package/dist/codemods/v0-9/edge-package-split.js.map +1 -1
- package/dist/commands/add.d.ts +18 -1
- package/dist/commands/add.d.ts.map +1 -1
- package/dist/commands/add.js +54 -49
- package/dist/commands/add.js.map +1 -1
- package/dist/commands/agent.d.ts +5 -1
- package/dist/commands/agent.d.ts.map +1 -1
- package/dist/commands/agent.js +16 -25
- package/dist/commands/agent.js.map +1 -1
- package/dist/commands/create.d.ts +36 -26
- package/dist/commands/create.d.ts.map +1 -1
- package/dist/commands/create.js +458 -519
- package/dist/commands/create.js.map +1 -1
- package/dist/commands/info.d.ts +5 -1
- package/dist/commands/info.d.ts.map +1 -1
- package/dist/commands/info.js +233 -314
- package/dist/commands/info.js.map +1 -1
- package/dist/commands/init.d.ts +12 -9
- package/dist/commands/init.d.ts.map +1 -1
- package/dist/commands/init.js +98 -136
- package/dist/commands/init.js.map +1 -1
- package/dist/commands/mcp.d.ts +5 -1
- package/dist/commands/mcp.d.ts.map +1 -1
- package/dist/commands/mcp.js +175 -214
- package/dist/commands/mcp.js.map +1 -1
- package/dist/commands/update.d.ts +5 -1
- package/dist/commands/update.d.ts.map +1 -1
- package/dist/commands/update.js +46 -55
- package/dist/commands/update.js.map +1 -1
- package/dist/commands/upgrade.d.ts +11 -7
- package/dist/commands/upgrade.d.ts.map +1 -1
- package/dist/commands/upgrade.js +26 -38
- package/dist/commands/upgrade.js.map +1 -1
- package/dist/index.d.ts +1 -3
- package/dist/index.js +15 -14
- package/dist/index.js.map +1 -1
- package/dist/lib/create-project.d.ts +27 -10
- package/dist/lib/create-project.d.ts.map +1 -1
- package/dist/lib/create-project.js +239 -277
- package/dist/lib/create-project.js.map +1 -1
- package/dist/lib/install-ai-sdk-lib.d.ts +4 -1
- package/dist/lib/install-ai-sdk-lib.d.ts.map +1 -1
- package/dist/lib/install-ai-sdk-lib.js +12 -8
- package/dist/lib/install-ai-sdk-lib.js.map +1 -1
- package/dist/lib/install-edge-lib.d.ts +4 -1
- package/dist/lib/install-edge-lib.d.ts.map +1 -1
- package/dist/lib/install-edge-lib.js +16 -12
- package/dist/lib/install-edge-lib.js.map +1 -1
- package/dist/lib/install-ui-lib.d.ts +4 -1
- package/dist/lib/install-ui-lib.d.ts.map +1 -1
- package/dist/lib/install-ui-lib.js +12 -8
- package/dist/lib/install-ui-lib.js.map +1 -1
- package/dist/lib/run-spawn.d.ts +9 -0
- package/dist/lib/run-spawn.d.ts.map +1 -0
- package/dist/lib/run-spawn.js +26 -0
- package/dist/lib/run-spawn.js.map +1 -0
- package/dist/lib/transform-options.d.ts +8 -5
- package/dist/lib/transform-options.d.ts.map +1 -1
- package/dist/lib/transform-options.js +0 -2
- package/dist/lib/transform.d.ts +15 -11
- package/dist/lib/transform.d.ts.map +1 -1
- package/dist/lib/transform.js +97 -114
- package/dist/lib/transform.js.map +1 -1
- package/dist/lib/upgrade.d.ts +6 -2
- package/dist/lib/upgrade.d.ts.map +1 -1
- package/dist/lib/upgrade.js +62 -64
- package/dist/lib/upgrade.js.map +1 -1
- package/dist/lib/utils/config.d.ts +21 -18
- package/dist/lib/utils/config.d.ts.map +1 -1
- package/dist/lib/utils/config.js +24 -28
- package/dist/lib/utils/config.js.map +1 -1
- package/dist/lib/utils/file-scanner.d.ts +9 -6
- package/dist/lib/utils/file-scanner.d.ts.map +1 -1
- package/dist/lib/utils/file-scanner.js +44 -51
- package/dist/lib/utils/file-scanner.js.map +1 -1
- package/dist/lib/utils/logger.d.ts +10 -7
- package/dist/lib/utils/logger.d.ts.map +1 -1
- package/dist/lib/utils/logger.js +23 -19
- package/dist/lib/utils/logger.js.map +1 -1
- package/dist/lib/utils/package-installer.d.ts +10 -7
- package/dist/lib/utils/package-installer.d.ts.map +1 -1
- package/dist/lib/utils/package-installer.js +18 -19
- package/dist/lib/utils/package-installer.js.map +1 -1
- package/dist/lib/utils/package-manager.d.ts +10 -7
- package/dist/lib/utils/package-manager.d.ts.map +1 -1
- package/dist/lib/utils/package-manager.js +68 -59
- package/dist/lib/utils/package-manager.js.map +1 -1
- package/package.json +7 -7
- package/plugin/skills/assistant-ui/SKILL.md +2 -2
- package/src/commands/add.ts +67 -30
- package/src/commands/create.ts +116 -84
- package/src/commands/init.ts +9 -42
- package/src/lib/create-project.ts +123 -74
- package/src/lib/run-spawn.ts +32 -0
- package/dist/index.d.ts.map +0 -1
- package/dist/lib/transform-options.js.map +0 -1
package/dist/commands/create.js
CHANGED
|
@@ -1,533 +1,472 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { logger } from "../lib/utils/logger.js";
|
|
2
|
+
import { SpawnExitError, runSpawn } from "../lib/run-spawn.js";
|
|
3
|
+
import { dlxCommand, downloadProject, resolveLatestReleaseRef, resolvePackageManager, resolvePackageManagerForCwd, scaffoldProject, transformProject } from "../lib/create-project.js";
|
|
4
|
+
import { Command, Option } from "commander";
|
|
2
5
|
import chalk from "chalk";
|
|
3
|
-
import { spawn } from "cross-spawn";
|
|
4
6
|
import fs from "node:fs";
|
|
5
7
|
import path from "node:path";
|
|
6
8
|
import * as p from "@clack/prompts";
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
path: "examples/with-tanstack",
|
|
226
|
-
hasLocalComponents: false,
|
|
227
|
-
},
|
|
9
|
+
//#region src/commands/create.ts
|
|
10
|
+
const PROJECT_METADATA = [
|
|
11
|
+
{
|
|
12
|
+
name: "default",
|
|
13
|
+
label: "Default",
|
|
14
|
+
description: "Default template with Vercel AI SDK",
|
|
15
|
+
category: "template",
|
|
16
|
+
path: "templates/default",
|
|
17
|
+
hasLocalComponents: false
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
name: "minimal",
|
|
21
|
+
label: "Minimal",
|
|
22
|
+
description: "Bare-bones starting point",
|
|
23
|
+
category: "template",
|
|
24
|
+
path: "templates/minimal",
|
|
25
|
+
hasLocalComponents: true
|
|
26
|
+
},
|
|
27
|
+
{
|
|
28
|
+
name: "cloud",
|
|
29
|
+
label: "Cloud",
|
|
30
|
+
description: "Cloud-backed persistence starter",
|
|
31
|
+
category: "template",
|
|
32
|
+
path: "templates/cloud",
|
|
33
|
+
hasLocalComponents: false
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
name: "cloud-clerk",
|
|
37
|
+
label: "Cloud + Clerk",
|
|
38
|
+
description: "Cloud-backed starter with Clerk auth",
|
|
39
|
+
category: "template",
|
|
40
|
+
path: "templates/cloud-clerk",
|
|
41
|
+
hasLocalComponents: false
|
|
42
|
+
},
|
|
43
|
+
{
|
|
44
|
+
name: "langgraph",
|
|
45
|
+
label: "LangGraph",
|
|
46
|
+
description: "LangGraph starter template",
|
|
47
|
+
category: "template",
|
|
48
|
+
path: "templates/langgraph",
|
|
49
|
+
hasLocalComponents: false
|
|
50
|
+
},
|
|
51
|
+
{
|
|
52
|
+
name: "mcp",
|
|
53
|
+
label: "MCP",
|
|
54
|
+
description: "MCP tools + MCP Apps renderer starter",
|
|
55
|
+
category: "template",
|
|
56
|
+
path: "templates/mcp",
|
|
57
|
+
hasLocalComponents: false
|
|
58
|
+
},
|
|
59
|
+
{
|
|
60
|
+
name: "with-ag-ui",
|
|
61
|
+
label: "AG-UI",
|
|
62
|
+
description: "AG-UI protocol integration",
|
|
63
|
+
category: "example",
|
|
64
|
+
path: "examples/with-ag-ui",
|
|
65
|
+
hasLocalComponents: false
|
|
66
|
+
},
|
|
67
|
+
{
|
|
68
|
+
name: "with-google-adk",
|
|
69
|
+
label: "Google ADK",
|
|
70
|
+
description: "Google ADK agent integration",
|
|
71
|
+
category: "example",
|
|
72
|
+
path: "examples/with-google-adk",
|
|
73
|
+
hasLocalComponents: false
|
|
74
|
+
},
|
|
75
|
+
{
|
|
76
|
+
name: "with-ai-sdk-v6",
|
|
77
|
+
label: "AI SDK v6",
|
|
78
|
+
description: "Vercel AI SDK v6",
|
|
79
|
+
category: "example",
|
|
80
|
+
path: "examples/with-ai-sdk-v6",
|
|
81
|
+
hasLocalComponents: false
|
|
82
|
+
},
|
|
83
|
+
{
|
|
84
|
+
name: "with-artifacts",
|
|
85
|
+
label: "Artifacts",
|
|
86
|
+
description: "Artifact rendering",
|
|
87
|
+
category: "example",
|
|
88
|
+
path: "examples/with-artifacts",
|
|
89
|
+
hasLocalComponents: false
|
|
90
|
+
},
|
|
91
|
+
{
|
|
92
|
+
name: "with-assistant-transport",
|
|
93
|
+
label: "Assistant Transport",
|
|
94
|
+
description: "Assistant transport protocol",
|
|
95
|
+
category: "example",
|
|
96
|
+
path: "examples/with-assistant-transport",
|
|
97
|
+
hasLocalComponents: false
|
|
98
|
+
},
|
|
99
|
+
{
|
|
100
|
+
name: "with-chain-of-thought",
|
|
101
|
+
label: "Chain of Thought",
|
|
102
|
+
description: "Chain-of-thought rendering",
|
|
103
|
+
category: "example",
|
|
104
|
+
path: "examples/with-chain-of-thought",
|
|
105
|
+
hasLocalComponents: false
|
|
106
|
+
},
|
|
107
|
+
{
|
|
108
|
+
name: "with-cloud",
|
|
109
|
+
label: "Cloud Example",
|
|
110
|
+
description: "Cloud integration example",
|
|
111
|
+
category: "example",
|
|
112
|
+
path: "examples/with-cloud",
|
|
113
|
+
hasLocalComponents: false
|
|
114
|
+
},
|
|
115
|
+
{
|
|
116
|
+
name: "with-custom-thread-list",
|
|
117
|
+
label: "Custom Thread List",
|
|
118
|
+
description: "Custom thread list UI",
|
|
119
|
+
category: "example",
|
|
120
|
+
path: "examples/with-custom-thread-list",
|
|
121
|
+
hasLocalComponents: false
|
|
122
|
+
},
|
|
123
|
+
{
|
|
124
|
+
name: "with-elevenlabs-conversational",
|
|
125
|
+
label: "ElevenLabs Conversational",
|
|
126
|
+
description: "Realtime voice with ElevenLabs",
|
|
127
|
+
category: "example",
|
|
128
|
+
path: "examples/with-elevenlabs-conversational",
|
|
129
|
+
hasLocalComponents: true
|
|
130
|
+
},
|
|
131
|
+
{
|
|
132
|
+
name: "with-elevenlabs-scribe",
|
|
133
|
+
label: "ElevenLabs Scribe",
|
|
134
|
+
description: "Audio/speech integration",
|
|
135
|
+
category: "example",
|
|
136
|
+
path: "examples/with-elevenlabs-scribe",
|
|
137
|
+
hasLocalComponents: false
|
|
138
|
+
},
|
|
139
|
+
{
|
|
140
|
+
name: "with-livekit",
|
|
141
|
+
label: "LiveKit Voice",
|
|
142
|
+
description: "Realtime voice with LiveKit",
|
|
143
|
+
category: "example",
|
|
144
|
+
path: "examples/with-livekit",
|
|
145
|
+
hasLocalComponents: true
|
|
146
|
+
},
|
|
147
|
+
{
|
|
148
|
+
name: "with-expo",
|
|
149
|
+
label: "Expo",
|
|
150
|
+
description: "Expo / React Native",
|
|
151
|
+
category: "example",
|
|
152
|
+
path: "examples/with-expo",
|
|
153
|
+
hasLocalComponents: true
|
|
154
|
+
},
|
|
155
|
+
{
|
|
156
|
+
name: "with-interactables",
|
|
157
|
+
label: "Interactables",
|
|
158
|
+
description: "AI-driven interactive UI components",
|
|
159
|
+
category: "example",
|
|
160
|
+
path: "examples/with-interactables",
|
|
161
|
+
hasLocalComponents: true
|
|
162
|
+
},
|
|
163
|
+
{
|
|
164
|
+
name: "with-external-store",
|
|
165
|
+
label: "External Store",
|
|
166
|
+
description: "Custom message store",
|
|
167
|
+
category: "example",
|
|
168
|
+
path: "examples/with-external-store",
|
|
169
|
+
hasLocalComponents: false
|
|
170
|
+
},
|
|
171
|
+
{
|
|
172
|
+
name: "with-ffmpeg",
|
|
173
|
+
label: "FFmpeg",
|
|
174
|
+
description: "File processing",
|
|
175
|
+
category: "example",
|
|
176
|
+
path: "examples/with-ffmpeg",
|
|
177
|
+
hasLocalComponents: false
|
|
178
|
+
},
|
|
179
|
+
{
|
|
180
|
+
name: "with-langgraph",
|
|
181
|
+
label: "LangGraph Example",
|
|
182
|
+
description: "LangGraph integration",
|
|
183
|
+
category: "example",
|
|
184
|
+
path: "examples/with-langgraph",
|
|
185
|
+
hasLocalComponents: false
|
|
186
|
+
},
|
|
187
|
+
{
|
|
188
|
+
name: "with-parent-id-grouping",
|
|
189
|
+
label: "Parent ID Grouping",
|
|
190
|
+
description: "Message grouping strategy",
|
|
191
|
+
category: "example",
|
|
192
|
+
path: "examples/with-parent-id-grouping",
|
|
193
|
+
hasLocalComponents: false
|
|
194
|
+
},
|
|
195
|
+
{
|
|
196
|
+
name: "with-react-hook-form",
|
|
197
|
+
label: "React Hook Form",
|
|
198
|
+
description: "Form integration",
|
|
199
|
+
category: "example",
|
|
200
|
+
path: "examples/with-react-hook-form",
|
|
201
|
+
hasLocalComponents: false
|
|
202
|
+
},
|
|
203
|
+
{
|
|
204
|
+
name: "with-react-ink",
|
|
205
|
+
label: "React Ink",
|
|
206
|
+
description: "Terminal UI chat",
|
|
207
|
+
category: "example",
|
|
208
|
+
path: "examples/with-react-ink",
|
|
209
|
+
hasLocalComponents: true
|
|
210
|
+
},
|
|
211
|
+
{
|
|
212
|
+
name: "with-react-router",
|
|
213
|
+
label: "React Router",
|
|
214
|
+
description: "React Router v7 + Vite",
|
|
215
|
+
category: "example",
|
|
216
|
+
path: "examples/with-react-router",
|
|
217
|
+
hasLocalComponents: false
|
|
218
|
+
},
|
|
219
|
+
{
|
|
220
|
+
name: "with-tanstack",
|
|
221
|
+
label: "TanStack",
|
|
222
|
+
description: "TanStack/React Router + Vite",
|
|
223
|
+
category: "example",
|
|
224
|
+
path: "examples/with-tanstack",
|
|
225
|
+
hasLocalComponents: false
|
|
226
|
+
}
|
|
228
227
|
];
|
|
229
|
-
// Examples that exist in the monorepo but are intentionally excluded from the CLI:
|
|
230
|
-
//
|
|
231
|
-
// - waterfall: Still in development, not ready for production.
|
|
232
|
-
// - with-cloud-standalone: For cloud without assistant-ui — not for the
|
|
233
|
-
// assistant-ui CLI.
|
|
234
|
-
// - with-store: In development, not ready for public use of the tap store.
|
|
235
|
-
// - with-tap-runtime: In development, not ready for public use of the tap
|
|
236
|
-
// store.
|
|
237
228
|
const templateNames = PROJECT_METADATA.filter((m) => m.category === "template").map((m) => m.name);
|
|
238
229
|
const exampleNames = PROJECT_METADATA.filter((m) => m.category === "example").map((m) => m.name);
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
logger.error(`Unknown selection: ${String(selected)}`);
|
|
293
|
-
process.exit(1);
|
|
294
|
-
}
|
|
295
|
-
return meta;
|
|
296
|
-
}
|
|
297
|
-
class SpawnExitError extends Error {
|
|
298
|
-
code;
|
|
299
|
-
constructor(code) {
|
|
300
|
-
super(`Process exited with code ${code}`);
|
|
301
|
-
this.code = code;
|
|
302
|
-
}
|
|
230
|
+
async function resolveProject(params) {
|
|
231
|
+
const { template, example, stdinIsTTY = process.stdin.isTTY, select = p.select, isCancel = p.isCancel } = params;
|
|
232
|
+
if (template !== void 0) {
|
|
233
|
+
const meta = PROJECT_METADATA.find((m) => m.name === template && m.category === "template");
|
|
234
|
+
if (!meta) {
|
|
235
|
+
logger.error(`Unknown template: ${template}`);
|
|
236
|
+
logger.info(`Available templates: ${templateNames.join(", ")}`);
|
|
237
|
+
process.exit(1);
|
|
238
|
+
}
|
|
239
|
+
return meta;
|
|
240
|
+
}
|
|
241
|
+
if (example !== void 0) {
|
|
242
|
+
const meta = PROJECT_METADATA.find((m) => m.name === example && m.category === "example");
|
|
243
|
+
if (!meta) {
|
|
244
|
+
logger.error(`Unknown example: ${example}`);
|
|
245
|
+
logger.info(`Available examples: ${exampleNames.join(", ")}`);
|
|
246
|
+
process.exit(1);
|
|
247
|
+
}
|
|
248
|
+
return meta;
|
|
249
|
+
}
|
|
250
|
+
if (!stdinIsTTY) return PROJECT_METADATA.find((m) => m.name === "default");
|
|
251
|
+
const selected = await select({
|
|
252
|
+
message: "Select a project to scaffold:",
|
|
253
|
+
options: [
|
|
254
|
+
{
|
|
255
|
+
value: "_separator",
|
|
256
|
+
label: "────── Starter Templates ──────",
|
|
257
|
+
disabled: true
|
|
258
|
+
},
|
|
259
|
+
...PROJECT_METADATA.filter((m) => m.category === "template").map((m) => ({
|
|
260
|
+
value: m.name,
|
|
261
|
+
label: m.label,
|
|
262
|
+
...m.description ? { hint: m.description } : {}
|
|
263
|
+
})),
|
|
264
|
+
{
|
|
265
|
+
value: "_separator",
|
|
266
|
+
label: "────── Feature Examples ──────",
|
|
267
|
+
disabled: true
|
|
268
|
+
},
|
|
269
|
+
...PROJECT_METADATA.filter((m) => m.category === "example").map((m) => ({
|
|
270
|
+
value: m.name,
|
|
271
|
+
label: m.label,
|
|
272
|
+
...m.description ? { hint: m.description } : {}
|
|
273
|
+
}))
|
|
274
|
+
]
|
|
275
|
+
});
|
|
276
|
+
if (isCancel(selected)) return null;
|
|
277
|
+
const meta = PROJECT_METADATA.find((m) => m.name === selected);
|
|
278
|
+
if (!meta) {
|
|
279
|
+
logger.error(`Unknown selection: ${String(selected)}`);
|
|
280
|
+
process.exit(1);
|
|
281
|
+
}
|
|
282
|
+
return meta;
|
|
303
283
|
}
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
cwd,
|
|
309
|
-
});
|
|
310
|
-
child.on("error", (error) => reject(error));
|
|
311
|
-
child.on("close", (code) => {
|
|
312
|
-
if (code !== 0) {
|
|
313
|
-
reject(new SpawnExitError(code || 1));
|
|
314
|
-
}
|
|
315
|
-
else {
|
|
316
|
-
resolve();
|
|
317
|
-
}
|
|
318
|
-
});
|
|
319
|
-
});
|
|
284
|
+
function resolveCreateProjectDirectory(params) {
|
|
285
|
+
const { projectDirectory, stdinIsTTY = process.stdin.isTTY } = params;
|
|
286
|
+
if (projectDirectory) return projectDirectory;
|
|
287
|
+
if (!stdinIsTTY) return "my-aui-app";
|
|
320
288
|
}
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
if (!stdinIsTTY)
|
|
326
|
-
return "my-aui-app";
|
|
327
|
-
return undefined;
|
|
289
|
+
const PLAYGROUND_PRESET_BASE_URL = "https://www.assistant-ui.com/playground/init";
|
|
290
|
+
function resolvePresetUrl(preset) {
|
|
291
|
+
if (preset.startsWith("http://") || preset.startsWith("https://")) return preset;
|
|
292
|
+
return `${PLAYGROUND_PRESET_BASE_URL}?preset=${encodeURIComponent(preset)}`;
|
|
328
293
|
}
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
if (opts.useYarn)
|
|
335
|
-
return "yarn";
|
|
336
|
-
if (opts.useBun)
|
|
337
|
-
return "bun";
|
|
338
|
-
return undefined;
|
|
294
|
+
const scaffoldSelectorHelp = "Choose one scaffold selector: --template <name>, --example <name>, --native, or --ink. --preset <name-or-url> can be used with --template or by itself.";
|
|
295
|
+
function getPresetConflict(opts) {
|
|
296
|
+
if (opts.example !== void 0) return "--example";
|
|
297
|
+
if (opts.native) return "--native";
|
|
298
|
+
if (opts.ink) return "--ink";
|
|
339
299
|
}
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
300
|
+
function resolveScaffoldSelector(opts) {
|
|
301
|
+
const hasPreset = opts.preset !== void 0;
|
|
302
|
+
const presetConflict = getPresetConflict(opts);
|
|
303
|
+
const selectors = [
|
|
304
|
+
opts.template !== void 0 ? "--template" : void 0,
|
|
305
|
+
opts.example !== void 0 ? "--example" : void 0,
|
|
306
|
+
opts.native ? "--native" : void 0,
|
|
307
|
+
opts.ink ? "--ink" : void 0
|
|
308
|
+
].filter((selector) => selector !== void 0);
|
|
309
|
+
if (selectors.length > 1) throw new Error(`Only one scaffold selector can be provided (${selectors.join(", ")}). ${scaffoldSelectorHelp}`);
|
|
310
|
+
if (hasPreset && presetConflict) throw new Error(`Cannot use --preset with ${presetConflict}. ${scaffoldSelectorHelp}`);
|
|
311
|
+
if (opts.native) return { example: "with-expo" };
|
|
312
|
+
if (opts.ink) return { example: "with-react-ink" };
|
|
313
|
+
if (opts.preset !== void 0 && opts.template === void 0) return {
|
|
314
|
+
template: "default",
|
|
315
|
+
preset: opts.preset
|
|
316
|
+
};
|
|
317
|
+
return {
|
|
318
|
+
...opts.template !== void 0 && { template: opts.template },
|
|
319
|
+
...opts.example !== void 0 && { example: opts.example },
|
|
320
|
+
...hasPreset && { preset: opts.preset }
|
|
321
|
+
};
|
|
346
322
|
}
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
catch {
|
|
493
|
-
logger.warn(`Preset application failed. You can retry manually with:\n ${dlxCmd} ${[...dlxArgs, "shadcn@latest", "add", presetUrl].join(" ")}`);
|
|
494
|
-
}
|
|
495
|
-
}
|
|
496
|
-
process.removeListener("exit", cleanupOnExit);
|
|
497
|
-
logger.break();
|
|
498
|
-
logger.success("Project created successfully!");
|
|
499
|
-
logger.break();
|
|
500
|
-
const runCmd = pm === "npm" ? "npm run" : pm;
|
|
501
|
-
let devScript = "dev";
|
|
502
|
-
let envFile = ".env.local";
|
|
503
|
-
try {
|
|
504
|
-
const scaffoldedPkg = JSON.parse(fs.readFileSync(path.join(absoluteProjectDir, "package.json"), "utf-8"));
|
|
505
|
-
devScript = scaffoldedPkg.scripts?.dev
|
|
506
|
-
? "dev"
|
|
507
|
-
: scaffoldedPkg.scripts?.start
|
|
508
|
-
? "start"
|
|
509
|
-
: "dev";
|
|
510
|
-
envFile = scaffoldedPkg.dependencies?.next ? ".env.local" : ".env";
|
|
511
|
-
}
|
|
512
|
-
catch {
|
|
513
|
-
// Fall back to defaults if package.json cannot be read
|
|
514
|
-
}
|
|
515
|
-
logger.info("Next steps:");
|
|
516
|
-
logger.info(` cd ${resolvedProjectDirectory}`);
|
|
517
|
-
if (opts.skipInstall) {
|
|
518
|
-
logger.info(` ${pm} install`);
|
|
519
|
-
}
|
|
520
|
-
logger.info(` # Set up your environment variables in ${envFile}`);
|
|
521
|
-
logger.info(` ${runCmd} ${devScript}`);
|
|
522
|
-
}
|
|
523
|
-
catch (error) {
|
|
524
|
-
if (error instanceof SpawnExitError) {
|
|
525
|
-
logger.error(`Project creation failed with code ${error.code}`);
|
|
526
|
-
process.exit(error.code);
|
|
527
|
-
}
|
|
528
|
-
const message = error instanceof Error ? error.message : String(error);
|
|
529
|
-
logger.error(`Failed to create project: ${message}`);
|
|
530
|
-
process.exit(1);
|
|
531
|
-
}
|
|
323
|
+
const create = new Command().name("create").description("create a new project").argument("[project-directory]").usage(`${chalk.green("[project-directory]")} [options]`).option("-t, --template <template>", `template to use (${templateNames.join(", ")})`).option("-e, --example <example>", `create from an example (${exampleNames.join(", ")})`).option("-p, --preset <name-or-url>", "preset name or URL (e.g., chatgpt or https://www.assistant-ui.com/playground/init?preset=chatgpt)").option("--use-npm", "explicitly use npm").option("--use-pnpm", "explicitly use pnpm").option("--use-yarn", "explicitly use yarn").option("--use-bun", "explicitly use bun").option("--native", "create an Expo / React Native project").option("--ink", "create a React Ink terminal project").option("--skip-install", "skip installing packages").addOption(new Option("--debug-source-root <path>", "copy templates/examples from a local assistant-ui repo root").hideHelp()).action(async (projectDirectory, opts) => {
|
|
324
|
+
let scaffoldSelector;
|
|
325
|
+
try {
|
|
326
|
+
scaffoldSelector = resolveScaffoldSelector(opts);
|
|
327
|
+
} catch (error) {
|
|
328
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
329
|
+
logger.error(message);
|
|
330
|
+
process.exit(1);
|
|
331
|
+
}
|
|
332
|
+
const localSourceRoot = opts.debugSourceRoot ? path.resolve(opts.debugSourceRoot) : void 0;
|
|
333
|
+
const refPromise = localSourceRoot ? Promise.resolve(void 0) : resolveLatestReleaseRef();
|
|
334
|
+
let resolvedProjectDirectory = resolveCreateProjectDirectory({ projectDirectory });
|
|
335
|
+
if (!resolvedProjectDirectory) {
|
|
336
|
+
const result = await p.text({
|
|
337
|
+
message: "Project name:",
|
|
338
|
+
placeholder: "my-aui-app",
|
|
339
|
+
defaultValue: "my-aui-app",
|
|
340
|
+
validate: (value) => {
|
|
341
|
+
const name = (value ?? "").trim();
|
|
342
|
+
if (!name) return "Project name cannot be empty";
|
|
343
|
+
if (name === "." || name === "..") return "Project name cannot be . or ..";
|
|
344
|
+
if (name.includes("/") || name.includes("\\")) return "Project name cannot contain path separators";
|
|
345
|
+
}
|
|
346
|
+
});
|
|
347
|
+
if (p.isCancel(result)) {
|
|
348
|
+
p.cancel("Project creation cancelled.");
|
|
349
|
+
process.exit(0);
|
|
350
|
+
}
|
|
351
|
+
resolvedProjectDirectory = result;
|
|
352
|
+
}
|
|
353
|
+
const absoluteProjectDir = path.resolve(resolvedProjectDirectory);
|
|
354
|
+
try {
|
|
355
|
+
if (fs.readdirSync(absoluteProjectDir).length > 0) {
|
|
356
|
+
logger.error(`Directory ${resolvedProjectDirectory} already exists and is not empty`);
|
|
357
|
+
process.exit(1);
|
|
358
|
+
}
|
|
359
|
+
} catch (err) {
|
|
360
|
+
const code = err instanceof Error ? err.code : void 0;
|
|
361
|
+
if (code === "ENOENT") {} else if (code === "ENOTDIR") {
|
|
362
|
+
logger.error(`${resolvedProjectDirectory} already exists and is not a directory`);
|
|
363
|
+
process.exit(1);
|
|
364
|
+
} else {
|
|
365
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
366
|
+
logger.error(`Cannot access ${resolvedProjectDirectory}: ${message}`);
|
|
367
|
+
process.exit(1);
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
const project = await resolveProject(scaffoldSelector);
|
|
371
|
+
if (!project) {
|
|
372
|
+
p.cancel("Project creation cancelled.");
|
|
373
|
+
process.exit(0);
|
|
374
|
+
}
|
|
375
|
+
logger.info(`Creating project from ${project.category}: ${project.label}`);
|
|
376
|
+
logger.break();
|
|
377
|
+
const pm = await resolvePackageManagerForCwd(path.dirname(absoluteProjectDir), resolvePackageManager(opts));
|
|
378
|
+
const cleanupOnExit = () => {
|
|
379
|
+
fs.rmSync(absoluteProjectDir, {
|
|
380
|
+
recursive: true,
|
|
381
|
+
force: true
|
|
382
|
+
});
|
|
383
|
+
};
|
|
384
|
+
process.once("exit", cleanupOnExit);
|
|
385
|
+
try {
|
|
386
|
+
if (!localSourceRoot) logger.step("Resolving latest release...");
|
|
387
|
+
const ref = await refPromise;
|
|
388
|
+
if (!localSourceRoot && !ref) logger.warn("Could not resolve latest release, downloading from HEAD");
|
|
389
|
+
logger.step(localSourceRoot ? `Copying project from local source: ${localSourceRoot}` : "Downloading project...");
|
|
390
|
+
try {
|
|
391
|
+
const source = localSourceRoot ? {
|
|
392
|
+
kind: "local",
|
|
393
|
+
rootDir: localSourceRoot
|
|
394
|
+
} : {
|
|
395
|
+
kind: "github",
|
|
396
|
+
ref
|
|
397
|
+
};
|
|
398
|
+
await scaffoldProject(project.path, absoluteProjectDir, source);
|
|
399
|
+
if (!localSourceRoot && ref && !fs.existsSync(path.join(absoluteProjectDir, "package.json"))) {
|
|
400
|
+
fs.rmSync(absoluteProjectDir, {
|
|
401
|
+
recursive: true,
|
|
402
|
+
force: true
|
|
403
|
+
});
|
|
404
|
+
logger.warn("Template not found at release tag, downloading from HEAD");
|
|
405
|
+
await downloadProject(project.path, absoluteProjectDir);
|
|
406
|
+
}
|
|
407
|
+
await transformProject(absoluteProjectDir, {
|
|
408
|
+
hasLocalComponents: project.hasLocalComponents,
|
|
409
|
+
skipInstall: opts.skipInstall,
|
|
410
|
+
packageManager: pm
|
|
411
|
+
});
|
|
412
|
+
} catch (err) {
|
|
413
|
+
fs.rmSync(absoluteProjectDir, {
|
|
414
|
+
recursive: true,
|
|
415
|
+
force: true
|
|
416
|
+
});
|
|
417
|
+
throw err;
|
|
418
|
+
}
|
|
419
|
+
if (scaffoldSelector.preset) {
|
|
420
|
+
const presetUrl = resolvePresetUrl(scaffoldSelector.preset);
|
|
421
|
+
logger.info("Applying preset configuration...");
|
|
422
|
+
logger.break();
|
|
423
|
+
const [dlxCmd, dlxArgs] = dlxCommand(pm);
|
|
424
|
+
try {
|
|
425
|
+
await runSpawn(dlxCmd, [
|
|
426
|
+
...dlxArgs,
|
|
427
|
+
"shadcn@latest",
|
|
428
|
+
"add",
|
|
429
|
+
"--yes",
|
|
430
|
+
"--overwrite",
|
|
431
|
+
presetUrl
|
|
432
|
+
], absoluteProjectDir);
|
|
433
|
+
} catch {
|
|
434
|
+
logger.warn(`Preset application failed. You can retry manually with:\n ${dlxCmd} ${[
|
|
435
|
+
...dlxArgs,
|
|
436
|
+
"shadcn@latest",
|
|
437
|
+
"add",
|
|
438
|
+
presetUrl
|
|
439
|
+
].join(" ")}`);
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
process.removeListener("exit", cleanupOnExit);
|
|
443
|
+
logger.break();
|
|
444
|
+
logger.success("Project created successfully!");
|
|
445
|
+
logger.break();
|
|
446
|
+
const runCmd = pm === "npm" ? "npm run" : pm;
|
|
447
|
+
let devScript = "dev";
|
|
448
|
+
let envFile = ".env.local";
|
|
449
|
+
try {
|
|
450
|
+
const scaffoldedPkg = JSON.parse(fs.readFileSync(path.join(absoluteProjectDir, "package.json"), "utf-8"));
|
|
451
|
+
devScript = scaffoldedPkg.scripts?.dev ? "dev" : scaffoldedPkg.scripts?.start ? "start" : "dev";
|
|
452
|
+
envFile = scaffoldedPkg.dependencies?.next ? ".env.local" : ".env";
|
|
453
|
+
} catch {}
|
|
454
|
+
logger.info("Next steps:");
|
|
455
|
+
logger.info(` cd ${resolvedProjectDirectory}`);
|
|
456
|
+
if (opts.skipInstall) logger.info(` ${pm} install`);
|
|
457
|
+
logger.info(` # Set up your environment variables in ${envFile}`);
|
|
458
|
+
logger.info(` ${runCmd} ${devScript}`);
|
|
459
|
+
} catch (error) {
|
|
460
|
+
if (error instanceof SpawnExitError) {
|
|
461
|
+
logger.error(`Project creation failed with code ${error.code}`);
|
|
462
|
+
process.exit(error.code);
|
|
463
|
+
}
|
|
464
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
465
|
+
logger.error(`Failed to create project: ${message}`);
|
|
466
|
+
process.exit(1);
|
|
467
|
+
}
|
|
532
468
|
});
|
|
469
|
+
//#endregion
|
|
470
|
+
export { PROJECT_METADATA, create, resolveCreateProjectDirectory, resolvePresetUrl, resolveProject, resolveScaffoldSelector };
|
|
471
|
+
|
|
533
472
|
//# sourceMappingURL=create.js.map
|