v1.1.26+110 android release

This commit is contained in:
Tibor Bossanyi (Freelancer) 2022-11-13 21:26:27 +01:00
parent 6ef311286c
commit cbaa1a5b81
9 changed files with 77 additions and 118 deletions

View File

@ -54,7 +54,6 @@ android {
android { android {
compileSdkVersion 33 compileSdkVersion 33
} }
signingConfigs { signingConfigs {

View File

@ -93,11 +93,10 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
Track().track(TrackingEvent.login, eventValue: "email"); Track().track(TrackingEvent.login, eventValue: "email");
Cache().setLoginType(LoginType.email); Cache().setLoginType(LoginType.email);
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { }
emit(LoginSuccess());
}
} }
void _onLoginFB(LoginFB event, Emitter<LoginState> emit) async { void _onLoginFB(LoginFB event, Emitter<LoginState> emit) async {
@ -107,11 +106,10 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
await userRepository.getUserByFB(); await userRepository.getUserByFB();
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
Track().track(TrackingEvent.login, eventValue: "FB"); Track().track(TrackingEvent.login, eventValue: "FB");
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { }
emit(LoginSuccess());
}
} }
void _onLoginGoogle(LoginGoogle event, Emitter<LoginState> emit) async { void _onLoginGoogle(LoginGoogle event, Emitter<LoginState> emit) async {
@ -121,11 +119,10 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
await userRepository.getUserByGoogle(); await userRepository.getUserByGoogle();
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
Track().track(TrackingEvent.login, eventValue: "Google"); Track().track(TrackingEvent.login, eventValue: "Google");
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { }
emit(LoginSuccess());
}
} }
void _onLoginApple(LoginApple event, Emitter<LoginState> emit) async { void _onLoginApple(LoginApple event, Emitter<LoginState> emit) async {
@ -135,10 +132,9 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
await userRepository.getUserByApple(); await userRepository.getUserByApple();
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
Track().track(TrackingEvent.login, eventValue: "Apple"); Track().track(TrackingEvent.login, eventValue: "Apple");
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally {
emit(LoginSuccess());
} }
} }
@ -154,12 +150,14 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0; customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0;
await afterRegistration("email"); await afterRegistration("email");
Cache().setLoginType(LoginType.email); Cache().setLoginType(LoginType.email);
emit(LoginSuccess());
} }
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { return;
emit(LoginSuccess()); }
}
} }
void _onRegistrationFB(RegistrationFB event, Emitter<LoginState> emit) async { void _onRegistrationFB(RegistrationFB event, Emitter<LoginState> emit) async {
@ -170,11 +168,12 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0; customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0;
await afterRegistration("FB"); await afterRegistration("FB");
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { }
emit(LoginSuccess());
}
} }
void _onRegistrationGoogle(RegistrationGoogle event, Emitter<LoginState> emit) async { void _onRegistrationGoogle(RegistrationGoogle event, Emitter<LoginState> emit) async {
@ -185,11 +184,11 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0; customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0;
await afterRegistration("Google"); await afterRegistration("Google");
} on Exception catch (e) {
emit(LoginError(message: e.toString()));
} finally {
emit(LoginSuccess()); emit(LoginSuccess());
} } on Exception catch (e) {
emit(LoginError(message: e.toString()));
}
} }
void _onRegistrationApple(RegistrationApple event, Emitter<LoginState> emit) async { void _onRegistrationApple(RegistrationApple event, Emitter<LoginState> emit) async {
@ -200,11 +199,10 @@ class LoginBloc extends Bloc<LoginEvent, LoginState> with Trans {
accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!)); accountBloc.add(AccountLogInFinished(customer: Cache().userLoggedIn!));
customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0; customerRepository!.customer!.emailSubscription = emailSubscription == true ? 1 : 0;
await afterRegistration("Apple"); await afterRegistration("Apple");
emit(LoginSuccess());
} on Exception catch (e) { } on Exception catch (e) {
emit(LoginError(message: e.toString())); emit(LoginError(message: e.toString()));
} finally { }
emit(LoginSuccess());
}
} }
void _onDataProtectionClicked(DataProtectionClicked event, Emitter<LoginState> emit) async { void _onDataProtectionClicked(DataProtectionClicked event, Emitter<LoginState> emit) async {

View File

@ -37,10 +37,9 @@ class SessionBloc extends Bloc<SessionEvent, SessionState> with Logging {
resultsFuture.then((results) { resultsFuture.then((results) {
print('iTunes results: $results'); print('iTunes results: $results');
}); });
emit(SessionReady());
} on Exception catch (e) { } on Exception catch (e) {
emit(SessionFailure(message: e.toString())); emit(SessionFailure(message: e.toString()));
} finally {
emit(SessionReady());
} }
} }

View File

@ -124,7 +124,7 @@ Future<Null> main() async {
Posthog().setContext({ Posthog().setContext({
'device': { 'device': {
'token': 'v1.26 test', 'token': 'v1.1.26',
} }
}); });
} }
@ -292,7 +292,7 @@ class WorkoutTestApp extends StatelessWidget {
)), )),
navigatorObservers: [ navigatorObservers: [
FirebaseAnalyticsObserver(analytics: analytics), FirebaseAnalyticsObserver(analytics: analytics),
//PosthogObserver(), PosthogObserver(),
], ],
home: AitrainerHome(), home: AitrainerHome(),
); );

View File

@ -3,6 +3,7 @@ import 'dart:convert';
import 'package:crypto/crypto.dart'; import 'package:crypto/crypto.dart';
import 'package:aitrainer_app/model/cache.dart'; import 'package:aitrainer_app/model/cache.dart';
import 'package:aitrainer_app/service/logging.dart' as logging; import 'package:aitrainer_app/service/logging.dart' as logging;
import 'package:sentry_flutter/sentry_flutter.dart';
import 'package:sign_in_with_apple/sign_in_with_apple.dart'; import 'package:sign_in_with_apple/sign_in_with_apple.dart';
import 'package:firebase_auth/firebase_auth.dart'; import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_core/firebase_core.dart'; import 'package:firebase_core/firebase_core.dart';
@ -36,26 +37,7 @@ class FirebaseApi with logging.Logging {
await Firebase.initializeApp(); await Firebase.initializeApp();
this.appleSignInAvailable = await SignInWithApple.isAvailable(); this.appleSignInAvailable = await SignInWithApple.isAvailable();
/* AwesomeNotifications().initialize(
// set the icon to null if you want to use the default app icon
null,
[
NotificationChannel(
channelKey: 'basic_channel',
channelName: 'Basic notifications',
channelDescription: 'Notification channel for basic tests',
defaultColor: Color(0xFF9D50DD),
ledColor: Colors.white)
]);
AwesomeNotifications().isNotificationAllowed().then((isAllowed) {
if (!isAllowed) {
// Insert here your friendly dialog box before call the request method
// This is very important to not harm the user experience
AwesomeNotifications().requestPermissionToSendNotifications();
}
}); */
await FirebaseMessaging.instance.setForegroundNotificationPresentationOptions( await FirebaseMessaging.instance.setForegroundNotificationPresentationOptions(
alert: true, // Required to display a heads up notification alert: true, // Required to display a heads up notification
@ -77,6 +59,7 @@ class FirebaseApi with logging.Logging {
}); });
} catch (e) { } catch (e) {
// Set `_error` state to true if Firebase initialization fails // Set `_error` state to true if Firebase initialization fails
Sentry.captureException(e);
log("Error initializing Firebase"); log("Error initializing Firebase");
} }
} }
@ -93,6 +76,7 @@ class FirebaseApi with logging.Logging {
userCredential = await FirebaseAuth.instance.signInWithEmailAndPassword(email: email, password: password); userCredential = await FirebaseAuth.instance.signInWithEmailAndPassword(email: email, password: password);
Cache().firebaseUid = userCredential.user!.uid; Cache().firebaseUid = userCredential.user!.uid;
} on FirebaseAuthException catch (e) { } on FirebaseAuthException catch (e) {
Sentry.captureException(e);
if (e.code == 'user-not-found') { if (e.code == 'user-not-found') {
log('No user found for that email.'); log('No user found for that email.');
rc = SIGN_IN_NOT_FOUND; rc = SIGN_IN_NOT_FOUND;
@ -112,6 +96,7 @@ class FirebaseApi with logging.Logging {
userCredential = await FirebaseAuth.instance.createUserWithEmailAndPassword(email: email, password: password); userCredential = await FirebaseAuth.instance.createUserWithEmailAndPassword(email: email, password: password);
Cache().firebaseUid = userCredential.user!.uid; Cache().firebaseUid = userCredential.user!.uid;
} on FirebaseAuthException catch (e) { } on FirebaseAuthException catch (e) {
Sentry.captureException(e);
if (e.code == 'weak-password') { if (e.code == 'weak-password') {
log('The password provided is too weak.'); log('The password provided is too weak.');
rc = REGISTER_WEAK_PWD; rc = REGISTER_WEAK_PWD;
@ -123,6 +108,7 @@ class FirebaseApi with logging.Logging {
} }
} catch (e) { } catch (e) {
log(e.toString()); log(e.toString());
Sentry.captureException(e);
throw Exception(e.toString()); throw Exception(e.toString());
} }
return rc; return rc;
@ -143,27 +129,7 @@ class FirebaseApi with logging.Logging {
Future<Map<String, dynamic>> signInWithApple() async { Future<Map<String, dynamic>> signInWithApple() async {
Map<String, dynamic> userData = Map(); Map<String, dynamic> userData = Map();
/* final apple.AuthorizationResult result = await SignInWithApple.performRequests([
apple.AppleIdRequest(requestedScopes: [apple.Scope.email, apple.Scope.fullName])
]);
switch (result.status) {
case apple.AuthorizationStatus.authorized:
print('User authorized');
break;
case apple.AuthorizationStatus.error:
print('User error');
throw Exception("Apple Sign-In failed");
case apple.AuthorizationStatus.cancelled:
print('User cancelled');
throw Exception("Apple Sign-In cancelled");
}
// Create an `OAuthCredential` from the credential returned by Apple.
final oauthCredential = OAuthProvider("apple.com").credential(
idToken: String.fromCharCodes(result.credential.identityToken),
accessToken: String.fromCharCodes(result.credential.authorizationCode!));
*/
// To prevent replay attacks with the credential returned from Apple, we // To prevent replay attacks with the credential returned from Apple, we
// include a nonce in the credential request. When signing in with // include a nonce in the credential request. When signing in with
// Firebase, the nonce in the id token returned by Apple, is expected to // Firebase, the nonce in the id token returned by Apple, is expected to
@ -185,9 +151,15 @@ class FirebaseApi with logging.Logging {
idToken: appleCredential.identityToken, idToken: appleCredential.identityToken,
rawNonce: rawNonce, rawNonce: rawNonce,
); );
// Sign in the user with Firebase. If the nonce we generated earlier does UserCredential? userCredential;
// not match the nonce in `appleCredential.identityToken`, sign in will fail. try {
UserCredential userCredential = await FirebaseAuth.instance.signInWithCredential(oauthCredential); // Sign in the user with Firebase. If the nonce we generated earlier does
// not match the nonce in `appleCredential.identityToken`, sign in will fail.
userCredential = await FirebaseAuth.instance.signInWithCredential(oauthCredential);
} on FirebaseAuthException catch(e) {
Sentry.captureException(e);
throw Exception(e);
}
Cache().firebaseUid = userCredential.user!.uid; Cache().firebaseUid = userCredential.user!.uid;
log("userCredential: " + userCredential.toString()); log("userCredential: " + userCredential.toString());
@ -199,21 +171,7 @@ class FirebaseApi with logging.Logging {
Future<Map<String, dynamic>> registerWithApple() async { Future<Map<String, dynamic>> registerWithApple() async {
Map<String, dynamic> userData = Map(); Map<String, dynamic> userData = Map();
/* final apple.AuthorizationResult result = await apple.TheAppleSignIn.performRequests([
apple.AppleIdRequest(requestedScopes: [apple.Scope.email, apple.Scope.fullName])
]);
switch (result.status) {
case apple.AuthorizationStatus.authorized:
print('Apple User authorized');
break;
case apple.AuthorizationStatus.error:
print('Apple User error');
throw Exception("Apple Sign-In failed");
case apple.AuthorizationStatus.cancelled:
print('User cancelled');
throw Exception("Apple Sign-In cancelled");
}
*/
final rawNonce = generateNonce(); final rawNonce = generateNonce();
final nonce = sha256ofString(rawNonce); final nonce = sha256ofString(rawNonce);
@ -231,18 +189,19 @@ class FirebaseApi with logging.Logging {
rawNonce: rawNonce, rawNonce: rawNonce,
); );
/* // Create an `OAuthCredential` from the credential returned by Apple. UserCredential? userCredential;
final oauthCredential = OAuthProvider("apple.com").credential( try {
idToken: String.fromCharCodes(result.credential.identityToken), // Sign in the user with Firebase. If the nonce we generated earlier does
accessToken: String.fromCharCodes(result.credential.authorizationCode)); // not match the nonce in `appleCredential.identityToken`, sign in will fail.
*/ userCredential = await FirebaseAuth.instance.signInWithCredential(oauthCredential);
// Sign in the user with Firebase. If the nonce we generated earlier does } on FirebaseAuthException catch(e) {
// not match the nonce in `appleCredential.identityToken`, sign in will fail. Sentry.captureException(e);
UserCredential userCredential = await FirebaseAuth.instance.signInWithCredential(oauthCredential); throw Exception(e);
}
Cache().firebaseUid = userCredential.user!.uid; Cache().firebaseUid = userCredential!.user!.uid;
userData['email'] = userCredential.user!.email; userData['email'] = userCredential!.user!.email;
return userData; return userData;
} }
@ -260,6 +219,7 @@ class FirebaseApi with logging.Logging {
final GoogleSignInAccount? googleUser = await _googleSignIn.signIn(); final GoogleSignInAccount? googleUser = await _googleSignIn.signIn();
if (googleUser == null) { if (googleUser == null) {
Sentry.captureException(new Exception("Google Sign In failed"));
throw Exception("Google Sign In failed"); throw Exception("Google Sign In failed");
} }
@ -296,6 +256,7 @@ class FirebaseApi with logging.Logging {
final GoogleSignInAccount? googleUser = await _googleSignIn.signIn(); final GoogleSignInAccount? googleUser = await _googleSignIn.signIn();
if (googleUser == null) { if (googleUser == null) {
Sentry.captureException(new Exception("Google Sign In failed"));
throw Exception("Google Sign In failed"); throw Exception("Google Sign In failed");
} }
@ -332,6 +293,7 @@ class FirebaseApi with logging.Logging {
Cache().firebaseUid = userData['id']; Cache().firebaseUid = userData['id'];
log(userData.toString()); log(userData.toString());
} else { } else {
Sentry.captureException(new Exception(result.message));
throw Exception("Facebook login was not successful"); throw Exception("Facebook login was not successful");
} }
@ -359,6 +321,7 @@ class FirebaseApi with logging.Logging {
Cache().firebaseUid = userCredential.user!.uid; Cache().firebaseUid = userCredential.user!.uid;
} else { } else {
Sentry.captureException(new Exception(result.message));
throw Exception("Facebook login was not successful"); throw Exception("Facebook login was not successful");
} }

View File

@ -39,14 +39,15 @@ class Track with Logging {
} else { } else {
MatomoTracker.instance.trackEvent(eventCategory: "wt", action: event.enumToString()); MatomoTracker.instance.trackEvent(eventCategory: "wt", action: event.enumToString());
} }
Posthog().capture( Posthog().capture(
eventName: event.enumToString(), eventName: event.enumToString(),
properties: { properties: {
'action': eventValue, 'eventValue': eventValue,
'customer': tracking.customerId, 'customer': tracking.customerId,
}, },
); );
} }
} }
} }

View File

@ -1,9 +1,8 @@
import 'dart:io';
import 'package:aitrainer_app/bloc/session/session_bloc.dart'; import 'package:aitrainer_app/bloc/session/session_bloc.dart';
import 'package:aitrainer_app/bloc/settings/settings_bloc.dart'; import 'package:aitrainer_app/bloc/settings/settings_bloc.dart';
import 'package:aitrainer_app/model/cache.dart'; import 'package:aitrainer_app/model/cache.dart';
import 'package:aitrainer_app/service/logging.dart'; import 'package:aitrainer_app/service/logging.dart';
import 'package:aitrainer_app/util/app_language.dart';
import 'package:aitrainer_app/util/trans.dart'; import 'package:aitrainer_app/util/trans.dart';
import 'package:aitrainer_app/view/customer_goal_page.dart'; import 'package:aitrainer_app/view/customer_goal_page.dart';
import 'package:aitrainer_app/view/login.dart'; import 'package:aitrainer_app/view/login.dart';
@ -73,19 +72,12 @@ class _HomePageState extends State<AitrainerHome> with Logging, Trans, Traceable
setContext(context); setContext(context);
final appcastURL = "https://raw.githubusercontent.com/bossanyit/appcast/main/android_rss.xml"; final appcastURL = "https://raw.githubusercontent.com/bossanyit/appcast/main/android_rss.xml";
final cfg = AppcastConfiguration(url: appcastURL, supportedOS: ['android']); final cfg = AppcastConfiguration(url: appcastURL, supportedOS: ['android']);
print("Packageinfo ${Cache().packageInfo}");
String minVersion = "";
if (Platform.isAndroid) {
minVersion = "[Minimum supported app version: 1.1.26]";
} else {
minVersion = "[:mav: 1.1.26]";
}
return Scaffold( return Scaffold(
key: _scaffoldKey, key: _scaffoldKey,
body: UpgradeAlert( body: UpgradeAlert(
upgrader: Upgrader( upgrader: Upgrader(
countryCode: "hu", minAppVersion: minVersion, appcastConfig: cfg, messages: MyLocalizedUpgraderMessages(context: context)), countryCode: AppLanguage().appLocal.toString(), appcastConfig: cfg, messages: MyLocalizedUpgraderMessages(context: context)),
child: BlocConsumer<SessionBloc, SessionState>(listener: (context, state) { child: BlocConsumer<SessionBloc, SessionState>(listener: (context, state) {
if (state is SessionFailure) { if (state is SessionFailure) {
showDialog( showDialog(

View File

@ -176,6 +176,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.3.0" version: "1.3.0"
cli_util:
dependency: transitive
description:
name: cli_util
url: "https://pub.dartlang.org"
source: hosted
version: "0.3.5"
clock: clock:
dependency: transitive dependency: transitive
description: description:
@ -574,12 +581,12 @@ packages:
source: hosted source: hosted
version: "2.2.1" version: "2.2.1"
flutter_launcher_icons: flutter_launcher_icons:
dependency: "direct dev" dependency: "direct main"
description: description:
name: flutter_launcher_icons name: flutter_launcher_icons
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "0.9.2" version: "0.10.0"
flutter_layout_grid: flutter_layout_grid:
dependency: transitive dependency: transitive
description: description:
@ -811,7 +818,7 @@ packages:
name: json_annotation name: json_annotation
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "4.4.0" version: "4.7.0"
keyboard_actions: keyboard_actions:
dependency: "direct main" dependency: "direct main"
description: description:

View File

@ -15,7 +15,7 @@ publish_to: 'none' # Remove this line if you wish to publish to pub.dev
# In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion. # In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion.
# Read more about iOS versioning at # Read more about iOS versioning at
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html # https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
version: 1.1.26+108 version: 1.1.26+110
environment: environment:
sdk: ">=2.12.0 <3.9.0" sdk: ">=2.12.0 <3.9.0"
@ -54,6 +54,7 @@ dependencies:
flutter_fancy_tree_view: ^0.5.1+1 flutter_fancy_tree_view: ^0.5.1+1
flutter_facebook_auth: ^4.4.1+1 flutter_facebook_auth: ^4.4.1+1
flutter_fadein: ^2.0.0 flutter_fadein: ^2.0.0
flutter_launcher_icons: ^0.10.0
flutter_lints: ^2.0.1 flutter_lints: ^2.0.1
flutter_radar_chart: ^0.2.1 flutter_radar_chart: ^0.2.1
flutter_secure_storage: ^5.0.2 flutter_secure_storage: ^5.0.2
@ -123,12 +124,11 @@ dev_dependencies:
intl: ^0.17.0 intl: ^0.17.0
shared_preferences: ^2.0.5 shared_preferences: ^2.0.5
flutter_launcher_icons: ^0.9.0
flutter_icons: flutter_icons:
android: "launcher_icon" android: "launcher_icon"
image_path: "asset/icon/icon.png" image_path: "asset/icon/icon.png"
ios: true
# For information on the generic Dart part of this file, see the # For information on the generic Dart part of this file, see the
# following page: https://dart.dev/tools/pub/pubspec # following page: https://dart.dev/tools/pub/pubspec