Initial PHP rebuild of the app
This commit is contained in:
690 files changed
+33944
-12046
No files matched your search
@@ -1,64 +0,0 @@
|
||||
/**
|
||||
* Builds the `mariadb` pool config from the discrete `DATABASE_HOST` /
|
||||
* `DATABASE_PORT` / `DATABASE_NAME` / `DATABASE_USER` / `DATABASE_PASSWORD`
|
||||
* env vars, shared by every Prisma Client instance in the app (the main
|
||||
* app client, the seed script, and the integration-test fixtures) so the
|
||||
* UTC-timezone and connection-limit handling can't drift between them. See
|
||||
* src/lib/db/prisma.ts for why `timezone`/`sessionVariables` matter — this
|
||||
* file exists only because that reasoning needs to apply to all three
|
||||
* call sites, not because the logic itself is complex.
|
||||
*/
|
||||
export function buildMysqlPoolConfig() {
|
||||
const host = process.env.DATABASE_HOST;
|
||||
const database = process.env.DATABASE_NAME;
|
||||
const user = process.env.DATABASE_USER;
|
||||
const password = process.env.DATABASE_PASSWORD;
|
||||
|
||||
if (!host || !database || !user || password === undefined) {
|
||||
throw new Error(
|
||||
"Database connection is not configured. Set DATABASE_HOST, DATABASE_NAME, DATABASE_USER, and DATABASE_PASSWORD (DATABASE_PORT is optional, defaults to 3306).",
|
||||
);
|
||||
}
|
||||
|
||||
return {
|
||||
host,
|
||||
port: process.env.DATABASE_PORT ? Number(process.env.DATABASE_PORT) : 3306,
|
||||
user,
|
||||
password,
|
||||
database,
|
||||
connectionLimit: Number(process.env.DATABASE_CONNECTION_LIMIT ?? 5),
|
||||
connectTimeout: Number(process.env.DATABASE_CONNECT_TIMEOUT_MS ?? 10_000),
|
||||
// Load-bearing, not cosmetic — see src/lib/db/prisma.ts's file header.
|
||||
timezone: "Etc/UTC",
|
||||
sessionVariables: { time_zone: "+00:00" },
|
||||
ssl: process.env.DATABASE_SSL === "true" ? { rejectUnauthorized: true } : undefined,
|
||||
// MySQL 8's default auth plugin (caching_sha2_password) needs to send
|
||||
// the client its RSA public key to encrypt the password, and the
|
||||
// `mariadb` driver refuses to fetch it over a plain connection unless
|
||||
// told to — surfacing as "Public Key Retrieval is not allowed" on
|
||||
// every connection attempt (not intermittent, not env-specific: it
|
||||
// fires against any caching_sha2_password server whenever DATABASE_SSL
|
||||
// isn't "true"). Opting in doesn't weaken authentication itself, only
|
||||
// lets the client ask for that public key; a connection that's already
|
||||
// on `ssl` above doesn't need this exchange in the first place.
|
||||
allowPublicKeyRetrieval: true,
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds a `mysql://` connection string from the same discrete env vars,
|
||||
* for the one place that genuinely needs a URL rather than a pool config
|
||||
* object: prisma.config.ts, whose `datasource.url` is a plain string
|
||||
* because the Prisma CLI (migrate/introspect) doesn't accept discrete
|
||||
* connection fields.
|
||||
*/
|
||||
export function buildMysqlConnectionUrl(): string | undefined {
|
||||
const host = process.env.DATABASE_HOST;
|
||||
const database = process.env.DATABASE_NAME;
|
||||
const user = process.env.DATABASE_USER;
|
||||
const password = process.env.DATABASE_PASSWORD;
|
||||
if (!host || !database || !user || password === undefined) return undefined;
|
||||
|
||||
const port = process.env.DATABASE_PORT || "3306";
|
||||
return `mysql://${encodeURIComponent(user)}:${encodeURIComponent(password)}@${host}:${port}/${database}`;
|
||||
}
|
||||
@@ -1,44 +0,0 @@
|
||||
import { PrismaClient } from "@/generated/prisma/client";
|
||||
import { PrismaMariaDb } from "@prisma/adapter-mariadb";
|
||||
import { buildMysqlPoolConfig } from "./mysql-pool-config";
|
||||
|
||||
/**
|
||||
* Single Prisma Client instance for the whole app.
|
||||
*
|
||||
* Prisma 7 requires a driver adapter instead of a `datasource.url` in the
|
||||
* schema (see prisma/schema.prisma). This is the ONLY file that imports a
|
||||
* database driver directly — every other file goes through `prisma`.
|
||||
*
|
||||
* Migrated from PostgreSQL (`@prisma/adapter-pg`) to MySQL in Phase 7 — see
|
||||
* docs/phase-7-summary.md for the full record. `@prisma/adapter-mariadb` is
|
||||
* Prisma's one official driver adapter for BOTH MySQL and MariaDB (there is
|
||||
* no separate "adapter-mysql" package): the underlying `mariadb` npm driver
|
||||
* speaks the MySQL wire protocol and is Prisma's documented, supported way
|
||||
* to connect to a genuine MySQL server. The package name is not a sign
|
||||
* we're accidentally targeting MariaDB — `datasource.provider` in
|
||||
* schema.prisma is `"mysql"`, and every environment this app runs against
|
||||
* (local Docker, CI, and the documented production target) is real MySQL.
|
||||
*
|
||||
* See mysql-pool-config.ts for why the pool is built from a parsed object
|
||||
* rather than passed the raw connection string — the short version is that
|
||||
* the UTC-timezone handling it sets is load-bearing, not cosmetic.
|
||||
*/
|
||||
|
||||
const globalForPrisma = globalThis as unknown as {
|
||||
prisma: PrismaClient | undefined;
|
||||
};
|
||||
|
||||
const adapter = new PrismaMariaDb(buildMysqlPoolConfig());
|
||||
|
||||
export const prisma =
|
||||
globalForPrisma.prisma ??
|
||||
new PrismaClient({
|
||||
adapter,
|
||||
log: process.env.NODE_ENV === "development" ? ["warn", "error"] : ["error"],
|
||||
});
|
||||
|
||||
// Reuse the client across hot-reloads in dev so we don't exhaust the
|
||||
// connection pool every time a file changes.
|
||||
if (process.env.NODE_ENV !== "production") {
|
||||
globalForPrisma.prisma = prisma;
|
||||
}
|
||||
Reference in new issue
Block a user