Skip to content

Commit 7bdb515

Browse files
committed
Refactor user service and co-relevant services to use transactions
1 parent c00bf13 commit 7bdb515

File tree

163 files changed

+10068
-8530
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

163 files changed

+10068
-8530
lines changed

backend/internal/authn/AuthenticationServiceInterface_mock_test.go

Lines changed: 216 additions & 160 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

backend/internal/authn/credentials/service.go

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,8 @@
2020
package credentials
2121

2222
import (
23+
"context"
24+
2325
"github.com/asgardeo/thunder/internal/authn/common"
2426
"github.com/asgardeo/thunder/internal/system/error/serviceerror"
2527
"github.com/asgardeo/thunder/internal/system/log"
@@ -32,7 +34,8 @@ const (
3234

3335
// CredentialsAuthnServiceInterface defines the contract for credentials-based authenticator services.
3436
type CredentialsAuthnServiceInterface interface {
35-
Authenticate(attributes map[string]interface{}) (*user.User, *serviceerror.ServiceError)
37+
Authenticate(ctx context.Context, attributes map[string]interface{}) (
38+
*user.User, *serviceerror.ServiceError)
3639
}
3740

3841
// credentialsAuthnService is the default implementation of CredentialsAuthnServiceInterface.
@@ -51,7 +54,7 @@ func newCredentialsAuthnService(userSvc user.UserServiceInterface) CredentialsAu
5154
}
5255

5356
// Authenticate authenticates a user using credentials.
54-
func (c *credentialsAuthnService) Authenticate(attributes map[string]interface{}) (
57+
func (c *credentialsAuthnService) Authenticate(ctx context.Context, attributes map[string]interface{}) (
5558
*user.User, *serviceerror.ServiceError) {
5659
logger := log.GetLogger().With(log.String(log.LoggerKeyComponentName, loggerComponentName))
5760
logger.Debug("Authenticating user with credentials")
@@ -61,7 +64,7 @@ func (c *credentialsAuthnService) Authenticate(attributes map[string]interface{}
6164
}
6265

6366
authRequest := user.AuthenticateUserRequest(attributes)
64-
authResponse, svcErr := c.userService.AuthenticateUser(authRequest)
67+
authResponse, svcErr := c.userService.AuthenticateUser(ctx, authRequest)
6568
if svcErr != nil {
6669
if svcErr.Type == serviceerror.ClientErrorType {
6770
switch svcErr.Code {
@@ -75,13 +78,14 @@ func (c *credentialsAuthnService) Authenticate(attributes map[string]interface{}
7578
}
7679
}
7780

78-
logger.Error("Error occurred while authenticating the user", log.String("errorCode", svcErr.Code),
81+
logger.Error("Error occurred while authenticating the user",
82+
log.String("errorCode", svcErr.Code),
7983
log.String("errorDescription", svcErr.ErrorDescription))
8084
return nil, &serviceerror.InternalServerError
8185
}
8286

8387
// Fetch the user details
84-
user, svcErr := c.userService.GetUser(authResponse.ID)
88+
user, svcErr := c.userService.GetUser(ctx, authResponse.ID)
8589
if svcErr != nil {
8690
if svcErr.Type == serviceerror.ClientErrorType {
8791
return nil, serviceerror.CustomServiceError(

backend/internal/authn/credentials/service_test.go

Lines changed: 15 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
package credentials
2020

2121
import (
22+
"context"
2223
"testing"
2324

2425
"github.com/stretchr/testify/mock"
@@ -66,10 +67,10 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateSuccess() {
6667
OrganizationUnit: orgUnit,
6768
}
6869

69-
suite.mockUserService.On("AuthenticateUser", mock.Anything).Return(authResp, nil)
70-
suite.mockUserService.On("GetUser", userID).Return(user, nil)
70+
suite.mockUserService.On("AuthenticateUser", mock.Anything, mock.Anything).Return(authResp, nil)
71+
suite.mockUserService.On("GetUser", mock.Anything, userID).Return(user, nil)
7172

72-
result, err := suite.service.Authenticate(attributes)
73+
result, err := suite.service.Authenticate(context.Background(), attributes)
7374
suite.Nil(err)
7475
suite.NotNil(result)
7576
suite.Equal(userID, result.ID)
@@ -96,7 +97,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateFailures() {
9697
"password": "testpass",
9798
},
9899
setupMock: func(m *usermock.UserServiceInterfaceMock) {
99-
m.On("AuthenticateUser", mock.Anything).Return(nil, &user.ErrorUserNotFound)
100+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(nil, &user.ErrorUserNotFound)
100101
},
101102
expectedErrorCode: common.ErrorUserNotFound.Code,
102103
},
@@ -107,7 +108,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateFailures() {
107108
"password": "wrongpass",
108109
},
109110
setupMock: func(m *usermock.UserServiceInterfaceMock) {
110-
m.On("AuthenticateUser", mock.Anything).Return(nil, &user.ErrorAuthenticationFailed)
111+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(nil, &user.ErrorAuthenticationFailed)
111112
},
112113
expectedErrorCode: ErrorInvalidCredentials.Code,
113114
},
@@ -121,7 +122,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateFailures() {
121122
}
122123
svc := newCredentialsAuthnService(m)
123124

124-
result, err := svc.Authenticate(tc.attributes)
125+
result, err := svc.Authenticate(context.Background(), tc.attributes)
125126
suite.Nil(result)
126127
suite.NotNil(err)
127128
suite.Equal(tc.expectedErrorCode, err.Code)
@@ -150,7 +151,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateWithServiceErrors
150151
Code: "INTERNAL_ERROR",
151152
ErrorDescription: "Database connection failed",
152153
}
153-
m.On("AuthenticateUser", mock.Anything).Return(nil, serverErr)
154+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(nil, serverErr)
154155
},
155156
expectedErrorCode: serviceerror.InternalServerError.Code,
156157
},
@@ -166,7 +167,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateWithServiceErrors
166167
Code: "CUSTOM_ERROR",
167168
ErrorDescription: "Custom error message",
168169
}
169-
m.On("AuthenticateUser", mock.Anything).Return(nil, clientErr)
170+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(nil, clientErr)
170171
},
171172
expectedErrorCode: ErrorClientErrorFromUserSvcAuthentication.Code,
172173
expectedErrContain: "Custom error message",
@@ -185,8 +186,8 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateWithServiceErrors
185186
Code: "INTERNAL_ERROR",
186187
ErrorDescription: "Database connection failed",
187188
}
188-
m.On("AuthenticateUser", mock.Anything).Return(authResp, nil)
189-
m.On("GetUser", userID).Return(nil, serverErr)
189+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(authResp, nil)
190+
m.On("GetUser", mock.Anything, userID).Return(nil, serverErr)
190191
},
191192
expectedErrorCode: serviceerror.InternalServerError.Code,
192193
},
@@ -201,11 +202,11 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateWithServiceErrors
201202
authResp := &user.AuthenticateUserResponse{ID: userID}
202203
clientErr := &serviceerror.ServiceError{
203204
Type: serviceerror.ClientErrorType,
204-
Code: "CUSTOM_ERROR",
205+
Code: "USER_LOCKED",
205206
ErrorDescription: "User locked",
206207
}
207-
m.On("AuthenticateUser", mock.Anything).Return(authResp, nil)
208-
m.On("GetUser", userID).Return(nil, clientErr)
208+
m.On("AuthenticateUser", mock.Anything, mock.Anything).Return(authResp, nil)
209+
m.On("GetUser", mock.Anything, userID).Return(nil, clientErr)
209210
},
210211
expectedErrorCode: ErrorClientErrorFromUserSvcAuthentication.Code,
211212
expectedErrContain: "User locked",
@@ -220,7 +221,7 @@ func (suite *CredentialsAuthnServiceTestSuite) TestAuthenticateWithServiceErrors
220221
}
221222
svc := newCredentialsAuthnService(m)
222223

223-
result, err := svc.Authenticate(tc.attributes)
224+
result, err := svc.Authenticate(context.Background(), tc.attributes)
224225
suite.Nil(result)
225226
suite.NotNil(err)
226227
suite.Equal(tc.expectedErrorCode, err.Code)

backend/internal/authn/github/service.go

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
package github
2121

2222
import (
23+
"context"
2324
"slices"
2425

2526
authncm "github.com/asgardeo/thunder/internal/authn/common"
@@ -64,26 +65,26 @@ func newGithubOAuthAuthnService(idpSvc idp.IDPServiceInterface,
6465
}
6566

6667
// BuildAuthorizeURL constructs the authorization request URL for GitHub OAuth authentication.
67-
func (g *githubOAuthAuthnService) BuildAuthorizeURL(idpID string) (string, *serviceerror.ServiceError) {
68-
return g.internal.BuildAuthorizeURL(idpID)
68+
func (g *githubOAuthAuthnService) BuildAuthorizeURL(ctx context.Context, idpID string) (string, *serviceerror.ServiceError) {
69+
return g.internal.BuildAuthorizeURL(ctx, idpID)
6970
}
7071

7172
// ExchangeCodeForToken exchanges the authorization code for a token with GitHub.
72-
func (g *githubOAuthAuthnService) ExchangeCodeForToken(idpID, code string, validateResponse bool) (
73-
*authnoauth.TokenResponse, *serviceerror.ServiceError) {
74-
return g.internal.ExchangeCodeForToken(idpID, code, validateResponse)
73+
func (g *githubOAuthAuthnService) ExchangeCodeForToken(ctx context.Context, idpID, code string,
74+
validateResponse bool) (*authnoauth.TokenResponse, *serviceerror.ServiceError) {
75+
return g.internal.ExchangeCodeForToken(ctx, idpID, code, validateResponse)
7576
}
7677

7778
// FetchUserInfo retrieves user information from the Github API, ensuring email resolution if necessary.
78-
func (g *githubOAuthAuthnService) FetchUserInfo(idpID, accessToken string) (
79+
func (g *githubOAuthAuthnService) FetchUserInfo(ctx context.Context, idpID, accessToken string) (
7980
map[string]interface{}, *serviceerror.ServiceError) {
8081
logger := g.logger
81-
oAuthClientConfig, svcErr := g.internal.GetOAuthClientConfig(idpID)
82+
oAuthClientConfig, svcErr := g.internal.GetOAuthClientConfig(ctx, idpID)
8283
if svcErr != nil {
8384
return nil, svcErr
8485
}
8586

86-
userInfo, svcErr := g.internal.FetchUserInfoWithClientConfig(oAuthClientConfig, accessToken)
87+
userInfo, svcErr := g.internal.FetchUserInfoWithClientConfig(ctx, oAuthClientConfig, accessToken)
8788
if svcErr != nil {
8889
return userInfo, svcErr
8990
}
@@ -148,14 +149,14 @@ func (g *githubOAuthAuthnService) fetchPrimaryEmail(
148149
}
149150

150151
// GetInternalUser retrieves the internal user based on the external subject identifier.
151-
func (g *githubOAuthAuthnService) GetInternalUser(sub string) (*user.User, *serviceerror.ServiceError) {
152-
return g.internal.GetInternalUser(sub)
152+
func (g *githubOAuthAuthnService) GetInternalUser(ctx context.Context, sub string) (*user.User, *serviceerror.ServiceError) {
153+
return g.internal.GetInternalUser(ctx, sub)
153154
}
154155

155156
// GetOAuthClientConfig retrieves and validates the OAuth client configuration for the given identity provider ID.
156-
func (g *githubOAuthAuthnService) GetOAuthClientConfig(idpID string) (
157+
func (g *githubOAuthAuthnService) GetOAuthClientConfig(ctx context.Context, idpID string) (
157158
*authnoauth.OAuthClientConfig, *serviceerror.ServiceError) {
158-
return g.internal.GetOAuthClientConfig(idpID)
159+
return g.internal.GetOAuthClientConfig(ctx, idpID)
159160
}
160161

161162
// getMetadata returns the authenticator metadata for GitHub OAuth authenticator.

0 commit comments

Comments
 (0)