diff options
Diffstat (limited to 'server/lib/hls.ts')
-rw-r--r-- | server/lib/hls.ts | 39 |
1 files changed, 21 insertions, 18 deletions
diff --git a/server/lib/hls.ts b/server/lib/hls.ts index 05be403f3..32b02bc26 100644 --- a/server/lib/hls.ts +++ b/server/lib/hls.ts | |||
@@ -1,7 +1,7 @@ | |||
1 | import { close, ensureDir, move, open, outputJSON, pathExists, read, readFile, remove, writeFile } from 'fs-extra' | 1 | import { close, ensureDir, move, open, outputJSON, pathExists, read, readFile, remove, writeFile } from 'fs-extra' |
2 | import { flatten, uniq } from 'lodash' | 2 | import { flatten, uniq } from 'lodash' |
3 | import { basename, dirname, join } from 'path' | 3 | import { basename, dirname, join } from 'path' |
4 | import { MVideoWithFile } from '@server/types/models' | 4 | import { MStreamingPlaylistFilesVideo, MVideoWithFile } from '@server/types/models' |
5 | import { sha256 } from '../helpers/core-utils' | 5 | import { sha256 } from '../helpers/core-utils' |
6 | import { getAudioStreamCodec, getVideoStreamCodec, getVideoStreamSize } from '../helpers/ffprobe-utils' | 6 | import { getAudioStreamCodec, getVideoStreamCodec, getVideoStreamSize } from '../helpers/ffprobe-utils' |
7 | import { logger } from '../helpers/logger' | 7 | import { logger } from '../helpers/logger' |
@@ -12,7 +12,7 @@ import { HLS_STREAMING_PLAYLIST_DIRECTORY, P2P_MEDIA_LOADER_PEER_VERSION } from | |||
12 | import { sequelizeTypescript } from '../initializers/database' | 12 | import { sequelizeTypescript } from '../initializers/database' |
13 | import { VideoFileModel } from '../models/video/video-file' | 13 | import { VideoFileModel } from '../models/video/video-file' |
14 | import { VideoStreamingPlaylistModel } from '../models/video/video-streaming-playlist' | 14 | import { VideoStreamingPlaylistModel } from '../models/video/video-streaming-playlist' |
15 | import { getVideoFilePath } from './video-paths' | 15 | import { getHlsResolutionPlaylistFilename, getVideoFilePath } from './video-paths' |
16 | 16 | ||
17 | async function updateStreamingPlaylistsInfohashesIfNeeded () { | 17 | async function updateStreamingPlaylistsInfohashesIfNeeded () { |
18 | const playlistsToUpdate = await VideoStreamingPlaylistModel.listByIncorrectPeerVersion() | 18 | const playlistsToUpdate = await VideoStreamingPlaylistModel.listByIncorrectPeerVersion() |
@@ -22,25 +22,29 @@ async function updateStreamingPlaylistsInfohashesIfNeeded () { | |||
22 | await sequelizeTypescript.transaction(async t => { | 22 | await sequelizeTypescript.transaction(async t => { |
23 | const videoFiles = await VideoFileModel.listByStreamingPlaylist(playlist.id, t) | 23 | const videoFiles = await VideoFileModel.listByStreamingPlaylist(playlist.id, t) |
24 | 24 | ||
25 | playlist.p2pMediaLoaderInfohashes = VideoStreamingPlaylistModel.buildP2PMediaLoaderInfoHashes(playlist.playlistUrl, videoFiles) | 25 | playlist.assignP2PMediaLoaderInfoHashes(playlist.Video, videoFiles) |
26 | playlist.p2pMediaLoaderPeerVersion = P2P_MEDIA_LOADER_PEER_VERSION | 26 | playlist.p2pMediaLoaderPeerVersion = P2P_MEDIA_LOADER_PEER_VERSION |
27 | |||
27 | await playlist.save({ transaction: t }) | 28 | await playlist.save({ transaction: t }) |
28 | }) | 29 | }) |
29 | } | 30 | } |
30 | } | 31 | } |
31 | 32 | ||
32 | async function updateMasterHLSPlaylist (video: MVideoWithFile) { | 33 | async function updateMasterHLSPlaylist (video: MVideoWithFile, playlist: MStreamingPlaylistFilesVideo) { |
33 | const directory = join(HLS_STREAMING_PLAYLIST_DIRECTORY, video.uuid) | 34 | const directory = join(HLS_STREAMING_PLAYLIST_DIRECTORY, video.uuid) |
35 | |||
34 | const masterPlaylists: string[] = [ '#EXTM3U', '#EXT-X-VERSION:3' ] | 36 | const masterPlaylists: string[] = [ '#EXTM3U', '#EXT-X-VERSION:3' ] |
35 | const masterPlaylistPath = join(directory, VideoStreamingPlaylistModel.getMasterHlsPlaylistFilename()) | ||
36 | const streamingPlaylist = video.getHLSPlaylist() | ||
37 | 37 | ||
38 | for (const file of streamingPlaylist.VideoFiles) { | 38 | const masterPlaylistPath = join(directory, playlist.playlistFilename) |
39 | |||
40 | for (const file of playlist.VideoFiles) { | ||
41 | const playlistFilename = getHlsResolutionPlaylistFilename(file.filename) | ||
42 | |||
39 | // If we did not generated a playlist for this resolution, skip | 43 | // If we did not generated a playlist for this resolution, skip |
40 | const filePlaylistPath = join(directory, VideoStreamingPlaylistModel.getHlsPlaylistFilename(file.resolution)) | 44 | const filePlaylistPath = join(directory, playlistFilename) |
41 | if (await pathExists(filePlaylistPath) === false) continue | 45 | if (await pathExists(filePlaylistPath) === false) continue |
42 | 46 | ||
43 | const videoFilePath = getVideoFilePath(streamingPlaylist, file) | 47 | const videoFilePath = getVideoFilePath(playlist, file) |
44 | 48 | ||
45 | const size = await getVideoStreamSize(videoFilePath) | 49 | const size = await getVideoStreamSize(videoFilePath) |
46 | 50 | ||
@@ -58,29 +62,28 @@ async function updateMasterHLSPlaylist (video: MVideoWithFile) { | |||
58 | line += `,CODECS="${codecs.filter(c => !!c).join(',')}"` | 62 | line += `,CODECS="${codecs.filter(c => !!c).join(',')}"` |
59 | 63 | ||
60 | masterPlaylists.push(line) | 64 | masterPlaylists.push(line) |
61 | masterPlaylists.push(VideoStreamingPlaylistModel.getHlsPlaylistFilename(file.resolution)) | 65 | masterPlaylists.push(playlistFilename) |
62 | } | 66 | } |
63 | 67 | ||
64 | await writeFile(masterPlaylistPath, masterPlaylists.join('\n') + '\n') | 68 | await writeFile(masterPlaylistPath, masterPlaylists.join('\n') + '\n') |
65 | } | 69 | } |
66 | 70 | ||
67 | async function updateSha256VODSegments (video: MVideoWithFile) { | 71 | async function updateSha256VODSegments (video: MVideoWithFile, playlist: MStreamingPlaylistFilesVideo) { |
68 | const json: { [filename: string]: { [range: string]: string } } = {} | 72 | const json: { [filename: string]: { [range: string]: string } } = {} |
69 | 73 | ||
70 | const playlistDirectory = join(HLS_STREAMING_PLAYLIST_DIRECTORY, video.uuid) | 74 | const playlistDirectory = join(HLS_STREAMING_PLAYLIST_DIRECTORY, video.uuid) |
71 | const hlsPlaylist = video.getHLSPlaylist() | ||
72 | 75 | ||
73 | // For all the resolutions available for this video | 76 | // For all the resolutions available for this video |
74 | for (const file of hlsPlaylist.VideoFiles) { | 77 | for (const file of playlist.VideoFiles) { |
75 | const rangeHashes: { [range: string]: string } = {} | 78 | const rangeHashes: { [range: string]: string } = {} |
76 | 79 | ||
77 | const videoPath = getVideoFilePath(hlsPlaylist, file) | 80 | const videoPath = getVideoFilePath(playlist, file) |
78 | const playlistPath = join(playlistDirectory, VideoStreamingPlaylistModel.getHlsPlaylistFilename(file.resolution)) | 81 | const resolutionPlaylistPath = join(playlistDirectory, getHlsResolutionPlaylistFilename(file.filename)) |
79 | 82 | ||
80 | // Maybe the playlist is not generated for this resolution yet | 83 | // Maybe the playlist is not generated for this resolution yet |
81 | if (!await pathExists(playlistPath)) continue | 84 | if (!await pathExists(resolutionPlaylistPath)) continue |
82 | 85 | ||
83 | const playlistContent = await readFile(playlistPath) | 86 | const playlistContent = await readFile(resolutionPlaylistPath) |
84 | const ranges = getRangesFromPlaylist(playlistContent.toString()) | 87 | const ranges = getRangesFromPlaylist(playlistContent.toString()) |
85 | 88 | ||
86 | const fd = await open(videoPath, 'r') | 89 | const fd = await open(videoPath, 'r') |
@@ -96,7 +99,7 @@ async function updateSha256VODSegments (video: MVideoWithFile) { | |||
96 | json[videoFilename] = rangeHashes | 99 | json[videoFilename] = rangeHashes |
97 | } | 100 | } |
98 | 101 | ||
99 | const outputPath = join(playlistDirectory, VideoStreamingPlaylistModel.getHlsSha256SegmentsFilename()) | 102 | const outputPath = join(playlistDirectory, playlist.segmentsSha256Filename) |
100 | await outputJSON(outputPath, json) | 103 | await outputJSON(outputPath, json) |
101 | } | 104 | } |
102 | 105 | ||