Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat(Auth Test): Custom parity testing for Custom Test without SRP #2149

Merged
merged 11 commits into from Dec 6, 2022
Expand Up @@ -61,6 +61,6 @@ object JsonGenerator {
}

fun main() {
cleanDirectory()
// cleanDirectory()
gpanshu marked this conversation as resolved.
Show resolved Hide resolved
JsonGenerator.generate()
}
Expand Up @@ -24,6 +24,7 @@ import com.amplifyframework.auth.cognito.featuretest.serializers.CognitoIdentity
import com.amplifyframework.auth.cognito.featuretest.serializers.CognitoIdentityProviderExceptionSerializer
import com.amplifyframework.auth.cognito.featuretest.serializers.deserializeToAuthState
import com.amplifyframework.auth.cognito.featuretest.serializers.serialize
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthSignInOptions
import com.amplifyframework.auth.result.AuthSessionResult
import com.amplifyframework.statemachine.codegen.states.AuthState
import com.google.gson.Gson
Expand Down Expand Up @@ -56,7 +57,7 @@ fun writeFile(json: String, dirName: String, fileName: String) {
}

fun cleanDirectory() {
val directory = File("$basePath")
val directory = File(basePath)
if (directory.exists()) {
directory.deleteRecursively()
}
Expand Down Expand Up @@ -173,6 +174,7 @@ fun Any?.toJsonElement(): JsonElement {
is String -> JsonPrimitive(this)
is Instant -> JsonPrimitive(this.epochSeconds)
is AuthException -> toJsonElement()
is AWSCognitoAuthSignInOptions -> toJsonElement()
is CognitoIdentityProviderException -> Json.encodeToJsonElement(
CognitoIdentityProviderExceptionSerializer,
this
Expand Down
Expand Up @@ -101,5 +101,26 @@ object AuthStateJsonGenerator : SerializableProvider {
AuthorizationState.SigningIn()
)

private val receivedCustomChallengeState = AuthState.Configured(
AuthenticationState.SigningIn(
SignInState.ResolvingChallenge(
SignInChallengeState.WaitingForAnswer(
AuthChallenge(
challengeName = "CUSTOM_CHALLENGE",
username = username,
session = "someSession",
parameters = mapOf(
"SALT" to "abc",
"SECRET_BLOCK" to "secretBlock",
"SRP_B" to "def",
"USERNAME" to "username"
)
)
)
)
),
AuthorizationState.SigningIn()
)

override val serializables: List<Any> = listOf(signedInState, signedOutState, receivedChallengeState)
}
Expand Up @@ -27,6 +27,7 @@ import com.amplifyframework.auth.cognito.featuretest.ResponseType
import com.amplifyframework.auth.cognito.featuretest.generators.SerializableProvider
import com.amplifyframework.auth.cognito.featuretest.generators.authstategenerators.AuthStateJsonGenerator
import com.amplifyframework.auth.cognito.featuretest.generators.toJsonElement
import com.amplifyframework.auth.cognito.options.AuthFlowType
import kotlinx.serialization.json.JsonObject

object SignInTestCaseGenerator : SerializableProvider {
Expand All @@ -51,6 +52,21 @@ object SignInTestCaseGenerator : SerializableProvider {
).toJsonElement()
)

private val mockedInitiateAuthForCustomAuthWithoutSRPResponse = MockResponse(
CognitoType.CognitoIdentityProvider,
"initiateAuth",
ResponseType.Success,
mapOf(
"challengeName" to ChallengeNameType.CustomChallenge.toString(),
"challengeParameters" to mapOf(
"SALT" to "abc",
"SECRET_BLOCK" to "secretBlock",
"SRP_B" to "def",
"USERNAME" to username,
)
).toJsonElement()
)

private val mockedRespondToAuthChallengeResponse = MockResponse(
CognitoType.CognitoIdentityProvider,
"respondToAuthChallenge",
Expand Down Expand Up @@ -97,6 +113,19 @@ object SignInTestCaseGenerator : SerializableProvider {
).toJsonElement()
)

private val mockedCustomChallengeResponse = MockResponse(
CognitoType.CognitoIdentityProvider,
"respondToAuthChallenge",
ResponseType.Success,
mapOf(
"session" to "someSession",
"challengeName" to "CUSTOM_CHALLENGE",
"challengeParameters" to mapOf(
"Code" to "1234"
)
).toJsonElement()
)

private val mockedIdentityIdResponse = MockResponse(
CognitoType.CognitoIdentity,
"getId",
Expand Down Expand Up @@ -146,6 +175,23 @@ object SignInTestCaseGenerator : SerializableProvider {
).toJsonElement()
)

private val mockedSignInCustomAuthChallengeExpectation = ExpectationShapes.Amplify(
apiName = AuthAPI.signIn,
responseType = ResponseType.Success,
response = mapOf(
"isSignedIn" to false,
"nextStep" to mapOf(
"signInStep" to "CONFIRM_SIGN_IN_WITH_CUSTOM_CHALLENGE",
"additionalInfo" to mapOf(
"SALT" to "abc",
"SECRET_BLOCK" to "secretBlock",
"USERNAME" to "username",
"SRP_B" to "def"
)
)
).toJsonElement()
)

private val mockConfirmDeviceResponse = MockResponse(
CognitoType.CognitoIdentityProvider,
"confirmDevice",
Expand Down Expand Up @@ -174,16 +220,6 @@ object SignInTestCaseGenerator : SerializableProvider {
options = JsonObject(emptyMap())
),
validations = listOf(
// ExpectationShapes.Cognito(
// apiName = "signIn",
// // see [https://docs.aws.amazon.com/cognito-user-identity-pools/latest/APIReference/API_InitiateAuth.html]
// // see [https://docs.aws.amazon.com/cognito-user-identity-pools/latest/APIReference/API_RespondToAuthChallenge.html]
// request = mapOf(
// "clientId" to "testAppClientId", // This should be pulled from configuration
// "authFlow" to AuthFlowType.UserSrpAuth,
// "authParameters" to mapOf("username" to username, "SRP_A" to "123")
// ).toJsonElement()
// ),
mockedSignInSuccessExpectation,
ExpectationShapes.State("SignedIn_SessionEstablished.json")
)
Expand Down Expand Up @@ -232,5 +268,32 @@ object SignInTestCaseGenerator : SerializableProvider {
)
)

override val serializables: List<Any> = listOf(baseCase, challengeCase, deviceSRPTestCase)
private val customAuthCase = FeatureTestCase(
description = "Test that Custom Auth signIn invokes proper cognito request and returns custom challenge",
preConditions = PreConditions(
"authconfiguration.json",
"SignedOut_Configured.json",
mockedResponses = listOf(
mockedInitiateAuthForCustomAuthWithoutSRPResponse,
mockedCustomChallengeResponse
)
),
api = API(
AuthAPI.signIn,
params = mapOf(
"username" to username,
"password" to "",
).toJsonElement(),
options = mapOf(
"signInOptions" to
mapOf("authFlow" to AuthFlowType.CUSTOM_AUTH_WITHOUT_SRP.toString())
).toJsonElement()
),
validations = listOf(
mockedSignInCustomAuthChallengeExpectation,
ExpectationShapes.State("CustomSignIn_SigningIn.json")
)
)

override val serializables: List<Any> = listOf(baseCase, challengeCase, deviceSRPTestCase, customAuthCase)
}
Expand Up @@ -21,6 +21,8 @@ import com.amplifyframework.auth.cognito.featuretest.AuthAPI
import com.amplifyframework.auth.cognito.featuretest.AuthAPI.resetPassword
import com.amplifyframework.auth.cognito.featuretest.AuthAPI.signIn
import com.amplifyframework.auth.cognito.featuretest.AuthAPI.signUp
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthSignInOptions
import com.amplifyframework.auth.cognito.options.AuthFlowType
import com.amplifyframework.auth.options.AuthConfirmResetPasswordOptions
import com.amplifyframework.auth.options.AuthConfirmSignInOptions
import com.amplifyframework.auth.options.AuthConfirmSignUpOptions
Expand Down Expand Up @@ -59,7 +61,7 @@ object AuthOptionsFactory {
AuthAPI.rememberDevice -> TODO()
AuthAPI.resendSignUpCode -> AuthResendSignUpCodeOptions.defaults()
AuthAPI.resendUserAttributeConfirmationCode -> AuthResendUserAttributeConfirmationCodeOptions.defaults()
signIn -> AuthSignInOptions.defaults()
signIn -> getSignInOptions(optionsData)
AuthAPI.signInWithSocialWebUI -> AuthWebUISignInOptions.builder().build()
AuthAPI.signInWithWebUI -> AuthWebUISignInOptions.builder().build()
AuthAPI.signOut -> getSignOutOptions(optionsData)
Expand All @@ -74,6 +76,17 @@ object AuthOptionsFactory {
AuthAPI.getVersion -> TODO()
} as T

private fun getSignInOptions(optionsData: JsonObject): AuthSignInOptions {
return if (optionsData.containsKey("signInOptions")) {
val authFlowType = AuthFlowType.valueOf(
((optionsData["signInOptions"] as Map<String, String>)["authFlow"] as JsonPrimitive).content
)
AWSCognitoAuthSignInOptions.builder().authFlowType(authFlowType).build()
gpanshu marked this conversation as resolved.
Show resolved Hide resolved
} else {
AuthSignInOptions.defaults()
}
}

private fun getSignUpOptions(optionsData: JsonObject): AuthSignUpOptions =
AuthSignUpOptions.builder().userAttributes(
(optionsData["userAttributes"] as Map<String, String>).map {
Expand Down
@@ -0,0 +1,26 @@
{
"type": "AuthState.Configured",
"AuthenticationState": {
"type": "AuthenticationState.SigningIn",
"SignInState": {
"type": "SignInState.ResolvingChallenge",
"SignInChallengeState": {
"type": "SignInChallengeState.WaitingForAnswer",
"authChallenge": {
"challengeName": "CUSTOM_CHALLENGE",
"username": "username",
"session": null,
"parameters": {
"SALT": "abc",
"SECRET_BLOCK": "secretBlock",
"SRP_B": "def",
"USERNAME": "username"
}
}
}
}
},
"AuthorizationState": {
"type": "AuthorizationState.SigningIn"
}
}

This file was deleted.

This file was deleted.