aboutsummaryrefslogtreecommitdiffhomepage
path: root/server/lib/job-queue
diff options
context:
space:
mode:
Diffstat (limited to 'server/lib/job-queue')
-rw-r--r--server/lib/job-queue/handlers/video-live-ending.ts77
1 files changed, 44 insertions, 33 deletions
diff --git a/server/lib/job-queue/handlers/video-live-ending.ts b/server/lib/job-queue/handlers/video-live-ending.ts
index 0e1bfb240..10507fb83 100644
--- a/server/lib/job-queue/handlers/video-live-ending.ts
+++ b/server/lib/job-queue/handlers/video-live-ending.ts
@@ -30,26 +30,36 @@ async function processVideoLiveEnding (job: Job) {
30 logger.warn('Video live %d does not exist anymore. Cannot process live ending.', payload.videoId, lTags()) 30 logger.warn('Video live %d does not exist anymore. Cannot process live ending.', payload.videoId, lTags())
31 } 31 }
32 32
33 const liveVideo = await VideoModel.load(payload.videoId) 33 const video = await VideoModel.load(payload.videoId)
34 const live = await VideoLiveModel.loadByVideoId(payload.videoId) 34 const live = await VideoLiveModel.loadByVideoId(payload.videoId)
35 const liveSession = await VideoLiveSessionModel.load(payload.liveSessionId) 35 const liveSession = await VideoLiveSessionModel.load(payload.liveSessionId)
36 36
37 if (!liveVideo || !live || !liveSession) { 37 const permanentLive = live.permanentLive
38
39 if (!video || !live || !liveSession) {
38 logError() 40 logError()
39 return 41 return
40 } 42 }
41 43
42 if (live.saveReplay !== true) { 44 liveSession.endingProcessed = true
43 return cleanupLiveAndFederate({ live, video: liveVideo, streamingPlaylistId: payload.streamingPlaylistId }) 45 await liveSession.save()
46
47 if (liveSession.saveReplay !== true) {
48 return cleanupLiveAndFederate({ permanentLive, video, streamingPlaylistId: payload.streamingPlaylistId })
44 } 49 }
45 50
46 if (live.permanentLive) { 51 if (permanentLive) {
47 await saveReplayToExternalVideo({ liveVideo, liveSession, publishedAt: payload.publishedAt, replayDirectory: payload.replayDirectory }) 52 await saveReplayToExternalVideo({
53 liveVideo: video,
54 liveSession,
55 publishedAt: payload.publishedAt,
56 replayDirectory: payload.replayDirectory
57 })
48 58
49 return cleanupLiveAndFederate({ live, video: liveVideo, streamingPlaylistId: payload.streamingPlaylistId }) 59 return cleanupLiveAndFederate({ permanentLive, video, streamingPlaylistId: payload.streamingPlaylistId })
50 } 60 }
51 61
52 return replaceLiveByReplay({ liveVideo, live, liveSession, replayDirectory: payload.replayDirectory }) 62 return replaceLiveByReplay({ video, liveSession, live, permanentLive, replayDirectory: payload.replayDirectory })
53} 63}
54 64
55// --------------------------------------------------------------------------- 65// ---------------------------------------------------------------------------
@@ -68,7 +78,7 @@ async function saveReplayToExternalVideo (options: {
68}) { 78}) {
69 const { liveVideo, liveSession, publishedAt, replayDirectory } = options 79 const { liveVideo, liveSession, publishedAt, replayDirectory } = options
70 80
71 const video = new VideoModel({ 81 const replayVideo = new VideoModel({
72 name: `${liveVideo.name} - ${new Date(publishedAt).toLocaleString()}`, 82 name: `${liveVideo.name} - ${new Date(publishedAt).toLocaleString()}`,
73 isLive: false, 83 isLive: false,
74 state: VideoState.TO_TRANSCODE, 84 state: VideoState.TO_TRANSCODE,
@@ -88,63 +98,64 @@ async function saveReplayToExternalVideo (options: {
88 channelId: liveVideo.channelId 98 channelId: liveVideo.channelId
89 }) as MVideoWithAllFiles 99 }) as MVideoWithAllFiles
90 100
91 video.Thumbnails = [] 101 replayVideo.Thumbnails = []
92 video.VideoFiles = [] 102 replayVideo.VideoFiles = []
93 video.VideoStreamingPlaylists = [] 103 replayVideo.VideoStreamingPlaylists = []
94 104
95 video.url = getLocalVideoActivityPubUrl(video) 105 replayVideo.url = getLocalVideoActivityPubUrl(replayVideo)
96 106
97 await video.save() 107 await replayVideo.save()
98 108
99 liveSession.replayVideoId = video.id 109 liveSession.replayVideoId = replayVideo.id
100 await liveSession.save() 110 await liveSession.save()
101 111
102 // If live is blacklisted, also blacklist the replay 112 // If live is blacklisted, also blacklist the replay
103 const blacklist = await VideoBlacklistModel.loadByVideoId(liveVideo.id) 113 const blacklist = await VideoBlacklistModel.loadByVideoId(liveVideo.id)
104 if (blacklist) { 114 if (blacklist) {
105 await VideoBlacklistModel.create({ 115 await VideoBlacklistModel.create({
106 videoId: video.id, 116 videoId: replayVideo.id,
107 unfederated: blacklist.unfederated, 117 unfederated: blacklist.unfederated,
108 reason: blacklist.reason, 118 reason: blacklist.reason,
109 type: blacklist.type 119 type: blacklist.type
110 }) 120 })
111 } 121 }
112 122
113 await assignReplayFilesToVideo({ video, replayDirectory }) 123 await assignReplayFilesToVideo({ video: replayVideo, replayDirectory })
114 124
115 await remove(replayDirectory) 125 await remove(replayDirectory)
116 126
117 for (const type of [ ThumbnailType.MINIATURE, ThumbnailType.PREVIEW ]) { 127 for (const type of [ ThumbnailType.MINIATURE, ThumbnailType.PREVIEW ]) {
118 const image = await generateVideoMiniature({ video, videoFile: video.getMaxQualityFile(), type }) 128 const image = await generateVideoMiniature({ video: replayVideo, videoFile: replayVideo.getMaxQualityFile(), type })
119 await video.addAndSaveThumbnail(image) 129 await replayVideo.addAndSaveThumbnail(image)
120 } 130 }
121 131
122 await moveToNextState({ video, isNewVideo: true }) 132 await moveToNextState({ video: replayVideo, isNewVideo: true })
123} 133}
124 134
125async function replaceLiveByReplay (options: { 135async function replaceLiveByReplay (options: {
126 liveVideo: MVideo 136 video: MVideo
127 liveSession: MVideoLiveSession 137 liveSession: MVideoLiveSession
128 live: MVideoLive 138 live: MVideoLive
139 permanentLive: boolean
129 replayDirectory: string 140 replayDirectory: string
130}) { 141}) {
131 const { liveVideo, liveSession, live, replayDirectory } = options 142 const { video, liveSession, live, permanentLive, replayDirectory } = options
132 143
133 await cleanupTMPLiveFiles(liveVideo) 144 await cleanupTMPLiveFiles(video)
134 145
135 await live.destroy() 146 await live.destroy()
136 147
137 liveVideo.isLive = false 148 video.isLive = false
138 liveVideo.waitTranscoding = true 149 video.waitTranscoding = true
139 liveVideo.state = VideoState.TO_TRANSCODE 150 video.state = VideoState.TO_TRANSCODE
140 151
141 await liveVideo.save() 152 await video.save()
142 153
143 liveSession.replayVideoId = liveVideo.id 154 liveSession.replayVideoId = video.id
144 await liveSession.save() 155 await liveSession.save()
145 156
146 // Remove old HLS playlist video files 157 // Remove old HLS playlist video files
147 const videoWithFiles = await VideoModel.loadFull(liveVideo.id) 158 const videoWithFiles = await VideoModel.loadFull(video.id)
148 159
149 const hlsPlaylist = videoWithFiles.getHLSPlaylist() 160 const hlsPlaylist = videoWithFiles.getHLSPlaylist()
150 await VideoFileModel.removeHLSFilesOfVideoId(hlsPlaylist.id) 161 await VideoFileModel.removeHLSFilesOfVideoId(hlsPlaylist.id)
@@ -157,7 +168,7 @@ async function replaceLiveByReplay (options: {
157 168
158 await assignReplayFilesToVideo({ video: videoWithFiles, replayDirectory }) 169 await assignReplayFilesToVideo({ video: videoWithFiles, replayDirectory })
159 170
160 if (live.permanentLive) { // Remove session replay 171 if (permanentLive) { // Remove session replay
161 await remove(replayDirectory) 172 await remove(replayDirectory)
162 } else { // We won't stream again in this live, we can delete the base replay directory 173 } else { // We won't stream again in this live, we can delete the base replay directory
163 await remove(getLiveReplayBaseDirectory(videoWithFiles)) 174 await remove(getLiveReplayBaseDirectory(videoWithFiles))
@@ -224,16 +235,16 @@ async function assignReplayFilesToVideo (options: {
224} 235}
225 236
226async function cleanupLiveAndFederate (options: { 237async function cleanupLiveAndFederate (options: {
227 live: MVideoLive
228 video: MVideo 238 video: MVideo
239 permanentLive: boolean
229 streamingPlaylistId: number 240 streamingPlaylistId: number
230}) { 241}) {
231 const { live, video, streamingPlaylistId } = options 242 const { permanentLive, video, streamingPlaylistId } = options
232 243
233 const streamingPlaylist = await VideoStreamingPlaylistModel.loadWithVideo(streamingPlaylistId) 244 const streamingPlaylist = await VideoStreamingPlaylistModel.loadWithVideo(streamingPlaylistId)
234 245
235 if (streamingPlaylist) { 246 if (streamingPlaylist) {
236 if (live.permanentLive) { 247 if (permanentLive) {
237 await cleanupPermanentLive(video, streamingPlaylist) 248 await cleanupPermanentLive(video, streamingPlaylist)
238 } else { 249 } else {
239 await cleanupUnsavedNormalLive(video, streamingPlaylist) 250 await cleanupUnsavedNormalLive(video, streamingPlaylist)