chore: allow case insensitive bearer
This commit is contained in:
parent
246e33d565
commit
6bd8c1e838
|
|
@ -9,7 +9,7 @@ import (
|
||||||
log "github.com/sirupsen/logrus"
|
log "github.com/sirupsen/logrus"
|
||||||
)
|
)
|
||||||
|
|
||||||
const localBearerPrefix = "Bearer "
|
const localBearerScheme = "Bearer"
|
||||||
|
|
||||||
func constantTimeEqualString(a, b string) bool {
|
func constantTimeEqualString(a, b string) bool {
|
||||||
if len(a) != len(b) {
|
if len(a) != len(b) {
|
||||||
|
|
@ -20,11 +20,16 @@ func constantTimeEqualString(a, b string) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
func bearerTokenFromAuthorizationHeader(authz string) (string, bool) {
|
func bearerTokenFromAuthorizationHeader(authz string) (string, bool) {
|
||||||
if !strings.HasPrefix(authz, localBearerPrefix) {
|
idx := strings.IndexByte(authz, ' ')
|
||||||
|
if idx <= 0 {
|
||||||
return "", false
|
return "", false
|
||||||
}
|
}
|
||||||
|
|
||||||
token := strings.TrimSpace(strings.TrimPrefix(authz, localBearerPrefix))
|
if !strings.EqualFold(authz[:idx], localBearerScheme) {
|
||||||
|
return "", false
|
||||||
|
}
|
||||||
|
|
||||||
|
token := strings.TrimSpace(authz[idx+1:])
|
||||||
if token == "" {
|
if token == "" {
|
||||||
return "", false
|
return "", false
|
||||||
}
|
}
|
||||||
|
|
@ -50,12 +55,19 @@ func findLocalUserByAPIKey(cfg *config.Config, token string) *config.LocalUser {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func localBearerAuthorizationHasEmptyCredential(authz string) bool {
|
||||||
|
idx := strings.IndexByte(authz, ' ')
|
||||||
|
return idx > 0 &&
|
||||||
|
strings.EqualFold(authz[:idx], localBearerScheme) &&
|
||||||
|
strings.TrimSpace(authz[idx+1:]) == ""
|
||||||
|
}
|
||||||
|
|
||||||
func logLocalBearerAPIKeyParseFailure(authz string) {
|
func logLocalBearerAPIKeyParseFailure(authz string) {
|
||||||
if strings.TrimSpace(authz) == "" {
|
if strings.TrimSpace(authz) == "" {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if strings.HasPrefix(authz, localBearerPrefix) {
|
if localBearerAuthorizationHasEmptyCredential(authz) {
|
||||||
log.Debugf("Local bearer API key: rejected (empty credential after Bearer prefix)")
|
log.Debugf("Local bearer API key: rejected (empty credential after Bearer prefix)")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -10,6 +10,28 @@ import (
|
||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func TestCheckUserFromLocalBearerApiKey_Match_LowercaseBearerScheme(t *testing.T) {
|
||||||
|
t.Parallel()
|
||||||
|
|
||||||
|
cfg := config.DefaultConfig()
|
||||||
|
cfg.AuthLocalUsers.Enabled = true
|
||||||
|
cfg.AuthLocalUsers.Users = []*config.LocalUser{{
|
||||||
|
Username: "bot",
|
||||||
|
Usergroup: "bots",
|
||||||
|
ApiKey: "secret-api-key",
|
||||||
|
}}
|
||||||
|
|
||||||
|
req := httptest.NewRequest("POST", "/", nil)
|
||||||
|
req.Header.Set("Authorization", "bearer secret-api-key")
|
||||||
|
|
||||||
|
ctx := &authpublic.AuthCheckingContext{Request: req, Config: cfg}
|
||||||
|
user := checkUserFromLocalBearerApiKey(ctx)
|
||||||
|
require.NotNil(t, user)
|
||||||
|
assert.Equal(t, "bot", user.Username)
|
||||||
|
assert.Equal(t, "bots", user.UsergroupLine)
|
||||||
|
assert.Equal(t, "local", user.Provider)
|
||||||
|
}
|
||||||
|
|
||||||
func TestCheckUserFromLocalBearerApiKey_Match(t *testing.T) {
|
func TestCheckUserFromLocalBearerApiKey_Match(t *testing.T) {
|
||||||
t.Parallel()
|
t.Parallel()
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue