diff --git a/client.go b/client.go index 672acbe0..ba589f72 100644 --- a/client.go +++ b/client.go @@ -206,6 +206,7 @@ type Client struct { sender *auth.Sender cseq int useGetParameter bool + lastDescribeURL *base.URL streamBaseURL *base.URL protocol *Transport tracks map[int]clientTrack @@ -657,6 +658,12 @@ func (c *Client) trySwitchingProtocol() error { c.scheme = prevBaseURL.Scheme c.host = prevBaseURL.Host + // some Hikvision cameras require a describe before a setup + _, _, _, err := c.doDescribe(c.lastDescribeURL) + if err != nil { + return err + } + for _, track := range prevTracks { _, err := c.doSetup(true, track.track, prevBaseURL, 0, 0) if err != nil { @@ -664,7 +671,7 @@ func (c *Client) trySwitchingProtocol() error { } } - _, err := c.doPlay(c.lastRange, true) + _, err = c.doPlay(c.lastRange, true) if err != nil { return err } @@ -905,15 +912,15 @@ func (c *Client) do(req *base.Request, skipResponse bool) (*base.Response, error req.Header["Session"] = base.HeaderValue{c.session} } - if c.sender != nil { - c.sender.AddAuthorization(req) - } - c.cseq++ req.Header["CSeq"] = base.HeaderValue{strconv.FormatInt(int64(c.cseq), 10)} req.Header["User-Agent"] = base.HeaderValue{"gortsplib"} + if c.sender != nil { + c.sender.AddAuthorization(req) + } + if c.OnRequest != nil { c.OnRequest(req) } @@ -1136,6 +1143,8 @@ func (c *Client) doDescribe(u *base.URL) (Tracks, *base.URL, *base.Response, err return nil, nil, nil, err } + c.lastDescribeURL = u + return tracks, baseURL, res, nil } diff --git a/client_read_test.go b/client_read_test.go index 2606c288..427c3fa4 100644 --- a/client_read_test.go +++ b/client_read_test.go @@ -1249,6 +1249,21 @@ func TestClientReadAutomaticProtocol(t *testing.T) { require.NoError(t, err) br = bufio.NewReader(conn) + req, err = readRequest(br) + require.NoError(t, err) + require.Equal(t, base.Describe, req.Method) + + base.Response{ + StatusCode: base.StatusOK, + Header: base.Header{ + "Content-Type": base.HeaderValue{"application/sdp"}, + "Content-Base": base.HeaderValue{"rtsp://localhost:8554/teststream/"}, + }, + Body: tracks.Write(false), + }.Write(&bb) + _, err = conn.Write(bb.Bytes()) + require.NoError(t, err) + req, err = readRequest(br) require.NoError(t, err) require.Equal(t, base.Setup, req.Method)