ddl-manager
Version:
store postgres procedures and triggers in files
121 lines • 5.73 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.TriggersComparator = void 0;
const lodash_1 = require("lodash");
const AbstractComparator_1 = require("./AbstractComparator");
class TriggersComparator extends AbstractComparator_1.AbstractComparator {
constructor(driver, database, fs, migration, allCacheTriggers) {
super(driver, database, fs, migration);
this.allCacheTriggers = allCacheTriggers;
this.fixedTriggersByTable = {};
this.fixBeforeUpdateTriggers();
}
drop() {
for (const dbTrigger of this.database.getAllTriggers()) {
if (dbTrigger.frozen) {
continue;
}
const fsTrigger = this.findFsTrigger(dbTrigger);
if (!(fsTrigger === null || fsTrigger === void 0 ? void 0 : fsTrigger.equal(dbTrigger))) {
this.migration.drop({
triggers: [dbTrigger]
});
}
}
}
create() {
const allTriggers = [
...this.fs.allTriggers(),
...this.allCacheTriggers.map(item => item.trigger)
].map(trigger => this.tryFindFixedTrigger(trigger));
for (const trigger of allTriggers) {
const dbTable = this.database.getTable(trigger.table);
const existsSameTriggerFromDb = dbTable === null || dbTable === void 0 ? void 0 : dbTable.triggers.some(dbTrigger => dbTrigger.equal(trigger));
if (!existsSameTriggerFromDb) {
this.migration.create({
triggers: [trigger]
});
}
}
}
findFsTrigger(dbTrigger) {
const fsTriggers = this.fs.getTableTriggers(dbTrigger.table);
const cacheTriggers = this.allCacheTriggers.map(item => item.trigger)
.filter(trigger => trigger.table.equal(dbTrigger.table));
const fsTrigger = [...fsTriggers, ...cacheTriggers].find(trigger => trigger.name === dbTrigger.name);
if (fsTrigger) {
return this.tryFindFixedTrigger(fsTrigger);
}
}
tryFindFixedTrigger(trigger) {
const fixedTriggers = this.fixedTriggersByTable[trigger.table.toString()] || [];
const fixedTrigger = fixedTriggers.find(fixed => fixed.name === trigger.name);
return fixedTrigger || trigger;
}
fixBeforeUpdateTriggers() {
for (const dbTable of this.database.tables) {
this.fixBeforeUpdateTriggersOn(dbTable);
}
}
fixBeforeUpdateTriggersOn(dbTable) {
const cacheTriggersAndFunctions = this.allCacheTriggers.filter(item => item.trigger.table.equal(dbTable));
const cacheTriggers = cacheTriggersAndFunctions.map(item => item.trigger);
const cacheProcedures = cacheTriggersAndFunctions.map(item => item.function);
const dbTriggers = dbTable.triggers.filter(trigger => trigger.frozen);
const fsTriggers = this.fs.getTableTriggers(dbTable);
const allTriggers = [...cacheTriggers, ...fsTriggers, ...dbTriggers];
const onUpdateTriggers = allTriggers.filter(trigger => { var _a; return (_a = trigger.updateOf) === null || _a === void 0 ? void 0 : _a.length; });
const beforeUpdateTriggers = onUpdateTriggers.filter(trigger => trigger.before);
const dependencyMap = this.buildDependencyMap(beforeUpdateTriggers, cacheProcedures);
for (const trigger of onUpdateTriggers) {
this.fixTrigger(dependencyMap, trigger);
}
}
buildDependencyMap(beforeUpdateTriggers, cacheProcedures) {
var _a;
const dependencyMap = {};
for (const trigger of beforeUpdateTriggers) {
const procedure = (this.fs.getTriggerFunction(trigger) ||
cacheProcedures.find(procedure => procedure.name === trigger.procedure.name) ||
this.database.getFunctions(trigger.procedure.name)[0]);
const updatedColumns = procedure.findAssignColumns();
const dependenciesColumns = trigger.updateOf;
for (const updatedColumnName of updatedColumns) {
(_a = dependencyMap[updatedColumnName]) !== null && _a !== void 0 ? _a : (dependencyMap[updatedColumnName] = []);
dependencyMap[updatedColumnName].push(...dependenciesColumns);
}
}
return dependencyMap;
}
fixTrigger(dependencyMap, trigger) {
var _a;
var _b, _c;
const dbTable = this.database.getTable(trigger.table);
const dependenciesColumns = findAllDependencies(dependencyMap, trigger.updateOf);
const fixedTrigger = trigger.clone({
updateOf: lodash_1.uniq([
...trigger.updateOf,
...dependenciesColumns
]).sort()
});
(_a = (_b = this.fixedTriggersByTable)[_c = dbTable.toString()]) !== null && _a !== void 0 ? _a : (_b[_c] = []);
this.fixedTriggersByTable[dbTable.toString()].push(fixedTrigger);
}
}
exports.TriggersComparator = TriggersComparator;
function findAllDependencies(dependencyMap, columns, scanned = {}) {
var _a;
const outputDependenciesColumns = [];
for (const columnName of columns) {
if (columnName in scanned) {
continue;
}
scanned[columnName] = true;
const dependenciesColumns = (_a = dependencyMap[columnName]) !== null && _a !== void 0 ? _a : [];
const subDependencies = findAllDependencies(dependencyMap, dependenciesColumns, scanned);
outputDependenciesColumns.push(...dependenciesColumns);
outputDependenciesColumns.push(...subDependencies);
}
return outputDependenciesColumns;
}
//# sourceMappingURL=TriggersComparator.js.map