@@ -401,6 +401,7 @@ async function handleSecurityChecks(input: {
401
401
});
402
402
} catch (err ) {
403
403
// silently fail in order to not break the auth flow
404
+ console .error (err );
404
405
return ;
405
406
}
406
407
@@ -505,10 +506,11 @@ SuperTokens.init({
505
506
const actionType = ' emailpassword-sign-up' ;
506
507
const ip = getIpFromRequest (input .options .req .original );
507
508
let email = input .formFields .filter ((f ) => f .id === " email" )[0 ].value ;
509
+ let password = input .formFields .filter ((f ) => f .id === " password" )[0 ].value ;
508
510
const bruteForceConfig = getBruteForceConfig (email , ip , actionType );
509
511
510
512
// we check the anomaly detection service before calling the original implementation of signUp
511
- let securityCheckResponse = await handleSecurityChecks ({ ... input , requestId , email , bruteForceConfig , actionType });
513
+ let securityCheckResponse = await handleSecurityChecks ({ requestId , email , password , bruteForceConfig , actionType });
512
514
if (securityCheckResponse !== undefined ) {
513
515
return securityCheckResponse ;
514
516
}
@@ -531,7 +533,7 @@ SuperTokens.init({
531
533
const bruteForceConfig = getBruteForceConfig (email , ip , actionType );
532
534
533
535
// we check the anomaly detection service before calling the original implementation of signIn
534
- let securityCheckResponse = await handleSecurityChecks ({ ... input , requestId , email , bruteForceConfig , actionType });
536
+ let securityCheckResponse = await handleSecurityChecks ({ requestId , email , bruteForceConfig , actionType });
535
537
if (securityCheckResponse !== undefined ) {
536
538
return securityCheckResponse ;
537
539
}
@@ -554,12 +556,20 @@ SuperTokens.init({
554
556
const bruteForceConfig = getBruteForceConfig (email , ip , actionType );
555
557
556
558
// we check the anomaly detection service before calling the original implementation of generatePasswordResetToken
557
- let securityCheckResponse = await handleSecurityChecks ({ ... input , requestId , email , bruteForceConfig , actionType });
559
+ let securityCheckResponse = await handleSecurityChecks ({ requestId , email , bruteForceConfig , actionType });
558
560
if (securityCheckResponse !== undefined ) {
559
561
return securityCheckResponse ;
560
562
}
561
563
562
564
return originalImplementation .generatePasswordResetTokenPOST !(input );
565
+ },
566
+ passwordResetPOST : async function (input ) {
567
+ let password = input .formFields .filter ((f ) => f .id === " password" )[0 ].value ;
568
+ let securityCheckResponse = await handleSecurityChecks ({ password });
569
+ if (securityCheckResponse !== undefined ) {
570
+ return securityCheckResponse ;
571
+ }
572
+ return originalImplementation .passwordResetPOST !(input );
563
573
}
564
574
}
565
575
}
@@ -888,7 +898,7 @@ func main() {
888
898
return resp, nil
889
899
}
890
900
891
- // rewrite the original implementation of SignInPOST
901
+ // rewrite the original implementation of GeneratePasswordResetTokenPOST
892
902
originalGeneratePasswordResetTokenPOST := *originalImplementation.GeneratePasswordResetTokenPOST
893
903
(*originalImplementation.GeneratePasswordResetTokenPOST ) = func (formFields []epmodels.TypeFormField , tenantId string , options epmodels.APIOptions , userContext supertokens.UserContext ) (epmodels.GeneratePasswordResetTokenPOSTResponse , error ) {
894
904
// Generate request ID for bot and suspicious IP detection
@@ -949,6 +959,46 @@ func main() {
949
959
return resp, nil
950
960
}
951
961
962
+ // rewrite the original implementation of PasswordResetPOST
963
+ originalPasswordResetPOST := *originalImplementation.PasswordResetPOST
964
+ (*originalImplementation.PasswordResetPOST ) = func (formFields []epmodels.TypeFormField , token string , tenantId string , options epmodels.APIOptions , userContext supertokens.UserContext ) (epmodels.ResetPasswordPOSTResponse , error ) {
965
+ password := " "
966
+ for _ , field := range formFields {
967
+ if field.ID == " password" {
968
+ valueAsString , asStrOk := field.Value .(string )
969
+ if !asStrOk {
970
+ return epmodels.ResetPasswordPOSTResponse {}, errors.New (" Should never come here as we check the type during validation" )
971
+ }
972
+ password = valueAsString
973
+ }
974
+ }
975
+
976
+ // Check anomaly detection service before proceeding
977
+ checkErr , err := handleSecurityChecks (
978
+ SecurityCheckInput{
979
+ Password: password,
980
+ },
981
+ )
982
+ if err != nil {
983
+ return epmodels.ResetPasswordPOSTResponse {}, err
984
+ }
985
+
986
+ if checkErr != nil {
987
+ return epmodels.ResetPasswordPOSTResponse {
988
+ GeneralError: checkErr,
989
+ }, nil
990
+ }
991
+
992
+ // First we call the original implementation
993
+ resp , err := originalPasswordResetPOST (formFields, token, tenantId, options, userContext)
994
+
995
+ if err != nil {
996
+ return epmodels.ResetPasswordPOSTResponse {}, err
997
+ }
998
+
999
+ return resp, nil
1000
+ }
1001
+
952
1002
return originalImplementation
953
1003
},
954
1004
Functions: func (originalImplementation epmodels.RecipeInterface ) epmodels.RecipeInterface {
@@ -993,7 +1043,7 @@ SECRET_API_KEY = "<secret-api-key>"; # Your secret API key that you received fro
993
1043
# The full URL with the correct region will be provided by the SuperTokens team
994
1044
ANOMALY_DETECTION_API_URL = " https://security-<region>.aws.supertokens.io/v1/security"
995
1045
996
- async def handle_security_checks (request_id : Union[str , None ], password : Union[str , None ], brute_force_config : List[Dict[str , Any]], email : Union[str , None ], phone_number : Union[str , None ], action_type : str ) -> Union[GeneralErrorResponse, None ]:
1046
+ async def handle_security_checks (request_id : Union[str , None ], password : Union[str , None ], brute_force_config : Union[ List[Dict[str , Any]], None ], email : Union[str , None ], phone_number : Union[str , None ], action_type : Union[ str , None ] ) -> Union[GeneralErrorResponse, None ]:
997
1047
request_body = {}
998
1048
999
1049
if request_id is not None :
@@ -1123,7 +1173,7 @@ def override_email_password_apis(original_implementation: APIInterface):
1123
1173
email = field.value
1124
1174
brute_force_config = get_brute_force_config(email, ip, action_type)
1125
1175
1126
- # we check the anomaly detection service before calling the original implementation of signUp
1176
+ # we check the anomaly detection service before calling the original implementation of sign_in_post
1127
1177
security_check_response = await handle_security_checks(
1128
1178
request_id = request_id,
1129
1179
password = None ,
@@ -1135,7 +1185,7 @@ def override_email_password_apis(original_implementation: APIInterface):
1135
1185
if security_check_response is not None :
1136
1186
return security_check_response
1137
1187
1138
- # We need to call the original implementation of sign_up_post .
1188
+ # We need to call the original implementation of sign_in_post .
1139
1189
response = await original_sign_in_post(form_fields, tenant_id, api_options, user_context)
1140
1190
1141
1191
return response
@@ -1159,7 +1209,7 @@ def override_email_password_apis(original_implementation: APIInterface):
1159
1209
email = field.value
1160
1210
brute_force_config = get_brute_force_config(email, ip, action_type)
1161
1211
1162
- # we check the anomaly detection service before calling the original implementation of signUp
1212
+ # we check the anomaly detection service before calling the original implementation of generate_password_reset_token_post
1163
1213
security_check_response = await handle_security_checks(
1164
1214
request_id = request_id,
1165
1215
password = None ,
@@ -1171,12 +1221,45 @@ def override_email_password_apis(original_implementation: APIInterface):
1171
1221
if security_check_response is not None :
1172
1222
return security_check_response
1173
1223
1174
- # We need to call the original implementation of sign_up_post .
1224
+ # We need to call the original implementation of generate_password_reset_token_post .
1175
1225
response = await original_generate_password_reset_token_post(form_fields, tenant_id, api_options, user_context)
1176
1226
1177
1227
return response
1178
1228
original_implementation.generate_password_reset_token_post = generate_password_reset_token_post
1179
1229
1230
+
1231
+ original_password_reset_post = original_implementation.password_reset_post
1232
+ async def password_reset_post (
1233
+ form_fields : List[FormField],
1234
+ token : str ,
1235
+ tenant_id : str ,
1236
+ api_options : APIOptions,
1237
+ user_context : Dict[str , Any],
1238
+ ):
1239
+ password = None
1240
+ for field in form_fields:
1241
+ if field.id == " password" :
1242
+ password = field.value
1243
+
1244
+ # we check the anomaly detection service before calling the original implementation of password_reset_post
1245
+ security_check_response = await handle_security_checks(
1246
+ request_id = None ,
1247
+ password = password,
1248
+ brute_force_config = None ,
1249
+ email = None ,
1250
+ phone_number = None ,
1251
+ action_type = None
1252
+ )
1253
+ if security_check_response is not None :
1254
+ return security_check_response
1255
+
1256
+ response = await original_password_reset_post(
1257
+ form_fields, token, tenant_id, api_options, user_context
1258
+ )
1259
+
1260
+ return response
1261
+ original_implementation.password_reset_post = password_reset_post
1262
+
1180
1263
return original_implementation
1181
1264
# highlight-end
1182
1265
@@ -1276,6 +1359,7 @@ async function handleSecurityChecks(input: {
1276
1359
});
1277
1360
} catch (err ) {
1278
1361
// silently fail in order to not break the auth flow
1362
+ console .error (err );
1279
1363
return ;
1280
1364
}
1281
1365
let responseData = response .data ;
@@ -1336,8 +1420,8 @@ SuperTokens.init({
1336
1420
const emailOrPhoneNumber = " email" in input ? input .email : input .phoneNumber ;
1337
1421
const bruteForceConfig = getBruteForceConfig (emailOrPhoneNumber , ip , actionType );
1338
1422
1339
- // we check the anomaly detection service before calling the original implementation of signUp
1340
- let securityCheckResponse = await handleSecurityChecks ({ ... input , bruteForceConfig , actionType });
1423
+ // we check the anomaly detection service before calling the original implementation of createCodePOST
1424
+ let securityCheckResponse = await handleSecurityChecks ({ bruteForceConfig , actionType });
1341
1425
if (securityCheckResponse !== undefined ) {
1342
1426
return securityCheckResponse ;
1343
1427
}
@@ -1357,8 +1441,8 @@ SuperTokens.init({
1357
1441
1358
1442
const bruteForceConfig = getBruteForceConfig (userIdentifier , ip , actionType );
1359
1443
1360
- // we check the anomaly detection service before calling the original implementation of signUp
1361
- let securityCheckResponse = await handleSecurityChecks ({ ... input , phoneNumber , email , bruteForceConfig , actionType });
1444
+ // we check the anomaly detection service before calling the original implementation of resendCodePOST
1445
+ let securityCheckResponse = await handleSecurityChecks ({ phoneNumber , email , bruteForceConfig , actionType });
1362
1446
if (securityCheckResponse !== undefined ) {
1363
1447
return securityCheckResponse ;
1364
1448
}
@@ -1631,7 +1715,7 @@ SECRET_API_KEY = "<secret-api-key>" # Your secret API key that you received from
1631
1715
# The full URL with the correct region will be provided by the SuperTokens team
1632
1716
ANOMALY_DETECTION_API_URL = " https://security-<region>.aws.supertokens.io/v1/security"
1633
1717
1634
- async def handle_security_checks (request_id : Union[str , None ], password : Union[str , None ], brute_force_config : List[Dict[str , Any]], email : Union[str , None ], phone_number : Union[str , None ], action_type : str ) -> Union[GeneralErrorResponse, None ]:
1718
+ async def handle_security_checks (request_id : Union[str , None ], password : Union[str , None ], brute_force_config : Union[ List[Dict[str , Any]], None ], email : Union[str , None ], phone_number : Union[str , None ], action_type : Union[ str , None ] ) -> Union[GeneralErrorResponse, None ]:
1635
1719
request_body = {}
1636
1720
1637
1721
request_body[' bruteForce' ] = brute_force_config
@@ -1693,7 +1777,7 @@ def override_passwordless_apis(original_implementation: APIInterface):
1693
1777
identifier = phone_number
1694
1778
brute_force_config = get_brute_force_config(identifier, ip, action_type)
1695
1779
1696
- # we check the anomaly detection service before calling the original implementation of signUp
1780
+ # we check the anomaly detection service before calling the original implementation of create_code_post
1697
1781
security_check_response = await handle_security_checks(
1698
1782
request_id = None ,
1699
1783
password = None ,
@@ -1705,7 +1789,7 @@ def override_passwordless_apis(original_implementation: APIInterface):
1705
1789
if security_check_response is not None :
1706
1790
return security_check_response
1707
1791
1708
- # We need to call the original implementation of sign_up_post .
1792
+ # We need to call the original implementation of create_code_post .
1709
1793
response = await original_create_code_post(email, phone_number, tenant_id, api_options, user_context)
1710
1794
1711
1795
return response
@@ -1728,7 +1812,7 @@ def override_passwordless_apis(original_implementation: APIInterface):
1728
1812
identifier = phone_number
1729
1813
brute_force_config = get_brute_force_config(identifier, ip, action_type)
1730
1814
1731
- # we check the anomaly detection service before calling the original implementation of signUp
1815
+ # we check the anomaly detection service before calling the original implementation of resend_code_post
1732
1816
security_check_response = await handle_security_checks(
1733
1817
request_id = None ,
1734
1818
password = None ,
@@ -1740,7 +1824,7 @@ def override_passwordless_apis(original_implementation: APIInterface):
1740
1824
if security_check_response is not None :
1741
1825
return security_check_response
1742
1826
1743
- # We need to call the original implementation of sign_up_post .
1827
+ # We need to call the original implementation of resend_code_post .
1744
1828
response = await original_resend_code_post(device_id, pre_auth_session_id, tenant_id, api_options, user_context)
1745
1829
1746
1830
return response
0 commit comments