Skip to main content
Glama

Prisma MCP Server

Official
by prisma
Apache 2.0
4
44,192
  • Linux
  • Apple
ensureDatabaseExists.ts6.58 kB
import { DataSource } from '@prisma/generator' import type { DatabaseCredentials } from '@prisma/internals' import { canConnectToDatabase, createDatabase, getEffectiveUrl, PRISMA_POSTGRES_PROVIDER, uriToCredentials, } from '@prisma/internals' import { bold } from 'kleur/colors' import path from 'path' import { ConnectorType } from './printDatasources' import { getSocketFromDatabaseCredentials } from './unixSocket' export type MigrateAction = 'create' | 'apply' | 'unapply' | 'dev' | 'push' export type PrettyProvider = | 'MySQL' | 'PostgreSQL' | 'Prisma Postgres' | 'SQLite' | 'SQL Server' | 'CockroachDB' | 'MongoDB' // TODO: extract functions in their own files? export type DatasourceInfo = { name?: string // from datasource name prettyProvider?: PrettyProvider // pretty name for the provider url?: string // from getConfig dbLocation?: string // host without credentials dbName?: string // database name schema?: string // database schema (!= multiSchema, can be found in the connection string like `?schema=myschema`) schemas?: string[] // database schemas from the datasource (multiSchema feature) configDir?: string } export function parseDatasourceInfo(datasource: DataSource | undefined): DatasourceInfo { if (!datasource) { return { name: undefined, prettyProvider: undefined, dbName: undefined, dbLocation: undefined, url: undefined, schema: undefined, schemas: undefined, configDir: undefined, } } const prettyProvider = prettifyProvider(datasource.provider) const url = getEffectiveUrl(datasource).value // url parsing for sql server is not implemented if (!url || datasource.provider === 'sqlserver') { return { name: datasource.name, prettyProvider, dbName: undefined, dbLocation: undefined, url: url || undefined, schema: undefined, schemas: datasource.schemas, configDir: path.dirname(datasource.sourceFilePath), } } try { const credentials = uriToCredentials(url) const dbLocation = getDbLocation(credentials) let schema: string | undefined = undefined if (['postgresql', 'cockroachdb'].includes(datasource.provider)) { if (credentials.schema) { schema = credentials.schema } else { schema = 'public' } } const datasourceInfo = { name: datasource.name, prettyProvider, dbName: credentials.database, dbLocation, url, schema, schemas: datasource.schemas, configDir: path.dirname(datasource.sourceFilePath), } // Default to `postgres` database name for PostgreSQL // It's not 100% accurate but it's the best we can do here if (datasource.provider === 'postgresql' && datasourceInfo.dbName === undefined) { datasourceInfo.dbName = 'postgres' } return datasourceInfo } catch (e) { return { name: datasource.name, prettyProvider, dbName: undefined, dbLocation: undefined, url, schema: undefined, schemas: datasource.schemas, configDir: path.dirname(datasource.sourceFilePath), } } } // check if we can connect to the database // if true: return true // if false: throw error export async function ensureCanConnectToDatabase(datasource: DataSource | undefined): Promise<Boolean | Error> { if (!datasource) { throw new Error(`A datasource block is missing in the Prisma schema file.`) } const schemaDir = path.dirname(datasource.sourceFilePath) const url = getConnectionUrl(datasource) // url exists because `ignoreEnvVarErrors: false` would have thrown an error if not const canConnect = await canConnectToDatabase(url, schemaDir) if (canConnect === true) { return true } else { const { code, message } = canConnect throw new Error(`${code}: ${message}`) } } export async function ensureDatabaseExists(datasource: DataSource | undefined) { if (!datasource) { throw new Error(`A datasource block is missing in the Prisma schema file.`) } const schemaDir = path.dirname(datasource.sourceFilePath) const url = getConnectionUrl(datasource) const canConnect = await canConnectToDatabase(url, schemaDir) if (canConnect === true) { return } const { code, message } = canConnect // P1003 means we can connect but that the database doesn't exist if (code !== 'P1003') { throw new Error(`${code}: ${message}`) } if (await createDatabase(url, schemaDir)) { // URI parsing is not implemented for SQL server yet if (datasource.provider === 'sqlserver') { return `SQL Server database created.\n` } // parse the url const credentials = uriToCredentials(url) const prettyProvider = prettifyProvider(datasource.provider) let message = `${prettyProvider} database${credentials.database ? ` ${credentials.database} ` : ' '}created` const dbLocation = getDbLocation(credentials) if (dbLocation) { message += ` at ${bold(dbLocation)}` } return message } return undefined } // returns the "host" like localhost / 127.0.0.1 + default port export function getDbLocation(credentials: DatabaseCredentials): string | undefined { if (credentials.type === 'sqlite') { return credentials.uri! } const socket = getSocketFromDatabaseCredentials(credentials) if (socket) { return `unix:${socket}` } else if (credentials.host && credentials.port) { return `${credentials.host}:${credentials.port}` } else if (credentials.host) { return `${credentials.host}` } return undefined } /** * Return a pretty version of a "provider" (with uppercase characters) * @param provider * @returns PrettyProvider */ export function prettifyProvider(provider: ConnectorType): PrettyProvider { switch (provider) { case 'mysql': return `MySQL` case 'postgres': case 'postgresql': return `PostgreSQL` case PRISMA_POSTGRES_PROVIDER: return `Prisma Postgres` case 'sqlite': return `SQLite` case 'cockroachdb': return `CockroachDB` case 'sqlserver': return `SQL Server` case 'mongodb': return `MongoDB` } } function getConnectionUrl(datasource: DataSource): string { const url = getEffectiveUrl(datasource) if (!url.value) { if (url.fromEnvVar) { throw new Error(`Environment variable '${url.fromEnvVar}' with database connection URL was not found.`) } else { throw new Error(`Datasource is missing a database connection URL.`) } } return url.value }

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/prisma/prisma'

If you have feedback or need assistance with the MCP directory API, please join our Discord server