E2E Fix integration test Twake Mail v0.18.4

E2E Fix integration test Twake Mail v0.18.4
This commit is contained in:
Dang Dat
2025-09-09 10:22:14 +07:00
committed by Dat H. Pham
parent fb53ba6568
commit c6ace7a9b5
29 changed files with 97 additions and 114 deletions
+1 -1
View File
@@ -19,7 +19,7 @@ class TestBase {
description, description,
config: const PatrolTesterConfig( config: const PatrolTesterConfig(
settlePolicy: SettlePolicy.trySettle, settlePolicy: SettlePolicy.trySettle,
visibleTimeout: Duration(minutes: 1), visibleTimeout: Duration(seconds: 30),
printLogs: true, printLogs: true,
), ),
nativeAutomatorConfig: const NativeAutomatorConfig( nativeAutomatorConfig: const NativeAutomatorConfig(
@@ -4,6 +4,7 @@ import 'dart:io' hide HttpClient;
import 'package:collection/collection.dart'; import 'package:collection/collection.dart';
import 'package:core/utils/app_logger.dart'; import 'package:core/utils/app_logger.dart';
import 'package:flutter/services.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:jmap_dart_client/http/http_client.dart'; import 'package:jmap_dart_client/http/http_client.dart';
import 'package:jmap_dart_client/jmap/core/capability/capability_identifier.dart'; import 'package:jmap_dart_client/jmap/core/capability/capability_identifier.dart';
@@ -270,4 +271,8 @@ mixin ScenarioUtilsMixin {
IdentityInteractorsBindings().dispose(); IdentityInteractorsBindings().dispose();
} }
Future<void> hideKeyboard() async {
await SystemChannels.textInput.invokeMethod('TextInput.hide');
}
} }
+5 -7
View File
@@ -10,6 +10,7 @@ import 'package:model/extensions/session_extension.dart';
import 'package:model/upload/file_info.dart'; import 'package:model/upload/file_info.dart';
import 'package:rich_text_composer/rich_text_composer.dart'; import 'package:rich_text_composer/rich_text_composer.dart';
import 'package:tmail_ui_user/features/base/widget/popup_item_widget.dart'; import 'package:tmail_ui_user/features/base/widget/popup_item_widget.dart';
import 'package:tmail_ui_user/features/composer/domain/state/download_image_as_base64_state.dart';
import 'package:tmail_ui_user/features/composer/presentation/composer_controller.dart'; import 'package:tmail_ui_user/features/composer/presentation/composer_controller.dart';
import 'package:tmail_ui_user/features/composer/presentation/composer_view.dart'; import 'package:tmail_ui_user/features/composer/presentation/composer_view.dart';
import 'package:tmail_ui_user/features/composer/presentation/view/mobile/mobile_editor_view.dart'; import 'package:tmail_ui_user/features/composer/presentation/view/mobile/mobile_editor_view.dart';
@@ -33,13 +34,6 @@ class ComposerRobot extends CoreRobot {
}) async { }) async {
final finder = $(RecipientComposerWidget).which<RecipientComposerWidget>( final finder = $(RecipientComposerWidget).which<RecipientComposerWidget>(
(widget) => widget.prefix == prefixEmailAddress); (widget) => widget.prefix == prefixEmailAddress);
final isTextFieldFocused = finder
.which<RecipientComposerWidget>(
(view) => view.focusNode?.hasFocus ?? false)
.exists;
if (!isTextFieldFocused) {
await finder.tap();
}
await finder.enterTextWithoutTapAction(email); await finder.enterTextWithoutTapAction(email);
await $(RecipientSuggestionItemWidget) await $(RecipientSuggestionItemWidget)
@@ -163,6 +157,10 @@ class ComposerRobot extends CoreRobot {
fileSize: await file.length(), fileSize: await file.length(),
fileName: file.path.split('/').last, fileName: file.path.split('/').last,
))); )));
await controller.viewState.stream.firstWhere((state) => state.fold(
(failure) => false,
(success) => success is DownloadImageAsBase64Success,
));
} }
Future<void> toggleReadReceipt() async { Future<void> toggleReadReceipt() async {
@@ -12,7 +12,7 @@ class EmailAddressDialogRobot extends CoreRobot {
} }
Future<void> tapCopyEmailAddressButton(AppLocalizations appLocalizations) async { Future<void> tapCopyEmailAddressButton(AppLocalizations appLocalizations) async {
await $(appLocalizations.copy_email_address).tap(); await $(#copy_email_address).tap();
} }
Future<void> tapComposeEmailButton(AppLocalizations appLocalizations) async { Future<void> tapComposeEmailButton(AppLocalizations appLocalizations) async {
+14 -20
View File
@@ -1,7 +1,6 @@
import 'package:core/presentation/views/button/tmail_button_widget.dart';
import 'package:flutter_test/flutter_test.dart'; import 'package:flutter_test/flutter_test.dart';
import 'package:tmail_ui_user/features/base/widget/material_text_button.dart';
import 'package:tmail_ui_user/features/email/presentation/widgets/email_view_back_button.dart'; import 'package:tmail_ui_user/features/email/presentation/widgets/email_view_back_button.dart';
import 'package:tmail_ui_user/features/email/presentation/widgets/information_sender_and_receiver_builder.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
import '../base/core_robot.dart'; import '../base/core_robot.dart';
@@ -40,47 +39,42 @@ class EmailRobot extends CoreRobot {
} }
Future<void> tapMarkAsUnreadOptionInContextMenu() async { Future<void> tapMarkAsUnreadOptionInContextMenu() async {
await $(#markAsUnread_action).tap(); await $(AppLocalizations().mark_as_unread).tap();
} }
Future<void> tapEmailDetailedStarButton() async { Future<void> tapEmailDetailedStarButton() async {
await $(#email_detailed_star_button).tap(); await $(AppLocalizations().starred).tap();
}
Future<void> tapEmailDetailedUnstarButton() async {
await $(AppLocalizations().not_starred).tap();
} }
Future<void> tapEmailDetailedMoveEmailButton() async { Future<void> tapEmailDetailedMoveEmailButton() async {
await $(#email_detailed_move_email_button).tap(); await $(AppLocalizations().moveMessage).tap();
} }
Future<void> tapEmailDetailedDeleteEmailButton() async { Future<void> tapEmailDetailedDeleteEmailButton() async {
await $(#email_detailed_delete_email_button).tap(); await $(AppLocalizations().move_to_trash).tap();
} }
Future<void> tapMarkAsSpamOptionInContextMenu() async { Future<void> tapMarkAsSpamOptionInContextMenu() async {
await $(#moveToSpam_action).tap(); await $(AppLocalizations().markAsSpam).tap();
} }
Future<void> tapArchiveMessageOptionInContextMenu() async { Future<void> tapArchiveMessageOptionInContextMenu() async {
await $(#archiveMessage_action).tap(); await $(AppLocalizations().archiveMessage).tap();
} }
Future<void> tapSenderEmailAddress(String email) async { Future<void> tapSenderEmailAddress(String email) async {
await $(MaterialTextButton) await $(InformationSenderAndReceiverBuilder).$(email).tap();
.which<MaterialTextButton>((widget) => widget.label.contains(email))
.first
.tap();
} }
Future<void> tapRecipientEmailAddress(String email) async { Future<void> tapRecipientEmailAddress(String email) async {
await $(TMailButtonWidget) await $(InformationSenderAndReceiverBuilder).$(email).tap();
.which<TMailButtonWidget>((widget) => widget.text.contains(email))
.first
.tap();
} }
Future<void> longPressSenderEmailAddress(String email) async { Future<void> longPressSenderEmailAddress(String email) async {
await $(MaterialTextButton) await $(InformationSenderAndReceiverBuilder).$(email).longPress();
.which<MaterialTextButton>((widget) => widget.label.contains(email))
.first
.longPress();
} }
} }
@@ -2,7 +2,6 @@
import 'package:core/presentation/resources/image_paths.dart'; import 'package:core/presentation/resources/image_paths.dart';
import 'package:core/presentation/views/button/tmail_button_widget.dart'; import 'package:core/presentation/views/button/tmail_button_widget.dart';
import 'package:core/presentation/views/text/text_field_builder.dart'; import 'package:core/presentation/views/text/text_field_builder.dart';
import 'package:flutter/material.dart';
import 'package:flutter_test/flutter_test.dart'; import 'package:flutter_test/flutter_test.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:tmail_ui_user/features/mailbox/presentation/widgets/label_mailbox_item_widget.dart'; import 'package:tmail_ui_user/features/mailbox/presentation/widgets/label_mailbox_item_widget.dart';
@@ -71,11 +70,7 @@ class MailboxMenuRobot extends CoreRobot {
} }
Future<void> closeMenu() async { Future<void> closeMenu() async {
await $(IconButton) await $.native.swipe(from: const Offset(0.9, 0.5), to: const Offset(0, 0.5));
.which<IconButton>((widget) {
return widget.tooltip == AppLocalizations().close;
})
.tap();
} }
int getCurrentInboxCount() { int getCurrentInboxCount() {
+3 -3
View File
@@ -57,14 +57,14 @@ class ThreadRobot extends CoreRobot {
} }
Future<void> selectAttachmentFilter() async { Future<void> selectAttachmentFilter() async {
await $(#filter_email_attachments).tap(); await $(#attachments_filter).tap();
} }
Future<void> selectUnreadFilter() async { Future<void> selectUnreadFilter() async {
await $(#filter_email_unread).tap(); await $(#unread_filter).tap();
} }
Future<void> selectStarredFilter() async { Future<void> selectStarredFilter() async {
await $(#filter_email_starred).tap(); await $(#starred_filter).tap();
} }
} }
@@ -27,10 +27,11 @@ class ComposerUploadAttachmentAndInlineImageScenario extends BaseTestScenario {
final png = await preparingPngWithName(pngName); final png = await preparingPngWithName(pngName);
await composerRobot.addAttachment(png); await composerRobot.addAttachment(png);
await $.pumpAndSettle();
await _expectAttachment(pngName);
await composerRobot.addInline(png); await composerRobot.addInline(png);
await $.pumpAndSettle(); await $.pumpAndSettle();
_expectAttachment(pngName);
await _expectInline(); await _expectInline();
await composerRobot.addAttachment(png); await composerRobot.addAttachment(png);
@@ -50,13 +51,11 @@ class ComposerUploadAttachmentAndInlineImageScenario extends BaseTestScenario {
); );
} }
void _expectAttachment(String pngName) { Future<void> _expectAttachment(String pngName) async {
return expect( await expectViewVisible(
$(AttachmentItemComposerWidget) $(AttachmentItemComposerWidget).which<AttachmentItemComposerWidget>(
.which<AttachmentItemComposerWidget>( (widget) => widget.fileName.contains(pngName),
(widget) => widget.fileName.contains(pngName) ),
),
findsOneWidget,
); );
} }
@@ -38,10 +38,10 @@ class ArchiveEmailScenario extends BaseTestScenario {
_expectEmailDetailedMoreButtonVisible(); _expectEmailDetailedMoreButtonVisible();
await emailRobot.tapEmailDetailedMoreButton(); await emailRobot.tapEmailDetailedMoreButton();
await $.pumpAndSettle(duration: const Duration(seconds: 2)); await $.pumpAndSettle(duration: const Duration(seconds: 1));
await emailRobot.tapArchiveMessageOptionInContextMenu(); await emailRobot.tapArchiveMessageOptionInContextMenu();
await $.pumpAndSettle(duration: const Duration(seconds: 3)); await $.pumpAndSettle(duration: const Duration(seconds: 1));
await emailRobot.onTapBackButton(); await emailRobot.onTapBackButton();
await $.pumpAndSettle(); await $.pumpAndSettle();
@@ -37,8 +37,9 @@ class DeleteEmailScenario extends BaseTestScenario {
await threadRobot.openEmailWithSubject(subject); await threadRobot.openEmailWithSubject(subject);
await $.pumpAndSettle(); await $.pumpAndSettle();
await emailRobot.tapEmailDetailedMoreButton();
await emailRobot.tapEmailDetailedDeleteEmailButton(); await emailRobot.tapEmailDetailedDeleteEmailButton();
await $.pumpAndSettle(duration: const Duration(seconds: 3)); await $.pumpAndSettle(duration: const Duration(seconds: 1));
_expectEmailViewInvisible(); _expectEmailViewInvisible();
@@ -52,7 +52,7 @@ class DisplayEmailAddressInfoDialogScenario extends BaseTestScenario {
Future<void> _expectEmailAddressInfoDialogVisible( Future<void> _expectEmailAddressInfoDialogVisible(
AppLocalizations appLocalizations, AppLocalizations appLocalizations,
) async { ) async {
await expectViewVisible($(appLocalizations.copy_email_address)); await expectViewVisible($(#copy_email_address));
await expectViewVisible($(appLocalizations.quickCreatingRule)); await expectViewVisible($(appLocalizations.quickCreatingRule));
await expectViewVisible($(appLocalizations.compose_email)); await expectViewVisible($(appLocalizations.compose_email));
} }
@@ -1,6 +1,3 @@
import 'package:core/presentation/resources/image_paths.dart';
import 'package:core/presentation/views/button/tmail_button_widget.dart';
import 'package:flutter_test/flutter_test.dart'; import 'package:flutter_test/flutter_test.dart';
import '../../base/base_test_scenario.dart'; import '../../base/base_test_scenario.dart';
@@ -18,7 +15,6 @@ class MarkAsStarEmailScenario extends BaseTestScenario {
const emailUser = String.fromEnvironment('BASIC_AUTH_EMAIL'); const emailUser = String.fromEnvironment('BASIC_AUTH_EMAIL');
final threadRobot = ThreadRobot($); final threadRobot = ThreadRobot($);
final emailRobot = EmailRobot($); final emailRobot = EmailRobot($);
final imagePaths = ImagePaths();
await provisionEmail( await provisionEmail(
[ [
@@ -34,32 +30,29 @@ class MarkAsStarEmailScenario extends BaseTestScenario {
await threadRobot.openEmailWithSubject(subject); await threadRobot.openEmailWithSubject(subject);
await $.pumpAndSettle(); await $.pumpAndSettle();
_expectEmailDetailedStarButtonVisible(); await emailRobot.tapEmailDetailedMoreButton();
await _expectEmailDetailedStarButtonVisible();
await emailRobot.tapEmailDetailedStarButton(); await emailRobot.tapEmailDetailedStarButton();
await $.pumpAndSettle(duration: const Duration(seconds: 2)); await $.pumpAndSettle(duration: const Duration(seconds: 1));
await _expectDisplayedStarIcon(imagePaths); await emailRobot.tapEmailDetailedMoreButton();
await _expectDisplayedUnStarIcon();
await emailRobot.tapEmailDetailedStarButton(); await emailRobot.tapEmailDetailedUnstarButton();
await $.pumpAndSettle(duration: const Duration(seconds: 2)); await $.pumpAndSettle(duration: const Duration(seconds: 1));
await _expectDisplayedUnStarIcon(imagePaths); await emailRobot.tapEmailDetailedMoreButton();
await _expectDisplayedStarIcon();
} }
void _expectEmailDetailedStarButtonVisible() { Future<void> _expectEmailDetailedStarButtonVisible() async {
expect($(#email_detailed_star_button), findsOneWidget); await expectViewVisible($(#markAsStarred_action));
} }
Future<void> _expectDisplayedStarIcon(ImagePaths imagePaths) async { Future<void> _expectDisplayedStarIcon() async {
await expectViewVisible( await expectViewVisible($(#markAsStarred_action));
$(#email_detailed_star_button).which<TMailButtonWidget>(
(widget) => widget.icon == imagePaths.icStar),
);
} }
Future<void> _expectDisplayedUnStarIcon(ImagePaths imagePaths) async { Future<void> _expectDisplayedUnStarIcon() async {
await expectViewVisible( await expectViewVisible($(#unMarkAsStarred_action));
$(#email_detailed_star_button).which<TMailButtonWidget>(
(widget) => widget.icon == imagePaths.icUnStar),
);
} }
} }
@@ -38,6 +38,7 @@ class MoveEmailToFolderScenario extends BaseTestScenario {
await threadRobot.openEmailWithSubject(subject); await threadRobot.openEmailWithSubject(subject);
await $.pumpAndSettle(); await $.pumpAndSettle();
await emailRobot.tapEmailDetailedMoreButton();
await emailRobot.tapEmailDetailedMoveEmailButton(); await emailRobot.tapEmailDetailedMoveEmailButton();
await $.pumpAndSettle(duration: const Duration(seconds: 2)); await $.pumpAndSettle(duration: const Duration(seconds: 2));
@@ -79,12 +79,15 @@ class ReplyEmailWithReplyToScenario extends BaseTestScenario {
} }
Future<void> _expectToFieldContainReplyToEmailAddress() async { Future<void> _expectToFieldContainReplyToEmailAddress() async {
expect( await expectViewVisible(
$(RecipientComposerWidget).which<RecipientComposerWidget>((widget) => $(RecipientComposerWidget).which<RecipientComposerWidget>(
widget.prefix == PrefixEmailAddress.to && (widget) =>
isMatchingEmailList(widget.listEmailAddress, {'emma-reply-to@example.com'}) widget.prefix == PrefixEmailAddress.to &&
).visible, isMatchingEmailList(
isTrue, widget.listEmailAddress,
{'emma-reply-to@example.com'},
),
),
); );
} }
} }
@@ -14,7 +14,7 @@ import '../robots/thread_robot.dart';
class ForwardEmailScenario extends BaseTestScenario { class ForwardEmailScenario extends BaseTestScenario {
static const String queryString = 'Fwd: Forward email to Bob'; static const String queryString = 'Forward email';
const ForwardEmailScenario(super.$); const ForwardEmailScenario(super.$);
@@ -21,7 +21,7 @@ class SaveAsTemplateScenario extends BaseTestScenario {
await _expectSaveToastSuccessVisible(); await _expectSaveToastSuccessVisible();
await composerRobot.addSubject('test subject'); await composerRobot.addSubject('test subject');
await hideKeyboard();
await composerRobot.saveAsTemplate(); await composerRobot.saveAsTemplate();
await _expectUpdateToastSuccessVisible(); await _expectUpdateToastSuccessVisible();
@@ -42,12 +42,15 @@ class ThreadDetailReplyRealTimeUpdateScenario extends BaseTestScenario {
await composerRobot.grantContactPermission(); await composerRobot.grantContactPermission();
await composerRobot.addContent(replyContent); await composerRobot.addContent(replyContent);
await composerRobot.sendEmail(imagePaths); await composerRobot.sendEmail(imagePaths);
await $.waitUntilVisible($(ThreadDetailCollapsedEmail));
expect( await _expectNewCollapsedEmail(replyContent);
$(ThreadDetailCollapsedEmail).which<ThreadDetailCollapsedEmail>((widget) { }
return widget.preview.contains(replyContent);
}), Future<void> _expectNewCollapsedEmail(String replyContent) async {
findsOneWidget, final collapsedEmail = $(ThreadDetailCollapsedEmail)
); .which<ThreadDetailCollapsedEmail>((widget) {
return widget.preview.contains(replyContent);
});
await expectViewVisible(collapsedEmail);
} }
} }
@@ -18,6 +18,7 @@ class ContextMenuDialogView extends StatelessWidget {
child: Column( child: Column(
mainAxisSize: MainAxisSize.min, mainAxisSize: MainAxisSize.min,
children: actions.map((menuAction) => ContextMenuDialogItem( children: actions.map((menuAction) => ContextMenuDialogItem(
key: menuAction.key != null ? Key(menuAction.key!) : null,
menuAction: menuAction, menuAction: menuAction,
onContextMenuActionClick: onContextMenuActionClick, onContextMenuActionClick: onContextMenuActionClick,
)).toList(), )).toList(),
@@ -6,11 +6,12 @@ typedef OnContextMenuActionClick = void Function(ContextMenuItemAction action);
abstract class ContextMenuItemAction<T> with EquatableMixin { abstract class ContextMenuItemAction<T> with EquatableMixin {
final T action; final T action;
final String? key;
ContextMenuItemAction(this.action); ContextMenuItemAction(this.action, {this.key});
@override @override
List<Object?> get props => [action]; List<Object?> get props => [action, key];
String get actionName; String get actionName;
@@ -33,7 +34,7 @@ mixin OptionalSelectedIcon<T> {
abstract class ContextMenuItemActionRequiredIcon<T> abstract class ContextMenuItemActionRequiredIcon<T>
extends ContextMenuItemAction<T> with OptionalIcon { extends ContextMenuItemAction<T> with OptionalIcon {
ContextMenuItemActionRequiredIcon(super.action); ContextMenuItemActionRequiredIcon(super.action, {super.key});
} }
abstract class ContextMenuItemActionRequiredSelectedIcon<T> abstract class ContextMenuItemActionRequiredSelectedIcon<T>
@@ -41,12 +42,12 @@ abstract class ContextMenuItemActionRequiredSelectedIcon<T>
final T? selectedAction; final T? selectedAction;
ContextMenuItemActionRequiredSelectedIcon(super.action, this.selectedAction); ContextMenuItemActionRequiredSelectedIcon(super.action, this.selectedAction, {super.key});
} }
abstract class ContextMenuItemActionRequiredFull<T> abstract class ContextMenuItemActionRequiredFull<T>
extends ContextMenuItemAction<T> with OptionalIcon, OptionalSelectedIcon<T> { extends ContextMenuItemAction<T> with OptionalIcon, OptionalSelectedIcon<T> {
final T selectedAction; final T selectedAction;
ContextMenuItemActionRequiredFull(super.action, this.selectedAction); ContextMenuItemActionRequiredFull(super.action, this.selectedAction, {super.key});
} }
@@ -37,6 +37,7 @@ class EmailAddressWithCopyWidget extends StatelessWidget {
), ),
if (label.isNotEmpty) if (label.isNotEmpty)
TMailButtonWidget.fromIcon( TMailButtonWidget.fromIcon(
key: const ValueKey('copy_email_address'),
icon: copyLabelIcon, icon: copyLabelIcon,
backgroundColor: Colors.transparent, backgroundColor: Colors.transparent,
iconSize: 20, iconSize: 20,
@@ -13,8 +13,9 @@ class ContextItemEmailAction
ContextItemEmailAction( ContextItemEmailAction(
super.action, super.action,
this.appLocalizations, this.appLocalizations,
this.imagePaths, this.imagePaths, {
); super.key,
});
@override @override
String get actionIcon => action.getIcon(imagePaths); String get actionIcon => action.getIcon(imagePaths);
@@ -591,6 +591,7 @@ class EmailActionReactor {
action, action,
AppLocalizations.of(currentContext!), AppLocalizations.of(currentContext!),
imagePaths, imagePaths,
key: '${action.name}_action',
), ),
) )
.toList(), .toList(),
@@ -162,7 +162,6 @@ class EmailViewAppBarWidget extends StatelessWidget {
); );
Widget _getMoveEmailButton(AppLocalizations appLocalizations) => TMailButtonWidget.fromIcon( Widget _getMoveEmailButton(AppLocalizations appLocalizations) => TMailButtonWidget.fromIcon(
key: const Key('email_detailed_move_email_button'),
icon: _imagePaths.icMoveEmail, icon: _imagePaths.icMoveEmail,
iconSize: EmailViewAppBarWidgetStyles.buttonIconSize, iconSize: EmailViewAppBarWidgetStyles.buttonIconSize,
iconColor: EmailViewAppBarWidgetStyles.iconColor, iconColor: EmailViewAppBarWidgetStyles.iconColor,
@@ -177,7 +176,6 @@ class EmailViewAppBarWidget extends StatelessWidget {
); );
Widget _getMarkStarButton(AppLocalizations applocalizations) => TMailButtonWidget.fromIcon( Widget _getMarkStarButton(AppLocalizations applocalizations) => TMailButtonWidget.fromIcon(
key: const Key('email_detailed_star_button'),
icon: presentationEmail.hasStarred icon: presentationEmail.hasStarred
? _imagePaths.icStar ? _imagePaths.icStar
: _imagePaths.icUnStar, : _imagePaths.icUnStar,
@@ -200,7 +198,6 @@ class EmailViewAppBarWidget extends StatelessWidget {
); );
Widget _getDeleteButton(AppLocalizations applocalizations) => TMailButtonWidget.fromIcon( Widget _getDeleteButton(AppLocalizations applocalizations) => TMailButtonWidget.fromIcon(
key: const Key('email_detailed_delete_email_button'),
icon: _imagePaths.icDeleteComposer, icon: _imagePaths.icDeleteComposer,
iconSize: EmailViewAppBarWidgetStyles.deleteButtonIconSize, iconSize: EmailViewAppBarWidgetStyles.deleteButtonIconSize,
iconColor: EmailViewAppBarWidgetStyles.iconColor, iconColor: EmailViewAppBarWidgetStyles.iconColor,
@@ -20,6 +20,7 @@ extension HandleSelectMessageFilterExtension on ThreadController {
selectedOption, selectedOption,
AppLocalizations.of(context), AppLocalizations.of(context),
imagePaths, imagePaths,
key: '${filter.name}_filter',
); );
}).toList(); }).toList();
@@ -12,8 +12,9 @@ class ContextItemFilterMessageOptionAction
super.action, super.action,
super.selectedAction, super.selectedAction,
this.appLocalizations, this.appLocalizations,
this.imagePaths, this.imagePaths, {
); super.key,
});
@override @override
String get actionIcon => action.getContextMenuIcon(imagePaths); String get actionIcon => action.getContextMenuIcon(imagePaths);
-6
View File
@@ -794,12 +794,6 @@
"placeholders_order": [], "placeholders_order": [],
"placeholders": {} "placeholders": {}
}, },
"copy_email_address": "Copy email address",
"@copy_email_address": {
"type": "text",
"placeholders_order": [],
"placeholders": {}
},
"compose_email": "Compose email", "compose_email": "Compose email",
"@compose_email": { "@compose_email": {
"type": "text", "type": "text",
@@ -805,12 +805,6 @@ class AppLocalizations {
name: 'hide'); name: 'hide');
} }
String get copy_email_address {
return Intl.message(
'Copy email address',
name: 'copy_email_address');
}
String get compose_email { String get compose_email {
return Intl.message( return Intl.message(
'Compose email', 'Compose email',
@@ -13,7 +13,6 @@ User-Agent: Twake-Mail/0.13.2 Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15;
rv:131.0) Gecko/20100101 Firefox/131.0 rv:131.0) Gecko/20100101 Firefox/131.0
Content-Type: multipart/alternative; Content-Type: multipart/alternative;
boundary="-=Part.4f.450e1cfbcd355387.192d67ae03d.c367d8042fea24dd=-" boundary="-=Part.4f.450e1cfbcd355387.192d67ae03d.c367d8042fea24dd=-"
List-Post: <mailto:emma-reply-to-list@example.com>
---=Part.4f.450e1cfbcd355387.192d67ae03d.c367d8042fea24dd=- ---=Part.4f.450e1cfbcd355387.192d67ae03d.c367d8042fea24dd=-
Content-Type: text/plain; charset=UTF-8 Content-Type: text/plain; charset=UTF-8
@@ -2,7 +2,7 @@
# Define users and folders # Define users and folders
users=("alice" "bob" "brian" "charlotte" "david" "emma") users=("alice" "bob" "brian" "charlotte" "david" "emma")
bobFolders=("Search Emails" "Forward Emails" "Disposition" "MailBase64" "Calendar" "Reply Emails" "Reply Emails") bobFolders=("Search Emails" "Forward Emails" "Disposition" "MailBase64" "Calendar" "Reply Emails")
# Add users # Add users
for user in "${users[@]}"; do for user in "${users[@]}"; do