add authJWTExclude to exclude actions when using JWT (#3431)

* Added authJWTExclude to allow exclusion of actions while using the JWT authentication method

* add test

---------

Co-authored-by: aler9 <46489434+aler9@users.noreply.github.com>
This commit is contained in:
Dimitri Marechal
2025-04-25 19:55:11 +02:00
committed by GitHub
parent d8e6be6fe8
commit 1827e062bd
5 changed files with 34 additions and 0 deletions

View File

@@ -106,6 +106,7 @@ type Manager struct {
HTTPExclude []conf.AuthInternalUserPermission
JWTJWKS string
JWTClaimKey string
JWTExclude []conf.AuthInternalUserPermission
ReadTimeout time.Duration
mutex sync.RWMutex
@@ -229,6 +230,10 @@ func (m *Manager) authenticateHTTP(req *Request) error {
}
func (m *Manager) authenticateJWT(req *Request) error {
if matchesPermission(m.JWTExclude, req) {
return nil
}
keyfunc, err := m.pullJWTJWKS()
if err != nil {
return err

View File

@@ -412,3 +412,25 @@ func TestAuthJWT(t *testing.T) {
})
}
}
func TestAuthJWTExclude(t *testing.T) {
m := Manager{
Method: conf.AuthMethodJWT,
JWTJWKS: "http://localhost:4567/jwks",
JWTClaimKey: "my_permission_key",
JWTExclude: []conf.AuthInternalUserPermission{{
Action: conf.AuthActionPublish,
}},
}
err := m.Authenticate(&Request{
User: "",
Pass: "",
IP: net.ParseIP("127.0.0.1"),
Action: conf.AuthActionPublish,
Path: "teststream",
Protocol: ProtocolRTSP,
Query: "param=value",
})
require.NoError(t, err)
}

View File

@@ -179,6 +179,7 @@ type Conf struct {
AuthHTTPExclude AuthInternalUserPermissions `json:"authHTTPExclude"`
AuthJWTJWKS string `json:"authJWTJWKS"`
AuthJWTClaimKey string `json:"authJWTClaimKey"`
AuthJWTExclude AuthInternalUserPermissions `json:"authJWTExclude"`
// Control API
API bool `json:"api"`
@@ -332,6 +333,7 @@ func (conf *Conf) setDefaults() {
},
}
conf.AuthJWTClaimKey = "mediamtx_permissions"
conf.AuthJWTExclude = []AuthInternalUserPermission{}
// Control API
conf.APIAddress = ":9997"

View File

@@ -275,6 +275,7 @@ func (p *Core) createResources(initial bool) error {
HTTPExclude: p.conf.AuthHTTPExclude,
JWTJWKS: p.conf.AuthJWTJWKS,
JWTClaimKey: p.conf.AuthJWTClaimKey,
JWTExclude: p.conf.AuthJWTExclude,
ReadTimeout: time.Duration(p.conf.ReadTimeout),
}
}
@@ -659,6 +660,7 @@ func (p *Core) closeResources(newConf *conf.Conf, calledByAPI bool) {
!reflect.DeepEqual(newConf.AuthHTTPExclude, p.conf.AuthHTTPExclude) ||
newConf.AuthJWTJWKS != p.conf.AuthJWTJWKS ||
newConf.AuthJWTClaimKey != p.conf.AuthJWTClaimKey ||
!reflect.DeepEqual(newConf.AuthJWTExclude, p.conf.AuthJWTExclude) ||
newConf.ReadTimeout != p.conf.ReadTimeout
if !closeAuthManager && !reflect.DeepEqual(newConf.AuthInternalUsers, p.conf.AuthInternalUsers) {
p.authManager.ReloadInternalUsers(newConf.AuthInternalUsers)

View File

@@ -125,6 +125,9 @@ authHTTPExclude:
authJWTJWKS:
# name of the claim that contains permissions.
authJWTClaimKey: mediamtx_permissions
# Actions to exclude from JWT-based authentication.
# Format is the same as the one of user permissions.
authJWTExclude: []
###############################################
# Global settings -> Control API