X-Git-Url: https://git.immae.eu/?a=blobdiff_plain;f=server%2Fhelpers%2Fdatabase-utils.ts;h=422774022ac549168faca01afa2a3b247c373c5d;hb=764b1a14fc494f2cfd7ea590d2f07b01df65c7ad;hp=7befa2c4955b934f397c6ccaf7781fe795e4c8c5;hpb=5b1a6d45b5d6e50102e1c7c8c845401b76b11b4d;p=github%2FChocobozzz%2FPeerTube.git diff --git a/server/helpers/database-utils.ts b/server/helpers/database-utils.ts index 7befa2c49..422774022 100644 --- a/server/helpers/database-utils.ts +++ b/server/helpers/database-utils.ts @@ -1,12 +1,12 @@ import * as retry from 'async/retry' import * as Bluebird from 'bluebird' -import { QueryTypes, Transaction } from 'sequelize' +import { BindOrReplacements, QueryTypes, Transaction } from 'sequelize' import { Model } from 'sequelize-typescript' import { sequelizeTypescript } from '@server/initializers/database' import { logger } from './logger' function retryTransactionWrapper ( - functionToRetry: (arg1: A, arg2: B, arg3: C, arg4: D) => Promise | Bluebird, + functionToRetry: (arg1: A, arg2: B, arg3: C, arg4: D) => Promise, arg1: A, arg2: B, arg3: C, @@ -14,20 +14,20 @@ function retryTransactionWrapper ( ): Promise function retryTransactionWrapper ( - functionToRetry: (arg1: A, arg2: B, arg3: C) => Promise | Bluebird, + functionToRetry: (arg1: A, arg2: B, arg3: C) => Promise, arg1: A, arg2: B, arg3: C ): Promise function retryTransactionWrapper ( - functionToRetry: (arg1: A, arg2: B) => Promise | Bluebird, + functionToRetry: (arg1: A, arg2: B) => Promise, arg1: A, arg2: B ): Promise function retryTransactionWrapper ( - functionToRetry: (arg1: A) => Promise | Bluebird, + functionToRetry: (arg1: A) => Promise, arg1: A ): Promise @@ -36,7 +36,7 @@ function retryTransactionWrapper ( ): Promise function retryTransactionWrapper ( - functionToRetry: (...args: any[]) => Promise | Bluebird, + functionToRetry: (...args: any[]) => Promise, ...args: any[] ): Promise { return transactionRetryer(callback => { @@ -58,7 +58,7 @@ function transactionRetryer (func: (err: any, data: T) => any) { errorFilter: err => { const willRetry = (err.name === 'SequelizeDatabaseError') - logger.debug('Maybe retrying the transaction function.', { willRetry, err }) + logger.debug('Maybe retrying the transaction function.', { willRetry, err, tags: [ 'sql', 'retry' ] }) return willRetry } }, @@ -68,6 +68,8 @@ function transactionRetryer (func: (err: any, data: T) => any) { }) } +// --------------------------------------------------------------------------- + function updateInstanceWithAnother > (instanceToUpdate: T, baseInstance: U) { const obj = baseInstance.toJSON() @@ -82,19 +84,15 @@ function resetSequelizeInstance (instance: Model, savedFields: object) { }) } -function afterCommitIfTransaction (t: Transaction, fn: Function) { - if (t) return t.afterCommit(() => fn()) - - return fn() -} - -function deleteNonExistingModels > ( +function filterNonExistingModels ( fromDatabase: T[], - newModels: T[], - t: Transaction + newModels: T[] ) { return fromDatabase.filter(f => !newModels.find(newModel => newModel.hasSameUniqueKeysThan(f))) - .map(f => f.destroy({ transaction: t })) +} + +function deleteAllModels > (models: T[], transaction: Transaction) { + return Promise.all(models.map(f => f.destroy({ transaction }))) } // Sequelize always skip the update if we only update updatedAt field @@ -111,12 +109,42 @@ function setAsUpdated (table: string, id: number, transaction?: Transaction) { // --------------------------------------------------------------------------- +function runInReadCommittedTransaction (fn: (t: Transaction) => Promise) { + const options = { isolationLevel: Transaction.ISOLATION_LEVELS.READ_COMMITTED } + + return sequelizeTypescript.transaction(options, t => fn(t)) +} + +function afterCommitIfTransaction (t: Transaction, fn: Function) { + if (t) return t.afterCommit(() => fn()) + + return fn() +} + +// --------------------------------------------------------------------------- + +function doesExist (query: string, bind?: BindOrReplacements) { + const options = { + type: QueryTypes.SELECT as QueryTypes.SELECT, + bind, + raw: true + } + + return sequelizeTypescript.query(query, options) + .then(results => results.length === 1) +} + +// --------------------------------------------------------------------------- + export { resetSequelizeInstance, retryTransactionWrapper, transactionRetryer, updateInstanceWithAnother, afterCommitIfTransaction, - deleteNonExistingModels, - setAsUpdated + filterNonExistingModels, + deleteAllModels, + setAsUpdated, + runInReadCommittedTransaction, + doesExist }