mirror of
https://github.com/rgrgogu/new_starr.git
synced 2026-09-27 00:12:54 +08:00
66 lines
2.9 KiB
JavaScript
66 lines
2.9 KiB
JavaScript
/***********************************************************************************************************************************************************************
|
|
* File Name : retry_stuck_transcodes.cron.js
|
|
* Type : Cron Job
|
|
* Description : Safety net for the .mov/.mkv -> faststart .mp4 background
|
|
* remux (see services/assetTranscode.service.js). Picks up:
|
|
* - "pending" — the fire-and-forget call in
|
|
* assets.controller.js#finalizeAssetFromStorage
|
|
* never actually started (e.g. this process
|
|
* crashed between the DB commit and the call).
|
|
* - "processing" for over 30 minutes — the job itself was
|
|
* running when the process restarted/crashed
|
|
* mid-remux and never got to flip the status.
|
|
*
|
|
* Processes at most 3 per run, sequentially — this runs on a
|
|
* small droplet, and remuxing is disk/CPU-bound; no reason to
|
|
* pile up concurrent ffmpeg processes for a background sweep.
|
|
*
|
|
* Schedule : Every 10 minutes ("*\/10 * * * *"). Registered by
|
|
* cron/admin.cron.js.
|
|
*
|
|
* Author: Kenneth Obsequio
|
|
* Date Created: Aug. 1, 2026
|
|
***********************************************************************************************************************************************************************/
|
|
const { Op } = require('sequelize');
|
|
const mdl_Assets = require('../../models/assets/assets.mdl');
|
|
const { transcodeAsset } = require('../../services/assetTranscode.service');
|
|
|
|
const MAX_PER_RUN = 3;
|
|
const STUCK_PROCESSING_MINUTES = 30;
|
|
|
|
async function run() {
|
|
try {
|
|
const stuckSince = new Date(Date.now() - STUCK_PROCESSING_MINUTES * 60 * 1000);
|
|
|
|
// Demote stale "processing" rows back to "pending" so transcodeAsset()'s
|
|
// own claim step (pending/failed -> processing) can pick them up again —
|
|
// it never claims an in-progress "processing" row, by design (avoids
|
|
// double-processing a job that's actually still running elsewhere).
|
|
await mdl_Assets.update(
|
|
{ transcode_status: 'pending' },
|
|
{ where: { transcode_status: 'processing', updatedAt: { [Op.lt]: stuckSince } } },
|
|
);
|
|
|
|
const candidates = await mdl_Assets.findAll({
|
|
where: { deletedAt: null, transcode_status: 'pending' },
|
|
limit: MAX_PER_RUN,
|
|
});
|
|
|
|
if (!candidates.length) return;
|
|
|
|
for (const asset of candidates) {
|
|
await transcodeAsset(asset);
|
|
}
|
|
|
|
console.log(`[CRON][RETRY STUCK TRANSCODES] Processed ${candidates.length} asset(s).`);
|
|
} catch (err) {
|
|
console.error('[CRON][RETRY STUCK TRANSCODES] Failed:', err);
|
|
}
|
|
}
|
|
|
|
module.exports = {
|
|
name: 'retryStuckTranscodes',
|
|
schedule: '*/10 * * * *',
|
|
run,
|
|
};
|