Skip to content

Commit

Permalink
feat(auth): add options to resendSignUpCode (#738)
Browse files Browse the repository at this point in the history
* feat(auth): add options to resendSignUpCode

* fix: add type export for sing up code options

* chore: fix formatting issues

* chore: update comments for consistency

* chore: rename private method names for consistency

* chore: update comments for consistency

* chore: make ResendSignUpCodeOptions abstract

* chore: update ResendSignUpCodeRequest serializeAsMap

* chore: update ios test

* chore update doc comments

* chore: bump amplify-android to 1.24.0

* chore: remove star import
  • Loading branch information
Jordan-Nelson authored Aug 16, 2021
1 parent f7821bc commit 994534c
Show file tree
Hide file tree
Showing 19 changed files with 177 additions and 19 deletions.
4 changes: 2 additions & 2 deletions packages/amplify_analytics_pinpoint/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -60,8 +60,8 @@ dependencies {
api amplifyCore

implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation 'com.amplifyframework:aws-analytics-pinpoint:1.22.0'
implementation 'com.amplifyframework:aws-auth-cognito:1.22.0'
implementation 'com.amplifyframework:aws-analytics-pinpoint:1.24.0'
implementation 'com.amplifyframework:aws-auth-cognito:1.24.0'
testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.1.0'
testImplementation 'org.mockito:mockito-inline:3.1.0'
Expand Down
4 changes: 2 additions & 2 deletions packages/amplify_api/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,8 @@ dependencies {
api amplifyCore

implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation "com.amplifyframework:aws-api:1.22.0"
implementation "com.amplifyframework:aws-api-appsync:1.22.0"
implementation "com.amplifyframework:aws-api:1.24.0"
implementation "com.amplifyframework:aws-api-appsync:1.24.0"

testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.10.0'
Expand Down
2 changes: 1 addition & 1 deletion packages/amplify_auth_cognito/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ android {
dependencies {
api amplifyCore
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation 'com.amplifyframework:aws-auth-cognito:1.22.0'
implementation 'com.amplifyframework:aws-auth-cognito:1.24.0'
testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.10.0'
testImplementation 'org.mockito:mockito-inline:3.1.0'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -246,6 +246,7 @@ public class AuthCognito : FlutterPlugin, ActivityAware, MethodCallHandler, Plug
var req = FlutterResendSignUpCodeRequest(request as HashMap<String, *>);
Amplify.Auth.resendSignUpCode(
req.username,
req.options,
{ result -> prepareResendSignUpCodeResult(flutterResult, result) },
{ error -> errorHandler.handleAuthError(flutterResult, error)}
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,19 @@ package com.amazonaws.amplify.amplify_auth_cognito.types

import com.amazonaws.amplify.amplify_core.exception.ExceptionMessages
import com.amazonaws.amplify.amplify_core.exception.InvalidRequestException
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthResendSignUpCodeOptions

data class FlutterResendSignUpCodeRequest(val map: HashMap<String, *>) {
val username: String = map["username"] as String;
val options: HashMap<String, *>? = map["options"] as HashMap<String, *>?;
val options: AWSCognitoAuthResendSignUpCodeOptions = createOptions(map["options"] as HashMap<String, Any>?)

private fun createOptions(rawOptions: HashMap<String, *>?): AWSCognitoAuthResendSignUpCodeOptions {
val optionsBuilder = AWSCognitoAuthResendSignUpCodeOptions.builder();
if (rawOptions?.get("clientMetadata") != null) {
optionsBuilder.metadata(rawOptions["clientMetadata"] as HashMap<String, String>);
}
return optionsBuilder.build();
}

companion object {
private const val validationErrorMessage: String = "ResendSignUpCode Request malformed."
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,9 +29,11 @@ import com.amplifyframework.auth.cognito.AWSCognitoAuthSession
import com.amplifyframework.auth.cognito.AWSCognitoUserPoolTokens
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthConfirmSignInOptions
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthConfirmSignUpOptions
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthResendSignUpCodeOptions
import com.amplifyframework.auth.cognito.options.AWSCognitoAuthSignInOptions
import com.amplifyframework.auth.options.AuthConfirmSignInOptions
import com.amplifyframework.auth.options.AuthConfirmSignUpOptions
import com.amplifyframework.auth.options.AuthResendSignUpCodeOptions
import com.amplifyframework.auth.options.AuthSignInOptions
import com.amplifyframework.auth.result.AuthSessionResult
import com.amplifyframework.auth.result.step.*
Expand Down Expand Up @@ -301,7 +303,12 @@ class AmplifyAuthCognitoPluginTest {
doAnswer { invocation: InvocationOnMock ->
plugin.prepareSignUpResult(mockResult, mockSignUpResult)
null as Void?
}.`when`(mockAuth).resendSignUpCode(anyString(), ArgumentMatchers.any<Consumer<AuthSignUpResult>>(), ArgumentMatchers.any<Consumer<AuthException>>())
}.`when`(mockAuth).resendSignUpCode(
anyString(),
any(),
ArgumentMatchers.any<Consumer<AuthSignUpResult>>(),
ArgumentMatchers.any<Consumer<AuthException>>()
)

val data: HashMap<*, *> = hashMapOf(
"username" to "testUser"
Expand All @@ -316,6 +323,49 @@ class AmplifyAuthCognitoPluginTest {
verify(mockResult, times(1)).success(ArgumentMatchers.any<LinkedTreeMap<String, Any>>());
}

@Test
fun resendSignUpCodeWithOptions_returnsSuccess() {
// Arrange
doAnswer { invocation: InvocationOnMock ->
plugin.prepareSignUpResult(mockResult, mockSignUpResult)
null as Void?
}.`when`(mockAuth).resendSignUpCode(
anyString(),
ArgumentMatchers.any<AuthResendSignUpCodeOptions>(),
ArgumentMatchers.any<Consumer<AuthSignUpResult>>(),
ArgumentMatchers.any<Consumer<AuthException>>()
)
val clientMetadata = hashMapOf("attribute" to "value")
val options = hashMapOf(
"clientMetadata" to clientMetadata
)
val username = "testUser"
val data: HashMap<*, *> = hashMapOf(
"username" to username,
"options" to options
)
val arguments: HashMap<String, Any> = hashMapOf("data" to data)
val call = MethodCall("resendSignUpCode", arguments)

// Act
plugin.onMethodCall(call, mockResult)

// Assert
verify(mockResult, times(1)).success(ArgumentMatchers.any<LinkedTreeMap<String, Any>>());

val expectedOptions = AWSCognitoAuthResendSignUpCodeOptions
.builder()
.metadata(clientMetadata)
.build()

verify(mockAuth).resendSignUpCode(
ArgumentMatchers.eq(username),
ArgumentMatchers.eq(expectedOptions),
ArgumentMatchers.any<Consumer<AuthSignUpResult>>(),
ArgumentMatchers.any<Consumer<AuthException>>()
)
}

@Test
fun signInNoOptions_returnsSuccess() {
// Arrange
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -549,6 +549,18 @@ class amplify_auth_cognito_tests: XCTestCase {
})
}

func test_resendSignUpCodeRequestWithClientMetadata() {
let metadata: Dictionary<String, Any> = ["attribute": "value"]
let rawOptions: Dictionary<String, Any> = ["clientMetadata": metadata]
let rawData: NSMutableDictionary = [
"username": _username,
"options": rawOptions
]
let request = FlutterResendSignUpCodeRequest(dict: rawData);
let options = request.options?.pluginOptions as! AWSAuthResendSignUpCodeOptions
XCTAssertEqual("value", options.metadata!["attribute"])
}

func test_resendSignUpCodeError() {

class ResendSignUpCodeMock: AuthCognitoBridge {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ class AuthCognitoBridge {
}

func onResendSignUpCode(flutterResult: @escaping FlutterResult, request: FlutterResendSignUpCodeRequest) {
_ = Amplify.Auth.resendSignUpCode(for: request.username) { response in
_ = Amplify.Auth.resendSignUpCode(for: request.username, options: request.options) { response in
switch response {
case .success:
let resendData = FlutterResendSignUpCodeResult(res: response)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,13 +14,25 @@
*/

import Foundation
import Amplify
import AmplifyPlugins
import amplify_core

struct FlutterResendSignUpCodeRequest {
var username: String
var options: AuthResendSignUpCodeRequest.Options?
init(dict: NSMutableDictionary){
self.username = dict["username"] as! String
self.options = createOptions(options: dict["options"] as! Dictionary<String, Any>?)
}

func createOptions(options: Dictionary<String, Any>?) -> AuthResendSignUpCodeOperation.Request.Options {
let pluginOptions = AWSAuthResendSignUpCodeOptions(
metadata: options?["clientMetadata"] as? [String : String]
)
return AuthResendSignUpCodeOperation.Request.Options(pluginOptions: pluginOptions)
}

static func validate(dict: NSMutableDictionary) throws {
let validationErrorMessage = "ResendSignUpCode Request malformed."
if (dict["username"] == nil) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
/*
* Copyright 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License").
* You may not use this file except in compliance with the License.
* A copy of the License is located at
*
* http://aws.amazon.com/apache2.0
*
* or in the "license" file accompanying this file. This file is distributed
* on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
* express or implied. See the License for the specific language governing
* permissions and limitations under the License.
*/

import 'package:amplify_auth_plugin_interface/amplify_auth_plugin_interface.dart';

/// Cognito extension of [ResendSignUpCodeOptions] to add the platform specific fields
class CognitoResendSignUpCodeOptions extends ResendSignUpCodeOptions {
/// Additional custom attributes to be sent to the service such as information about the client
Map<String, String>? clientMetadata;

/// Default constructor
CognitoResendSignUpCodeOptions({this.clientMetadata}) : super();

Map<String, dynamic> serializeAsMap() {
final Map<String, dynamic> pendingRequest = {
'clientMetadata': clientMetadata
};
pendingRequest.removeWhere((_, v) => v == null);
return pendingRequest;
}
}
1 change: 1 addition & 0 deletions packages/amplify_auth_cognito/lib/src/types.dart
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ export 'CognitoSignUp/CognitoSignUpOptions.dart';
export 'CognitoSignUp/CognitoSignUpResult.dart';
export 'CognitoSignUp/CognitoConfirmSignUpOptions.dart';
export 'CognitoSignUp/CognitoResendSignUpCodeResult.dart';
export 'CognitoSignUp/CognitoResendSignUpCodeOptions.dart';
export 'CognitoSignUp/cognito_user_attributes.dart';

// SignIn
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
/*
* Copyright 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
*
* Licensed under the Apache License, Version 2.0 (the "License").
* You may not use this file except in compliance with the License.
* A copy of the License is located at
*
* http://aws.amazon.com/apache2.0
*
* or in the "license" file accompanying this file. This file is distributed
* on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
* express or implied. See the License for the specific language governing
* permissions and limitations under the License.
*/

/// The shared resend sign up code options among all Auth plugins
abstract class ResendSignUpCodeOptions {
/// Serialize the object to a map
Map<String, dynamic> serializeAsMap();
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,25 @@
* permissions and limitations under the License.
*/

import 'package:amplify_auth_plugin_interface/amplify_auth_plugin_interface.dart';

/// Encapsulates parameters for a resend sign up code request
class ResendSignUpCodeRequest {
/// A login identifier or an email/phone number, depending on configuration
String username;

ResendSignUpCodeRequest({required this.username});
/// Plugin-specific, advanced options such as information about the client
ResendSignUpCodeOptions? options;

/// Default constructor
ResendSignUpCodeRequest({required this.username, this.options});

/// Serialize the object to a map for use over the method channel
Map<String, dynamic> serializeAsMap() {
final Map<String, dynamic> pendingRequest = {'username': username};
pendingRequest.removeWhere((_, v) => v == null);
final Map<String, dynamic> pendingRequest = {
'username': username,
if (options != null) 'options': options?.serializeAsMap(),
};
return pendingRequest;
}
}
1 change: 1 addition & 0 deletions packages/amplify_auth_plugin_interface/lib/src/types.dart
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ export 'SignUp/ConfirmSignUpRequest.dart';
export 'SignUp/ConfirmSignUpOptions.dart';
export 'SignUp/SignUpOptions.dart';
export 'SignUp/AuthNextSignUpStep.dart';
export 'SignUp/ResendSignUpCodeOptions.dart';
export 'SignUp/ResendSignUpCodeRequest.dart';
export 'SignUp/ResendSignUpCodeResult.dart';

Expand Down
2 changes: 1 addition & 1 deletion packages/amplify_core/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ android {

dependencies {
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation 'com.amplifyframework:core:1.22.0'
implementation 'com.amplifyframework:core:1.24.0'
implementation 'com.google.code.gson:gson:2.8.6'
testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.1.0'
Expand Down
4 changes: 2 additions & 2 deletions packages/amplify_datastore/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@ android {

dependencies {
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation "com.amplifyframework:aws-datastore:1.22.0"
implementation "com.amplifyframework:aws-api-appsync:1.22.0"
implementation "com.amplifyframework:aws-datastore:1.24.0"
implementation "com.amplifyframework:aws-api-appsync:1.24.0"
testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.10.0'
testImplementation 'org.mockito:mockito-inline:3.10.0'
Expand Down
4 changes: 2 additions & 2 deletions packages/amplify_flutter/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -58,13 +58,13 @@ android {

dependencies {
api amplifyCore
implementation 'com.amplifyframework:core:1.22.0'
implementation 'com.amplifyframework:core:1.24.0'
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
testImplementation 'junit:junit:4.13'
testImplementation 'org.mockito:mockito-core:3.1.0'
testImplementation 'org.mockito:mockito-inline:3.1.0'
testImplementation 'androidx.test:core:1.3.0'
testImplementation 'org.robolectric:robolectric:4.3.1'
testImplementation 'com.google.code.gson:gson:2.8.6'
testImplementation 'com.amplifyframework:aws-auth-cognito:1.22.0'
testImplementation 'com.amplifyframework:aws-auth-cognito:1.24.0'
}
Original file line number Diff line number Diff line change
Expand Up @@ -69,8 +69,15 @@ class AuthCategory {
: throw _pluginNotAddedException("Auth");
}

Future<ResendSignUpCodeResult> resendSignUpCode({required String username}) {
var request = ResendSignUpCodeRequest(username: username);
/// Resends the code that is used to confirm the user's account after sign up
///
/// Resends the code to the user with the given [username], where [username]
/// is a login identifier or an email/phone number, depending on the configuration
///
/// Accepts plugin-specific, advanced [options] for the request
Future<ResendSignUpCodeResult> resendSignUpCode(
{required String username, ResendSignUpCodeOptions? options}) {
var request = ResendSignUpCodeRequest(username: username, options: options);
return plugins.length == 1
? plugins[0].resendSignUpCode(request: request)
: throw _pluginNotAddedException("Auth");
Expand Down
2 changes: 1 addition & 1 deletion packages/amplify_storage_s3/android/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -49,5 +49,5 @@ android {
dependencies {
api amplifyCore
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
implementation 'com.amplifyframework:aws-storage-s3:1.22.0'
implementation 'com.amplifyframework:aws-storage-s3:1.24.0'
}

0 comments on commit 994534c

Please sign in to comment.