feat: preload hints in segments

This commit is contained in:
2025-06-13 11:42:07 +01:00
parent d76ff96326
commit 5b7aa0c659
2 changed files with 18 additions and 11 deletions

View File

@ -874,6 +874,8 @@ pub enum MediaSegmentType {
Full(MediaSegment), Full(MediaSegment),
/// HLS-LL: Partial segment (#EXT-X-PART) /// HLS-LL: Partial segment (#EXT-X-PART)
Partial(Part), Partial(Part),
/// HLS-LL: Preload hint (#EXT-X-PRELOAD-HINT)
PreloadHint(PreloadHint),
} }
impl MediaSegmentType { impl MediaSegmentType {
@ -881,6 +883,7 @@ impl MediaSegmentType {
match self { match self {
MediaSegmentType::Full(s) => s.write_to(w), MediaSegmentType::Full(s) => s.write_to(w),
MediaSegmentType::Partial(s) => s.write_to(w), MediaSegmentType::Partial(s) => s.write_to(w),
MediaSegmentType::PreloadHint(s) => s.write_to(w),
} }
} }
} }
@ -1413,7 +1416,8 @@ impl Skip {
pub struct PreloadHint { pub struct PreloadHint {
pub hint_type: String, pub hint_type: String,
pub uri: String, pub uri: String,
pub byte_range: Option<ByteRange>, pub byte_range_start: Option<u64>,
pub byte_range_length: Option<u64>,
} }
impl PreloadHint { impl PreloadHint {
@ -1424,11 +1428,15 @@ impl PreloadHint {
.ok_or_else(|| String::from("EXT-X-PRELOAD-HINT without mandatory TYPE attribute"))?; .ok_or_else(|| String::from("EXT-X-PRELOAD-HINT without mandatory TYPE attribute"))?;
let uri = quoted_string!(attrs, "URI") let uri = quoted_string!(attrs, "URI")
.ok_or_else(|| String::from("EXT-X-PRELOAD-HINT without mandatory URI attribute"))?; .ok_or_else(|| String::from("EXT-X-PRELOAD-HINT without mandatory URI attribute"))?;
let byte_range = quoted_string_parse!(attrs, "BYTERANGE", |s: &str| s.parse::<ByteRange>()); let byte_range_start =
quoted_string_parse!(attrs, "BYTERANGE-START", |s: &str| s.parse::<u64>());
let byte_range_length =
quoted_string_parse!(attrs, "BYTERANGE-LENGTH", |s: &str| s.parse::<u64>());
Ok(PreloadHint { Ok(PreloadHint {
hint_type, hint_type,
uri, uri,
byte_range, byte_range_start,
byte_range_length,
}) })
} }
@ -1438,10 +1446,11 @@ impl PreloadHint {
"#EXT-X-PRELOAD-HINT:TYPE={},URI=\"{}\"", "#EXT-X-PRELOAD-HINT:TYPE={},URI=\"{}\"",
self.hint_type, self.uri self.hint_type, self.uri
)?; )?;
if let Some(ref byte_range) = self.byte_range { if let Some(ref r) = self.byte_range_start {
write!(w, ",BYTERANGE=\"")?; write!(w, ",BYTERANGE-START=\"{}\"", r)?;
byte_range.write_value_to(w)?; }
write!(w, "\"")?; if let Some(ref r) = self.byte_range_length {
write!(w, ",BYTERANGE-LENGTH=\"{}\"", r)?;
} }
writeln!(w) writeln!(w)
} }

View File

@ -577,10 +577,8 @@ fn create_and_parse_media_playlist_llhls() {
preload_hint: Some(PreloadHint { preload_hint: Some(PreloadHint {
hint_type: "PART".into(), hint_type: "PART".into(),
uri: "next_part.ts".into(), uri: "next_part.ts".into(),
byte_range: Some(ByteRange { byte_range_start: Some(50000),
length: 50000, byte_range_length: Some(60000),
offset: Some(100000),
}),
}), }),
rendition_report: Some(RenditionReport { rendition_report: Some(RenditionReport {
uri: "rendition.m3u8".into(), uri: "rendition.m3u8".into(),