2019-12-10 13:51:09 +00:00
|
|
|
package openshift
|
|
|
|
|
|
|
|
import (
|
|
|
|
"context"
|
|
|
|
"encoding/json"
|
|
|
|
"fmt"
|
|
|
|
"net/http"
|
|
|
|
"net/http/httptest"
|
|
|
|
"net/url"
|
|
|
|
"reflect"
|
|
|
|
"testing"
|
2021-11-23 18:39:23 +00:00
|
|
|
"time"
|
2019-12-10 13:51:09 +00:00
|
|
|
|
|
|
|
"github.com/sirupsen/logrus"
|
2019-12-22 06:46:35 +00:00
|
|
|
"golang.org/x/oauth2"
|
2020-11-03 19:50:09 +00:00
|
|
|
|
|
|
|
"github.com/dexidp/dex/connector"
|
|
|
|
"github.com/dexidp/dex/storage/kubernetes/k8sapi"
|
2019-12-10 13:51:09 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
func TestOpen(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
hostURL, err := url.Parse(s.URL)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
_, err = http.NewRequest("GET", hostURL.String(), nil)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
c := Config{
|
|
|
|
Issuer: s.URL,
|
|
|
|
ClientID: "testClientId",
|
|
|
|
ClientSecret: "testClientSecret",
|
|
|
|
RedirectURI: "https://localhost/callback",
|
|
|
|
InsecureCA: true,
|
|
|
|
}
|
|
|
|
|
|
|
|
logger := logrus.New()
|
|
|
|
|
|
|
|
oconfig, err := c.Open("id", logger)
|
|
|
|
|
|
|
|
oc, ok := oconfig.(*openshiftConnector)
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
expectEquals(t, ok, true)
|
|
|
|
expectEquals(t, oc.apiURL, s.URL)
|
|
|
|
expectEquals(t, oc.clientID, "testClientId")
|
|
|
|
expectEquals(t, oc.clientSecret, "testClientSecret")
|
|
|
|
expectEquals(t, oc.redirectURI, "https://localhost/callback")
|
|
|
|
expectEquals(t, oc.oauth2Config.Endpoint.AuthURL, fmt.Sprintf("%s/oauth/authorize", s.URL))
|
|
|
|
expectEquals(t, oc.oauth2Config.Endpoint.TokenURL, fmt.Sprintf("%s/oauth/token", s.URL))
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestGetUser(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{
|
|
|
|
"/apis/user.openshift.io/v1/users/~": user{
|
|
|
|
ObjectMeta: k8sapi.ObjectMeta{
|
|
|
|
Name: "jdoe",
|
|
|
|
},
|
|
|
|
FullName: "John Doe",
|
|
|
|
Groups: []string{"users"},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
hostURL, err := url.Parse(s.URL)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
_, err = http.NewRequest("GET", hostURL.String(), nil)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
h, err := newHTTPClient(true, "")
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oc := openshiftConnector{apiURL: s.URL, httpClient: h}
|
|
|
|
u, err := oc.user(context.Background(), h)
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
expectEquals(t, u.Name, "jdoe")
|
|
|
|
expectEquals(t, u.FullName, "John Doe")
|
|
|
|
expectEquals(t, len(u.Groups), 1)
|
|
|
|
}
|
|
|
|
|
2019-12-27 02:32:12 +00:00
|
|
|
func TestVerifySingleGroupFn(t *testing.T) {
|
|
|
|
allowedGroups := []string{"users"}
|
2019-12-21 16:48:08 +00:00
|
|
|
groupMembership := []string{"users", "org1"}
|
2019-12-10 13:51:09 +00:00
|
|
|
|
2019-12-27 02:32:12 +00:00
|
|
|
validGroupMembership := validateAllowedGroups(groupMembership, allowedGroups)
|
|
|
|
|
|
|
|
expectEquals(t, validGroupMembership, true)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestVerifySingleGroupFailureFn(t *testing.T) {
|
|
|
|
allowedGroups := []string{"admins"}
|
|
|
|
groupMembership := []string{"users"}
|
|
|
|
|
|
|
|
validGroupMembership := validateAllowedGroups(groupMembership, allowedGroups)
|
|
|
|
|
|
|
|
expectEquals(t, validGroupMembership, false)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestVerifyMultipleGroupFn(t *testing.T) {
|
|
|
|
allowedGroups := []string{"users", "admins"}
|
|
|
|
groupMembership := []string{"users", "org1"}
|
|
|
|
|
|
|
|
validGroupMembership := validateAllowedGroups(groupMembership, allowedGroups)
|
2019-12-10 13:51:09 +00:00
|
|
|
|
|
|
|
expectEquals(t, validGroupMembership, true)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestVerifyGroup(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{
|
|
|
|
"/apis/user.openshift.io/v1/users/~": user{
|
|
|
|
ObjectMeta: k8sapi.ObjectMeta{
|
|
|
|
Name: "jdoe",
|
|
|
|
},
|
|
|
|
FullName: "John Doe",
|
|
|
|
Groups: []string{"users"},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
hostURL, err := url.Parse(s.URL)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
_, err = http.NewRequest("GET", hostURL.String(), nil)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
h, err := newHTTPClient(true, "")
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oc := openshiftConnector{apiURL: s.URL, httpClient: h}
|
|
|
|
u, err := oc.user(context.Background(), h)
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
expectEquals(t, u.Name, "jdoe")
|
|
|
|
expectEquals(t, u.FullName, "John Doe")
|
|
|
|
expectEquals(t, len(u.Groups), 1)
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestCallbackIdentity(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{
|
|
|
|
"/apis/user.openshift.io/v1/users/~": user{
|
|
|
|
ObjectMeta: k8sapi.ObjectMeta{
|
|
|
|
Name: "jdoe",
|
|
|
|
UID: "12345",
|
|
|
|
},
|
|
|
|
FullName: "John Doe",
|
|
|
|
Groups: []string{"users"},
|
|
|
|
},
|
|
|
|
"/oauth/token": map[string]interface{}{
|
|
|
|
"access_token": "oRzxVjCnohYRHEYEhZshkmakKmoyVoTjfUGC",
|
|
|
|
"expires_in": "30",
|
|
|
|
},
|
|
|
|
})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
hostURL, err := url.Parse(s.URL)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
req, err := http.NewRequest("GET", hostURL.String(), nil)
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
h, err := newHTTPClient(true, "")
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oc := openshiftConnector{apiURL: s.URL, httpClient: h, oauth2Config: &oauth2.Config{
|
|
|
|
Endpoint: oauth2.Endpoint{
|
|
|
|
AuthURL: fmt.Sprintf("%s/oauth/authorize", s.URL),
|
|
|
|
TokenURL: fmt.Sprintf("%s/oauth/token", s.URL),
|
|
|
|
},
|
|
|
|
}}
|
|
|
|
identity, err := oc.HandleCallback(connector.Scopes{Groups: true}, req)
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
expectEquals(t, identity.UserID, "12345")
|
|
|
|
expectEquals(t, identity.Username, "jdoe")
|
|
|
|
expectEquals(t, identity.PreferredUsername, "jdoe")
|
2020-02-21 15:53:46 +00:00
|
|
|
expectEquals(t, identity.Email, "jdoe")
|
2019-12-10 13:51:09 +00:00
|
|
|
expectEquals(t, len(identity.Groups), 1)
|
|
|
|
expectEquals(t, identity.Groups[0], "users")
|
|
|
|
}
|
|
|
|
|
2021-11-23 18:39:23 +00:00
|
|
|
func TestRefreshIdentity(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{
|
|
|
|
usersURLPath: user{
|
|
|
|
ObjectMeta: k8sapi.ObjectMeta{
|
|
|
|
Name: "jdoe",
|
|
|
|
UID: "12345",
|
|
|
|
},
|
|
|
|
FullName: "John Doe",
|
|
|
|
Groups: []string{"users"},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
h, err := newHTTPClient(true, "")
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oc := openshiftConnector{apiURL: s.URL, httpClient: h, oauth2Config: &oauth2.Config{
|
|
|
|
Endpoint: oauth2.Endpoint{
|
2021-12-06 12:28:09 +00:00
|
|
|
AuthURL: fmt.Sprintf("%s/oauth/authorize", s.URL),
|
2021-11-23 18:39:23 +00:00
|
|
|
TokenURL: fmt.Sprintf("%s/oauth/token", s.URL),
|
|
|
|
},
|
|
|
|
}}
|
|
|
|
|
|
|
|
data, err := json.Marshal(oauth2.Token{AccessToken: "fFAGRNJru1FTz70BzhT3Zg"})
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oldID := connector.Identity{ConnectorData: data}
|
|
|
|
|
|
|
|
identity, err := oc.Refresh(context.Background(), connector.Scopes{Groups: true}, oldID)
|
|
|
|
|
|
|
|
expectNil(t, err)
|
|
|
|
expectEquals(t, identity.UserID, "12345")
|
|
|
|
expectEquals(t, identity.Username, "jdoe")
|
|
|
|
expectEquals(t, identity.PreferredUsername, "jdoe")
|
|
|
|
expectEquals(t, identity.Email, "jdoe")
|
|
|
|
expectEquals(t, len(identity.Groups), 1)
|
|
|
|
expectEquals(t, identity.Groups[0], "users")
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestRefreshIdentityFailure(t *testing.T) {
|
|
|
|
s := newTestServer(map[string]interface{}{
|
|
|
|
usersURLPath: user{
|
|
|
|
ObjectMeta: k8sapi.ObjectMeta{
|
|
|
|
Name: "jdoe",
|
|
|
|
UID: "12345",
|
|
|
|
},
|
|
|
|
FullName: "John Doe",
|
|
|
|
Groups: []string{"users"},
|
|
|
|
},
|
|
|
|
})
|
|
|
|
defer s.Close()
|
|
|
|
|
|
|
|
h, err := newHTTPClient(true, "")
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oc := openshiftConnector{apiURL: s.URL, httpClient: h, oauth2Config: &oauth2.Config{
|
|
|
|
Endpoint: oauth2.Endpoint{
|
2021-12-06 12:28:09 +00:00
|
|
|
AuthURL: fmt.Sprintf("%s/oauth/authorize", s.URL),
|
2021-11-23 18:39:23 +00:00
|
|
|
TokenURL: fmt.Sprintf("%s/oauth/token", s.URL),
|
|
|
|
},
|
|
|
|
}}
|
|
|
|
|
|
|
|
data, err := json.Marshal(oauth2.Token{AccessToken: "oRzxVjCnohYRHEYEhZshkmakKmoyVoTjfUGC", Expiry: time.Now().Add(-time.Hour)})
|
|
|
|
expectNil(t, err)
|
|
|
|
|
|
|
|
oldID := connector.Identity{ConnectorData: data}
|
|
|
|
|
|
|
|
identity, err := oc.Refresh(context.Background(), connector.Scopes{Groups: true}, oldID)
|
|
|
|
expectNotNil(t, err)
|
|
|
|
expectEquals(t, connector.Identity{}, identity)
|
|
|
|
}
|
|
|
|
|
2019-12-10 13:51:09 +00:00
|
|
|
func newTestServer(responses map[string]interface{}) *httptest.Server {
|
|
|
|
var s *httptest.Server
|
|
|
|
s = httptest.NewTLSServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
|
|
|
responses["/.well-known/oauth-authorization-server"] = map[string]interface{}{
|
2019-12-22 05:02:08 +00:00
|
|
|
"issuer": s.URL,
|
2019-12-10 13:51:09 +00:00
|
|
|
"authorization_endpoint": fmt.Sprintf("%s/oauth/authorize", s.URL),
|
|
|
|
"token_endpoint": fmt.Sprintf("%s/oauth/token", s.URL),
|
|
|
|
"scopes_supported": []string{"user:full", "user:info", "user:check-access", "user:list-scoped-projects", "user:list-projects"},
|
|
|
|
"response_types_supported": []string{"token", "code"},
|
|
|
|
"grant_types_supported": []string{"authorization_code", "implicit"},
|
|
|
|
"code_challenge_methods_supported": []string{"plain", "S256"},
|
|
|
|
}
|
|
|
|
|
|
|
|
response := responses[r.RequestURI]
|
|
|
|
w.Header().Add("Content-Type", "application/json")
|
|
|
|
json.NewEncoder(w).Encode(response)
|
|
|
|
}))
|
|
|
|
|
|
|
|
return s
|
|
|
|
}
|
|
|
|
|
|
|
|
func expectNil(t *testing.T, a interface{}) {
|
|
|
|
if a != nil {
|
|
|
|
t.Errorf("Expected %+v to equal nil", a)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func expectEquals(t *testing.T, a interface{}, b interface{}) {
|
|
|
|
if !reflect.DeepEqual(a, b) {
|
|
|
|
t.Errorf("Expected %+v to equal %+v", a, b)
|
|
|
|
}
|
|
|
|
}
|
2021-11-23 18:39:23 +00:00
|
|
|
|
|
|
|
func expectNotNil(t *testing.T, a interface{}) {
|
|
|
|
if a == nil {
|
|
|
|
t.Errorf("Expected %+v to not equal nil", a)
|
|
|
|
}
|
|
|
|
}
|