Skip to content

Commit

Permalink
The new way of getting first and last transcoded segment was faulty s…
Browse files Browse the repository at this point in the history
…ince it didn't take into account that the user could be skipping around and there for return an incorrect range of transcoded segments
  • Loading branch information
thomaserlang committed Dec 10, 2023
1 parent bf69709 commit c5826ea
Show file tree
Hide file tree
Showing 3 changed files with 23 additions and 19 deletions.
5 changes: 3 additions & 2 deletions seplis_play_server/routes/hls.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

from .. import config
from ..dependencies import get_metadata
from ..transcoders.video import Transcode_settings, close_transcoder, sessions
from ..transcoders.video import Transcode_settings, sessions
from ..transcoders.hls import Hls_transcoder

router = APIRouter()
Expand Down Expand Up @@ -41,7 +41,8 @@ async def get_media(

# If the segment is within 15 segments of the last transcoded segment
# then wait for the segment to be transcoded.
first_transcoded_segment, last_transcoded_segment = await Hls_transcoder.first_last_transcoded_segment(folder)
first_transcoded_segment, last_transcoded_segment = \
await Hls_transcoder.first_last_transcoded_segment(settings.session, folder)
if first_transcoded_segment <= segment and (last_transcoded_segment + 15) >= segment:
logger.debug(f'Requested segment {segment} is within the range {first_transcoded_segment}-{last_transcoded_segment+15} to wait for transcoding')
if await Hls_transcoder.wait_for_segment(folder, segment):
Expand Down
32 changes: 17 additions & 15 deletions seplis_play_server/transcoders/hls.py
Original file line number Diff line number Diff line change
@@ -1,10 +1,8 @@
from ast import Dict
import asyncio, os
import math
import re
from urllib.parse import urlencode
from decimal import Decimal
from aiofile import async_open
import anyio

from seplis_play_server import logger
Expand All @@ -14,7 +12,7 @@ class Hls_transcoder(video.Transcoder):

media_name: str = 'media.m3u8'

def __init__(self, settings: video.Transcode_settings, metadata: Dict):
def __init__(self, settings: video.Transcode_settings, metadata: dict):
#if settings.transcode_video_codec not in ('h264', 'hevc'):
settings.transcode_video_codec = 'h264'
# Still issues with hevc
Expand All @@ -33,10 +31,11 @@ def ffmpeg_extend_args(self) -> None:
{'-y': None},
])

if self.output_codec == 'h264':
self.ffmpeg_args.append({'-bsf:v': 'h264_mp4toannexb'})
elif self.output_codec == 'hevc':
self.ffmpeg_args.append({'-bsf:v': 'hevc_mp4toannexb'})
if self.can_copy_video:
if self.output_codec == 'h264':
self.ffmpeg_args.append({'-bsf:v': 'h264_mp4toannexb'})
elif self.output_codec == 'hevc':
self.ffmpeg_args.append({'-bsf:v': 'hevc_mp4toannexb'})

self.ffmpeg_args.append({self.media_path: None})

Expand All @@ -49,6 +48,7 @@ async def wait_for_media(self):
self.transcode_folder,
self.settings.start_segment or 0,
)
video.sessions[self.settings.session].start_segment = self.settings.start_segment or 0

@classmethod
async def wait_for_segment(cls, transcode_folder: str, segment: str | int):
Expand All @@ -64,19 +64,21 @@ async def wait_for():
return False

@classmethod
async def first_last_transcoded_segment(cls, transcode_folder: str):
first, last = (-1, 0)
async def first_last_transcoded_segment(cls, session: str, transcode_folder: str):
if session not in video.sessions:
return (0, 0)
first = video.sessions[session].start_segment or 0
last = first
segments: list[int] = []
if await anyio.to_thread.run_sync(os.path.exists, transcode_folder):
files = await anyio.to_thread.run_sync(os.listdir, transcode_folder)
for f in files:
m = re.search(r'media(\d+)\.m4s', f)
if m:
v = int(m.group(1))
if v > last:
last = v
if v < first or first == -1:
first = v
first = int(m.group(1))
segments.append(int(m.group(1)))
for s in sorted(segments):
if s > last and s - last == 1:
last = s
else:
logger.debug(f'No media file {f}')
return (first, last)
Expand Down
5 changes: 3 additions & 2 deletions seplis_play_server/transcoders/video.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,8 @@ class Video_color(BaseModel):

class Session_model(BaseModel):
process: asyncio.subprocess.Process
transcode_folder: Optional[str] = None
transcode_folder: Optional[str] | None = None
start_segment: Optional[int] | None = None
call_later: asyncio.TimerHandle

model_config = ConfigDict(
Expand Down Expand Up @@ -237,7 +238,7 @@ def set_video(self):
codec = 'copy'
if self.settings.start_time > 0:
i = self.find_ffmpeg_arg_index('-ss')
# Audio goes out if sync if not used
# Audio goes out of sync if not used
self.ffmpeg_args.insert(i+1, {'-noaccurate_seek': None})

self.ffmpeg_args.extend([
Expand Down

0 comments on commit c5826ea

Please sign in to comment.