1
21
22 package oauth2
23
24 import (
25 "fmt"
26 "net/http"
27 "testing"
28 "time"
29
30 "github.com/golang/mock/gomock"
31 "github.com/stretchr/testify/require"
32
33 "github.com/ory/fosite"
34 "github.com/ory/fosite/internal"
35 )
36
37 func TestClientCredentials_HandleTokenEndpointRequest(t *testing.T) {
38 ctrl := gomock.NewController(t)
39 store := internal.NewMockClientCredentialsGrantStorage(ctrl)
40 chgen := internal.NewMockAccessTokenStrategy(ctrl)
41 areq := internal.NewMockAccessRequester(ctrl)
42 defer ctrl.Finish()
43
44 h := ClientCredentialsGrantHandler{
45 HandleHelper: &HandleHelper{
46 AccessTokenStorage: store,
47 AccessTokenStrategy: chgen,
48 AccessTokenLifespan: time.Hour,
49 },
50 ScopeStrategy: fosite.HierarchicScopeStrategy,
51 AudienceMatchingStrategy: fosite.DefaultAudienceMatchingStrategy,
52 }
53 for k, c := range []struct {
54 description string
55 mock func()
56 req *http.Request
57 expectErr error
58 }{
59 {
60 description: "should fail because not responsible",
61 expectErr: fosite.ErrUnknownRequest,
62 mock: func() {
63 areq.EXPECT().GetGrantTypes().Return(fosite.Arguments{""})
64 },
65 },
66 {
67 description: "should fail because audience not valid",
68 expectErr: fosite.ErrInvalidRequest,
69 mock: func() {
70 areq.EXPECT().GetGrantTypes().Return(fosite.Arguments{"client_credentials"})
71 areq.EXPECT().GetRequestedScopes().Return([]string{})
72 areq.EXPECT().GetRequestedAudience().Return([]string{"https://www.ory.sh/not-api"})
73 areq.EXPECT().GetClient().Return(&fosite.DefaultClient{
74 GrantTypes: fosite.Arguments{"client_credentials"},
75 Audience: []string{"https://www.ory.sh/api"},
76 })
77 },
78 },
79 {
80 description: "should fail because scope not valid",
81 expectErr: fosite.ErrInvalidScope,
82 mock: func() {
83 areq.EXPECT().GetGrantTypes().Return(fosite.Arguments{"client_credentials"})
84 areq.EXPECT().GetRequestedScopes().Return([]string{"foo", "bar", "baz.bar"})
85 areq.EXPECT().GetClient().Return(&fosite.DefaultClient{
86 GrantTypes: fosite.Arguments{"client_credentials"},
87 Scopes: []string{"foo"},
88 })
89 },
90 },
91 {
92 description: "should pass",
93 mock: func() {
94 areq.EXPECT().GetSession().Return(new(fosite.DefaultSession))
95 areq.EXPECT().GetGrantTypes().Return(fosite.Arguments{"client_credentials"})
96 areq.EXPECT().GetRequestedScopes().Return([]string{"foo", "bar", "baz.bar"})
97 areq.EXPECT().GetRequestedAudience().Return([]string{})
98 areq.EXPECT().GetClient().Return(&fosite.DefaultClient{
99 GrantTypes: fosite.Arguments{"client_credentials"},
100 Scopes: []string{"foo", "bar", "baz"},
101 })
102 },
103 },
104 } {
105 t.Run(fmt.Sprintf("case=%d", k), func(t *testing.T) {
106 c.mock()
107 err := h.HandleTokenEndpointRequest(nil, areq)
108 if c.expectErr != nil {
109 require.EqualError(t, err, c.expectErr.Error())
110 } else {
111 require.NoError(t, err)
112 }
113 })
114 }
115 }
116
117 func TestClientCredentials_PopulateTokenEndpointResponse(t *testing.T) {
118 ctrl := gomock.NewController(t)
119 store := internal.NewMockClientCredentialsGrantStorage(ctrl)
120 chgen := internal.NewMockAccessTokenStrategy(ctrl)
121 areq := fosite.NewAccessRequest(new(fosite.DefaultSession))
122 aresp := fosite.NewAccessResponse()
123 defer ctrl.Finish()
124
125 h := ClientCredentialsGrantHandler{
126 HandleHelper: &HandleHelper{
127 AccessTokenStorage: store,
128 AccessTokenStrategy: chgen,
129 AccessTokenLifespan: time.Hour,
130 },
131 ScopeStrategy: fosite.HierarchicScopeStrategy,
132 }
133 for k, c := range []struct {
134 description string
135 mock func()
136 req *http.Request
137 expectErr error
138 }{
139 {
140 description: "should fail because not responsible",
141 expectErr: fosite.ErrUnknownRequest,
142 mock: func() {
143 areq.GrantTypes = fosite.Arguments{""}
144 },
145 },
146 {
147 description: "should fail because grant_type not allowed",
148 expectErr: fosite.ErrUnauthorizedClient,
149 mock: func() {
150 areq.GrantTypes = fosite.Arguments{"client_credentials"}
151 areq.Client = &fosite.DefaultClient{GrantTypes: fosite.Arguments{"authorization_code"}}
152 },
153 },
154 {
155 description: "should pass",
156 mock: func() {
157 areq.GrantTypes = fosite.Arguments{"client_credentials"}
158 areq.Session = &fosite.DefaultSession{}
159 areq.Client = &fosite.DefaultClient{GrantTypes: fosite.Arguments{"client_credentials"}}
160 chgen.EXPECT().GenerateAccessToken(nil, areq).Return("tokenfoo.bar", "bar", nil)
161 store.EXPECT().CreateAccessTokenSession(nil, "bar", gomock.Eq(areq.Sanitize([]string{}))).Return(nil)
162 },
163 },
164 } {
165 t.Run(fmt.Sprintf("case=%d", k), func(t *testing.T) {
166 c.mock()
167 err := h.PopulateTokenEndpointResponse(nil, areq, aresp)
168 if c.expectErr != nil {
169 require.EqualError(t, err, c.expectErr.Error())
170 } else {
171 require.NoError(t, err)
172 }
173 })
174 }
175 }
176
View as plain text