diff --git a/apidocs/openapi.yaml b/apidocs/openapi.yaml index 74b34998..ad9720c7 100644 --- a/apidocs/openapi.yaml +++ b/apidocs/openapi.yaml @@ -657,6 +657,9 @@ components: bytesSent: type: integer format: int64 + session: + type: string + nullable: true RTSPConnList: type: object diff --git a/go.mod b/go.mod index 1b8c1a8a..62b3c282 100644 --- a/go.mod +++ b/go.mod @@ -10,7 +10,7 @@ require ( github.com/alecthomas/kong v1.6.0 github.com/asticode/go-astits v1.13.0 github.com/bluenviron/gohlslib/v2 v2.1.0 - github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225143216-4d3d6bc108f3 + github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225145501-66410517c85f github.com/bluenviron/mediacommon v1.13.2 github.com/datarhei/gosrt v0.8.0 github.com/fsnotify/fsnotify v1.8.0 diff --git a/go.sum b/go.sum index 2e7e1eb9..935926c2 100644 --- a/go.sum +++ b/go.sum @@ -33,8 +33,8 @@ github.com/benburkert/openpgp v0.0.0-20160410205803-c2471f86866c h1:8XZeJrs4+ZYh github.com/benburkert/openpgp v0.0.0-20160410205803-c2471f86866c/go.mod h1:x1vxHcL/9AVzuk5HOloOEPrtJY0MaalYr78afXZ+pWI= github.com/bluenviron/gohlslib/v2 v2.1.0 h1:I0KXXPjnt7QxsR39z97fKe/x1yj22e1NhSqZ5P6FbWE= github.com/bluenviron/gohlslib/v2 v2.1.0/go.mod h1:irD+TAdUsb400Gp8v80LKPPC4YumiAieUSO6ICykeWo= -github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225143216-4d3d6bc108f3 h1:9JqYzxhzIQhPqe5MIq2leJNARrs7VPNgL2o3qwmlgqA= -github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225143216-4d3d6bc108f3/go.mod h1:MwFrCmflxvLTMjgtnPJ2H4SQSB/r9wX8nsR5YPtUs7M= +github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225145501-66410517c85f h1:x+W67M2KMNCumzQ8XpIFXbVE+quKD/xP5PiaJhKwqTY= +github.com/bluenviron/gortsplib/v4 v4.12.1-0.20241225145501-66410517c85f/go.mod h1:MwFrCmflxvLTMjgtnPJ2H4SQSB/r9wX8nsR5YPtUs7M= github.com/bluenviron/mediacommon v1.13.2 h1:Ssq+59ZtPm5f9iAVVugWNOyl89Vp0G758RMv033lkik= github.com/bluenviron/mediacommon v1.13.2/go.mod h1:tffg+sPMErUIe7WMq7ZlYry/rPE6TyENWCrYT5JWcgs= github.com/bwesterb/go-ristretto v1.2.3/go.mod h1:fUIoIZaG73pV5biE2Blr2xEzDoMj7NFEuV9ekS419A0= diff --git a/internal/core/api_test.go b/internal/core/api_test.go index 56f54ca3..a7d21434 100644 --- a/internal/core/api_test.go +++ b/internal/core/api_test.go @@ -602,6 +602,7 @@ func TestAPIProtocolListGet(t *testing.T) { "created": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["created"], "id": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["id"], "remoteAddr": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["remoteAddr"], + "session": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["session"], }, }, }, out1) @@ -644,6 +645,7 @@ func TestAPIProtocolListGet(t *testing.T) { "created": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["created"], "id": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["id"], "remoteAddr": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["remoteAddr"], + "session": out1.(map[string]interface{})["items"].([]interface{})[0].(map[string]interface{})["session"], }, }, }, out1) diff --git a/internal/defs/api.go b/internal/defs/api.go index a8272634..9b3ae361 100644 --- a/internal/defs/api.go +++ b/internal/defs/api.go @@ -92,11 +92,12 @@ type APIRTMPConnList struct { // APIRTSPConn is a RTSP connection. type APIRTSPConn struct { - ID uuid.UUID `json:"id"` - Created time.Time `json:"created"` - RemoteAddr string `json:"remoteAddr"` - BytesReceived uint64 `json:"bytesReceived"` - BytesSent uint64 `json:"bytesSent"` + ID uuid.UUID `json:"id"` + Created time.Time `json:"created"` + RemoteAddr string `json:"remoteAddr"` + BytesReceived uint64 `json:"bytesReceived"` + BytesSent uint64 `json:"bytesSent"` + Session *uuid.UUID `json:"session"` } // APIRTSPConnsList is a list of RTSP connections. diff --git a/internal/servers/rtsp/conn.go b/internal/servers/rtsp/conn.go index ff345c80..290c3430 100644 --- a/internal/servers/rtsp/conn.go +++ b/internal/servers/rtsp/conn.go @@ -23,6 +23,11 @@ const ( rtspAuthRealm = "IPCAM" ) +type connParent interface { + logger.Writer + findSessionByRSession(rsession *gortsplib.ServerSession) *session +} + type conn struct { isTLS bool rtspAddress string @@ -35,7 +40,7 @@ type conn struct { pathManager serverPathManager rconn *gortsplib.ServerConn rserver *gortsplib.Server - parent *Server + parent connParent uuid uuid.UUID created time.Time @@ -216,5 +221,12 @@ func (c *conn) apiItem() *defs.APIRTSPConn { RemoteAddr: c.remoteAddr().String(), BytesReceived: stats.BytesReceived, BytesSent: stats.BytesSent, + Session: func() *uuid.UUID { + sx := c.parent.findSessionByRSession(c.rconn.Session()) + if sx != nil { + return &sx.uuid + } + return nil + }(), } } diff --git a/internal/servers/rtsp/server.go b/internal/servers/rtsp/server.go index a36ce12b..0c22dfeb 100644 --- a/internal/servers/rtsp/server.go +++ b/internal/servers/rtsp/server.go @@ -337,6 +337,13 @@ func (s *Server) findSessionByUUID(uuid uuid.UUID) (*gortsplib.ServerSession, *s return nil, nil } +func (s *Server) findSessionByRSession(rsession *gortsplib.ServerSession) *session { + s.mutex.RLock() + defer s.mutex.RUnlock() + + return s.sessions[rsession] +} + // APIConnsList is called by api and metrics. func (s *Server) APIConnsList() (*defs.APIRTSPConnsList, error) { select { diff --git a/internal/servers/rtsp/session.go b/internal/servers/rtsp/session.go index c1ee6415..eb9a49ee 100644 --- a/internal/servers/rtsp/session.go +++ b/internal/servers/rtsp/session.go @@ -31,7 +31,7 @@ type session struct { rserver *gortsplib.Server externalCmdPool *externalcmd.Pool pathManager serverPathManager - parent *Server + parent logger.Writer uuid uuid.UUID created time.Time