streaming

Media streaming and broadcast systems in Go
Log | Files | Refs | README | LICENSE

commit 52ca0d40aee46b2fdb156b73c5c16509f3e3505e
parent 8b9dabb3f7e20b95c9d353d7cdc8deed50330b9f
Author: Oliver Lowe <o@olowe.co>
Date:   Sat, 18 May 2024 21:26:07 +1000

m3u8: use scte35.SpliceInfo in the DateRange instead of raw bytes

This means we don't need to test whether encoding splices works;
that's already the responsibility of package scte35. Makes
documentation much clearer.

Diffstat:
Mm3u8/m3u8.go | 14++++++++++----
Mm3u8/write.go | 14++++++++++++--
Mm3u8/write_test.go | 21---------------------
3 files changed, 22 insertions(+), 27 deletions(-)

diff --git a/m3u8/m3u8.go b/m3u8/m3u8.go @@ -6,6 +6,8 @@ import ( "fmt" "strconv" "time" + + "github.com/untangledco/streaming/scte35" ) type Playlist struct { @@ -111,10 +113,14 @@ type DateRange struct { Planned time.Duration // value must be a string, float or hex sequence (int?) Custom map[string]any - CueCommand []byte - CueIn []byte - CueOut []byte - EndOnNext bool + CueCommand *scte35.SpliceInfo + // Contains the first of the in/out cue pair. Command may be + // TimeSignal or Insert, with OutOfNetwork set to true. + CueOut *scte35.SpliceInfo + // Contains the second of the cue in/out pair. The Command's + // Type must match the "out" cue. + CueIn *scte35.SpliceInfo + EndOnNext bool } type PlaylistType uint8 diff --git a/m3u8/write.go b/m3u8/write.go @@ -6,6 +6,8 @@ import ( "io" "strings" "time" + + "github.com/untangledco/streaming/scte35" ) func Encode(w io.Writer, p *Playlist) error { @@ -52,10 +54,18 @@ func writeDateRange(w io.Writer, dr *DateRange) error { // TODO(otl): dr.Custom. // TODO(otl): dr.CueCommand, when to write this versuse cuein, cueout. if dr.CueIn != nil { - attrs = append(attrs, fmt.Sprintf("SCTE35-IN=0x%s", hex.EncodeToString(dr.CueIn))) + b, err := scte35.EncodeSpliceInfo(dr.CueIn) + if err != nil { + return fmt.Errorf("encode cue in: %w", err) + } + attrs = append(attrs, fmt.Sprintf("SCTE35-IN=0x%s", hex.EncodeToString(b))) } if dr.CueOut != nil { - attrs = append(attrs, fmt.Sprintf("SCTE35-OUT=0x%s", hex.EncodeToString(dr.CueOut))) + b, err := scte35.EncodeSpliceInfo(dr.CueOut) + if err != nil { + return fmt.Errorf("encode cue out: %w", err) + } + attrs = append(attrs, fmt.Sprintf("SCTE35-OUT=0x%s", hex.EncodeToString(b))) } if dr.EndOnNext { attrs = append(attrs, "END-ON-NEXT:YES") diff --git a/m3u8/write_test.go b/m3u8/write_test.go @@ -3,7 +3,6 @@ package m3u8 import ( "bufio" "bytes" - "encoding/base64" "testing" "time" ) @@ -33,23 +32,3 @@ func TestEncodeSegDuration(t *testing.T) { t.Errorf("no matching segment duration %s", want) } } - -func TestDateRange(t *testing.T) { - // splice insert from SCTE 35 section 14.2 - out, err := base64.StdEncoding.DecodeString("/DAvAAAAAAAA///wFAVIAACPf+/+c2nALv4AUsz1AAAAAAAKAAhDVUVJAAABNWLbowo=") - if err != nil { - t.Fatal(err) - } - dr := DateRange{ - ID: "break", - CueOut: out, - } - buf := &bytes.Buffer{} - if err := writeDateRange(buf, &dr); err != nil { - t.Fatalf("write date range: %v", err) - } - want := `#EXT-X-DATERANGE:ID="break",SCTE35-OUT=0xfc302f000000000000fffff014054800008f7feffe7369c02efe0052ccf500000000000a0008435545490000013562dba30a` + "\n" - if buf.String() != want { - t.Errorf("encode %v: got %s, want %s", dr, buf.String(), want) - } -}