mirror of https://github.com/authelia/authelia.git
394 lines
8.4 KiB
Go
394 lines
8.4 KiB
Go
package model
|
|
|
|
import (
|
|
"fmt"
|
|
"testing"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
)
|
|
|
|
func TestAuthorization_Parse(t *testing.T) {
|
|
testCases := []struct {
|
|
name string
|
|
have string
|
|
expected string
|
|
expectedsr string
|
|
scheme AuthorizationScheme
|
|
value string
|
|
username string
|
|
password string
|
|
err string
|
|
}{
|
|
{
|
|
"ShouldParseBearer",
|
|
"Bearer abc123",
|
|
"Bearer abc123",
|
|
"Bearer",
|
|
AuthorizationSchemeBearer,
|
|
"abc123",
|
|
"",
|
|
"",
|
|
"",
|
|
},
|
|
{
|
|
"ShouldParseBearerAnyCase",
|
|
"BeareR abc123",
|
|
"Bearer abc123",
|
|
"BeareR",
|
|
AuthorizationSchemeBearer,
|
|
"abc123",
|
|
"",
|
|
"",
|
|
"",
|
|
},
|
|
{
|
|
"ShouldFailParseBearerNoScheme",
|
|
"Bearer",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid scheme: the scheme is missing",
|
|
},
|
|
{
|
|
"ShouldFailParseBearerEmpty",
|
|
"Bearer ",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: bearer scheme value must not be empty",
|
|
},
|
|
{
|
|
"ShouldFailParseBearerWithBadValues",
|
|
"Bearer !(@)#&!@$&(^T)*@#&^!",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: bearer scheme value must only contain characters noted in RFC6750 2.1",
|
|
},
|
|
{
|
|
"ShouldParseBasic",
|
|
"Basic YWJjOjEyMw==",
|
|
"Basic YWJjOjEyMw==",
|
|
"Basic",
|
|
AuthorizationSchemeBasic,
|
|
"YWJjOjEyMw==",
|
|
"abc",
|
|
"123",
|
|
"",
|
|
},
|
|
{
|
|
"ShouldFailParseBasicNoUsername",
|
|
"Basic OjEyMw==",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: failed to find the username in the decoded basic value as it was empty",
|
|
},
|
|
{
|
|
"ShouldFailParseBasicNoPassword",
|
|
"Basic YWJjOg==",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: failed to find the password in the decoded basic value as it was empty",
|
|
},
|
|
{
|
|
"ShouldFailParseBasicNoSep",
|
|
"Basic YWJjMTIz",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: failed to find the username password separator in the decoded basic scheme value",
|
|
},
|
|
{
|
|
"ShouldFailParseBasicBadBase64",
|
|
"Basic ===YWJjMTIz",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: failed to parse base64 basic scheme value: illegal base64 data at input byte 0",
|
|
},
|
|
{
|
|
"ShouldFailParseBadScheme",
|
|
"Baser YWJjOjEyMw==",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid scheme: scheme with name 'baser' is unknown",
|
|
},
|
|
{
|
|
"ShouldFailParseEmpty",
|
|
"",
|
|
"",
|
|
"",
|
|
AuthorizationSchemeNone,
|
|
"",
|
|
"",
|
|
"",
|
|
"invalid value: the value provided to be parsed was empty",
|
|
},
|
|
}
|
|
|
|
for _, tc := range testCases {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
|
|
err := authz.Parse(tc.have)
|
|
|
|
if len(tc.err) == 0 {
|
|
assert.NoError(t, err)
|
|
assert.Equal(t, tc.scheme, authz.Scheme())
|
|
assert.Equal(t, tc.expectedsr, authz.SchemeRaw())
|
|
assert.Equal(t, tc.password, authz.password)
|
|
assert.Equal(t, tc.username, authz.username)
|
|
assert.Equal(t, tc.expected, authz.EncodeHeader())
|
|
|
|
assert.EqualError(t, authz.Parse(tc.have), "invalid state: this scheme has already performed a parse action")
|
|
|
|
bauthz := NewAuthorization()
|
|
|
|
assert.NoError(t, bauthz.ParseBytes([]byte(tc.have)))
|
|
} else {
|
|
assert.EqualError(t, err, tc.err)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestAuthorization_ParsBasic(t *testing.T) {
|
|
testCases := []struct {
|
|
name string
|
|
username string
|
|
password string
|
|
expected string
|
|
err string
|
|
}{
|
|
{
|
|
"ShouldParseGoodValues",
|
|
"abc",
|
|
"123",
|
|
"YWJjOjEyMw==",
|
|
"",
|
|
},
|
|
{
|
|
"ShouldFailUsernameWithColon",
|
|
"abc:abc",
|
|
"123",
|
|
"",
|
|
"invalid value: username must not contain the ':' character",
|
|
},
|
|
{
|
|
"ShouldFailUsernameEmpty",
|
|
"",
|
|
"123",
|
|
"",
|
|
"invalid value: username must not be empty",
|
|
},
|
|
{
|
|
"ShouldFailPasswordEmpty",
|
|
"abc",
|
|
"",
|
|
"",
|
|
"invalid value: password must not be empty",
|
|
},
|
|
}
|
|
|
|
for _, tc := range testCases {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
|
|
err := authz.ParseBasic(tc.username, tc.password)
|
|
|
|
if len(tc.err) == 0 {
|
|
assert.NoError(t, err)
|
|
|
|
assert.Equal(t, AuthorizationSchemeBasic, authz.Scheme())
|
|
assert.Equal(t, fmt.Sprintf("Basic %s", tc.expected), authz.EncodeHeader())
|
|
assert.Equal(t, tc.expected, authz.value)
|
|
assert.Equal(t, tc.expected, authz.Value())
|
|
assert.Equal(t, tc.username, authz.username)
|
|
assert.Equal(t, tc.username, authz.BasicUsername())
|
|
assert.Equal(t, tc.password, authz.password)
|
|
|
|
username, password := authz.Basic()
|
|
|
|
assert.Equal(t, tc.username, username)
|
|
assert.Equal(t, tc.password, password)
|
|
|
|
assert.EqualError(t, authz.ParseBasic(tc.username, tc.password), "invalid state: this scheme has already performed a parse action")
|
|
} else {
|
|
assert.EqualError(t, err, tc.err)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestAuthorization_ParsBearer(t *testing.T) {
|
|
testCases := []struct {
|
|
name string
|
|
bearer string
|
|
expected string
|
|
err string
|
|
}{
|
|
{
|
|
"ShouldParseGoodValues",
|
|
"abc",
|
|
"abc",
|
|
"",
|
|
},
|
|
{
|
|
"ShouldFailParseBadBearerValue",
|
|
"abc!(*@^&(!@*^$",
|
|
"",
|
|
"invalid value: bearer scheme value must only contain characters noted in RFC6750 2.1",
|
|
},
|
|
{
|
|
"ShouldFailParseEmptyBearerValue",
|
|
"",
|
|
"",
|
|
"invalid value: bearer scheme value must not be empty",
|
|
},
|
|
}
|
|
|
|
for _, tc := range testCases {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
|
|
err := authz.ParseBearer(tc.bearer)
|
|
|
|
if len(tc.err) == 0 {
|
|
assert.NoError(t, err)
|
|
|
|
assert.Equal(t, AuthorizationSchemeBearer, authz.Scheme())
|
|
assert.Equal(t, fmt.Sprintf("Bearer %s", tc.expected), authz.EncodeHeader())
|
|
assert.Equal(t, tc.expected, authz.value)
|
|
assert.Equal(t, tc.expected, authz.Value())
|
|
|
|
username, password := authz.Basic()
|
|
assert.Equal(t, "", authz.BasicUsername())
|
|
assert.Equal(t, "", username)
|
|
assert.Equal(t, "", password)
|
|
|
|
assert.EqualError(t, authz.ParseBearer(tc.bearer), "invalid state: this scheme has already performed a parse action")
|
|
} else {
|
|
assert.EqualError(t, err, tc.err)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestAuthorization_NotParsed(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
|
|
assert.Equal(t, "", authz.EncodeHeader())
|
|
assert.Equal(t, "", authz.BasicUsername())
|
|
|
|
username, password := authz.Basic()
|
|
assert.Equal(t, "", username)
|
|
assert.Equal(t, "", password)
|
|
}
|
|
|
|
func TestAuthorization_SchemeNone(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
authz.parsed = true
|
|
|
|
assert.Equal(t, "", authz.EncodeHeader())
|
|
assert.Equal(t, "", authz.BasicUsername())
|
|
|
|
username, password := authz.Basic()
|
|
assert.Equal(t, "", username)
|
|
assert.Equal(t, "", password)
|
|
}
|
|
|
|
func TestAuthorization_Misc(t *testing.T) {
|
|
authz := NewAuthorization()
|
|
authz.parsed = true
|
|
authz.scheme = -1
|
|
|
|
assert.Equal(t, "", authz.EncodeHeader())
|
|
|
|
assert.Equal(t, "", AuthorizationScheme(-1).String())
|
|
}
|
|
|
|
func TestNewAuthorizationSchemes(t *testing.T) {
|
|
testCases := []struct {
|
|
name string
|
|
have []string
|
|
expected AuthorizationSchemes
|
|
expectedf func(t *testing.T, schemes AuthorizationSchemes)
|
|
}{
|
|
{
|
|
"ShouldParseEmpty",
|
|
nil,
|
|
nil,
|
|
nil,
|
|
},
|
|
{
|
|
"ShouldParseBasic",
|
|
[]string{"BaSiC"},
|
|
AuthorizationSchemes{AuthorizationSchemeBasic},
|
|
func(t *testing.T, schemes AuthorizationSchemes) {
|
|
assert.False(t, schemes.Has(AuthorizationSchemeNone))
|
|
assert.True(t, schemes.Has(AuthorizationSchemeBasic))
|
|
assert.False(t, schemes.Has(AuthorizationSchemeBearer))
|
|
},
|
|
},
|
|
{
|
|
"ShouldParseBearer",
|
|
[]string{"Bearer"},
|
|
AuthorizationSchemes{AuthorizationSchemeBearer},
|
|
func(t *testing.T, schemes AuthorizationSchemes) {
|
|
assert.False(t, schemes.Has(AuthorizationSchemeNone))
|
|
assert.False(t, schemes.Has(AuthorizationSchemeBasic))
|
|
assert.True(t, schemes.Has(AuthorizationSchemeBearer))
|
|
},
|
|
},
|
|
{
|
|
"ShouldParseBoth",
|
|
[]string{"Bearer", "Basic"},
|
|
AuthorizationSchemes{AuthorizationSchemeBearer, AuthorizationSchemeBasic},
|
|
func(t *testing.T, schemes AuthorizationSchemes) {
|
|
assert.False(t, schemes.Has(AuthorizationSchemeNone))
|
|
assert.True(t, schemes.Has(AuthorizationSchemeBasic))
|
|
assert.True(t, schemes.Has(AuthorizationSchemeBearer))
|
|
},
|
|
},
|
|
}
|
|
|
|
for _, tc := range testCases {
|
|
t.Run(tc.name, func(t *testing.T) {
|
|
actual := NewAuthorizationSchemes(tc.have...)
|
|
|
|
assert.Equal(t, tc.expected, actual)
|
|
|
|
if tc.expectedf != nil {
|
|
tc.expectedf(t, actual)
|
|
}
|
|
})
|
|
}
|
|
}
|