@lazarv/create-react-server 0.0.0-experimental-d003259-20250211-2495688e
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/LICENSE +21 -0
- package/README.md +31 -0
- package/generator.mjs +195 -0
- package/globals.d.ts +59 -0
- package/index.mjs +87 -0
- package/launch.mjs +136 -0
- package/lib/code-merge.mjs +246 -0
- package/lib/dynamic-checkbox.mjs +259 -0
- package/lib/files.mjs +6 -0
- package/lib/formatter.mjs +16 -0
- package/lib/generate-name.mjs +220 -0
- package/lib/theme.mjs +56 -0
- package/logo.mjs +3 -0
- package/package.json +26 -0
- package/steps/alias.mjs +50 -0
- package/steps/authentication.mjs +62 -0
- package/steps/database.mjs +56 -0
- package/steps/deploy.mjs +151 -0
- package/steps/features.mjs +415 -0
- package/steps/host.mjs +40 -0
- package/steps/index.mjs +33 -0
- package/steps/integrations.mjs +104 -0
- package/steps/name.mjs +69 -0
- package/steps/package.mjs +104 -0
- package/steps/port.mjs +42 -0
- package/steps/preset.mjs +188 -0
- package/steps/state-management.mjs +68 -0
- package/steps/third-party.mjs +19 -0
- package/steps/ui.mjs +87 -0
- package/templates/.dockerignore +5 -0
- package/templates/.gitignore.template +19 -0
- package/templates/.prettierignore +3 -0
- package/templates/.prettierrc +11 -0
- package/templates/Dockerfile.npm +49 -0
- package/templates/Dockerfile.pnpm +71 -0
- package/templates/Dockerfile.yarn +71 -0
- package/templates/README.docker.md +15 -0
- package/templates/README.md +35 -0
- package/templates/blank/package.json +6 -0
- package/templates/blank/src/App.jsx +5 -0
- package/templates/blank-ts/package.json +6 -0
- package/templates/blank-ts/src/App.tsx +5 -0
- package/templates/eslint.config.template.mjs +98 -0
- package/templates/get-started/package.json +6 -0
- package/templates/get-started/src/App.jsx +60 -0
- package/templates/get-started/src/Button.jsx +14 -0
- package/templates/get-started/src/Confetti.jsx +19 -0
- package/templates/get-started/src/global.css +3 -0
- package/templates/get-started-ts/globals.d.ts +3 -0
- package/templates/get-started-ts/package.json +6 -0
- package/templates/get-started-ts/src/App.tsx +66 -0
- package/templates/get-started-ts/src/Button.tsx +18 -0
- package/templates/get-started-ts/src/Confetti.tsx +19 -0
- package/templates/get-started-ts/src/global.css +3 -0
- package/templates/nextjs/globals.d.ts +3 -0
- package/templates/nextjs/react-server.config.json +9 -0
- package/templates/nextjs/src/app/layout.tsx +38 -0
- package/templates/nextjs/src/app/page.tsx +33 -0
- package/templates/nextjs/src/components/Button.tsx +18 -0
- package/templates/nextjs/src/components/Confetti.tsx +19 -0
- package/templates/nextjs/src/global.css +3 -0
- package/templates/package.css.json +5 -0
- package/templates/package.eslint.json +19 -0
- package/templates/package.eslint.ts.json +7 -0
- package/templates/package.json +12 -0
- package/templates/package.lightningcss.json +6 -0
- package/templates/package.prettier.json +8 -0
- package/templates/package.react-compiler.json +7 -0
- package/templates/package.swc.json +5 -0
- package/templates/package.tailwind.json +7 -0
- package/templates/package.ts.json +11 -0
- package/templates/postcss.config.mjs +6 -0
- package/templates/router/globals.d.ts +3 -0
- package/templates/router/react-server.config.json +19 -0
- package/templates/router/src/app/@content/about.tsx +98 -0
- package/templates/router/src/app/@content/index.tsx +33 -0
- package/templates/router/src/app/layout.tsx +44 -0
- package/templates/router/src/app/page.tsx +17 -0
- package/templates/router/src/components/Button.tsx +18 -0
- package/templates/router/src/components/Confetti.tsx +19 -0
- package/templates/router/src/components/Navigation.tsx +31 -0
- package/templates/router/src/global.css +3 -0
- package/templates/shared/public/github.svg +4 -0
- package/templates/shared/public/react-server.svg +51 -0
- package/templates/tailwind.config.mjs +6 -0
- package/templates/tsconfig.css.json +9 -0
- package/templates/tsconfig.template.json +15 -0
- package/templates/vite.config.lightningcss.mjs +15 -0
- package/templates/vite.config.lightningcss.ts +15 -0
- package/templates/vite.config.react-compiler.mjs +19 -0
- package/templates/vite.config.react-compiler.ts +19 -0
- package/templates/vite.config.swc.mjs +6 -0
- package/templates/vite.config.swc.ts +6 -0
- package/templates/vite.config.ts +3 -0
- package/wizard.mjs +122 -0
|
@@ -0,0 +1,246 @@
|
|
|
1
|
+
import { Project, ts } from "ts-morph";
|
|
2
|
+
|
|
3
|
+
import { format } from "./formatter.mjs";
|
|
4
|
+
|
|
5
|
+
export async function mergeCodeFiles(...fileContents) {
|
|
6
|
+
const project = new Project({
|
|
7
|
+
useInMemoryFileSystem: true,
|
|
8
|
+
compilerOptions: {
|
|
9
|
+
allowJs: true,
|
|
10
|
+
checkJs: false,
|
|
11
|
+
esModuleInterop: true,
|
|
12
|
+
},
|
|
13
|
+
});
|
|
14
|
+
|
|
15
|
+
const mergedSourceFile = project.createSourceFile("mergedFile.ts", "", {
|
|
16
|
+
overwrite: true,
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
const importDeclarations = [];
|
|
20
|
+
const otherStatementsMap = new Map();
|
|
21
|
+
|
|
22
|
+
fileContents.forEach((content, index) => {
|
|
23
|
+
const sourceFile = project.createSourceFile(`file${index}.ts`, content, {
|
|
24
|
+
overwrite: true,
|
|
25
|
+
});
|
|
26
|
+
|
|
27
|
+
sourceFile.getImportDeclarations().forEach((importDecl) => {
|
|
28
|
+
importDeclarations.push(importDecl);
|
|
29
|
+
});
|
|
30
|
+
|
|
31
|
+
sourceFile.getStatements().forEach((stmt) => {
|
|
32
|
+
if (!stmt.isKind(ts.SyntaxKind.ImportDeclaration)) {
|
|
33
|
+
const key = getStatementKey(stmt);
|
|
34
|
+
if (!otherStatementsMap.has(key)) {
|
|
35
|
+
otherStatementsMap.set(key, stmt);
|
|
36
|
+
} else {
|
|
37
|
+
const existingStmt = otherStatementsMap.get(key);
|
|
38
|
+
mergeNodes(existingStmt, stmt);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
const groupedImports = groupAndSortImports(importDeclarations);
|
|
45
|
+
groupedImports.forEach((importDecl) => {
|
|
46
|
+
mergedSourceFile.addImportDeclaration({
|
|
47
|
+
moduleSpecifier: importDecl.getModuleSpecifierValue(),
|
|
48
|
+
defaultImport: importDecl.getDefaultImport()?.getText(),
|
|
49
|
+
namedImports: importDecl.getNamedImports().map((ni) => ni.getText()),
|
|
50
|
+
});
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
otherStatementsMap.forEach((stmt) => {
|
|
54
|
+
mergedSourceFile.addStatements(stmt.getFullText());
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
const mergedCode = mergedSourceFile.getFullText();
|
|
58
|
+
return format(mergedCode, "typescript");
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
function getStatementKey(stmt) {
|
|
62
|
+
if (stmt.isKind(ts.SyntaxKind.VariableStatement)) {
|
|
63
|
+
const declarations = stmt.getDeclarationList().getDeclarations();
|
|
64
|
+
return declarations.map((decl) => decl.getName()).join(",");
|
|
65
|
+
} else if (stmt.isKind(ts.SyntaxKind.FunctionDeclaration)) {
|
|
66
|
+
return `Function:${stmt.getName()}`;
|
|
67
|
+
} else if (stmt.isKind(ts.SyntaxKind.ClassDeclaration)) {
|
|
68
|
+
return `Class:${stmt.getName()}`;
|
|
69
|
+
} else if (stmt.isKind(ts.SyntaxKind.ExpressionStatement)) {
|
|
70
|
+
const expression = stmt.getExpression();
|
|
71
|
+
return `Expression:${expression.getText()}`;
|
|
72
|
+
} else if (stmt.isKind(ts.SyntaxKind.ExportAssignment)) {
|
|
73
|
+
return `ExportAssignment`;
|
|
74
|
+
}
|
|
75
|
+
return `Kind:${stmt.getKindName()}:${stmt.getText()}`;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function mergeNodes(target, source) {
|
|
79
|
+
if (
|
|
80
|
+
ts.isObjectLiteralExpression(target.compilerNode) &&
|
|
81
|
+
ts.isObjectLiteralExpression(source.compilerNode)
|
|
82
|
+
) {
|
|
83
|
+
mergeObjectLiterals(target, source);
|
|
84
|
+
} else if (target.getChildCount() > 0 && source.getChildCount() > 0) {
|
|
85
|
+
const targetChildren = target.getChildren();
|
|
86
|
+
const sourceChildren = source.getChildren();
|
|
87
|
+
const length = Math.max(targetChildren.length, sourceChildren.length);
|
|
88
|
+
|
|
89
|
+
for (let i = 0; i < length; i++) {
|
|
90
|
+
const targetChild = targetChildren[i];
|
|
91
|
+
const sourceChild = sourceChildren[i];
|
|
92
|
+
|
|
93
|
+
if (targetChild && sourceChild) {
|
|
94
|
+
mergeNodes(targetChild, sourceChild);
|
|
95
|
+
} else if (sourceChild) {
|
|
96
|
+
target.addChildText(sourceChild.getFullText());
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
} else {
|
|
100
|
+
target.replaceWithText(source.getFullText());
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
function mergeObjectLiterals(target, source) {
|
|
105
|
+
const targetProperties = target.getProperties();
|
|
106
|
+
const sourceProperties = source.getProperties();
|
|
107
|
+
|
|
108
|
+
const targetPropertyMap = new Map();
|
|
109
|
+
targetProperties.forEach((prop) => {
|
|
110
|
+
const name = prop.getName();
|
|
111
|
+
if (name) {
|
|
112
|
+
targetPropertyMap.set(name, prop);
|
|
113
|
+
}
|
|
114
|
+
});
|
|
115
|
+
|
|
116
|
+
sourceProperties.forEach((sourceProp) => {
|
|
117
|
+
const name = sourceProp.getName();
|
|
118
|
+
if (name) {
|
|
119
|
+
const targetProp = targetPropertyMap.get(name);
|
|
120
|
+
|
|
121
|
+
if (targetProp) {
|
|
122
|
+
const targetInitializer = getInitializer(targetProp);
|
|
123
|
+
const sourceInitializer = getInitializer(sourceProp);
|
|
124
|
+
|
|
125
|
+
if (
|
|
126
|
+
targetInitializer &&
|
|
127
|
+
sourceInitializer &&
|
|
128
|
+
ts.isObjectLiteralExpression(targetInitializer.compilerNode) &&
|
|
129
|
+
ts.isObjectLiteralExpression(sourceInitializer.compilerNode)
|
|
130
|
+
) {
|
|
131
|
+
mergeObjectLiterals(targetInitializer, sourceInitializer);
|
|
132
|
+
} else if (
|
|
133
|
+
targetInitializer &&
|
|
134
|
+
sourceInitializer &&
|
|
135
|
+
ts.isArrayLiteralExpression(targetInitializer.compilerNode) &&
|
|
136
|
+
ts.isArrayLiteralExpression(sourceInitializer.compilerNode)
|
|
137
|
+
) {
|
|
138
|
+
mergeArrays(targetInitializer, sourceInitializer);
|
|
139
|
+
} else {
|
|
140
|
+
targetProp.replaceWithText(sourceProp.getFullText());
|
|
141
|
+
}
|
|
142
|
+
} else {
|
|
143
|
+
target.addProperty(sourceProp.getFullText());
|
|
144
|
+
}
|
|
145
|
+
} else {
|
|
146
|
+
target.addProperty(sourceProp.getFullText());
|
|
147
|
+
}
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
function mergeArrays(targetArray, sourceArray) {
|
|
152
|
+
const targetElements = targetArray.getElements();
|
|
153
|
+
const sourceElements = sourceArray.getElements();
|
|
154
|
+
|
|
155
|
+
const targetTexts = targetElements.map((el) => el.getText());
|
|
156
|
+
const sourceTexts = sourceElements.map((el) => el.getText());
|
|
157
|
+
|
|
158
|
+
const mergedTexts = [...targetTexts, ...sourceTexts];
|
|
159
|
+
|
|
160
|
+
const mergedArrayText = `[${mergedTexts.join(", ")}]`;
|
|
161
|
+
targetArray.replaceWithText(mergedArrayText);
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
function getInitializer(prop) {
|
|
165
|
+
if (prop.isKind(ts.SyntaxKind.PropertyAssignment)) {
|
|
166
|
+
return prop.getInitializer();
|
|
167
|
+
} else if (prop.isKind(ts.SyntaxKind.ShorthandPropertyAssignment)) {
|
|
168
|
+
return prop.getNameNode();
|
|
169
|
+
} else if (prop.isKind(ts.SyntaxKind.MethodDeclaration)) {
|
|
170
|
+
return prop;
|
|
171
|
+
}
|
|
172
|
+
return null;
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
function groupAndSortImports(importDeclarations) {
|
|
176
|
+
const externalImports = [];
|
|
177
|
+
const builtInImports = [];
|
|
178
|
+
const relativeImports = [];
|
|
179
|
+
|
|
180
|
+
const importMap = new Map();
|
|
181
|
+
|
|
182
|
+
importDeclarations.forEach((importDecl) => {
|
|
183
|
+
const moduleSpecifier = importDecl.getModuleSpecifierValue();
|
|
184
|
+
const importKey = moduleSpecifier;
|
|
185
|
+
|
|
186
|
+
if (importMap.has(importKey)) {
|
|
187
|
+
const existingImport = importMap.get(importKey);
|
|
188
|
+
mergeImportDeclarations(existingImport, importDecl);
|
|
189
|
+
} else {
|
|
190
|
+
importMap.set(importKey, importDecl);
|
|
191
|
+
|
|
192
|
+
if (isRelativeImport(moduleSpecifier)) {
|
|
193
|
+
relativeImports.push(importDecl);
|
|
194
|
+
} else if (isBuiltInImport(moduleSpecifier)) {
|
|
195
|
+
builtInImports.push(importDecl);
|
|
196
|
+
} else {
|
|
197
|
+
externalImports.push(importDecl);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
builtInImports.sort(compareModuleSpecifiers);
|
|
203
|
+
externalImports.sort(compareModuleSpecifiers);
|
|
204
|
+
relativeImports.sort(compareModuleSpecifiers);
|
|
205
|
+
|
|
206
|
+
return [...builtInImports, ...externalImports, ...relativeImports];
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
function isRelativeImport(moduleSpecifier) {
|
|
210
|
+
return (
|
|
211
|
+
moduleSpecifier.startsWith("./") ||
|
|
212
|
+
moduleSpecifier.startsWith("../") ||
|
|
213
|
+
moduleSpecifier === "." ||
|
|
214
|
+
moduleSpecifier === ".."
|
|
215
|
+
);
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
function isBuiltInImport(moduleSpecifier) {
|
|
219
|
+
return moduleSpecifier.startsWith("node:");
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
function compareModuleSpecifiers(a, b) {
|
|
223
|
+
const specA = a.getModuleSpecifierValue();
|
|
224
|
+
const specB = b.getModuleSpecifierValue();
|
|
225
|
+
return specA.localeCompare(specB);
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
function mergeImportDeclarations(targetImport, sourceImport) {
|
|
229
|
+
const targetNamedImports = new Set(
|
|
230
|
+
targetImport.getNamedImports().map((ni) => ni.getText())
|
|
231
|
+
);
|
|
232
|
+
sourceImport.getNamedImports().forEach((ni) => {
|
|
233
|
+
const name = ni.getText();
|
|
234
|
+
if (!targetNamedImports.has(name)) {
|
|
235
|
+
targetImport.addNamedImport(name);
|
|
236
|
+
targetNamedImports.add(name);
|
|
237
|
+
}
|
|
238
|
+
});
|
|
239
|
+
|
|
240
|
+
const targetDefaultImport = targetImport.getDefaultImport()?.getText();
|
|
241
|
+
const sourceDefaultImport = sourceImport.getDefaultImport()?.getText();
|
|
242
|
+
|
|
243
|
+
if (!targetDefaultImport && sourceDefaultImport) {
|
|
244
|
+
targetImport.setDefaultImport(sourceDefaultImport);
|
|
245
|
+
}
|
|
246
|
+
}
|
|
@@ -0,0 +1,259 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createPrompt,
|
|
3
|
+
isDownKey,
|
|
4
|
+
isEnterKey,
|
|
5
|
+
isNumberKey,
|
|
6
|
+
isSpaceKey,
|
|
7
|
+
isUpKey,
|
|
8
|
+
makeTheme,
|
|
9
|
+
Separator,
|
|
10
|
+
useKeypress,
|
|
11
|
+
useMemo,
|
|
12
|
+
usePagination,
|
|
13
|
+
usePrefix,
|
|
14
|
+
useRef,
|
|
15
|
+
useState,
|
|
16
|
+
ValidationError,
|
|
17
|
+
} from "@inquirer/core";
|
|
18
|
+
import figures from "@inquirer/figures";
|
|
19
|
+
import ansiEscapes from "ansi-escapes";
|
|
20
|
+
import colors from "picocolors";
|
|
21
|
+
|
|
22
|
+
const checkboxTheme = {
|
|
23
|
+
icon: {
|
|
24
|
+
checked: colors.green(figures.circleFilled),
|
|
25
|
+
unchecked: figures.circle,
|
|
26
|
+
cursor: figures.pointer,
|
|
27
|
+
},
|
|
28
|
+
style: {
|
|
29
|
+
disabledChoice: (text) => colors.dim(`- ${text}`),
|
|
30
|
+
renderSelectedChoices: (selectedChoices) =>
|
|
31
|
+
selectedChoices.map((choice) => choice.short).join(", "),
|
|
32
|
+
description: (text) => colors.cyan(text),
|
|
33
|
+
},
|
|
34
|
+
helpMode: "auto",
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
function isSelectable(item) {
|
|
38
|
+
return !Separator.isSeparator(item) && !item.disabled;
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
function isChecked(item) {
|
|
42
|
+
return isSelectable(item) && Boolean(item.checked);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
function toggle(item) {
|
|
46
|
+
return isSelectable(item) ? { ...item, checked: !item.checked } : item;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
function check(checked) {
|
|
50
|
+
return function (item) {
|
|
51
|
+
return isSelectable(item) ? { ...item, checked } : item;
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
function normalizeChoices(choices) {
|
|
56
|
+
return choices.map((choice) => {
|
|
57
|
+
if (Separator.isSeparator(choice)) return choice;
|
|
58
|
+
|
|
59
|
+
if (typeof choice === "string") {
|
|
60
|
+
return {
|
|
61
|
+
value: choice,
|
|
62
|
+
name: choice,
|
|
63
|
+
short: choice,
|
|
64
|
+
disabled: false,
|
|
65
|
+
checked: false,
|
|
66
|
+
};
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
const name = choice.name ?? String(choice.value);
|
|
70
|
+
return {
|
|
71
|
+
value: choice.value,
|
|
72
|
+
name,
|
|
73
|
+
short: choice.short ?? name,
|
|
74
|
+
description: choice.description,
|
|
75
|
+
disabled: choice.disabled ?? false,
|
|
76
|
+
checked: choice.checked ?? false,
|
|
77
|
+
};
|
|
78
|
+
});
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
export default createPrompt((config, done) => {
|
|
82
|
+
const {
|
|
83
|
+
instructions,
|
|
84
|
+
pageSize = 7,
|
|
85
|
+
loop = true,
|
|
86
|
+
required,
|
|
87
|
+
validate = () => true,
|
|
88
|
+
} = config;
|
|
89
|
+
const theme = makeTheme(checkboxTheme, config.theme);
|
|
90
|
+
const firstRender = useRef(true);
|
|
91
|
+
const [status, setStatus] = useState("idle");
|
|
92
|
+
const prefix = usePrefix({ status, theme });
|
|
93
|
+
const [items, setItems] = useState(
|
|
94
|
+
normalizeChoices(
|
|
95
|
+
typeof config.choices === "function" ? config.choices([]) : config.choices
|
|
96
|
+
)
|
|
97
|
+
);
|
|
98
|
+
|
|
99
|
+
const bounds = useMemo(() => {
|
|
100
|
+
const first = items.findIndex(isSelectable);
|
|
101
|
+
const last = items.findLastIndex(isSelectable);
|
|
102
|
+
|
|
103
|
+
if (first === -1) {
|
|
104
|
+
throw new ValidationError(
|
|
105
|
+
"[checkbox prompt] No selectable choices. All choices are disabled."
|
|
106
|
+
);
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
return { first, last };
|
|
110
|
+
}, [items]);
|
|
111
|
+
|
|
112
|
+
const [active, setActive] = useState(bounds.first);
|
|
113
|
+
const [showHelpTip, setShowHelpTip] = useState(true);
|
|
114
|
+
const [errorMsg, setError] = useState();
|
|
115
|
+
|
|
116
|
+
useKeypress(async (key) => {
|
|
117
|
+
if (isEnterKey(key)) {
|
|
118
|
+
const selection = items.filter(isChecked);
|
|
119
|
+
const isValid = await validate([...selection]);
|
|
120
|
+
if (required && !items.some(isChecked)) {
|
|
121
|
+
setError("At least one choice must be selected");
|
|
122
|
+
} else if (isValid === true) {
|
|
123
|
+
setStatus("done");
|
|
124
|
+
done(selection.map((choice) => choice.value));
|
|
125
|
+
} else {
|
|
126
|
+
setError(isValid || "You must select a valid value");
|
|
127
|
+
}
|
|
128
|
+
} else if (isUpKey(key) || isDownKey(key)) {
|
|
129
|
+
if (
|
|
130
|
+
loop ||
|
|
131
|
+
(isUpKey(key) && active !== bounds.first) ||
|
|
132
|
+
(isDownKey(key) && active !== bounds.last)
|
|
133
|
+
) {
|
|
134
|
+
const offset = isUpKey(key) ? -1 : 1;
|
|
135
|
+
let next = active;
|
|
136
|
+
do {
|
|
137
|
+
next = (next + offset + items.length) % items.length;
|
|
138
|
+
} while (!isSelectable(items[next]));
|
|
139
|
+
setActive(next);
|
|
140
|
+
}
|
|
141
|
+
} else if (isSpaceKey(key)) {
|
|
142
|
+
setError(undefined);
|
|
143
|
+
setShowHelpTip(false);
|
|
144
|
+
let newItems = items.map((choice, i) =>
|
|
145
|
+
i === active ? toggle(choice) : choice
|
|
146
|
+
);
|
|
147
|
+
if (typeof config.choices === "function") {
|
|
148
|
+
const selected = newItems
|
|
149
|
+
.filter(isChecked)
|
|
150
|
+
.map((choice) => choice.value);
|
|
151
|
+
const choices = config.choices(selected);
|
|
152
|
+
newItems = newItems.map((choice) => {
|
|
153
|
+
const updated = choices.find((c) => c.value === choice.value);
|
|
154
|
+
return { ...choice, ...updated };
|
|
155
|
+
});
|
|
156
|
+
}
|
|
157
|
+
setItems(newItems);
|
|
158
|
+
} else if (key.name === "a") {
|
|
159
|
+
const selectAll = items.some(
|
|
160
|
+
(choice) => isSelectable(choice) && !choice.checked
|
|
161
|
+
);
|
|
162
|
+
setItems(items.map(check(selectAll)));
|
|
163
|
+
} else if (key.name === "i") {
|
|
164
|
+
setItems(items.map(toggle));
|
|
165
|
+
} else if (isNumberKey(key)) {
|
|
166
|
+
// Adjust index to start at 1
|
|
167
|
+
const position = Number(key.name) - 1;
|
|
168
|
+
const item = items[position];
|
|
169
|
+
if (item != null && isSelectable(item)) {
|
|
170
|
+
setActive(position);
|
|
171
|
+
setItems(
|
|
172
|
+
items.map((choice, i) => (i === position ? toggle(choice) : choice))
|
|
173
|
+
);
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
});
|
|
177
|
+
|
|
178
|
+
const message = theme.style.message(config.message, status);
|
|
179
|
+
|
|
180
|
+
let description;
|
|
181
|
+
const page = usePagination({
|
|
182
|
+
items,
|
|
183
|
+
active,
|
|
184
|
+
renderItem({ item, isActive }) {
|
|
185
|
+
if (Separator.isSeparator(item)) {
|
|
186
|
+
return ` ${item.separator}`;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
if (item.disabled) {
|
|
190
|
+
const disabledLabel =
|
|
191
|
+
typeof item.disabled === "string" ? item.disabled : "(disabled)";
|
|
192
|
+
return theme.style.disabledChoice(`${item.name} ${disabledLabel}`);
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
if (isActive) {
|
|
196
|
+
description = item.description;
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
const checkbox = item.checked ? theme.icon.checked : theme.icon.unchecked;
|
|
200
|
+
const color = isActive ? theme.style.highlight : (x) => x;
|
|
201
|
+
const cursor = isActive ? theme.icon.cursor : " ";
|
|
202
|
+
return color(`${cursor}${checkbox} ${item.name}`);
|
|
203
|
+
},
|
|
204
|
+
pageSize,
|
|
205
|
+
loop,
|
|
206
|
+
});
|
|
207
|
+
|
|
208
|
+
if (status === "done") {
|
|
209
|
+
const selection = items.filter(isChecked);
|
|
210
|
+
const answer = theme.style.answer(
|
|
211
|
+
theme.style.renderSelectedChoices(selection, items)
|
|
212
|
+
);
|
|
213
|
+
|
|
214
|
+
return `${prefix} ${message} ${answer}`;
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
let helpTipTop = "";
|
|
218
|
+
let helpTipBottom = "";
|
|
219
|
+
if (
|
|
220
|
+
theme.helpMode === "always" ||
|
|
221
|
+
(theme.helpMode === "auto" &&
|
|
222
|
+
showHelpTip &&
|
|
223
|
+
(instructions === undefined || instructions))
|
|
224
|
+
) {
|
|
225
|
+
if (typeof instructions === "string") {
|
|
226
|
+
helpTipTop = instructions;
|
|
227
|
+
} else {
|
|
228
|
+
const keys = [
|
|
229
|
+
`${theme.style.key("space")} to select`,
|
|
230
|
+
`${theme.style.key("a")} to toggle all`,
|
|
231
|
+
`${theme.style.key("i")} to invert selection`,
|
|
232
|
+
`and ${theme.style.key("enter")} to proceed`,
|
|
233
|
+
];
|
|
234
|
+
helpTipTop = ` (Press ${keys.join(", ")})`;
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
if (
|
|
238
|
+
items.length > pageSize &&
|
|
239
|
+
(theme.helpMode === "always" ||
|
|
240
|
+
(theme.helpMode === "auto" && firstRender.current))
|
|
241
|
+
) {
|
|
242
|
+
helpTipBottom = `\n${theme.style.help("(Use arrow keys to reveal more choices)")}`;
|
|
243
|
+
firstRender.current = false;
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
const choiceDescription = description
|
|
248
|
+
? `\n${theme.style.description(description)}`
|
|
249
|
+
: ``;
|
|
250
|
+
|
|
251
|
+
let error = "";
|
|
252
|
+
if (errorMsg) {
|
|
253
|
+
error = `\n${theme.style.error(errorMsg)}`;
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
return `${prefix} ${message}${helpTipTop}\n${page}${helpTipBottom}${choiceDescription}${error}${ansiEscapes.cursorHide}`;
|
|
257
|
+
});
|
|
258
|
+
|
|
259
|
+
export { Separator } from "@inquirer/core";
|
package/lib/files.mjs
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import prettier from "prettier";
|
|
2
|
+
|
|
3
|
+
export async function format(code, parser) {
|
|
4
|
+
return prettier.format(code, {
|
|
5
|
+
parser,
|
|
6
|
+
printWidth: 80,
|
|
7
|
+
tabWidth: 2,
|
|
8
|
+
useTabs: false,
|
|
9
|
+
semi: true,
|
|
10
|
+
singleQuote: false,
|
|
11
|
+
quoteProps: "as-needed",
|
|
12
|
+
trailingComma: "es5",
|
|
13
|
+
bracketSpacing: true,
|
|
14
|
+
bracketSameLine: false,
|
|
15
|
+
});
|
|
16
|
+
}
|