create-better-t-stack 3.7.3-canary.8e4d5716 → 3.7.3-canary.98ba1e7a
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/dist/cli.d.ts +1 -0
- package/dist/cli.js +8 -0
- package/dist/index.d.ts +347 -0
- package/dist/index.js +4 -0
- package/dist/src-yXf02Wox.js +7077 -0
- package/package.json +11 -7
- package/src/cli.ts +0 -3
- package/src/constants.ts +0 -188
- package/src/helpers/addons/addons-setup.ts +0 -226
- package/src/helpers/addons/examples-setup.ts +0 -104
- package/src/helpers/addons/fumadocs-setup.ts +0 -103
- package/src/helpers/addons/ruler-setup.ts +0 -139
- package/src/helpers/addons/starlight-setup.ts +0 -51
- package/src/helpers/addons/tauri-setup.ts +0 -96
- package/src/helpers/addons/ultracite-setup.ts +0 -232
- package/src/helpers/addons/vite-pwa-setup.ts +0 -59
- package/src/helpers/core/add-addons.ts +0 -85
- package/src/helpers/core/add-deployment.ts +0 -102
- package/src/helpers/core/api-setup.ts +0 -280
- package/src/helpers/core/auth-setup.ts +0 -203
- package/src/helpers/core/backend-setup.ts +0 -73
- package/src/helpers/core/command-handlers.ts +0 -354
- package/src/helpers/core/convex-codegen.ts +0 -14
- package/src/helpers/core/create-project.ts +0 -133
- package/src/helpers/core/create-readme.ts +0 -687
- package/src/helpers/core/db-setup.ts +0 -184
- package/src/helpers/core/detect-project-config.ts +0 -41
- package/src/helpers/core/env-setup.ts +0 -449
- package/src/helpers/core/git.ts +0 -31
- package/src/helpers/core/install-dependencies.ts +0 -32
- package/src/helpers/core/payments-setup.ts +0 -48
- package/src/helpers/core/post-installation.ts +0 -383
- package/src/helpers/core/project-config.ts +0 -246
- package/src/helpers/core/runtime-setup.ts +0 -76
- package/src/helpers/core/template-manager.ts +0 -917
- package/src/helpers/core/workspace-setup.ts +0 -184
- package/src/helpers/database-providers/d1-setup.ts +0 -28
- package/src/helpers/database-providers/docker-compose-setup.ts +0 -50
- package/src/helpers/database-providers/mongodb-atlas-setup.ts +0 -186
- package/src/helpers/database-providers/neon-setup.ts +0 -243
- package/src/helpers/database-providers/planetscale-setup.ts +0 -78
- package/src/helpers/database-providers/prisma-postgres-setup.ts +0 -196
- package/src/helpers/database-providers/supabase-setup.ts +0 -218
- package/src/helpers/database-providers/turso-setup.ts +0 -309
- package/src/helpers/deployment/alchemy/alchemy-combined-setup.ts +0 -80
- package/src/helpers/deployment/alchemy/alchemy-next-setup.ts +0 -51
- package/src/helpers/deployment/alchemy/alchemy-nuxt-setup.ts +0 -104
- package/src/helpers/deployment/alchemy/alchemy-react-router-setup.ts +0 -32
- package/src/helpers/deployment/alchemy/alchemy-solid-setup.ts +0 -32
- package/src/helpers/deployment/alchemy/alchemy-svelte-setup.ts +0 -98
- package/src/helpers/deployment/alchemy/alchemy-tanstack-router-setup.ts +0 -33
- package/src/helpers/deployment/alchemy/alchemy-tanstack-start-setup.ts +0 -98
- package/src/helpers/deployment/alchemy/env-dts-setup.ts +0 -76
- package/src/helpers/deployment/alchemy/index.ts +0 -7
- package/src/helpers/deployment/server-deploy-setup.ts +0 -55
- package/src/helpers/deployment/web-deploy-setup.ts +0 -58
- package/src/index.ts +0 -253
- package/src/prompts/addons.ts +0 -178
- package/src/prompts/api.ts +0 -49
- package/src/prompts/auth.ts +0 -84
- package/src/prompts/backend.ts +0 -83
- package/src/prompts/config-prompts.ts +0 -138
- package/src/prompts/database-setup.ts +0 -112
- package/src/prompts/database.ts +0 -57
- package/src/prompts/examples.ts +0 -64
- package/src/prompts/frontend.ts +0 -118
- package/src/prompts/git.ts +0 -16
- package/src/prompts/install.ts +0 -16
- package/src/prompts/orm.ts +0 -53
- package/src/prompts/package-manager.ts +0 -32
- package/src/prompts/payments.ts +0 -50
- package/src/prompts/project-name.ts +0 -86
- package/src/prompts/runtime.ts +0 -47
- package/src/prompts/server-deploy.ts +0 -91
- package/src/prompts/web-deploy.ts +0 -107
- package/src/types.ts +0 -2
- package/src/utils/add-package-deps.ts +0 -57
- package/src/utils/analytics.ts +0 -39
- package/src/utils/better-auth-plugin-setup.ts +0 -71
- package/src/utils/biome-formatter.ts +0 -82
- package/src/utils/bts-config.ts +0 -122
- package/src/utils/command-exists.ts +0 -16
- package/src/utils/compatibility-rules.ts +0 -319
- package/src/utils/compatibility.ts +0 -11
- package/src/utils/config-processing.ts +0 -130
- package/src/utils/config-validation.ts +0 -470
- package/src/utils/display-config.ts +0 -96
- package/src/utils/docker-utils.ts +0 -70
- package/src/utils/errors.ts +0 -32
- package/src/utils/generate-reproducible-command.ts +0 -53
- package/src/utils/get-latest-cli-version.ts +0 -11
- package/src/utils/get-package-manager.ts +0 -13
- package/src/utils/open-url.ts +0 -25
- package/src/utils/package-runner.ts +0 -23
- package/src/utils/project-directory.ts +0 -102
- package/src/utils/project-name-validation.ts +0 -43
- package/src/utils/render-title.ts +0 -48
- package/src/utils/setup-catalogs.ts +0 -192
- package/src/utils/sponsors.ts +0 -101
- package/src/utils/telemetry.ts +0 -19
- package/src/utils/template-processor.ts +0 -64
- package/src/utils/templates.ts +0 -94
- package/src/utils/ts-morph.ts +0 -26
- package/src/validation.ts +0 -117
|
@@ -1,78 +0,0 @@
|
|
|
1
|
-
import path from "node:path";
|
|
2
|
-
import fs from "fs-extra";
|
|
3
|
-
import type { ProjectConfig } from "../../types";
|
|
4
|
-
import { addEnvVariablesToFile, type EnvVariable } from "../core/env-setup";
|
|
5
|
-
|
|
6
|
-
export async function setupPlanetScale(config: ProjectConfig) {
|
|
7
|
-
const { projectDir, database, orm, backend } = config;
|
|
8
|
-
|
|
9
|
-
const targetApp = backend === "self" ? "apps/web" : "apps/server";
|
|
10
|
-
const envPath = path.join(projectDir, targetApp, ".env");
|
|
11
|
-
|
|
12
|
-
if (database === "mysql" && orm === "drizzle") {
|
|
13
|
-
const variables: EnvVariable[] = [
|
|
14
|
-
{
|
|
15
|
-
key: "DATABASE_URL",
|
|
16
|
-
value: 'mysql://username:password@host/database?ssl={"rejectUnauthorized":true}',
|
|
17
|
-
condition: true,
|
|
18
|
-
},
|
|
19
|
-
{
|
|
20
|
-
key: "DATABASE_HOST",
|
|
21
|
-
value: "",
|
|
22
|
-
condition: true,
|
|
23
|
-
},
|
|
24
|
-
{
|
|
25
|
-
key: "DATABASE_USERNAME",
|
|
26
|
-
value: "",
|
|
27
|
-
condition: true,
|
|
28
|
-
},
|
|
29
|
-
{
|
|
30
|
-
key: "DATABASE_PASSWORD",
|
|
31
|
-
value: "",
|
|
32
|
-
condition: true,
|
|
33
|
-
},
|
|
34
|
-
];
|
|
35
|
-
|
|
36
|
-
await fs.ensureDir(path.join(projectDir, targetApp));
|
|
37
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
if (database === "postgres" && orm === "prisma") {
|
|
41
|
-
const variables: EnvVariable[] = [
|
|
42
|
-
{
|
|
43
|
-
key: "DATABASE_URL",
|
|
44
|
-
value: "postgresql://username:password@host/database?sslaccept=strict",
|
|
45
|
-
condition: true,
|
|
46
|
-
},
|
|
47
|
-
];
|
|
48
|
-
|
|
49
|
-
await fs.ensureDir(path.join(projectDir, targetApp));
|
|
50
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
if (database === "postgres" && orm === "drizzle") {
|
|
54
|
-
const variables: EnvVariable[] = [
|
|
55
|
-
{
|
|
56
|
-
key: "DATABASE_URL",
|
|
57
|
-
value: "postgresql://username:password@host/database?sslmode=verify-full",
|
|
58
|
-
condition: true,
|
|
59
|
-
},
|
|
60
|
-
];
|
|
61
|
-
|
|
62
|
-
await fs.ensureDir(path.join(projectDir, targetApp));
|
|
63
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
if (database === "mysql" && orm === "prisma") {
|
|
67
|
-
const variables: EnvVariable[] = [
|
|
68
|
-
{
|
|
69
|
-
key: "DATABASE_URL",
|
|
70
|
-
value: "mysql://username:password@host/database?sslaccept=strict",
|
|
71
|
-
condition: true,
|
|
72
|
-
},
|
|
73
|
-
];
|
|
74
|
-
|
|
75
|
-
await fs.ensureDir(path.join(projectDir, targetApp));
|
|
76
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
77
|
-
}
|
|
78
|
-
}
|
|
@@ -1,196 +0,0 @@
|
|
|
1
|
-
import path from "node:path";
|
|
2
|
-
import { isCancel, log, select, spinner } from "@clack/prompts";
|
|
3
|
-
import { consola } from "consola";
|
|
4
|
-
import { execa } from "execa";
|
|
5
|
-
import fs from "fs-extra";
|
|
6
|
-
import pc from "picocolors";
|
|
7
|
-
import type { PackageManager, ProjectConfig } from "../../types";
|
|
8
|
-
import { getPackageExecutionCommand } from "../../utils/package-runner";
|
|
9
|
-
import { addEnvVariablesToFile, type EnvVariable } from "../core/env-setup";
|
|
10
|
-
|
|
11
|
-
type PrismaConfig = {
|
|
12
|
-
databaseUrl: string;
|
|
13
|
-
claimUrl?: string;
|
|
14
|
-
};
|
|
15
|
-
|
|
16
|
-
type CreateDbResponse = {
|
|
17
|
-
connectionString: string;
|
|
18
|
-
directConnectionString: string;
|
|
19
|
-
claimUrl: string;
|
|
20
|
-
deletionDate: string;
|
|
21
|
-
region: string;
|
|
22
|
-
name: string;
|
|
23
|
-
projectId: string;
|
|
24
|
-
};
|
|
25
|
-
|
|
26
|
-
const AVAILABLE_REGIONS = [
|
|
27
|
-
{ value: "ap-southeast-1", label: "Asia Pacific (Singapore)" },
|
|
28
|
-
{ value: "ap-northeast-1", label: "Asia Pacific (Tokyo)" },
|
|
29
|
-
{ value: "eu-central-1", label: "Europe (Frankfurt)" },
|
|
30
|
-
{ value: "eu-west-3", label: "Europe (Paris)" },
|
|
31
|
-
{ value: "us-east-1", label: "US East (N. Virginia)" },
|
|
32
|
-
{ value: "us-west-1", label: "US West (N. California)" },
|
|
33
|
-
];
|
|
34
|
-
|
|
35
|
-
async function setupWithCreateDb(serverDir: string, packageManager: PackageManager) {
|
|
36
|
-
try {
|
|
37
|
-
log.info("Starting Prisma Postgres setup with create-db.");
|
|
38
|
-
|
|
39
|
-
const selectedRegion = await select({
|
|
40
|
-
message: "Select your preferred region:",
|
|
41
|
-
options: AVAILABLE_REGIONS,
|
|
42
|
-
initialValue: "ap-southeast-1",
|
|
43
|
-
});
|
|
44
|
-
|
|
45
|
-
if (isCancel(selectedRegion)) return null;
|
|
46
|
-
|
|
47
|
-
const createDbCommand = getPackageExecutionCommand(
|
|
48
|
-
packageManager,
|
|
49
|
-
`create-db@latest --json --region ${selectedRegion}`,
|
|
50
|
-
);
|
|
51
|
-
|
|
52
|
-
const s = spinner();
|
|
53
|
-
s.start("Creating Prisma Postgres database...");
|
|
54
|
-
|
|
55
|
-
const { stdout } = await execa(createDbCommand, {
|
|
56
|
-
cwd: serverDir,
|
|
57
|
-
shell: true,
|
|
58
|
-
});
|
|
59
|
-
|
|
60
|
-
s.stop("Database created successfully!");
|
|
61
|
-
|
|
62
|
-
let createDbResponse: CreateDbResponse;
|
|
63
|
-
try {
|
|
64
|
-
createDbResponse = JSON.parse(stdout) as CreateDbResponse;
|
|
65
|
-
} catch {
|
|
66
|
-
consola.error("Failed to parse create-db response");
|
|
67
|
-
return null;
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
return {
|
|
71
|
-
databaseUrl: createDbResponse.connectionString,
|
|
72
|
-
claimUrl: createDbResponse.claimUrl,
|
|
73
|
-
};
|
|
74
|
-
} catch (error) {
|
|
75
|
-
if (error instanceof Error) {
|
|
76
|
-
consola.error(error.message);
|
|
77
|
-
}
|
|
78
|
-
return null;
|
|
79
|
-
}
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
async function writeEnvFile(
|
|
83
|
-
projectDir: string,
|
|
84
|
-
backend: ProjectConfig["backend"],
|
|
85
|
-
config?: PrismaConfig,
|
|
86
|
-
) {
|
|
87
|
-
try {
|
|
88
|
-
const targetApp = backend === "self" ? "apps/web" : "apps/server";
|
|
89
|
-
const envPath = path.join(projectDir, targetApp, ".env");
|
|
90
|
-
const variables: EnvVariable[] = [
|
|
91
|
-
{
|
|
92
|
-
key: "DATABASE_URL",
|
|
93
|
-
value:
|
|
94
|
-
config?.databaseUrl ?? "postgresql://postgres:postgres@localhost:5432/mydb?schema=public",
|
|
95
|
-
condition: true,
|
|
96
|
-
},
|
|
97
|
-
];
|
|
98
|
-
|
|
99
|
-
if (config?.claimUrl) {
|
|
100
|
-
variables.push({
|
|
101
|
-
key: "CLAIM_URL",
|
|
102
|
-
value: config.claimUrl,
|
|
103
|
-
condition: true,
|
|
104
|
-
});
|
|
105
|
-
}
|
|
106
|
-
|
|
107
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
108
|
-
} catch {
|
|
109
|
-
consola.error("Failed to update environment configuration");
|
|
110
|
-
}
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
function displayManualSetupInstructions(target: "apps/web" | "apps/server") {
|
|
114
|
-
log.info(`Manual Prisma PostgreSQL Setup Instructions:
|
|
115
|
-
|
|
116
|
-
1. Visit https://console.prisma.io and create an account
|
|
117
|
-
2. Create a new PostgreSQL database from the dashboard
|
|
118
|
-
3. Get your database URL
|
|
119
|
-
4. Add the database URL to the .env file in ${target}/.env
|
|
120
|
-
|
|
121
|
-
DATABASE_URL="your_database_url"`);
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
export async function setupPrismaPostgres(
|
|
125
|
-
config: ProjectConfig,
|
|
126
|
-
cliInput?: { manualDb?: boolean },
|
|
127
|
-
) {
|
|
128
|
-
const { packageManager, projectDir, backend } = config;
|
|
129
|
-
const manualDb = cliInput?.manualDb ?? false;
|
|
130
|
-
const dbDir = path.join(projectDir, "packages/db");
|
|
131
|
-
|
|
132
|
-
try {
|
|
133
|
-
await fs.ensureDir(dbDir);
|
|
134
|
-
|
|
135
|
-
if (manualDb) {
|
|
136
|
-
await writeEnvFile(projectDir, backend);
|
|
137
|
-
displayManualSetupInstructions(backend === "self" ? "apps/web" : "apps/server");
|
|
138
|
-
return;
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
const setupMode = await select({
|
|
142
|
-
message: "Prisma Postgres setup: choose mode",
|
|
143
|
-
options: [
|
|
144
|
-
{
|
|
145
|
-
label: "Automatic (create-db)",
|
|
146
|
-
value: "auto",
|
|
147
|
-
hint: "Provision a database via Prisma's create-db CLI",
|
|
148
|
-
},
|
|
149
|
-
{
|
|
150
|
-
label: "Manual",
|
|
151
|
-
value: "manual",
|
|
152
|
-
hint: "Add your own DATABASE_URL later",
|
|
153
|
-
},
|
|
154
|
-
],
|
|
155
|
-
initialValue: "auto",
|
|
156
|
-
});
|
|
157
|
-
|
|
158
|
-
if (isCancel(setupMode)) return;
|
|
159
|
-
|
|
160
|
-
if (setupMode === "manual") {
|
|
161
|
-
await writeEnvFile(projectDir, backend);
|
|
162
|
-
displayManualSetupInstructions(backend === "self" ? "apps/web" : "apps/server");
|
|
163
|
-
return;
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
const prismaConfig = await setupWithCreateDb(dbDir, packageManager);
|
|
167
|
-
|
|
168
|
-
if (prismaConfig) {
|
|
169
|
-
await writeEnvFile(projectDir, backend, prismaConfig);
|
|
170
|
-
|
|
171
|
-
log.success(pc.green("Prisma Postgres database configured successfully!"));
|
|
172
|
-
|
|
173
|
-
if (prismaConfig.claimUrl) {
|
|
174
|
-
log.info(pc.blue(`Claim URL saved to .env: ${prismaConfig.claimUrl}`));
|
|
175
|
-
}
|
|
176
|
-
} else {
|
|
177
|
-
await writeEnvFile(projectDir, backend);
|
|
178
|
-
displayManualSetupInstructions(backend === "self" ? "apps/web" : "apps/server");
|
|
179
|
-
}
|
|
180
|
-
} catch (error) {
|
|
181
|
-
consola.error(
|
|
182
|
-
pc.red(
|
|
183
|
-
`Error during Prisma Postgres setup: ${
|
|
184
|
-
error instanceof Error ? error.message : String(error)
|
|
185
|
-
}`,
|
|
186
|
-
),
|
|
187
|
-
);
|
|
188
|
-
|
|
189
|
-
try {
|
|
190
|
-
await writeEnvFile(projectDir, backend);
|
|
191
|
-
displayManualSetupInstructions(backend === "self" ? "apps/web" : "apps/server");
|
|
192
|
-
} catch {}
|
|
193
|
-
|
|
194
|
-
log.info("Setup completed with manual configuration required.");
|
|
195
|
-
}
|
|
196
|
-
}
|
|
@@ -1,218 +0,0 @@
|
|
|
1
|
-
import path from "node:path";
|
|
2
|
-
import { isCancel, log, select } from "@clack/prompts";
|
|
3
|
-
import { consola } from "consola";
|
|
4
|
-
import { type ExecaError, execa } from "execa";
|
|
5
|
-
import fs from "fs-extra";
|
|
6
|
-
import pc from "picocolors";
|
|
7
|
-
import type { PackageManager, ProjectConfig } from "../../types";
|
|
8
|
-
import { exitCancelled } from "../../utils/errors";
|
|
9
|
-
import { getPackageExecutionCommand } from "../../utils/package-runner";
|
|
10
|
-
import { addEnvVariablesToFile, type EnvVariable } from "../core/env-setup";
|
|
11
|
-
|
|
12
|
-
async function writeSupabaseEnvFile(
|
|
13
|
-
projectDir: string,
|
|
14
|
-
backend: ProjectConfig["backend"],
|
|
15
|
-
databaseUrl: string,
|
|
16
|
-
) {
|
|
17
|
-
try {
|
|
18
|
-
const targetApp = backend === "self" ? "apps/web" : "apps/server";
|
|
19
|
-
const envPath = path.join(projectDir, targetApp, ".env");
|
|
20
|
-
const dbUrlToUse = databaseUrl || "postgresql://postgres:postgres@127.0.0.1:54322/postgres";
|
|
21
|
-
const variables: EnvVariable[] = [
|
|
22
|
-
{
|
|
23
|
-
key: "DATABASE_URL",
|
|
24
|
-
value: dbUrlToUse,
|
|
25
|
-
condition: true,
|
|
26
|
-
},
|
|
27
|
-
{
|
|
28
|
-
key: "DIRECT_URL",
|
|
29
|
-
value: dbUrlToUse,
|
|
30
|
-
condition: true,
|
|
31
|
-
},
|
|
32
|
-
];
|
|
33
|
-
await addEnvVariablesToFile(envPath, variables);
|
|
34
|
-
return true;
|
|
35
|
-
} catch (error) {
|
|
36
|
-
consola.error(pc.red("Failed to update .env file for Supabase."));
|
|
37
|
-
if (error instanceof Error) {
|
|
38
|
-
consola.error(error.message);
|
|
39
|
-
}
|
|
40
|
-
return false;
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
function extractDbUrl(output: string) {
|
|
45
|
-
const dbUrlMatch = output.match(/DB URL:\s*(postgresql:\/\/[^\s]+)/);
|
|
46
|
-
const url = dbUrlMatch?.[1];
|
|
47
|
-
if (url) {
|
|
48
|
-
return url;
|
|
49
|
-
}
|
|
50
|
-
return null;
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
async function initializeSupabase(serverDir: string, packageManager: PackageManager) {
|
|
54
|
-
log.info("Initializing Supabase project...");
|
|
55
|
-
try {
|
|
56
|
-
const supabaseInitCommand = getPackageExecutionCommand(packageManager, "supabase init");
|
|
57
|
-
await execa(supabaseInitCommand, {
|
|
58
|
-
cwd: serverDir,
|
|
59
|
-
stdio: "inherit",
|
|
60
|
-
shell: true,
|
|
61
|
-
});
|
|
62
|
-
log.success("Supabase project initialized");
|
|
63
|
-
return true;
|
|
64
|
-
} catch (error) {
|
|
65
|
-
consola.error(pc.red("Failed to initialize Supabase project."));
|
|
66
|
-
if (error instanceof Error) {
|
|
67
|
-
consola.error(error.message);
|
|
68
|
-
} else {
|
|
69
|
-
consola.error(String(error));
|
|
70
|
-
}
|
|
71
|
-
if (error instanceof Error && error.message.includes("ENOENT")) {
|
|
72
|
-
log.error(
|
|
73
|
-
pc.red("Supabase CLI not found. Please install it globally or ensure it's in your PATH."),
|
|
74
|
-
);
|
|
75
|
-
log.info("You can install it using: npm install -g supabase");
|
|
76
|
-
}
|
|
77
|
-
return false;
|
|
78
|
-
}
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
async function startSupabase(serverDir: string, packageManager: PackageManager) {
|
|
82
|
-
log.info("Starting Supabase services (this may take a moment)...");
|
|
83
|
-
const supabaseStartCommand = getPackageExecutionCommand(packageManager, "supabase start");
|
|
84
|
-
try {
|
|
85
|
-
const subprocess = execa(supabaseStartCommand, {
|
|
86
|
-
cwd: serverDir,
|
|
87
|
-
shell: true,
|
|
88
|
-
});
|
|
89
|
-
|
|
90
|
-
let stdoutData = "";
|
|
91
|
-
|
|
92
|
-
if (subprocess.stdout) {
|
|
93
|
-
subprocess.stdout.on("data", (data) => {
|
|
94
|
-
const text = data.toString();
|
|
95
|
-
process.stdout.write(text);
|
|
96
|
-
stdoutData += text;
|
|
97
|
-
});
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
if (subprocess.stderr) {
|
|
101
|
-
subprocess.stderr.pipe(process.stderr);
|
|
102
|
-
}
|
|
103
|
-
|
|
104
|
-
await subprocess;
|
|
105
|
-
|
|
106
|
-
await new Promise((resolve) => setTimeout(resolve, 100));
|
|
107
|
-
|
|
108
|
-
return stdoutData;
|
|
109
|
-
} catch (error) {
|
|
110
|
-
consola.error(pc.red("Failed to start Supabase services."));
|
|
111
|
-
const execaError = error as ExecaError;
|
|
112
|
-
if (execaError?.message) {
|
|
113
|
-
consola.error(`Error details: ${execaError.message}`);
|
|
114
|
-
if (execaError.message.includes("Docker is not running")) {
|
|
115
|
-
log.error(pc.red("Docker is not running. Please start Docker and try again."));
|
|
116
|
-
}
|
|
117
|
-
} else {
|
|
118
|
-
consola.error(String(error));
|
|
119
|
-
}
|
|
120
|
-
return null;
|
|
121
|
-
}
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
function displayManualSupabaseInstructions(output?: string | null) {
|
|
125
|
-
log.info(
|
|
126
|
-
`"Manual Supabase Setup Instructions:"
|
|
127
|
-
1. Ensure Docker is installed and running.
|
|
128
|
-
2. Install the Supabase CLI (e.g., \`npm install -g supabase\`).
|
|
129
|
-
3. Run \`supabase init\` in your project's \`packages/db\` directory.
|
|
130
|
-
4. Run \`supabase start\` in your project's \`packages/db\` directory.
|
|
131
|
-
5. Copy the 'DB URL' from the output.${
|
|
132
|
-
output
|
|
133
|
-
? `
|
|
134
|
-
${pc.bold("Relevant output from `supabase start`:")}
|
|
135
|
-
${pc.dim(output)}`
|
|
136
|
-
: ""
|
|
137
|
-
}
|
|
138
|
-
6. Add the DB URL to the .env file in \`packages/db/.env\` as \`DATABASE_URL\`:
|
|
139
|
-
${pc.gray('DATABASE_URL="your_supabase_db_url"')}`,
|
|
140
|
-
);
|
|
141
|
-
}
|
|
142
|
-
|
|
143
|
-
export async function setupSupabase(config: ProjectConfig, cliInput?: { manualDb?: boolean }) {
|
|
144
|
-
const { projectDir, packageManager, backend } = config;
|
|
145
|
-
const manualDb = cliInput?.manualDb ?? false;
|
|
146
|
-
|
|
147
|
-
const serverDir = path.join(projectDir, "packages", "db");
|
|
148
|
-
|
|
149
|
-
try {
|
|
150
|
-
await fs.ensureDir(serverDir);
|
|
151
|
-
|
|
152
|
-
if (manualDb) {
|
|
153
|
-
displayManualSupabaseInstructions();
|
|
154
|
-
await writeSupabaseEnvFile(projectDir, backend, "");
|
|
155
|
-
return;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
const mode = await select({
|
|
159
|
-
message: "Supabase setup: choose mode",
|
|
160
|
-
options: [
|
|
161
|
-
{
|
|
162
|
-
label: "Automatic",
|
|
163
|
-
value: "auto",
|
|
164
|
-
hint: "Automated setup with provider CLI, sets .env",
|
|
165
|
-
},
|
|
166
|
-
{
|
|
167
|
-
label: "Manual",
|
|
168
|
-
value: "manual",
|
|
169
|
-
hint: "Manual setup, add env vars yourself",
|
|
170
|
-
},
|
|
171
|
-
],
|
|
172
|
-
initialValue: "auto",
|
|
173
|
-
});
|
|
174
|
-
|
|
175
|
-
if (isCancel(mode)) return exitCancelled("Operation cancelled");
|
|
176
|
-
|
|
177
|
-
if (mode === "manual") {
|
|
178
|
-
displayManualSupabaseInstructions();
|
|
179
|
-
await writeSupabaseEnvFile(projectDir, backend, "");
|
|
180
|
-
return;
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
const initialized = await initializeSupabase(serverDir, packageManager);
|
|
184
|
-
if (!initialized) {
|
|
185
|
-
displayManualSupabaseInstructions();
|
|
186
|
-
return;
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
const supabaseOutput = await startSupabase(serverDir, packageManager);
|
|
190
|
-
if (!supabaseOutput) {
|
|
191
|
-
displayManualSupabaseInstructions();
|
|
192
|
-
return;
|
|
193
|
-
}
|
|
194
|
-
|
|
195
|
-
const dbUrl = extractDbUrl(supabaseOutput);
|
|
196
|
-
|
|
197
|
-
if (dbUrl) {
|
|
198
|
-
const envUpdated = await writeSupabaseEnvFile(projectDir, backend, dbUrl);
|
|
199
|
-
|
|
200
|
-
if (envUpdated) {
|
|
201
|
-
log.success(pc.green("Supabase local development setup ready!"));
|
|
202
|
-
} else {
|
|
203
|
-
log.error(pc.red("Supabase setup completed, but failed to update .env automatically."));
|
|
204
|
-
displayManualSupabaseInstructions(supabaseOutput);
|
|
205
|
-
}
|
|
206
|
-
} else {
|
|
207
|
-
log.error(pc.yellow("Supabase started, but could not extract DB URL automatically."));
|
|
208
|
-
displayManualSupabaseInstructions(supabaseOutput);
|
|
209
|
-
}
|
|
210
|
-
} catch (error) {
|
|
211
|
-
if (error instanceof Error) {
|
|
212
|
-
consola.error(pc.red(`Error during Supabase setup: ${error.message}`));
|
|
213
|
-
} else {
|
|
214
|
-
consola.error(pc.red(`An unknown error occurred during Supabase setup: ${String(error)}`));
|
|
215
|
-
}
|
|
216
|
-
displayManualSupabaseInstructions();
|
|
217
|
-
}
|
|
218
|
-
}
|