Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
There was a problem hiding this comment.
Security Review — No High-Confidence Vulnerabilities Found
The diff introduces two focused changes: a hardcoded --output path for Prisma codegen and updated Prisma scaffold templates. After reviewing each change against the threat checklist, no exploitable security vulnerabilities were identified.
Analysis
Injection risks (CLI argument building)
getOutputForAdapter returns one of three hardcoded literal strings ("prisma/schema.prisma", "src/db/schema.ts", "migrations/schema.sql"). The adapter and orm values are resolved through a constant allowlist (ADAPTERS), so no user-controlled data flows into the constructed argument array. runCliPassthrough calls execa in array mode (not a shell string), which fully eliminates shell-injection risk regardless of argument content.
Path traversal
The new --output argument value is derived from a hardcoded lookup, not from user or filesystem input. No traversal vector exists.
Secrets / credential handling
The scaffolded stack.ts uses process.env.DATABASE_URL! and the prisma.config.ts uses process.env.DATABASE_URL ?? ''. Both are standard environment-variable references in generated template code. Neither logs nor leaks credentials.
Supply-chain
The only new dependency introduced in generated code is @prisma/adapter-pg, a first-party Prisma package. No novel or unknown third-party packages are added.
Functional notes (not security findings)
- The generated
prisma/schema.prismaomits aurlfield indatasource db; Prisma will refuse to run without it. This is a misconfiguration bug, not a vulnerability. DATABASE_URL ?? ''inprisma.config.tssilently passes an empty string when the env var is unset, causing a confusing runtime failure rather than an early error. Consider failing loudly instead.- The non-null assertion
process.env.DATABASE_URL!instack.tspassesundefinedat runtime if the variable is missing; a guard or explicit error would be safer ergonomically, though not exploitable.
Sent by Cursor Automation: Find vulnerabilities
…k file depth Co-authored-by: Ollie <olliethedev@users.noreply.github.com>
Co-authored-by: Ollie <olliethedev@users.noreply.github.com>
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 1 potential issue.
Bugbot Autofix prepared a fix for the issue found in the latest run.
- ✅ Fixed: Missing
pgdependency in Prisma adapter extra packages- Added
"pg"to theextraPackagesarray for the prisma adapter inconstants.tsso it gets installed alongside@prisma/adapter-pg.
- Added
Preview (1a6c772ba3)
diff --git a/packages/cli/src/commands/init.ts b/packages/cli/src/commands/init.ts
--- a/packages/cli/src/commands/init.ts
+++ b/packages/cli/src/commands/init.ts
@@ -321,8 +321,13 @@
const orm = ADAPTERS.find(
(item) => item.key === adapter,
)?.ormForGenerate;
+ const outputPath = getOutputForAdapter(adapter);
const args = orm
- ? [`--orm=${orm}`, `--config=${stackPath}`]
+ ? [
+ `--orm=${orm}`,
+ `--config=${stackPath}`,
+ ...(outputPath ? [`--output=${outputPath}`] : []),
+ ]
: [`--config=${stackPath}`];
const exitCode = await runCliPassthrough({
cwd,
diff --git a/packages/cli/src/utils/constants.ts b/packages/cli/src/utils/constants.ts
--- a/packages/cli/src/utils/constants.ts
+++ b/packages/cli/src/utils/constants.ts
@@ -5,6 +5,8 @@
label: string;
packageName: string;
ormForGenerate?: "prisma" | "drizzle" | "kysely";
+ /** Additional npm packages that must be installed when this adapter is selected. */
+ extraPackages?: string[];
}
export interface PluginMeta {
@@ -33,6 +35,7 @@
label: "Prisma",
packageName: "@btst/adapter-prisma",
ormForGenerate: "prisma",
+ extraPackages: ["@prisma/adapter-pg", "pg"],
},
{
key: "drizzle",
diff --git a/packages/cli/src/utils/package-installer.ts b/packages/cli/src/utils/package-installer.ts
--- a/packages/cli/src/utils/package-installer.ts
+++ b/packages/cli/src/utils/package-installer.ts
@@ -39,6 +39,7 @@
"@btst/yar",
"@tanstack/react-query",
adapterMeta.packageName,
+ ...(adapterMeta.extraPackages ?? []),
...pluginExtraPackages,
];
const { command, args } = getInstallCommand(input.packageManager, packages);
diff --git a/packages/cli/src/utils/passthrough.ts b/packages/cli/src/utils/passthrough.ts
--- a/packages/cli/src/utils/passthrough.ts
+++ b/packages/cli/src/utils/passthrough.ts
@@ -7,6 +7,15 @@
return Boolean(ADAPTERS.find((item) => item.key === adapter)?.ormForGenerate);
}
+export function getOutputForAdapter(adapter: Adapter): string | null {
+ const meta = ADAPTERS.find((item) => item.key === adapter);
+ if (!meta?.ormForGenerate) return null;
+
+ if (meta.ormForGenerate === "prisma") return "prisma/schema.prisma";
+ if (meta.ormForGenerate === "drizzle") return "src/db/schema.ts";
+ return "migrations/schema.sql";
+}
+
export function getGenerateHintForAdapter(
adapter: Adapter,
configPath: string,
@@ -14,12 +23,8 @@
const meta = ADAPTERS.find((item) => item.key === adapter);
if (!meta?.ormForGenerate) return null;
- const output =
- meta.ormForGenerate === "prisma"
- ? "schema.prisma"
- : meta.ormForGenerate === "drizzle"
- ? "src/db/schema.ts"
- : "migrations/schema.sql";
+ const output = getOutputForAdapter(adapter);
+ if (!output) return null;
return `npx @btst/codegen generate --orm=${meta.ormForGenerate} --config=${configPath} --output=${output}`;
}
diff --git a/packages/cli/src/utils/scaffold-plan.ts b/packages/cli/src/utils/scaffold-plan.ts
--- a/packages/cli/src/utils/scaffold-plan.ts
+++ b/packages/cli/src/utils/scaffold-plan.ts
@@ -322,7 +322,7 @@
};
}
-function buildAdapterTemplateContext(adapter: Adapter) {
+function buildAdapterTemplateContext(adapter: Adapter, stackPath: string) {
const meta = ADAPTERS.find((item) => item.key === adapter);
if (!meta) {
throw new Error(`Unsupported adapter: ${adapter}`);
@@ -337,15 +337,19 @@
}
if (adapter === "prisma") {
+ const depth = stackPath.split("/").length - 1;
+ const prismaClientPath = `${"../".repeat(depth)}generated/prisma/client`;
return {
adapterImport: `import { createPrismaAdapter } from "${meta.packageName}"
-import { PrismaClient } from "@prisma/client"`,
- adapterSetup: `const prisma = new PrismaClient()
+import { PrismaClient } from "${prismaClientPath}"
+import { PrismaPg } from "@prisma/adapter-pg"`,
+ adapterSetup: `const pgAdapter = new PrismaPg({ connectionString: process.env.DATABASE_URL! })
+const prisma = new PrismaClient({ adapter: pgAdapter })
-const provider = process.env.BTST_PRISMA_PROVIDER ?? "postgresql"
+const provider = (process.env.BTST_PRISMA_PROVIDER ?? "postgresql") as "postgresql" | "sqlite" | "cockroachdb" | "mysql" | "sqlserver" | "mongodb"
`,
adapterStackLine:
- "adapter: (db) => createPrismaAdapter(prisma, db, { provider }),",
+ "adapter: (db) => createPrismaAdapter(prisma, db, { provider })({}),",
};
}
@@ -385,7 +389,10 @@
input.plugins,
input.framework,
);
- const adapterContext = buildAdapterTemplateContext(input.adapter);
+ const adapterContext = buildAdapterTemplateContext(
+ input.adapter,
+ frameworkPaths.stackPath,
+ );
const sharedContext = {
alias: input.alias,
@@ -402,6 +409,20 @@
content: await renderTemplate("shared/lib/stack.ts.hbs", sharedContext),
description: "BTST backend stack configuration",
},
+ ...(input.adapter === "prisma"
+ ? [
+ {
+ path: "prisma/schema.prisma",
+ content: `generator client {\n provider = "prisma-client"\n output = "../generated/prisma"\n}\n\ndatasource db {\n provider = "postgresql"\n}\n`,
+ description: "Prisma schema with explicit client output path",
+ },
+ {
+ path: "prisma.config.ts",
+ content: `import { defineConfig } from 'prisma/config'\n\nexport default defineConfig({\n schema: 'prisma/schema.prisma',\n datasource: {\n url: process.env.DATABASE_URL ?? '',\n },\n})\n`,
+ description: "Prisma configuration file",
+ },
+ ]
+ : []),
{
path: frameworkPaths.stackClientPath,
content: await renderTemplate(You can send follow-ups to the cloud agent here.
Reviewed by Cursor Bugbot for commit c112ecd. Configure here.
Co-authored-by: Ollie <olliethedev@users.noreply.github.com>



Summary
Type of change
Checklist
pnpm buildpassespnpm typecheckpassespnpm lintpassesdocs/content/docs/) if consumer-facing types or behavior changedScreenshots
Note
Medium Risk
Touches
initscaffolding, dependency installation, andgeneratepassthrough args; mistakes could break new project setup or produce codegen output in the wrong location, especially for Prisma.Overview
Fixes Prisma adapter initialization so generated projects can run codegen successfully and resolve the Prisma client consistently.
initnow passes an explicit--outputtogenerate(via newgetOutputForAdapter) and updates the generate hint accordingly. The Prisma adapter metadata now installs required extra dependencies (@prisma/adapter-pg,pg), and the scaffolded Prisma stack config switches to aPrismaPg-backedPrismaClientimported from the scaffoldedgenerated/prismaoutput.When Prisma is selected, scaffolding also writes a
prisma/schema.prismawith an explicit client output directory plus aprisma.config.tsto point Prisma at the schema andDATABASE_URL.Reviewed by Cursor Bugbot for commit 1a6c772. Bugbot is set up for automated code reviews on this repo. Configure here.