Closed rahul-insight closed 2 years ago
Hello @rahul-insight - What version of amplify-flutter are you using?
Hello @Jordan-Nelson We are using the below packages in our project. We tried upgrading all of them to the latest version 0.2.10 but that didn't make a difference.
amplify_auth_cognito: ^0.2.0 amplify_api: ^0.2.0 amplify_flutter: ^0.2.0 amplify_core: ^0.2.0 amplify_analytics_pinpoint: ^0.2.0
Our Amplify CLI version is 5.1.2
Hello @Jordan-Nelson . Is there any update on this? This is blocking our release. Can you please provide your input.
Here is some more info. This is what we have in our build.gradle
buildTypes {
release {
signingConfig signingConfigs.release
minifyEnabled false
shrinkResources false
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
}
}
And the proguard-rule.pro contains:
-keep class com.amazonaws.** { *; }
-keep class com.amplifyframework.** { *; }
-keepnames class com.amazonaws.**
-keepnames class com.amazon.**
# Request handlers defined in request.handlers
-keep class com.amazonaws.services.**.*Handler
# The following are referenced but aren't required to run
-dontwarn com.fasterxml.jackson.**
-dontwarn org.apache.commons.logging.**
# Android 6.0 release removes support for the Apache HTTP client
-dontwarn org.apache.http.**
# The SDK has several references of Apache HTTP client
-dontwarn com.amazonaws.http.**
-dontwarn com.amazonaws.metrics.**
-dontwarn com.amazonaws.mobile.**
-dontwarn com.amazonaws.mobileconnectors.**
-keep class org.apache.commons.logging.** { *; }
-keep class com.amazonaws.services.sqs.QueueUrlHandler { *; }
-keep class com.amazonaws.javax.xml.transform.sax.* { public *; }
-keep class com.amazonaws.javax.xml.stream.** { *; }
-keep class com.amazonaws.services.**.model.*Exception* { *; }
-keep class org.codehaus.** { *; }
-keepattributes Signature,*Annotation*
@rahul-insight thanks for the info. I will attempt to reproduce this with the info above.
@Jordan-Nelson While trying to debug this issue, I have a hunch that AmplifyAuthCognito
is somehow getting obfuscated while building in "release mode". What I'm observing is on subsequent app openings Amplify.Auth.getCurrentUser()
returns Null in release mode, but returns proper value in debug mode.
A little hack that I'm trying just for the purpose of debugging is making await on the function that adds Auth plugin (for that I've to temporarily make main async). Can you please suggest how to prevent AmplifyAuthCognito plugin from getting obfuscated in release build?
void main() **async** {
WidgetsFlutterBinding.ensureInitialized();
**await** initAmplify();
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp])
.then((_) {
runApp(MaterialApp(
home: App(),
debugShowCheckedModeBanner: false,
));
});
}
Future<void> initAmplify() async {
// Add Pinpoint and Cognito Plugins
final AmplifyAuthCognito authPlugin = AmplifyAuthCognito();
final AmplifyAPI apiPlugin = AmplifyAPI();
final AmplifyAnalyticsPinpoint analyticsPinpoint = AmplifyAnalyticsPinpoint();
Amplify.addPlugins([authPlugin, apiPlugin, analyticsPinpoint]);
// Once Plugins are added, configure Amplify
// Note: Amplify can only be configured once.
try {
await Amplify.configure(amplifyconfig);
} on AmplifyAlreadyConfiguredException {
AppLogger.instance
.e('Amplify was already configured. Was the app restarted?');
} catch (e) {
AppLogger.instance.e(e);
}
}
Hi @rahul-insight thanks for providing more information.
You mentioned the issue only happens on the actual physical device. But when you deploy your app from Android Studio to a physical device do you observe the same problem? Also you said that if you build an AAB from Android Studio there is no problem as well? So is your code actually working on physical devices in those 2 cases?
Can you provide more details on what is happening when Authentication fails when the user closes the app (sign out happens). What error message are you getting? What exactly is happening here?
You mentioned that the build kicks out some of the Amplify files, how do you know this and what files do you see as missing?
Depending on your answers to the questions above, it might be easier for you to share your repo with us so we can try to reproduce on our side. It would also be helpful to know if this is just due to codemagic or if your issue arises in other deployment cases as well.
Hi @rahul-insight
Following up on this if you can get back to us please with the details requested by @fjnoyp above
Regards Mo
@offlineprogrammer To summarize our experience:
Amplify.Auth.getCurrentUser()
returned NULLvoid main() **async** {
WidgetsFlutterBinding.ensureInitialized();
**await** initAmplify();
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp])
.then((_) {
runApp(MaterialApp(
home: App(),
debugShowCheckedModeBanner: false,
));
});
}
@rahul-insight - Sorry for the lag in response here.
When you were experiencing this issue, did you have initAmplify
in the same location, just without the await
?
Without the await, there would be nothing preventing your app from calling amplify methods before configuration has finished (unless you have some logic elsewhere to prevent this). I would expect getCurrentUser()
to throw an Exception if called before Amplify.configure()
had completed, but it is possible it behaves differently in release mode. I would need to test the behavior in release mode. Either way, it would be expected to see issues if getCurrentUser()
was called before Amplify.configure()
had completed. It is possible you are only seeing the issues in release mode since the calls to configure and getCurrentUser would present a race condition.
Adding the await
to ensure amplify is initialized before calling runApp is one way to ensure that no Amplify methods are called prior to configuration. There shouldn't be an issue with this. However, the way we recommend doing this in our docs is a little different. The way we typically recommend to do this is to call Amplify.configure() in a stateful widget and display some sort of a loading indicator in your app until it completes. Below is an example of that.
import 'package:amplify_auth_cognito/amplify_auth_cognito.dart';
import 'package:amplify_flutter/amplify_flutter.dart';
import 'package:flutter/material.dart';
import 'amplifyconfiguration.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({Key? key}) : super(key: key);
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
/// boolean to keep track of configuration state.
bool _isConfigured = false;
@override
void initState() {
super.initState();
/// configure Amplify within initState.
_configureAmplify();
}
void _configureAmplify() async {
try {
await Amplify.addPlugin(AmplifyAuthCognito());
await Amplify.configure(amplifyconfig);
// set _isConfigured to true after `Amplify.configure` completes.
setState(() {
_isConfigured = true;
});
} on Exception catch (e) {
print('Error configuring Amplify: $e');
}
}
@override
Widget build(BuildContext context) {
return MaterialApp(
/// display a loading indicator until amplify is configured.
home: _isConfigured
? const HomeWidget()
: const Center(
child: CircularProgressIndicator(),
),
);
}
}
class HomeWidget extends StatefulWidget {
const HomeWidget({
Key? key,
}) : super(key: key);
@override
State<HomeWidget> createState() => _HomeWidgetState();
}
class _HomeWidgetState extends State<HomeWidget> {
@override
void initState() {
try {
/// HomeWidget will not display until Amplify is configured, so calling
/// Amplify methods will be safe.
final session = Amplify.Auth.getCurrentUser();
} on Exception catch (e) {
/// handle exception (direct user to login for example)
}
super.initState();
}
@override
Widget build(BuildContext context) {
/// display your app
}
}
@rahul-insight - Based on the code sample and workaround that you provided, I think it is likely you are seeing a race condition that is only presenting itself in a release built. As mentioned above, Amplify.configure should either be awaited as you have done, or you should track the completion of this call to prevent other amplify methods from being called before it completes.
Please let me know if you have any questions. Thanks.
@rahul-insight - I am going to close this out since the way that you have worked around this is the suggested pattern. Please open a new issue if you are still experiencing any issues.
Describe the bug We are using AWS Amplify and building our Flutter app on Codemagic by pulling in Amplify env. For Android while building an AAB on Codemagic in "release" mode, the build kicks out some of the Amplify files, resulting in Authentication failing when the user closes the app (sign out happens). This issue doesn't happen on iOS or if we build in "debug" mode or build an AAB on the local machine.
The issue only happens on the actual device. Does anyone know why Amplify is signing out for a release AAB on every app closure?
Adding "--no-shrink" during build or "proguard-rules.pro" to the android/app as mentioned here didn't work: https://github.com/aws-amplify/amplify-flutter/issues/317 https://stackoverflow.com/questions/64565537/aws-amplify-flutters-auth-signup-function-is-not-working-when-deployed-via-andr
To Reproduce Build AAB file from Flutter app using Amplify Authentication (Social sign in) using:
flutter build appbundle --release
Platform Amplify Flutter current supports iOS and Android. This issue is reproducible in (check all that apply): [X] Android [] iOS
Output of
```[√] Flutter (Channel stable, 2.5.3, on Microsoft Windows [Version 10.0.22000.348], locale en-US) • Flutter version 2.5.3 at C:\Users\rahul\Projects\flutter • Upstream repository https://github.com/flutter/flutter.git • Framework revision 18116933e7 (6 weeks ago), 2021-10-15 10:46:35 -0700 • Engine revision d3ea636dc5 • Dart version 2.14.4 [!] Android toolchain - develop for Android devices (Android SDK version 30.0.3) • Android SDK at C:\Users\rahul\AppData\Local\Android\sdk X cmdline-tools component is missing Run `path/to/sdkmanager --install "cmdline-tools;latest"` See https://developer.android.com/studio/command-line for more details. X Android license status unknown. Run `flutter doctor --android-licenses` to accept the SDK licenses. See https://flutter.dev/docs/get-started/install/windows#android-setup for more details. [√] Chrome - develop for the web • Chrome at C:\Program Files\Google\Chrome\Application\chrome.exe [√] Android Studio (version 4.1) • Android Studio at C:\Program Files\Android\Android Studio • Flutter plugin can be installed from: https://plugins.jetbrains.com/plugin/9212-flutter • Dart plugin can be installed from: https://plugins.jetbrains.com/plugin/6351-dart • Java version OpenJDK Runtime Environment (build 1.8.0_242-release-1644-b01) [√] VS Code (version 1.62.3) • VS Code at C:\Users\rahul\AppData\Local\Programs\Microsoft VS Code • Flutter extension version 3.28.0 [√] Connected device (3 available) • sdk gphone x86 (mobile) • emulator-5554 • android-x86 • Android 11 (API 30) (emulator) • Chrome (web) • chrome • web-javascript • Google Chrome 96.0.4664.45 • Edge (web) • edge • web-javascript • Microsoft Edge 95.0.1020.53 ! Doctor found issues in 1 category.```flutter doctor -v
Dependencies (
``` Paste the contents of your "pubspec.lock" file here ```pubspec.lock
)Smartphone (please complete the following information):
Additional context Add any other context about the problem here.