mirror of
https://github.com/cake-tech/cake_wallet.git
synced 2025-01-31 06:55:59 +00:00
Show popup on un-caught exceptions to send errors via email
This commit is contained in:
parent
baeff1ea14
commit
e904c0a7b7
3 changed files with 40 additions and 114 deletions
|
@ -9,7 +9,6 @@ import 'package:cake_wallet/buy/order.dart';
|
||||||
import 'package:cake_wallet/entities/preferences_key.dart';
|
import 'package:cake_wallet/entities/preferences_key.dart';
|
||||||
import 'package:cake_wallet/ionia/ionia_category.dart';
|
import 'package:cake_wallet/ionia/ionia_category.dart';
|
||||||
import 'package:cake_wallet/ionia/ionia_merchant.dart';
|
import 'package:cake_wallet/ionia/ionia_merchant.dart';
|
||||||
import 'package:cake_wallet/src/screens/failure_page.dart';
|
|
||||||
import 'package:cake_wallet/src/widgets/alert_with_two_actions.dart';
|
import 'package:cake_wallet/src/widgets/alert_with_two_actions.dart';
|
||||||
import 'package:cake_wallet/store/yat/yat_store.dart';
|
import 'package:cake_wallet/store/yat/yat_store.dart';
|
||||||
import 'package:cake_wallet/themes/theme_list.dart';
|
import 'package:cake_wallet/themes/theme_list.dart';
|
||||||
|
@ -17,6 +16,7 @@ import 'package:cake_wallet/utils/show_pop_up.dart';
|
||||||
import 'package:flutter/foundation.dart';
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter/services.dart';
|
import 'package:flutter/services.dart';
|
||||||
|
import 'package:flutter_mailer/flutter_mailer.dart';
|
||||||
import 'package:hive/hive.dart';
|
import 'package:hive/hive.dart';
|
||||||
import 'package:cake_wallet/di.dart';
|
import 'package:cake_wallet/di.dart';
|
||||||
import 'package:path_provider/path_provider.dart';
|
import 'package:path_provider/path_provider.dart';
|
||||||
|
@ -57,31 +57,14 @@ Future<void> main() async {
|
||||||
WidgetsFlutterBinding.ensureInitialized();
|
WidgetsFlutterBinding.ensureInitialized();
|
||||||
|
|
||||||
FlutterError.onError = (errorDetails) {
|
FlutterError.onError = (errorDetails) {
|
||||||
print("@@@@@@@@@@@@@@@@@ in on error");
|
|
||||||
print(errorDetails.exception.toString());
|
|
||||||
_onError(errorDetails);
|
_onError(errorDetails);
|
||||||
_saveException(errorDetails.exception.toString(), errorDetails.stack);
|
|
||||||
};
|
|
||||||
|
|
||||||
ErrorWidget.builder = (errorDetails) {
|
|
||||||
print("@@@@@@@@@@@@@@@@@ in widget error");
|
|
||||||
// TODO: uncomment
|
|
||||||
// if (kDebugMode) {
|
|
||||||
// return ErrorWidget(errorDetails.exception);
|
|
||||||
// }
|
|
||||||
|
|
||||||
return FailurePage(
|
|
||||||
error: errorDetails.exception.toString(),
|
|
||||||
stackTrace: errorDetails.stack,
|
|
||||||
);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/// A callback that is invoked when an unhandled error occurs in the root
|
/// A callback that is invoked when an unhandled error occurs in the root
|
||||||
/// isolate.
|
/// isolate.
|
||||||
PlatformDispatcher.instance.onError = (error, stack) {
|
PlatformDispatcher.instance.onError = (error, stack) {
|
||||||
print("@@@@@@@@@@@@@@@");
|
_onError(FlutterErrorDetails(exception: error, stack: stack));
|
||||||
print("PlatformDispatcher.instance.onError");
|
|
||||||
_saveException(error.toString(), stack);
|
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -187,12 +170,42 @@ void _saveException(String? error, StackTrace? stackTrace) async {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
await file.writeAsString(jsonEncode(exception), mode: FileMode.append);
|
String separator = "\n\n==========================================================" +
|
||||||
|
"\n==========================================================\n\n";
|
||||||
|
|
||||||
|
await file.writeAsString(
|
||||||
|
jsonEncode(exception) + separator,
|
||||||
|
mode: FileMode.append,
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
void _onError(FlutterErrorDetails details) {
|
void _sendExceptionFile() async {
|
||||||
print("#############");
|
final appDocDir = await getApplicationDocumentsDirectory();
|
||||||
print(details.exception.toString());
|
|
||||||
|
final file = File('${appDocDir.path}/error.txt');
|
||||||
|
|
||||||
|
print(file.readAsStringSync());
|
||||||
|
|
||||||
|
final MailOptions mailOptions = MailOptions(
|
||||||
|
subject: 'Mobile App Issue',
|
||||||
|
recipients: ['support@cakewallet.com'],
|
||||||
|
attachments: [file.path],
|
||||||
|
);
|
||||||
|
|
||||||
|
final result = await FlutterMailer.send(mailOptions);
|
||||||
|
|
||||||
|
// clear file content if the error was sent or saved
|
||||||
|
// on android we can't know if it was sent or saved
|
||||||
|
if (result.name == MailerResponse.sent.name ||
|
||||||
|
result.name == MailerResponse.saved.name ||
|
||||||
|
result.name == MailerResponse.android.name) {
|
||||||
|
file.writeAsString("", mode: FileMode.write);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void _onError(FlutterErrorDetails errorDetails) {
|
||||||
|
_saveException(errorDetails.exception.toString(), errorDetails.stack);
|
||||||
|
|
||||||
WidgetsBinding.instance.addPostFrameCallback(
|
WidgetsBinding.instance.addPostFrameCallback(
|
||||||
(timeStamp) {
|
(timeStamp) {
|
||||||
showPopUp<void>(
|
showPopUp<void>(
|
||||||
|
@ -204,12 +217,12 @@ void _onError(FlutterErrorDetails details) {
|
||||||
alertContent: "Oops, we got some error.\n\nPlease send crash report to our support team to make the application better.",
|
alertContent: "Oops, we got some error.\n\nPlease send crash report to our support team to make the application better.",
|
||||||
rightButtonText: S.of(context).send,
|
rightButtonText: S.of(context).send,
|
||||||
leftButtonText: "Don't send",
|
leftButtonText: "Don't send",
|
||||||
actionRightButton: () async {
|
actionRightButton: () {
|
||||||
Navigator.of(context).pop();
|
Navigator.of(context).pop();
|
||||||
|
_sendExceptionFile();
|
||||||
},
|
},
|
||||||
actionLeftButton: () {
|
actionLeftButton: () {
|
||||||
Navigator.of(context).pop();
|
Navigator.of(context).pop();
|
||||||
_saveException(details.exception.toString(), details.stack);
|
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
|
|
@ -1,87 +0,0 @@
|
||||||
import 'dart:io';
|
|
||||||
|
|
||||||
import 'package:cake_wallet/generated/i18n.dart';
|
|
||||||
import 'package:cake_wallet/src/widgets/primary_button.dart';
|
|
||||||
import 'package:flutter/material.dart';
|
|
||||||
import 'package:flutter_mailer/flutter_mailer.dart';
|
|
||||||
import 'package:path_provider/path_provider.dart';
|
|
||||||
|
|
||||||
class FailurePage extends StatelessWidget {
|
|
||||||
final String? error;
|
|
||||||
final StackTrace? stackTrace;
|
|
||||||
|
|
||||||
FailurePage({Key? key, this.error, this.stackTrace});
|
|
||||||
|
|
||||||
@override
|
|
||||||
Widget build(BuildContext context) {
|
|
||||||
final theme = Theme.of(context);
|
|
||||||
return Scaffold(
|
|
||||||
backgroundColor: Colors.grey.shade400,
|
|
||||||
body: Center(
|
|
||||||
child: Padding(
|
|
||||||
padding: EdgeInsets.symmetric(
|
|
||||||
horizontal: MediaQuery.of(context).size.width * 0.2),
|
|
||||||
child: Column(
|
|
||||||
mainAxisSize: MainAxisSize.min,
|
|
||||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
|
||||||
children: [
|
|
||||||
Icon(
|
|
||||||
Icons.warning,
|
|
||||||
color: theme.errorColor,
|
|
||||||
size: 50,
|
|
||||||
),
|
|
||||||
Padding(
|
|
||||||
padding: const EdgeInsets.symmetric(vertical: 20),
|
|
||||||
child: Text(
|
|
||||||
"Oops, we got some error.",
|
|
||||||
style: theme.textTheme.headline1?.copyWith(fontSize: 20),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
Text(
|
|
||||||
"Please send crash report to our support team to make the application better.",
|
|
||||||
textAlign: TextAlign.center,
|
|
||||||
style: theme.textTheme.headline1?.copyWith(fontSize: 16),
|
|
||||||
),
|
|
||||||
Padding(
|
|
||||||
padding: const EdgeInsets.symmetric(vertical: 20),
|
|
||||||
child: PrimaryButton(
|
|
||||||
onPressed: _sendExceptionFile,
|
|
||||||
text: S.of(context).send,
|
|
||||||
textColor: Colors.white,
|
|
||||||
color: theme.accentTextTheme.bodyText1!.color!,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
PrimaryButton(
|
|
||||||
onPressed: () {
|
|
||||||
},
|
|
||||||
text: "Don't Send",
|
|
||||||
color: Theme.of(context).accentTextTheme.caption!.color!,
|
|
||||||
textColor:
|
|
||||||
Theme.of(context).primaryTextTheme.headline6!.color!,
|
|
||||||
),
|
|
||||||
],
|
|
||||||
),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
void _sendExceptionFile() async {
|
|
||||||
final appDocDir = await getApplicationDocumentsDirectory();
|
|
||||||
|
|
||||||
final file = File('${appDocDir.path}/error.txt');
|
|
||||||
|
|
||||||
print(file.readAsStringSync());
|
|
||||||
|
|
||||||
final MailOptions mailOptions = MailOptions(
|
|
||||||
subject: 'Mobile App Issue',
|
|
||||||
recipients: ['support@cakewallet.com'],
|
|
||||||
attachments: [file.path],
|
|
||||||
);
|
|
||||||
|
|
||||||
await FlutterMailer.send(mailOptions);
|
|
||||||
|
|
||||||
// clear file content
|
|
||||||
// file.writeAsString("", mode: FileMode.write);
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -61,7 +61,7 @@ dependencies:
|
||||||
permission_handler: ^10.0.0
|
permission_handler: ^10.0.0
|
||||||
device_display_brightness: ^0.0.6
|
device_display_brightness: ^0.0.6
|
||||||
platform_device_id: ^1.0.1
|
platform_device_id: ^1.0.1
|
||||||
flutter_mailer: ^2.0.1
|
flutter_mailer: ^2.0.2
|
||||||
cake_backup:
|
cake_backup:
|
||||||
git:
|
git:
|
||||||
url: https://github.com/cake-tech/cake_backup.git
|
url: https://github.com/cake-tech/cake_backup.git
|
||||||
|
|
Loading…
Reference in a new issue