From 2baea0c77cc765f7cbca9c9a2f4272268892a35c Mon Sep 17 00:00:00 2001 From: Chocobozzz Date: Thu, 14 Jun 2018 18:06:56 +0200 Subject: Add ability for uploaders to schedule video update --- server/lib/schedulers/abstract-scheduler.ts | 8 +-- .../lib/schedulers/bad-actor-follow-scheduler.ts | 3 ++ server/lib/schedulers/remove-old-jobs-scheduler.ts | 3 ++ server/lib/schedulers/update-videos-scheduler.ts | 62 ++++++++++++++++++++++ 4 files changed, 73 insertions(+), 3 deletions(-) create mode 100644 server/lib/schedulers/update-videos-scheduler.ts (limited to 'server/lib/schedulers') diff --git a/server/lib/schedulers/abstract-scheduler.ts b/server/lib/schedulers/abstract-scheduler.ts index 473544ddf..6ec5e3360 100644 --- a/server/lib/schedulers/abstract-scheduler.ts +++ b/server/lib/schedulers/abstract-scheduler.ts @@ -1,11 +1,13 @@ -import { SCHEDULER_INTERVAL } from '../../initializers' - export abstract class AbstractScheduler { + protected abstract schedulerIntervalMs: number + private interval: NodeJS.Timer enable () { - this.interval = setInterval(() => this.execute(), SCHEDULER_INTERVAL) + if (!this.schedulerIntervalMs) throw new Error('Interval is not correctly set.') + + this.interval = setInterval(() => this.execute(), this.schedulerIntervalMs) } disable () { diff --git a/server/lib/schedulers/bad-actor-follow-scheduler.ts b/server/lib/schedulers/bad-actor-follow-scheduler.ts index 121f7145e..617149aaf 100644 --- a/server/lib/schedulers/bad-actor-follow-scheduler.ts +++ b/server/lib/schedulers/bad-actor-follow-scheduler.ts @@ -2,11 +2,14 @@ import { isTestInstance } from '../../helpers/core-utils' import { logger } from '../../helpers/logger' import { ActorFollowModel } from '../../models/activitypub/actor-follow' import { AbstractScheduler } from './abstract-scheduler' +import { SCHEDULER_INTERVALS_MS } from '../../initializers' export class BadActorFollowScheduler extends AbstractScheduler { private static instance: AbstractScheduler + protected schedulerIntervalMs = SCHEDULER_INTERVALS_MS.badActorFollow + private constructor () { super() } diff --git a/server/lib/schedulers/remove-old-jobs-scheduler.ts b/server/lib/schedulers/remove-old-jobs-scheduler.ts index 0e8ad1554..a29a6b800 100644 --- a/server/lib/schedulers/remove-old-jobs-scheduler.ts +++ b/server/lib/schedulers/remove-old-jobs-scheduler.ts @@ -2,11 +2,14 @@ import { isTestInstance } from '../../helpers/core-utils' import { logger } from '../../helpers/logger' import { JobQueue } from '../job-queue' import { AbstractScheduler } from './abstract-scheduler' +import { SCHEDULER_INTERVALS_MS } from '../../initializers' export class RemoveOldJobsScheduler extends AbstractScheduler { private static instance: AbstractScheduler + protected schedulerIntervalMs = SCHEDULER_INTERVALS_MS.removeOldJobs + private constructor () { super() } diff --git a/server/lib/schedulers/update-videos-scheduler.ts b/server/lib/schedulers/update-videos-scheduler.ts new file mode 100644 index 000000000..d123c3ceb --- /dev/null +++ b/server/lib/schedulers/update-videos-scheduler.ts @@ -0,0 +1,62 @@ +import { isTestInstance } from '../../helpers/core-utils' +import { logger } from '../../helpers/logger' +import { JobQueue } from '../job-queue' +import { AbstractScheduler } from './abstract-scheduler' +import { ScheduleVideoUpdateModel } from '../../models/video/schedule-video-update' +import { retryTransactionWrapper } from '../../helpers/database-utils' +import { federateVideoIfNeeded } from '../activitypub' +import { SCHEDULER_INTERVALS_MS, sequelizeTypescript } from '../../initializers' +import { VideoPrivacy } from '../../../shared/models/videos' + +export class UpdateVideosScheduler extends AbstractScheduler { + + private static instance: AbstractScheduler + + protected schedulerIntervalMs = SCHEDULER_INTERVALS_MS.updateVideos + + private isRunning = false + + private constructor () { + super() + } + + async execute () { + if (this.isRunning === true) return + this.isRunning = true + + try { + await retryTransactionWrapper(this.updateVideos.bind(this)) + } catch (err) { + logger.error('Cannot execute update videos scheduler.', { err }) + } finally { + this.isRunning = false + } + } + + private updateVideos () { + return sequelizeTypescript.transaction(async t => { + const schedules = await ScheduleVideoUpdateModel.listVideosToUpdate(t) + + for (const schedule of schedules) { + const video = schedule.Video + logger.info('Executing scheduled video update on %s.', video.uuid) + + if (schedule.privacy) { + const oldPrivacy = video.privacy + + video.privacy = schedule.privacy + await video.save({ transaction: t }) + + const isNewVideo = oldPrivacy === VideoPrivacy.PRIVATE + await federateVideoIfNeeded(video, isNewVideo, t) + } + + await schedule.destroy({ transaction: t }) + } + }) + } + + static get Instance () { + return this.instance || (this.instance = new this()) + } +} -- cgit v1.2.3