Skip to content

Commit ea32eb6

Browse files
fix(cli): improve flags handling (#552)
1 parent d7a3904 commit ea32eb6

File tree

8 files changed

+880
-2142
lines changed

8 files changed

+880
-2142
lines changed

apps/cli/CHANGELOG.md

Lines changed: 0 additions & 1675 deletions
This file was deleted.

apps/cli/src/helpers/core/command-handlers.ts

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ import type {
1717
ProjectConfig,
1818
} from "../../types";
1919
import { trackProjectCreation } from "../../utils/analytics";
20-
import { coerceBackendPresets } from "../../utils/compatibility-rules";
20+
2121
import { displayConfig } from "../../utils/display-config";
2222
import { exitWithError, handleError } from "../../utils/errors";
2323
import { generateReproducibleCommand } from "../../utils/generate-reproducible-command";
@@ -148,20 +148,8 @@ export async function createProjectHandler(
148148
relativePath: finalPathInput,
149149
};
150150

151-
coerceBackendPresets(config);
152-
153151
validateConfigCompatibility(config, providedFlags, cliInput);
154152

155-
if (config.backend === "convex") {
156-
log.info(
157-
`Due to '--backend convex' flag, the following options have been automatically set: database=none, orm=none, api=none, runtime=none, dbSetup=none, examples=todo`,
158-
);
159-
} else if (config.backend === "none") {
160-
log.info(
161-
"Due to '--backend none', the following options have been automatically set: --auth none, --database=none, --orm=none, --api=none, --runtime=none, --db-setup=none, --examples=none",
162-
);
163-
}
164-
165153
log.info(pc.yellow("Using default/flag options (config prompts skipped):"));
166154
log.message(displayConfig(config));
167155
log.message("");

apps/cli/src/utils/compatibility-rules.ts

Lines changed: 0 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -133,72 +133,6 @@ export function validateWorkersCompatibility(
133133
}
134134
}
135135

136-
export function coerceBackendPresets(config: Partial<ProjectConfig>) {
137-
if (config.backend === "convex") {
138-
config.database = "none";
139-
config.orm = "none";
140-
config.api = "none";
141-
config.runtime = "none";
142-
config.dbSetup = "none";
143-
config.examples = ["todo"] as ProjectConfig["examples"];
144-
}
145-
if (config.backend === "none") {
146-
config.auth = "none" as ProjectConfig["auth"];
147-
config.database = "none";
148-
config.orm = "none";
149-
config.api = "none";
150-
config.runtime = "none";
151-
config.dbSetup = "none";
152-
config.examples = [] as ProjectConfig["examples"];
153-
}
154-
}
155-
156-
export function incompatibleFlagsForBackend(
157-
backend: ProjectConfig["backend"] | undefined,
158-
providedFlags: Set<string>,
159-
options: CLIInput,
160-
): string[] {
161-
const list: string[] = [];
162-
if (backend === "convex") {
163-
if (
164-
providedFlags.has("auth") &&
165-
options.auth &&
166-
options.auth !== "none" &&
167-
options.auth !== "clerk"
168-
)
169-
list.push(`--auth ${options.auth}`);
170-
if (providedFlags.has("database") && options.database !== "none")
171-
list.push(`--database ${options.database}`);
172-
if (providedFlags.has("orm") && options.orm !== "none")
173-
list.push(`--orm ${options.orm}`);
174-
if (providedFlags.has("api") && options.api !== "none")
175-
list.push(`--api ${options.api}`);
176-
if (providedFlags.has("runtime") && options.runtime !== "none")
177-
list.push(`--runtime ${options.runtime}`);
178-
if (providedFlags.has("dbSetup") && options.dbSetup !== "none")
179-
list.push(`--db-setup ${options.dbSetup}`);
180-
}
181-
if (backend === "none") {
182-
if (providedFlags.has("auth") && options.auth && options.auth !== "none")
183-
list.push(`--auth ${options.auth}`);
184-
if (providedFlags.has("database") && options.database !== "none")
185-
list.push(`--database ${options.database}`);
186-
if (providedFlags.has("orm") && options.orm !== "none")
187-
list.push(`--orm ${options.orm}`);
188-
if (providedFlags.has("api") && options.api !== "none")
189-
list.push(`--api ${options.api}`);
190-
if (providedFlags.has("runtime") && options.runtime !== "none")
191-
list.push(`--runtime ${options.runtime}`);
192-
if (providedFlags.has("dbSetup") && options.dbSetup !== "none")
193-
list.push(`--db-setup ${options.dbSetup}`);
194-
if (providedFlags.has("examples") && options.examples) {
195-
const hasNonNoneExamples = options.examples.some((ex) => ex !== "none");
196-
if (hasNonNoneExamples) list.push("--examples");
197-
}
198-
}
199-
return list;
200-
}
201-
202136
export function validateApiFrontendCompatibility(
203137
api: API | undefined,
204138
frontends: Frontend[] = [],

apps/cli/src/utils/config-validation.ts

Lines changed: 9 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,7 @@ import type {
66
Runtime,
77
} from "../types";
88
import {
9-
coerceBackendPresets,
109
ensureSingleWebAndNative,
11-
incompatibleFlagsForBackend,
1210
isWebFrontend,
1311
validateAddonsAgainstFrontends,
1412
validateAlchemyCompatibility,
@@ -226,38 +224,19 @@ export function validateBackendConstraints(
226224
}
227225
}
228226

229-
if (backend === "convex" || backend === "none") {
230-
const incompatibleFlags = incompatibleFlagsForBackend(
231-
backend,
232-
providedFlags,
233-
options,
234-
);
235-
if (incompatibleFlags.length > 0) {
227+
if (
228+
backend === "convex" &&
229+
providedFlags.has("frontend") &&
230+
options.frontend
231+
) {
232+
const incompatibleFrontends = options.frontend.filter((f) => f === "solid");
233+
if (incompatibleFrontends.length > 0) {
236234
exitWithError(
237-
`The following flags are incompatible with '--backend ${backend}': ${incompatibleFlags.join(
235+
`The following frontends are not compatible with '--backend convex': ${incompatibleFrontends.join(
238236
", ",
239-
)}. Please remove them.`,
237+
)}. Please choose a different frontend or backend.`,
240238
);
241239
}
242-
243-
if (
244-
backend === "convex" &&
245-
providedFlags.has("frontend") &&
246-
options.frontend
247-
) {
248-
const incompatibleFrontends = options.frontend.filter(
249-
(f) => f === "solid",
250-
);
251-
if (incompatibleFrontends.length > 0) {
252-
exitWithError(
253-
`The following frontends are not compatible with '--backend convex': ${incompatibleFrontends.join(
254-
", ",
255-
)}. Please choose a different frontend or backend.`,
256-
);
257-
}
258-
}
259-
260-
coerceBackendPresets(config);
261240
}
262241
}
263242

apps/cli/src/validation.ts

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,39 @@ import {
1111
import { exitWithError } from "./utils/errors";
1212
import { extractAndValidateProjectName } from "./utils/project-name-validation";
1313

14+
const CORE_STACK_FLAGS = new Set([
15+
"database",
16+
"orm",
17+
"backend",
18+
"runtime",
19+
"frontend",
20+
"addons",
21+
"examples",
22+
"auth",
23+
"dbSetup",
24+
"api",
25+
"webDeploy",
26+
"serverDeploy",
27+
]);
28+
29+
function validateYesFlagCombination(
30+
options: CLIInput,
31+
providedFlags: Set<string>,
32+
) {
33+
if (!options.yes) return;
34+
35+
const coreStackFlagsProvided = Array.from(providedFlags).filter((flag) =>
36+
CORE_STACK_FLAGS.has(flag),
37+
);
38+
39+
if (coreStackFlagsProvided.length > 0) {
40+
exitWithError(
41+
`Cannot combine --yes with core stack configuration flags: ${coreStackFlagsProvided.map((f) => `--${f}`).join(", ")}. ` +
42+
"The --yes flag uses default configuration. Remove these flags or use --yes without them.",
43+
);
44+
}
45+
}
46+
1447
export function processAndValidateFlags(
1548
options: CLIInput,
1649
providedFlags: Set<string>,
@@ -29,6 +62,8 @@ export function processAndValidateFlags(
2962
return cfg;
3063
}
3164

65+
validateYesFlagCombination(options, providedFlags);
66+
3267
try {
3368
validateArrayOptions(options);
3469
} catch (error) {
@@ -55,6 +90,11 @@ export function processProvidedFlagsWithoutValidation(
5590
options: CLIInput,
5691
projectName?: string,
5792
): Partial<ProjectConfig> {
93+
if (!options.yolo) {
94+
const providedFlags = getProvidedFlags(options);
95+
validateYesFlagCombination(options, providedFlags);
96+
}
97+
5898
const config = processFlags(options, projectName);
5999

60100
const validatedProjectName = extractAndValidateProjectName(

0 commit comments

Comments
 (0)