- Fix migration template for sqlite - Add declare for payload.db.drizzle as type LibSQLDatabase - Correct drizzle snapshot version
117 lines
3.6 KiB
TypeScript
117 lines
3.6 KiB
TypeScript
import type { DrizzleSnapshotJSON } from 'drizzle-kit/payload'
|
|
import type { CreateMigration } from 'payload'
|
|
|
|
import fs from 'fs'
|
|
import { createRequire } from 'module'
|
|
import path from 'path'
|
|
import { getPredefinedMigration } from 'payload'
|
|
import prompts from 'prompts'
|
|
import { fileURLToPath } from 'url'
|
|
|
|
import type { SQLiteAdapter } from './types.js'
|
|
|
|
import { defaultDrizzleSnapshot } from './defaultSnapshot.js'
|
|
import { getMigrationTemplate } from './getMigrationTemplate.js'
|
|
|
|
const require = createRequire(import.meta.url)
|
|
|
|
export const createMigration: CreateMigration = async function createMigration(
|
|
this: SQLiteAdapter,
|
|
{ file, forceAcceptWarning, migrationName, payload },
|
|
) {
|
|
const filename = fileURLToPath(import.meta.url)
|
|
const dirname = path.dirname(filename)
|
|
const dir = payload.db.migrationDir
|
|
if (!fs.existsSync(dir)) {
|
|
fs.mkdirSync(dir)
|
|
}
|
|
const { generateSQLiteDrizzleJson, generateSQLiteMigration } = require('drizzle-kit/payload')
|
|
const drizzleJsonAfter = await generateSQLiteDrizzleJson(this.schema)
|
|
const [yyymmdd, hhmmss] = new Date().toISOString().split('T')
|
|
const formattedDate = yyymmdd.replace(/\D/g, '')
|
|
const formattedTime = hhmmss.split('.')[0].replace(/\D/g, '')
|
|
let imports: string = ''
|
|
let downSQL: string
|
|
let upSQL: string
|
|
;({ downSQL, imports, upSQL } = await getPredefinedMigration({
|
|
dirname,
|
|
file,
|
|
migrationName,
|
|
payload,
|
|
}))
|
|
|
|
const timestamp = `${formattedDate}_${formattedTime}`
|
|
|
|
const name = migrationName || file?.split('/').slice(2).join('/')
|
|
const fileName = `${timestamp}${name ? `_${name.replace(/\W/g, '_')}` : ''}`
|
|
|
|
const filePath = `${dir}/${fileName}`
|
|
|
|
let drizzleJsonBefore = defaultDrizzleSnapshot as any
|
|
|
|
if (!upSQL) {
|
|
// Get latest migration snapshot
|
|
const latestSnapshot = fs
|
|
.readdirSync(dir)
|
|
.filter((file) => file.endsWith('.json'))
|
|
.sort()
|
|
.reverse()?.[0]
|
|
|
|
if (latestSnapshot) {
|
|
drizzleJsonBefore = JSON.parse(
|
|
fs.readFileSync(`${dir}/${latestSnapshot}`, 'utf8'),
|
|
) as DrizzleSnapshotJSON
|
|
}
|
|
|
|
const sqlStatementsUp = await generateSQLiteMigration(drizzleJsonBefore, drizzleJsonAfter)
|
|
const sqlStatementsDown = await generateSQLiteMigration(drizzleJsonAfter, drizzleJsonBefore)
|
|
// need to create tables as separate statements
|
|
const sqlExecute = 'await payload.db.drizzle.run(sql`'
|
|
|
|
if (sqlStatementsUp?.length) {
|
|
upSQL = sqlStatementsUp
|
|
.map((statement) => `${sqlExecute}${statement?.replaceAll('`', '\\`')}\`)`)
|
|
.join('\n')
|
|
}
|
|
if (sqlStatementsDown?.length) {
|
|
downSQL = sqlStatementsDown
|
|
.map((statement) => `${sqlExecute}${statement?.replaceAll('`', '\\`')}\`)`)
|
|
.join('\n')
|
|
}
|
|
|
|
if (!upSQL?.length && !downSQL?.length && !forceAcceptWarning) {
|
|
const { confirm: shouldCreateBlankMigration } = await prompts(
|
|
{
|
|
name: 'confirm',
|
|
type: 'confirm',
|
|
initial: false,
|
|
message: 'No schema changes detected. Would you like to create a blank migration file?',
|
|
},
|
|
{
|
|
onCancel: () => {
|
|
process.exit(0)
|
|
},
|
|
},
|
|
)
|
|
|
|
if (!shouldCreateBlankMigration) {
|
|
process.exit(0)
|
|
}
|
|
}
|
|
|
|
// write schema
|
|
fs.writeFileSync(`${filePath}.json`, JSON.stringify(drizzleJsonAfter, null, 2))
|
|
}
|
|
|
|
// write migration
|
|
fs.writeFileSync(
|
|
`${filePath}.ts`,
|
|
getMigrationTemplate({
|
|
downSQL: downSQL || ` // Migration code`,
|
|
imports,
|
|
upSQL: upSQL || ` // Migration code`,
|
|
}),
|
|
)
|
|
payload.logger.info({ msg: `Migration created at ${filePath}.ts` })
|
|
}
|