Script para lanzar solo determinadas migraciones en base a la version
actual y objetivo
This commit is contained in:
81
src/index.ts
81
src/index.ts
@@ -21,6 +21,13 @@ type MigrationFile = {
|
|||||||
fullPath: string;
|
fullPath: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type DBVersion = {
|
||||||
|
version: string,
|
||||||
|
notes: string,
|
||||||
|
creation_date: Date,
|
||||||
|
stable: boolean
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Carga de variables de entorno manual (para evitar dependencias como dotenv)
|
* Carga de variables de entorno manual (para evitar dependencias como dotenv)
|
||||||
* Busca el .env en el directorio actual (CWD)
|
* Busca el .env en el directorio actual (CWD)
|
||||||
@@ -33,7 +40,7 @@ async function loadEnv(envpath?: string) {
|
|||||||
const [key, value] = line.split('=');
|
const [key, value] = line.split('=');
|
||||||
if (key && value) process.env[key.trim()] = value.trim();
|
if (key && value) process.env[key.trim()] = value.trim();
|
||||||
});
|
});
|
||||||
console.log('ℹ️ Archivo .env cargado desde el directorio actual.');
|
console.log('[i] Archivo .env cargado desde ' + envpath);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -48,24 +55,29 @@ function getArgs() {
|
|||||||
description: "Versión objetivo de la migracion",
|
description: "Versión objetivo de la migracion",
|
||||||
requiresArg: false
|
requiresArg: false
|
||||||
})
|
})
|
||||||
.parse()
|
.option("env", {
|
||||||
|
alias: "e",
|
||||||
|
type: 'string',
|
||||||
|
description: "Path del archivo .env con los datos de la BDD"
|
||||||
|
})
|
||||||
|
.option("migrations", {
|
||||||
|
alias: "m",
|
||||||
|
type: "string",
|
||||||
|
description: "Path del directorio de migrations"
|
||||||
|
})
|
||||||
|
.parse() as {
|
||||||
|
target: string,
|
||||||
|
env: string,
|
||||||
|
migrations: string
|
||||||
|
}
|
||||||
|
|
||||||
console.log("args", argv)
|
console.log("args", argv)
|
||||||
/* Antiguo */
|
/* Antiguo */
|
||||||
const args = process.argv.slice(2);
|
|
||||||
|
|
||||||
const targetIdx = args.indexOf('--target') !== -1 ? args.indexOf('--target') : args.indexOf('-t');
|
|
||||||
const envIdx = args.indexOf('--env') !== -1 ? args.indexOf('--env') : args.indexOf('-e');
|
|
||||||
const migrtionsIdx = args.indexOf("")
|
|
||||||
|
|
||||||
if (targetIdx === -1 || !args[targetIdx + 1]) {
|
|
||||||
console.error('❌ Error: Debes especificar una versión objetivo con --target o -t');
|
|
||||||
process.exit(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
target: args[targetIdx + 1],
|
target: argv.target,
|
||||||
env: args[envIdx + 1]
|
env: argv.env,
|
||||||
|
migrations: argv.migrations
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -99,34 +111,55 @@ function compareVersions(va: string, vb: string) {
|
|||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async function getCurrentVersion() {
|
||||||
|
try {
|
||||||
|
const lastVersion = await db.query<DBVersion>(`
|
||||||
|
SELECT * form db_versions
|
||||||
|
ORDER BY creation_date DESC
|
||||||
|
LIMIT 1
|
||||||
|
`)
|
||||||
|
return lastVersion.rows[0]
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e)
|
||||||
|
} finally {
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Lógica principal de ejecución de migraciones
|
* Lógica principal de ejecución de migraciones
|
||||||
* @param targetVersion Versión objetivo pasada por el usuario
|
* @param targetVersion Versión objetivo pasada por el usuario
|
||||||
* @param currentVersion Versión actual obtenida de la DB
|
* @param currentVersion Versión actual obtenida de la DB
|
||||||
*/
|
*/
|
||||||
async function runMigrations(targetVersion: string, currentVersion: string, migrationDir: string) {
|
async function runMigrations(args: {
|
||||||
|
targetVersion: string,
|
||||||
|
currentVersion?: string,
|
||||||
|
migrationDir: string
|
||||||
|
}) {
|
||||||
const dbClient = await db.connect()
|
const dbClient = await db.connect()
|
||||||
try {
|
try {
|
||||||
const files = await fs.readdir(migrationDir);
|
// 1º La version explicita 2º La versión almacenada en BDD 3º 0.0.0 como version base
|
||||||
|
const currentVersion = args.currentVersion ?? (await getCurrentVersion())?.version ?? "0.0.0"
|
||||||
|
console.log("[i] Migrando desde la version " + currentVersion)
|
||||||
|
const files = await fs.readdir(args.migrationDir);
|
||||||
|
|
||||||
const pendingMigrations: MigrationFile[] = files
|
const pendingMigrations: MigrationFile[] = files
|
||||||
.map(f => (<MigrationFile>{
|
.map(f => (<MigrationFile>{
|
||||||
version: path.parse(f).name,
|
version: path.parse(f).name,
|
||||||
fileName: f,
|
fileName: f,
|
||||||
fullPath: path.join(migrationDir, f)
|
fullPath: path.join(args.migrationDir, f)
|
||||||
}))
|
}))
|
||||||
// 1. Filtrar las migraciones > que la actual
|
// 1. Filtrar las migraciones > que la actual
|
||||||
.filter(v => compareVersions(v.version, currentVersion) == -1)
|
.filter(v => compareVersions(v.version, currentVersion) == -1)
|
||||||
// 2. Filtra las migraciones <= que la objetivo
|
// 2. Filtra las migraciones <= que la objetivo
|
||||||
.filter(v => compareVersions(v.version, targetVersion) >= 0)
|
.filter(v => compareVersions(v.version, args.targetVersion) >= 0)
|
||||||
.sort((a, b) => compareVersions(a.version, b.version));
|
.sort((a, b) => compareVersions(a.version, b.version));
|
||||||
|
|
||||||
if (pendingMigrations.length === 0) {
|
if (pendingMigrations.length === 0) {
|
||||||
console.log("✅ La base de datos ya está actualizada.");
|
console.log("[o] La base de datos ya está actualizada.");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
console.log("Migraciones pendietes", pendingMigrations)
|
console.log("[i] Migraciones pendietes", pendingMigrations)
|
||||||
console.log(`🚀 Aplicando ${pendingMigrations.length} migraciones...`);
|
console.log(`[i] Aplicando ${pendingMigrations.length} migraciones...`);
|
||||||
|
|
||||||
// Iniciamos Transacción (Ejemplo conceptual con un cliente genérico)
|
// Iniciamos Transacción (Ejemplo conceptual con un cliente genérico)
|
||||||
// await db.query('BEGIN');
|
// await db.query('BEGIN');
|
||||||
@@ -169,15 +202,15 @@ async function runMigrations(targetVersion: string, currentVersion: string, migr
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* *******************************************************************
|
* *******************************************************************
|
||||||
* *******************************************************************
|
* *******************************************************************
|
||||||
*/
|
*/
|
||||||
|
|
||||||
async function main() {
|
async function main() {
|
||||||
const { target: targetVersion, env: envPath } = getArgs();
|
const args = getArgs();
|
||||||
await loadEnv(envPath)
|
await loadEnv(args.env);
|
||||||
|
runMigrations({ targetVersion: args.target, migrationDir: args.migrations })
|
||||||
}
|
}
|
||||||
|
|
||||||
main().then(e => console.log(e)).catch(console.error)
|
main().then(e => console.log(e)).catch(console.error)
|
||||||
|
|||||||
Reference in New Issue
Block a user