mirror of
https://github.com/datarhei/core.git
synced 2025-10-05 16:07:07 +08:00
Get rid of $localhost pseudo user
This commit is contained in:
@@ -444,27 +444,11 @@ func (a *api) start() error {
|
|||||||
// Create default policies for anonymous users in order to mimic the behaviour before IAM
|
// Create default policies for anonymous users in order to mimic the behaviour before IAM
|
||||||
|
|
||||||
iam.RemovePolicy("$anon", "$none", "", nil)
|
iam.RemovePolicy("$anon", "$none", "", nil)
|
||||||
iam.RemovePolicy("$localhost", "$none", "", nil)
|
|
||||||
|
|
||||||
iam.AddPolicy("$anon", "$none", "fs:/**", []string{"GET", "HEAD", "OPTIONS"})
|
iam.AddPolicy("$anon", "$none", "fs:/**", []string{"GET", "HEAD", "OPTIONS"})
|
||||||
iam.AddPolicy("$anon", "$none", "api:/api", []string{"GET", "HEAD", "OPTIONS"})
|
iam.AddPolicy("$anon", "$none", "api:/api", []string{"GET", "HEAD", "OPTIONS"})
|
||||||
iam.AddPolicy("$anon", "$none", "api:/api/v3/widget/process/**", []string{"GET", "HEAD", "OPTIONS"})
|
iam.AddPolicy("$anon", "$none", "api:/api/v3/widget/process/**", []string{"GET", "HEAD", "OPTIONS"})
|
||||||
|
|
||||||
if !cfg.API.Auth.Enable {
|
|
||||||
iam.AddPolicy("$anon", "$none", "api:/api/**", []string{"ANY"})
|
|
||||||
iam.AddPolicy("$anon", "$none", "process:*", []string{"ANY"})
|
|
||||||
iam.AddPolicy("$anon", "$none", "iam:*", []string{"ANY"})
|
|
||||||
} else {
|
|
||||||
if cfg.API.Auth.DisableLocalhost {
|
|
||||||
iam.AddPolicy("$localhost", "$none", "api:/api", []string{"GET", "HEAD", "OPTIONS"})
|
|
||||||
iam.AddPolicy("$localhost", "$none", "api:/api/v3/widget/process/**", []string{"GET", "HEAD", "OPTIONS"})
|
|
||||||
|
|
||||||
iam.AddPolicy("$localhost", "$none", "api:/api/**", []string{"ANY"})
|
|
||||||
iam.AddPolicy("$localhost", "$none", "process:*", []string{"ANY"})
|
|
||||||
iam.AddPolicy("$localhost", "$none", "iam:*", []string{"ANY"})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if !cfg.Storage.Memory.Auth.Enable {
|
if !cfg.Storage.Memory.Auth.Enable {
|
||||||
iam.AddPolicy("$anon", "$none", "fs:/memfs/**", []string{"ANY"})
|
iam.AddPolicy("$anon", "$none", "fs:/memfs/**", []string{"ANY"})
|
||||||
}
|
}
|
||||||
@@ -671,7 +655,7 @@ func (a *api) start() error {
|
|||||||
var identity iam.IdentityVerifier = nil
|
var identity iam.IdentityVerifier = nil
|
||||||
|
|
||||||
if len(config.Owner) == 0 {
|
if len(config.Owner) == 0 {
|
||||||
identity, _ = a.iam.GetDefaultVerifier()
|
identity = a.iam.GetDefaultVerifier()
|
||||||
} else {
|
} else {
|
||||||
identity, _ = a.iam.GetVerifier(config.Owner)
|
identity, _ = a.iam.GetVerifier(config.Owner)
|
||||||
}
|
}
|
||||||
@@ -697,7 +681,7 @@ func (a *api) start() error {
|
|||||||
var identity iam.IdentityVerifier = nil
|
var identity iam.IdentityVerifier = nil
|
||||||
|
|
||||||
if len(config.Owner) == 0 {
|
if len(config.Owner) == 0 {
|
||||||
identity, _ = a.iam.GetDefaultVerifier()
|
identity = a.iam.GetDefaultVerifier()
|
||||||
} else {
|
} else {
|
||||||
identity, _ = a.iam.GetVerifier(config.Owner)
|
identity, _ = a.iam.GetVerifier(config.Owner)
|
||||||
}
|
}
|
||||||
@@ -1117,14 +1101,29 @@ func (a *api) start() error {
|
|||||||
Cors: http.CorsConfig{
|
Cors: http.CorsConfig{
|
||||||
Origins: cfg.Storage.CORS.Origins,
|
Origins: cfg.Storage.CORS.Origins,
|
||||||
},
|
},
|
||||||
RTMP: a.rtmpserver,
|
RTMP: a.rtmpserver,
|
||||||
SRT: a.srtserver,
|
SRT: a.srtserver,
|
||||||
Config: a.config.store,
|
Config: a.config.store,
|
||||||
Sessions: a.sessions,
|
Sessions: a.sessions,
|
||||||
Router: router,
|
Router: router,
|
||||||
ReadOnly: cfg.API.ReadOnly,
|
ReadOnly: cfg.API.ReadOnly,
|
||||||
IAM: a.iam,
|
IAM: a.iam,
|
||||||
IAMDisableLocalhost: cfg.API.Auth.Enable && cfg.API.Auth.DisableLocalhost,
|
IAMSkipper: func(ip string) bool {
|
||||||
|
if !cfg.API.Auth.Enable {
|
||||||
|
return true
|
||||||
|
} else {
|
||||||
|
isLocalhost := false
|
||||||
|
if ip == "127.0.0.1" || ip == "::1" {
|
||||||
|
isLocalhost = true
|
||||||
|
}
|
||||||
|
|
||||||
|
if isLocalhost && cfg.API.Auth.DisableLocalhost {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false
|
||||||
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
mainserverhandler, err := http.NewServer(serverConfig)
|
mainserverhandler, err := http.NewServer(serverConfig)
|
||||||
|
@@ -17,9 +17,8 @@
|
|||||||
// only allow JWT as authentication method.
|
// only allow JWT as authentication method.
|
||||||
//
|
//
|
||||||
// If the identity can't be detected, the identity of "$anon" is given, representing
|
// If the identity can't be detected, the identity of "$anon" is given, representing
|
||||||
// an anonmyous user. If the request originates from localhost and DisableLocalhost
|
// an anonmyous user. If the Skipper function returns true for the request and the
|
||||||
// is configured, the identity will be $localhost, representing an anonymous user from
|
// API is accessed, the username will be the one of the IAM superuser.
|
||||||
// localhost.
|
|
||||||
//
|
//
|
||||||
// The domain is provided as query parameter "group" for all API requests or the
|
// The domain is provided as query parameter "group" for all API requests or the
|
||||||
// first path element after a mountpoint for filesystem requests.
|
// first path element after a mountpoint for filesystem requests.
|
||||||
@@ -57,7 +56,6 @@ type Config struct {
|
|||||||
Skipper middleware.Skipper
|
Skipper middleware.Skipper
|
||||||
Mounts []string
|
Mounts []string
|
||||||
IAM iam.IAM
|
IAM iam.IAM
|
||||||
DisableLocalhost bool
|
|
||||||
WaitAfterFailedLogin bool
|
WaitAfterFailedLogin bool
|
||||||
Logger log.Logger
|
Logger log.Logger
|
||||||
}
|
}
|
||||||
@@ -66,7 +64,6 @@ var DefaultConfig = Config{
|
|||||||
Skipper: middleware.DefaultSkipper,
|
Skipper: middleware.DefaultSkipper,
|
||||||
Mounts: []string{},
|
Mounts: []string{},
|
||||||
IAM: nil,
|
IAM: nil,
|
||||||
DisableLocalhost: false,
|
|
||||||
WaitAfterFailedLogin: false,
|
WaitAfterFailedLogin: false,
|
||||||
Logger: nil,
|
Logger: nil,
|
||||||
}
|
}
|
||||||
@@ -111,15 +108,15 @@ func NewWithConfig(config Config) echo.MiddlewareFunc {
|
|||||||
|
|
||||||
return func(next echo.HandlerFunc) echo.HandlerFunc {
|
return func(next echo.HandlerFunc) echo.HandlerFunc {
|
||||||
return func(c echo.Context) error {
|
return func(c echo.Context) error {
|
||||||
if config.Skipper(c) {
|
|
||||||
c.Set("user", "$anon")
|
|
||||||
return next(c)
|
|
||||||
}
|
|
||||||
|
|
||||||
if config.IAM == nil {
|
if config.IAM == nil {
|
||||||
return api.Err(http.StatusForbidden, "Forbidden", "IAM is not provided")
|
return api.Err(http.StatusForbidden, "Forbidden", "IAM is not provided")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
isAPISuperuser := false
|
||||||
|
if config.Skipper(c) {
|
||||||
|
isAPISuperuser = true
|
||||||
|
}
|
||||||
|
|
||||||
var identity iam.IdentityVerifier = nil
|
var identity iam.IdentityVerifier = nil
|
||||||
var err error
|
var err error
|
||||||
|
|
||||||
@@ -173,11 +170,8 @@ func NewWithConfig(config Config) echo.MiddlewareFunc {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if config.DisableLocalhost {
|
if isAPISuperuser {
|
||||||
ip := c.RealIP()
|
username = config.IAM.GetDefaultVerifier().Name()
|
||||||
if ip == "127.0.0.1" || ip == "::1" {
|
|
||||||
username = "$localhost"
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
domain = c.QueryParam("group")
|
domain = c.QueryParam("group")
|
||||||
|
@@ -75,25 +75,25 @@ import (
|
|||||||
var ListenAndServe = http.ListenAndServe
|
var ListenAndServe = http.ListenAndServe
|
||||||
|
|
||||||
type Config struct {
|
type Config struct {
|
||||||
Logger log.Logger
|
Logger log.Logger
|
||||||
LogBuffer log.BufferWriter
|
LogBuffer log.BufferWriter
|
||||||
Restream restream.Restreamer
|
Restream restream.Restreamer
|
||||||
Metrics monitor.HistoryReader
|
Metrics monitor.HistoryReader
|
||||||
Prometheus prometheus.Reader
|
Prometheus prometheus.Reader
|
||||||
MimeTypesFile string
|
MimeTypesFile string
|
||||||
Filesystems []fs.FS
|
Filesystems []fs.FS
|
||||||
IPLimiter net.IPLimiter
|
IPLimiter net.IPLimiter
|
||||||
Profiling bool
|
Profiling bool
|
||||||
Cors CorsConfig
|
Cors CorsConfig
|
||||||
RTMP rtmp.Server
|
RTMP rtmp.Server
|
||||||
SRT srt.Server
|
SRT srt.Server
|
||||||
Config cfgstore.Store
|
Config cfgstore.Store
|
||||||
Cache cache.Cacher
|
Cache cache.Cacher
|
||||||
Sessions session.RegistryReader
|
Sessions session.RegistryReader
|
||||||
Router router.Router
|
Router router.Router
|
||||||
ReadOnly bool
|
ReadOnly bool
|
||||||
IAM iam.IAM
|
IAM iam.IAM
|
||||||
IAMDisableLocalhost bool
|
IAMSkipper func(ip string) bool
|
||||||
}
|
}
|
||||||
|
|
||||||
type CorsConfig struct {
|
type CorsConfig struct {
|
||||||
@@ -132,8 +132,6 @@ type server struct {
|
|||||||
middleware struct {
|
middleware struct {
|
||||||
iplimit echo.MiddlewareFunc
|
iplimit echo.MiddlewareFunc
|
||||||
log echo.MiddlewareFunc
|
log echo.MiddlewareFunc
|
||||||
accessJWT echo.MiddlewareFunc
|
|
||||||
refreshJWT echo.MiddlewareFunc
|
|
||||||
cors echo.MiddlewareFunc
|
cors echo.MiddlewareFunc
|
||||||
cache echo.MiddlewareFunc
|
cache echo.MiddlewareFunc
|
||||||
session echo.MiddlewareFunc
|
session echo.MiddlewareFunc
|
||||||
@@ -223,9 +221,11 @@ func NewServer(config Config) (Server, error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
s.middleware.iam = mwiam.NewWithConfig(mwiam.Config{
|
s.middleware.iam = mwiam.NewWithConfig(mwiam.Config{
|
||||||
|
Skipper: func(c echo.Context) bool {
|
||||||
|
return config.IAMSkipper(c.RealIP())
|
||||||
|
},
|
||||||
IAM: config.IAM,
|
IAM: config.IAM,
|
||||||
Mounts: mounts,
|
Mounts: mounts,
|
||||||
DisableLocalhost: config.IAMDisableLocalhost,
|
|
||||||
WaitAfterFailedLogin: true,
|
WaitAfterFailedLogin: true,
|
||||||
Logger: s.logger.WithComponent("IAM"),
|
Logger: s.logger.WithComponent("IAM"),
|
||||||
})
|
})
|
||||||
|
16
iam/iam.go
16
iam/iam.go
@@ -28,7 +28,7 @@ type IAM interface {
|
|||||||
|
|
||||||
GetVerifier(name string) (IdentityVerifier, error)
|
GetVerifier(name string) (IdentityVerifier, error)
|
||||||
GetVerfierFromAuth0(name string) (IdentityVerifier, error)
|
GetVerfierFromAuth0(name string) (IdentityVerifier, error)
|
||||||
GetDefaultVerifier() (IdentityVerifier, error)
|
GetDefaultVerifier() IdentityVerifier
|
||||||
|
|
||||||
CreateJWT(name string) (string, string, error)
|
CreateJWT(name string) (string, string, error)
|
||||||
|
|
||||||
@@ -107,10 +107,6 @@ func (i *iam) Enforce(name, domain, resource, action string) bool {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//if name == "$localhost" {
|
|
||||||
// superuser = true
|
|
||||||
//}
|
|
||||||
|
|
||||||
l := i.logger.Debug().WithFields(log.Fields{
|
l := i.logger.Debug().WithFields(log.Fields{
|
||||||
"subject": name,
|
"subject": name,
|
||||||
"domain": domain,
|
"domain": domain,
|
||||||
@@ -128,6 +124,10 @@ func (i *iam) Enforce(name, domain, resource, action string) bool {
|
|||||||
if !ok {
|
if !ok {
|
||||||
l.Log("no match")
|
l.Log("no match")
|
||||||
} else {
|
} else {
|
||||||
|
if name == "$superuser" {
|
||||||
|
rule = ""
|
||||||
|
}
|
||||||
|
|
||||||
l.WithField("rule", rule).Log("match")
|
l.WithField("rule", rule).Log("match")
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -166,8 +166,10 @@ func (i *iam) GetVerfierFromAuth0(name string) (IdentityVerifier, error) {
|
|||||||
return i.im.GetVerifierFromAuth0(name)
|
return i.im.GetVerifierFromAuth0(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i *iam) GetDefaultVerifier() (IdentityVerifier, error) {
|
func (i *iam) GetDefaultVerifier() IdentityVerifier {
|
||||||
return i.im.GetDefaultVerifier()
|
v, _ := i.im.GetDefaultVerifier()
|
||||||
|
|
||||||
|
return v
|
||||||
}
|
}
|
||||||
|
|
||||||
func (i *iam) CreateJWT(name string) (string, string, error) {
|
func (i *iam) CreateJWT(name string) (string, string, error) {
|
||||||
|
@@ -424,12 +424,7 @@ func (r *restream) enforce(name, group, processid, action string) bool {
|
|||||||
if len(name) == 0 {
|
if len(name) == 0 {
|
||||||
// This is for backwards compatibility. Existing processes don't have an owner.
|
// This is for backwards compatibility. Existing processes don't have an owner.
|
||||||
// All processes that will be added later will have an owner ($anon, ...).
|
// All processes that will be added later will have an owner ($anon, ...).
|
||||||
identity, err := r.iam.GetDefaultVerifier()
|
name = r.iam.GetDefaultVerifier().Name()
|
||||||
if err != nil {
|
|
||||||
name = "$anon"
|
|
||||||
} else {
|
|
||||||
name = identity.Name()
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(group) == 0 {
|
if len(group) == 0 {
|
||||||
|
@@ -428,7 +428,7 @@ func (s *server) findIdentityFromStreamKey(key string) (string, error) {
|
|||||||
|
|
||||||
elements := strings.Split(key, ":")
|
elements := strings.Split(key, ":")
|
||||||
if len(elements) == 1 {
|
if len(elements) == 1 {
|
||||||
identity, err = s.iam.GetDefaultVerifier()
|
identity = s.iam.GetDefaultVerifier()
|
||||||
token = elements[0]
|
token = elements[0]
|
||||||
} else {
|
} else {
|
||||||
identity, err = s.iam.GetVerifier(elements[0])
|
identity, err = s.iam.GetVerifier(elements[0])
|
||||||
|
@@ -387,7 +387,7 @@ func (s *server) findIdentityFromToken(key string) (string, error) {
|
|||||||
|
|
||||||
elements := strings.Split(key, ":")
|
elements := strings.Split(key, ":")
|
||||||
if len(elements) == 1 {
|
if len(elements) == 1 {
|
||||||
identity, err = s.iam.GetDefaultVerifier()
|
identity = s.iam.GetDefaultVerifier()
|
||||||
token = elements[0]
|
token = elements[0]
|
||||||
} else {
|
} else {
|
||||||
identity, err = s.iam.GetVerifier(elements[0])
|
identity, err = s.iam.GetVerifier(elements[0])
|
||||||
|
Reference in New Issue
Block a user