From 47371fbdcf54e6970a209719f9eaae86cff07d35 Mon Sep 17 00:00:00 2001 From: Alexey Khit Date: Tue, 14 Feb 2023 14:25:13 +0300 Subject: [PATCH] Add support incoming MJPEG stream --- cmd/mjpeg/mjpeg.go | 30 ++++++++++++++++++++++++++++++ pkg/mjpeg/client.go | 2 +- 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/cmd/mjpeg/mjpeg.go b/cmd/mjpeg/mjpeg.go index fa9b7fdf..f116ad70 100644 --- a/cmd/mjpeg/mjpeg.go +++ b/cmd/mjpeg/mjpeg.go @@ -6,6 +6,7 @@ import ( "github.com/AlexxIT/go2rtc/cmd/streams" "github.com/AlexxIT/go2rtc/pkg/mjpeg" "github.com/rs/zerolog/log" + "io" "net/http" "strconv" ) @@ -62,6 +63,14 @@ func handlerKeyframe(w http.ResponseWriter, r *http.Request) { const header = "--frame\r\nContent-Type: image/jpeg\r\nContent-Length: " func handlerStream(w http.ResponseWriter, r *http.Request) { + if r.Method != "POST" { + outputMjpeg(w, r) + } else { + inputMjpeg(w, r) + } +} + +func outputMjpeg(w http.ResponseWriter, r *http.Request) { src := r.URL.Query().Get("src") stream := streams.GetOrNew(src) if stream == nil { @@ -108,6 +117,27 @@ func handlerStream(w http.ResponseWriter, r *http.Request) { //log.Trace().Msg("[api.mjpeg] close") } +func inputMjpeg(w http.ResponseWriter, r *http.Request) { + dst := r.URL.Query().Get("dst") + stream := streams.Get(dst) + if stream == nil { + http.Error(w, api.StreamNotFound, http.StatusNotFound) + return + } + + res := &http.Response{Body: r.Body, Header: r.Header, Request: r} + res.Header.Set("Content-Type", "multipart/mixed;boundary=") + + client := mjpeg.NewClient(res) + stream.AddProducer(client) + + if err := client.Start(); err != nil && err != io.EOF { + log.Warn().Err(err).Caller().Send() + } + + stream.RemoveProducer(client) +} + func handlerWS(tr *api.Transport, _ *api.Message) error { src := tr.Request.URL.Query().Get("src") stream := streams.GetOrNew(src) diff --git a/pkg/mjpeg/client.go b/pkg/mjpeg/client.go index 0b85fa11..5af52df1 100644 --- a/pkg/mjpeg/client.go +++ b/pkg/mjpeg/client.go @@ -136,7 +136,7 @@ func (c *Client) startMJPEG(boundary string) error { if err != nil { return err } - if s != boundary { + if !strings.HasPrefix(s, boundary) { return errors.New("wrong boundary: " + s) }