TF-3416 Implement preview EML attachment
This commit is contained in:
+2
-1
@@ -14,9 +14,9 @@ export 'presentation/extensions/compare_string_extension.dart';
|
||||
export 'presentation/extensions/compare_list_extensions.dart';
|
||||
export 'presentation/extensions/string_extension.dart';
|
||||
export 'presentation/extensions/tap_down_details_extension.dart';
|
||||
export 'domain/extensions/media_type_extension.dart';
|
||||
export 'presentation/extensions/map_extensions.dart';
|
||||
export 'presentation/extensions/either_view_state_extension.dart';
|
||||
export 'presentation/extensions/media_type_extension.dart';
|
||||
|
||||
// Exceptions
|
||||
export 'domain/exceptions/download_file_exception.dart';
|
||||
@@ -51,6 +51,7 @@ export 'utils/broadcast_channel/broadcast_channel.dart';
|
||||
export 'utils/list_utils.dart';
|
||||
export 'utils/mail/domain.dart';
|
||||
export 'utils/mail/mail_address.dart';
|
||||
export 'utils/preview_eml_file_utils.dart';
|
||||
|
||||
// Views
|
||||
export 'presentation/views/text/slogan_builder.dart';
|
||||
|
||||
@@ -9,4 +9,5 @@ class Constant {
|
||||
static const imageType = 'image';
|
||||
static const textVCardMimeType = 'text/x-vcard';
|
||||
static const textPlainMimeType = 'text/plain';
|
||||
static const emlMimeType = 'message/rfc822';
|
||||
}
|
||||
@@ -1,23 +0,0 @@
|
||||
import 'package:core/domain/preview/document_uti.dart';
|
||||
import 'package:core/domain/preview/supported_preview_file_types.dart';
|
||||
import 'package:http_parser/http_parser.dart';
|
||||
|
||||
extension MediaTypeExtension on MediaType {
|
||||
bool isAndroidSupportedPreview() => SupportedPreviewFileTypes.androidSupportedTypes.contains(mimeType);
|
||||
|
||||
bool isIOSSupportedPreview() => SupportedPreviewFileTypes.iOSSupportedTypes.containsKey(mimeType);
|
||||
|
||||
bool isImageFile() => SupportedPreviewFileTypes.imageMimeTypes.contains(mimeType);
|
||||
|
||||
bool isDocFile() => SupportedPreviewFileTypes.docMimeTypes.contains(mimeType);
|
||||
|
||||
bool isPowerPointFile() => SupportedPreviewFileTypes.pptMimeTypes.contains(mimeType);
|
||||
|
||||
bool isExcelFile() => SupportedPreviewFileTypes.xlsMimeTypes.contains(mimeType);
|
||||
|
||||
bool isZipFile() => SupportedPreviewFileTypes.zipMimeTypes.contains(mimeType);
|
||||
|
||||
bool isPdfFile() => SupportedPreviewFileTypes.pdfMimeTypes.contains(mimeType);
|
||||
|
||||
DocumentUti getDocumentUti() => DocumentUti(SupportedPreviewFileTypes.iOSSupportedTypes[mimeType]);
|
||||
}
|
||||
@@ -14,9 +14,7 @@ class SupportedPreviewFileTypes {
|
||||
'application/msword',
|
||||
'application/vnd.ms-works'];
|
||||
|
||||
static const pdfMimeTypes = [
|
||||
'application/pdf',
|
||||
'application/rtf'];
|
||||
static const rtfMimeTypes = ['application/rtf'];
|
||||
|
||||
static const xlsMimeTypes = [
|
||||
'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
|
||||
|
||||
@@ -0,0 +1,50 @@
|
||||
import 'package:core/data/constants/constant.dart';
|
||||
import 'package:core/domain/preview/document_uti.dart';
|
||||
import 'package:core/domain/preview/supported_preview_file_types.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:http_parser/http_parser.dart';
|
||||
|
||||
extension MediaTypeExtension on MediaType {
|
||||
bool isAndroidSupportedPreview() => SupportedPreviewFileTypes.androidSupportedTypes.contains(mimeType);
|
||||
|
||||
bool isIOSSupportedPreview() => SupportedPreviewFileTypes.iOSSupportedTypes.containsKey(mimeType);
|
||||
|
||||
bool isImageFile() => SupportedPreviewFileTypes.imageMimeTypes.contains(mimeType);
|
||||
|
||||
bool isDocFile() => SupportedPreviewFileTypes.docMimeTypes.contains(mimeType);
|
||||
|
||||
bool isPowerPointFile() => SupportedPreviewFileTypes.pptMimeTypes.contains(mimeType);
|
||||
|
||||
bool isExcelFile() => SupportedPreviewFileTypes.xlsMimeTypes.contains(mimeType);
|
||||
|
||||
bool isZipFile() => SupportedPreviewFileTypes.zipMimeTypes.contains(mimeType);
|
||||
|
||||
bool isRtfFile() => SupportedPreviewFileTypes.rtfMimeTypes.contains(mimeType);
|
||||
|
||||
DocumentUti getDocumentUti() => DocumentUti(SupportedPreviewFileTypes.iOSSupportedTypes[mimeType]);
|
||||
|
||||
String getIcon(ImagePaths imagePaths, {String? fileName}) {
|
||||
if (isPDFFile(fileName: fileName) == true || isRtfFile()) {
|
||||
return imagePaths.icFilePdf;
|
||||
} else if (isDocFile()) {
|
||||
return imagePaths.icFileDocx;
|
||||
} else if (isExcelFile()) {
|
||||
return imagePaths.icFileXlsx;
|
||||
} else if (isPowerPointFile()) {
|
||||
return imagePaths.icFilePptx;
|
||||
} else if (isZipFile()) {
|
||||
return imagePaths.icFileZip;
|
||||
} else if (isImageFile()) {
|
||||
return imagePaths.icFilePng;
|
||||
} else {
|
||||
return imagePaths.icFileEPup;
|
||||
}
|
||||
}
|
||||
|
||||
bool isPDFFile({required String? fileName}) =>
|
||||
mimeType == Constant.pdfMimeType ||
|
||||
(mimeType == Constant.octetStreamMimeType &&
|
||||
fileName?.endsWith(Constant.pdfExtension) == true);
|
||||
|
||||
bool get isEMLFile => mimeType == Constant.emlMimeType;
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
|
||||
class HtmlTemplate {
|
||||
static const String fontLink = '<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap" rel="stylesheet">';
|
||||
static const String nameClassToolTip = 'tmail-tooltip';
|
||||
static const String tooltipLinkCss = '''
|
||||
.$nameClassToolTip .tooltiptext {
|
||||
@@ -64,4 +65,154 @@ class HtmlTemplate {
|
||||
}
|
||||
</style>
|
||||
''';
|
||||
|
||||
static const String previewEMLFileCssStyle = '''
|
||||
<style>
|
||||
body {
|
||||
font-family: Arial, 'Inter', sans-serif;
|
||||
color: #333;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.email-container {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
padding: 16px;
|
||||
}
|
||||
|
||||
.email-subject {
|
||||
font-weight: bold;
|
||||
font-size: 16px;
|
||||
color: #333;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.email-header {
|
||||
display: flex;
|
||||
align-items: flex-start;
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
.placeholder-icon {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background-color: #f2f2f2;
|
||||
border-radius: 50%;
|
||||
color: #d9534f;
|
||||
font-size: 18px;
|
||||
font-weight: bold;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.email-info {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
flex-grow: 1;
|
||||
}
|
||||
|
||||
.sender {
|
||||
font-weight: bold;
|
||||
color: #333;
|
||||
}
|
||||
|
||||
.sender-email {
|
||||
font-size: 12px;
|
||||
color: #666;
|
||||
}
|
||||
|
||||
.recipients {
|
||||
font-size: 12px;
|
||||
color: #666;
|
||||
margin-top: 5px;
|
||||
word-wrap: break-word;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.email-meta {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 5px;
|
||||
}
|
||||
|
||||
.attachment-icon {
|
||||
width: 16px;
|
||||
height: 16px;
|
||||
}
|
||||
|
||||
.email-date {
|
||||
font-size: 12px;
|
||||
color: #666;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.email-body {
|
||||
font-size: 14px;
|
||||
color: #333;
|
||||
margin-top: 10px;
|
||||
margin-left: 40px;
|
||||
}
|
||||
|
||||
.attachments {
|
||||
margin-top: 15px;
|
||||
padding-top: 10px;
|
||||
border-top: 1px solid #ddd;
|
||||
margin-left: 40px;
|
||||
}
|
||||
|
||||
.attachment-title {
|
||||
font-weight: bold;
|
||||
color: #333;
|
||||
margin-bottom: 10px;
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
.attachment-item {
|
||||
display: flex;
|
||||
align-items: flex-start;
|
||||
gap: 10px;
|
||||
font-size: 12px;
|
||||
color: #666;
|
||||
margin-bottom: 10px;
|
||||
cursor: pointer;
|
||||
padding: 5px;
|
||||
transition: background-color 0.3s, box-shadow 0.3s;
|
||||
}
|
||||
|
||||
.attachment-item:hover {
|
||||
background-color: #f5f5f5;
|
||||
box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
|
||||
}
|
||||
|
||||
.attachment-item .icon {
|
||||
width: 20px;
|
||||
height: 20px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
background-color: #f2f2f2;
|
||||
border-radius: 50%;
|
||||
color: #007bff;
|
||||
}
|
||||
|
||||
.attachment-item .file-details {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
.attachment-item .file-name {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.attachment-item .file-size {
|
||||
font-size: 12px;
|
||||
color: #666;
|
||||
}
|
||||
</style>
|
||||
''';
|
||||
}
|
||||
@@ -421,4 +421,28 @@ class HtmlUtils {
|
||||
const fileSizeSpan = document.getElementById('file-size');
|
||||
fileSizeSpan.textContent = formatFileSize(bytesJs.length);''';
|
||||
}
|
||||
|
||||
static void openNewWindowByUrl(
|
||||
String url,
|
||||
{
|
||||
int width = 800,
|
||||
int height = 600,
|
||||
}
|
||||
) async {
|
||||
try {
|
||||
final screenWidth = html.window.screen?.width ?? width;
|
||||
final screenHeight = html.window.screen?.height ?? height;
|
||||
|
||||
final left = (screenWidth - width) ~/ 2;
|
||||
final top = (screenHeight - height) ~/ 2;
|
||||
|
||||
final options = 'width=$width,height=$height,top=$top,left=$left';
|
||||
|
||||
html.window.open(url, '_blank', options);
|
||||
|
||||
html.Url.revokeObjectUrl(url);
|
||||
} catch (e) {
|
||||
logError('AppUtils::openNewWindowByUrl:Exception = $e');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,179 @@
|
||||
|
||||
import 'package:core/data/model/print_attachment.dart';
|
||||
import 'package:core/utils/app_logger.dart';
|
||||
import 'package:core/utils/html/html_template.dart';
|
||||
import 'package:core/utils/html/html_utils.dart';
|
||||
import 'package:html/dom.dart';
|
||||
import 'package:html/parser.dart';
|
||||
|
||||
class PreviewEmlFileUtils {
|
||||
|
||||
Element? _createEmailElement({
|
||||
required String subjectPrefix,
|
||||
required String fromPrefix,
|
||||
required String toPrefix,
|
||||
required String ccPrefix,
|
||||
required String bccPrefix,
|
||||
required String replyToPrefix,
|
||||
required String titleAttachment,
|
||||
String? subject,
|
||||
String? senderName,
|
||||
String? senderEmailAddress,
|
||||
String? toAddress,
|
||||
String? ccAddress,
|
||||
String? bccAddress,
|
||||
String? replyToAddress,
|
||||
String? dateTime,
|
||||
String? attachmentIcon,
|
||||
String? emailContent,
|
||||
List<PrintAttachment>? listAttachment,
|
||||
}) {
|
||||
try {
|
||||
return Element.html('''
|
||||
<div class="email-container">
|
||||
<!-- Email Subject -->
|
||||
<div class="email-subject">$subjectPrefix: $subject</div>
|
||||
|
||||
<!-- Email Header -->
|
||||
<div class="email-header">
|
||||
<!-- Placeholder icon -->
|
||||
<div class="placeholder-icon">?</div>
|
||||
|
||||
<!-- Email information -->
|
||||
<div class="email-info">
|
||||
<div class="sender">
|
||||
${senderName ?? ''} <span class="sender-email"><${senderEmailAddress ?? ''}></span>
|
||||
</div>
|
||||
${replyToAddress?.isNotEmpty == true ? _createRecipientHtmlTag(replyToPrefix, replyToAddress!) : ''}
|
||||
${toAddress?.isNotEmpty == true ? _createRecipientHtmlTag(toPrefix, toAddress!) : ''}
|
||||
${ccAddress?.isNotEmpty == true ? _createRecipientHtmlTag(ccPrefix, ccAddress!) : ''}
|
||||
${bccAddress?.isNotEmpty == true ? _createRecipientHtmlTag(bccPrefix, bccAddress!) : ''}
|
||||
</div>
|
||||
|
||||
<!-- Email metadata -->
|
||||
<div class="email-meta">
|
||||
${attachmentIcon?.isNotEmpty == true ? '<img width="16" height="16" src="${HtmlUtils.generateSVGImageData(attachmentIcon!)}" alt="Attachment Icon" class="attachment-icon">' : ''}
|
||||
${dateTime?.isNotEmpty == true ? '<div class="email-date">$dateTime</div>' : ''}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- Email Body -->
|
||||
<div class="email-body">
|
||||
<p>$emailContent</p>
|
||||
</div>
|
||||
|
||||
${listAttachment?.isNotEmpty == true ? _createAttachmentsElement(listAttachment: listAttachment ?? [], titleAttachment: titleAttachment) : ''}
|
||||
''');
|
||||
} catch (e) {
|
||||
logError('PreviewEmlFileUtils::_createEmailElement: Exception = $e');
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
String _createRecipientHtmlTag(String prefix, String emailAddress) {
|
||||
try {
|
||||
return '''
|
||||
<div class="recipients">
|
||||
$prefix: $emailAddress
|
||||
</div>
|
||||
''';
|
||||
} catch (e) {
|
||||
logError('PreviewEmlFileUtils::_createRecipientHtmlTag: Exception = $e');
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
String _createAttachmentHtmlTag(PrintAttachment printAttachment) {
|
||||
return '''
|
||||
<div class="attachment-item">
|
||||
<div class="icon">
|
||||
<img width="16" height="16" src="${HtmlUtils.generateSVGImageData(printAttachment.iconBase64Data)}" alt="attachment-icon"/>
|
||||
</div>
|
||||
<div class="file-details">
|
||||
<div class="file-name">${printAttachment.name}</div>
|
||||
<div class="file-size">${printAttachment.size}</div>
|
||||
</div>
|
||||
</div>
|
||||
''';
|
||||
}
|
||||
|
||||
String _createAttachmentsElement({
|
||||
required String titleAttachment,
|
||||
required List<PrintAttachment> listAttachment
|
||||
}) {
|
||||
try {
|
||||
return '''
|
||||
<div class="attachments">
|
||||
<!-- Attachment Title -->
|
||||
<div class="attachment-title">${listAttachment.length} $titleAttachment</div>
|
||||
|
||||
<!-- Attachment Items -->
|
||||
${listAttachment.map((attachment) => _createAttachmentHtmlTag(attachment)).toList().join('\n')}
|
||||
</div>
|
||||
''';
|
||||
} catch (e) {
|
||||
logError('PreviewEmlFileUtils::_createAttachmentsElement: Exception = $e');
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
String generatePreviewEml({
|
||||
required String appName,
|
||||
required String userName,
|
||||
required String subjectPrefix,
|
||||
required String subject,
|
||||
required String emailContent,
|
||||
required String senderName,
|
||||
required String senderEmailAddress,
|
||||
required String dateTime,
|
||||
required String fromPrefix,
|
||||
required String toPrefix,
|
||||
required String ccPrefix,
|
||||
required String bccPrefix,
|
||||
required String replyToPrefix,
|
||||
required String titleAttachment,
|
||||
required String attachmentIcon,
|
||||
String? toAddress,
|
||||
String? ccAddress,
|
||||
String? bccAddress,
|
||||
String? replyToAddress,
|
||||
List<PrintAttachment>? listAttachment,
|
||||
}) {
|
||||
Document document = parse(HtmlUtils.createTemplateHtmlDocument(title: '$subject - $userName'));
|
||||
|
||||
Element? emailElement = _createEmailElement(
|
||||
subjectPrefix: subjectPrefix,
|
||||
fromPrefix: fromPrefix,
|
||||
toPrefix: toPrefix,
|
||||
ccPrefix: ccPrefix,
|
||||
bccPrefix: bccPrefix,
|
||||
replyToPrefix: replyToPrefix,
|
||||
subject: subject,
|
||||
toAddress: toAddress,
|
||||
ccAddress: ccAddress,
|
||||
bccAddress: bccAddress,
|
||||
replyToAddress: replyToAddress,
|
||||
senderName: senderName,
|
||||
senderEmailAddress: senderEmailAddress,
|
||||
dateTime: dateTime,
|
||||
emailContent: emailContent,
|
||||
attachmentIcon: attachmentIcon,
|
||||
titleAttachment: titleAttachment,
|
||||
listAttachment: listAttachment,
|
||||
);
|
||||
|
||||
Element linkFontElement = Element.html(HtmlTemplate.fontLink);
|
||||
document.head?.append(linkFontElement);
|
||||
|
||||
Element styleElement = Element.html(HtmlTemplate.previewEMLFileCssStyle);
|
||||
document.head?.append(styleElement);
|
||||
|
||||
if (emailElement != null) {
|
||||
document.body?.append(emailElement);
|
||||
}
|
||||
|
||||
final htmlDocument = document.outerHtml;
|
||||
|
||||
return htmlDocument;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
class NotFoundDataWithThisKeyException implements Exception {}
|
||||
@@ -0,0 +1,27 @@
|
||||
|
||||
import 'package:collection/collection.dart';
|
||||
import 'package:tmail_ui_user/features/caching/exceptions/local_storage_exception.dart';
|
||||
import 'package:universal_html/html.dart' as html;
|
||||
|
||||
class LocalStorageManager {
|
||||
|
||||
void save(String key, String value) {
|
||||
html.window.localStorage.addAll({key: value});
|
||||
}
|
||||
|
||||
String get(String key) {
|
||||
final entry = html.window.localStorage
|
||||
.entries
|
||||
.firstWhereOrNull((entry) => entry.key == key);
|
||||
|
||||
if (entry != null) {
|
||||
return entry.value;
|
||||
} else {
|
||||
throw NotFoundDataWithThisKeyException();
|
||||
}
|
||||
}
|
||||
|
||||
void remove(String key) {
|
||||
html.window.localStorage.remove(key);
|
||||
}
|
||||
}
|
||||
@@ -2,6 +2,7 @@ import 'package:core/core.dart';
|
||||
import 'package:core/utils/application_manager.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/base_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/composer/data/datasource/composer_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/composer/data/datasource/contact_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/composer/data/datasource_impl/composer_datasource_impl.dart';
|
||||
@@ -24,6 +25,7 @@ import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dar
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
@@ -131,6 +133,9 @@ class ComposerBindings extends BaseBindings {
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => RemoteServerSettingsDataSourceImpl(
|
||||
Get.find<ServerSettingsAPI>(),
|
||||
Get.find<RemoteExceptionThrower>()));
|
||||
@@ -170,7 +175,8 @@ class ComposerBindings extends BaseBindings {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>()
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
|
||||
@@ -24,6 +24,7 @@ import 'package:tmail_ui_user/features/composer/domain/model/email_request.dart'
|
||||
import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/domain/model/create_new_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/sending_queue/domain/model/sending_email.dart';
|
||||
@@ -187,4 +188,10 @@ abstract class EmailDataSource {
|
||||
List<EmailId> emailIds);
|
||||
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds);
|
||||
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest);
|
||||
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent);
|
||||
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored);
|
||||
}
|
||||
@@ -1,13 +1,23 @@
|
||||
import 'dart:async';
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:core/data/model/print_attachment.dart';
|
||||
import 'package:core/data/network/download/downloaded_response.dart';
|
||||
import 'package:core/domain/extensions/datetime_extension.dart';
|
||||
import 'package:core/presentation/extensions/html_extension.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:core/presentation/utils/html_transformer/transform_configuration.dart';
|
||||
import 'package:core/utils/app_logger.dart';
|
||||
import 'package:core/utils/file_utils.dart';
|
||||
import 'package:core/utils/platform_info.dart';
|
||||
import 'package:core/utils/preview_eml_file_utils.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:dio/dio.dart';
|
||||
import 'package:email_recovery/email_recovery/email_recovery_action.dart';
|
||||
import 'package:email_recovery/email_recovery/email_recovery_action_id.dart';
|
||||
import 'package:filesize/filesize.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:jmap_dart_client/jmap/account_id.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/error/set_error.dart';
|
||||
@@ -19,11 +29,14 @@ import 'package:jmap_dart_client/jmap/mail/email/email.dart';
|
||||
import 'package:model/model.dart';
|
||||
import 'package:tmail_ui_user/features/composer/domain/model/email_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/network/email_api.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/presentation/extensions/attachment_extension.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/domain/model/create_new_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/sending_queue/domain/model/sending_email.dart';
|
||||
import 'package:tmail_ui_user/main/exceptions/exception_thrower.dart';
|
||||
@@ -34,6 +47,10 @@ class EmailDataSourceImpl extends EmailDataSource {
|
||||
final EmailAPI emailAPI;
|
||||
final ExceptionThrower _exceptionThrower;
|
||||
final ExceptionThrower _sendEmailExceptionThrower = Get.find<SendEmailExceptionThrower>();
|
||||
final PreviewEmlFileUtils _previewEmailUtils = Get.find<PreviewEmlFileUtils>();
|
||||
final HtmlAnalyzer _htmlAnalyzer = Get.find<HtmlAnalyzer>();
|
||||
final FileUtils _fileUtils = Get.find<FileUtils>();
|
||||
final ImagePaths _imagePaths = Get.find<ImagePaths>();
|
||||
|
||||
EmailDataSourceImpl(this.emailAPI, this._exceptionThrower);
|
||||
|
||||
@@ -385,4 +402,125 @@ class EmailDataSourceImpl extends EmailDataSource {
|
||||
return await emailAPI.parseEmailByBlobIds(accountId, blobIds);
|
||||
}).catchError(_exceptionThrower.throwException);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest) {
|
||||
return Future.sync(() async {
|
||||
final email = previewEmailEMLRequest.email;
|
||||
final appLocalizations = previewEmailEMLRequest.appLocalizations;
|
||||
final locale = previewEmailEMLRequest.locale.toLanguageTag();
|
||||
|
||||
final listAttachments = email
|
||||
.allAttachments
|
||||
.getListAttachmentsDisplayedOutside(email.htmlBodyAttachments);
|
||||
|
||||
final listInlineImages = email
|
||||
.allAttachments
|
||||
.listAttachmentsDisplayedInContent;
|
||||
|
||||
final mapCidImageDownloadUrl = listInlineImages.toMapCidImageDownloadUrl(
|
||||
accountId: previewEmailEMLRequest.accountId,
|
||||
downloadUrl: previewEmailEMLRequest.baseDownloadUrl,
|
||||
);
|
||||
|
||||
final emailContentEscaped = await _transformEmailContent(
|
||||
email.emailContentList,
|
||||
mapCidImageDownloadUrl,
|
||||
);
|
||||
|
||||
final sender = email.from?.isNotEmpty == true
|
||||
? email.from!.first
|
||||
: null;
|
||||
|
||||
final receiveTime = email.getReceivedAt(
|
||||
newLocale: locale,
|
||||
pattern: email.receivedAt?.value.toLocal().toPatternForPrinting(locale)
|
||||
);
|
||||
|
||||
final sentTime = email.getSentAt(
|
||||
newLocale: locale,
|
||||
pattern: email.sentAt?.value.toLocal().toPatternForPrinting(locale)
|
||||
);
|
||||
|
||||
final List<PrintAttachment> listPrintAttachment = [];
|
||||
|
||||
if (listAttachments.isNotEmpty) {
|
||||
await Future.forEach<Attachment>(listAttachments, (attachment) async {
|
||||
final iconBase64Data = await _fileUtils.convertImageAssetToBase64(
|
||||
attachment.getIcon(_imagePaths));
|
||||
|
||||
final printAttachment = PrintAttachment(
|
||||
iconBase64Data: iconBase64Data,
|
||||
name: attachment.name.escapeLtGtHtmlString(),
|
||||
size: filesize(attachment.size?.value),
|
||||
);
|
||||
|
||||
listPrintAttachment.add(printAttachment);
|
||||
});
|
||||
}
|
||||
|
||||
final attachmentIconBase64Data = email.hasAttachment == true
|
||||
? await _fileUtils.convertImageAssetToBase64(_imagePaths.icAttachment)
|
||||
: '';
|
||||
|
||||
final previewEmlHtmlDocument = _previewEmailUtils.generatePreviewEml(
|
||||
appName: appLocalizations.app_name,
|
||||
userName: previewEmailEMLRequest.userName.value,
|
||||
subjectPrefix: appLocalizations.subject,
|
||||
subject: previewEmailEMLRequest.email.subject?.escapeLtGtHtmlString() ?? '',
|
||||
emailContent: emailContentEscaped,
|
||||
senderName: sender?.name.escapeLtGtHtmlString() ?? '',
|
||||
senderEmailAddress: sender?.email ?? '',
|
||||
dateTime: receiveTime.isNotEmpty ? receiveTime : sentTime,
|
||||
fromPrefix: appLocalizations.from_email_address_prefix,
|
||||
toPrefix: appLocalizations.to_email_address_prefix,
|
||||
ccPrefix: appLocalizations.cc_email_address_prefix,
|
||||
bccPrefix: appLocalizations.bcc_email_address_prefix,
|
||||
replyToPrefix: appLocalizations.replyToEmailAddressPrefix,
|
||||
titleAttachment: appLocalizations.attachments.toLowerCase(),
|
||||
attachmentIcon: attachmentIconBase64Data,
|
||||
toAddress: email.to?.listEmailAddressToString(isFullEmailAddress: true),
|
||||
ccAddress: email.cc?.listEmailAddressToString(isFullEmailAddress: true),
|
||||
bccAddress: email.bcc?.listEmailAddressToString(isFullEmailAddress: true),
|
||||
replyToAddress: email.replyTo?.listEmailAddressToString(isFullEmailAddress: true),
|
||||
listAttachment: listPrintAttachment,
|
||||
);
|
||||
|
||||
return previewEmlHtmlDocument;
|
||||
}).catchError(_exceptionThrower.throwException);
|
||||
}
|
||||
|
||||
Future<String> _transformEmailContent(
|
||||
List<EmailContent> emailContents,
|
||||
Map<String, String> mapCidImageDownloadUrl,
|
||||
) async {
|
||||
try {
|
||||
final transformConfiguration = PlatformInfo.isWeb
|
||||
? TransformConfiguration.forPreviewEmailOnWeb()
|
||||
: TransformConfiguration.forPreviewEmail();
|
||||
|
||||
final listEmailContent = await Future.wait(emailContents
|
||||
.map((emailContent) async => await _htmlAnalyzer.transformEmailContent(
|
||||
emailContent,
|
||||
mapCidImageDownloadUrl,
|
||||
transformConfiguration,
|
||||
))
|
||||
.toList());
|
||||
|
||||
return listEmailContent.asHtmlString;
|
||||
} catch (e) {
|
||||
logError('EmailDataSourceImpl::_transformEmailContent:Exception = $e');
|
||||
return '';
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
}
|
||||
@@ -34,6 +34,7 @@ import 'package:tmail_ui_user/features/email/domain/extensions/detailed_email_hi
|
||||
import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/domain/model/create_new_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/extensions/list_sending_email_hive_cache_extension.dart';
|
||||
@@ -531,4 +532,19 @@ class EmailHiveCacheDataSourceImpl extends EmailDataSource {
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,224 @@
|
||||
|
||||
import 'dart:async';
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:core/data/network/download/downloaded_response.dart';
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:dio/dio.dart';
|
||||
import 'package:email_recovery/email_recovery/email_recovery_action.dart';
|
||||
import 'package:email_recovery/email_recovery/email_recovery_action_id.dart';
|
||||
import 'package:jmap_dart_client/jmap/account_id.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/error/set_error.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/id.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/properties/properties.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/session/session.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/user_name.dart';
|
||||
import 'package:jmap_dart_client/jmap/mail/email/email.dart';
|
||||
import 'package:model/account/account_request.dart';
|
||||
import 'package:model/download/download_task_id.dart';
|
||||
import 'package:model/email/attachment.dart';
|
||||
import 'package:model/email/mark_star_action.dart';
|
||||
import 'package:model/email/read_actions.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/composer/domain/model/email_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/domain/model/create_new_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/sending_queue/domain/model/sending_email.dart';
|
||||
import 'package:tmail_ui_user/main/exceptions/exception_thrower.dart';
|
||||
|
||||
class EmailLocalStorageDataSourceImpl extends EmailDataSource {
|
||||
|
||||
final LocalStorageManager _localStorageManager;
|
||||
final ExceptionThrower _exceptionThrower;
|
||||
|
||||
EmailLocalStorageDataSourceImpl(
|
||||
this._localStorageManager,
|
||||
this._exceptionThrower,
|
||||
);
|
||||
|
||||
@override
|
||||
Future<bool> deleteEmailPermanently(Session session, AccountId accountId, EmailId emailId, {CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<({List<EmailId> emailIdsSuccess, Map<Id, SetError> mapErrors})> deleteMultipleEmailsPermanently(Session session, AccountId accountId, List<EmailId> emailIds) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> deleteMultipleSendingEmail(AccountId accountId, UserName userName, List<String> sendingIds) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> deleteSendingEmail(AccountId accountId, UserName userName, String sendingId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Uint8List> downloadAttachmentForWeb(DownloadTaskId taskId, Attachment attachment, AccountId accountId, String baseDownloadUrl, AccountRequest accountRequest, StreamController<Either<Failure, Success>> onReceiveController, {CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<List<DownloadTaskId>> downloadAttachments(List<Attachment> attachments, AccountId accountId, String baseDownloadUrl, AccountRequest accountRequest) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<DownloadedResponse> exportAttachment(Attachment attachment, AccountId accountId, String baseDownloadUrl, AccountRequest accountRequest, CancelToken cancelToken) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<List<SendingEmail>> getAllSendingEmails(AccountId accountId, UserName userName) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Email> getDetailedEmailById(Session session, AccountId accountId, EmailId emailId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Email> getEmailContent(Session session, AccountId accountId, EmailId emailId, {Properties? additionalProperties}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<EmailRecoveryAction> getRestoredDeletedMessage(EmailRecoveryActionId emailRecoveryActionId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Email> getStoredEmail(Session session, AccountId accountId, EmailId emailId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<DetailedEmail> getStoredNewEmail(Session session, AccountId accountId, EmailId emailId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<DetailedEmail> getStoredOpenedEmail(Session session, AccountId accountId, EmailId emailId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<SendingEmail> getStoredSendingEmail(AccountId accountId, UserName userName, String sendingId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<({List<EmailId> emailIdsSuccess, Map<Id, SetError> mapErrors})> markAsRead(Session session, AccountId accountId, List<EmailId> emailIds, ReadActions readActions) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<({List<EmailId> emailIdsSuccess, Map<Id, SetError> mapErrors})> markAsStar(Session session, AccountId accountId, List<EmailId> emailIds, MarkStarAction markStarAction) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<({List<EmailId> emailIdsSuccess, Map<Id, SetError> mapErrors})> moveToMailbox(Session session, AccountId accountId, MoveToMailboxRequest moveRequest) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<bool> removeEmailDrafts(Session session, AccountId accountId, EmailId emailId, {CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<EmailRecoveryAction> restoreDeletedMessage(RestoredDeletedMessageRequest restoredDeletedMessageRequest) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Email> saveEmailAsDrafts(Session session, AccountId accountId, Email email, {CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> sendEmail(Session session, AccountId accountId, EmailRequest emailRequest, {CreateNewMailboxRequest? mailboxRequest, CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent) {
|
||||
return Future.sync(() async {
|
||||
return _localStorageManager.save(keyStored, previewEMLContent);
|
||||
}).catchError(_exceptionThrower.throwException);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> storeDetailedNewEmail(Session session, AccountId accountId, DetailedEmail detailedEmail) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> storeEmail(Session session, AccountId accountId, Email email) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> storeEventAttendanceStatus(Session session, AccountId accountId, EmailId emailId, EventActionType eventActionType) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> storeOpenedEmail(Session session, AccountId accountId, DetailedEmail detailedEmail) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<SendingEmail> storeSendingEmail(AccountId accountId, UserName userName, SendingEmail sendingEmail) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> unsubscribeMail(Session session, AccountId accountId, EmailId emailId) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<Email> updateEmailDrafts(Session session, AccountId accountId, Email newEmail, EmailId oldEmailId, {CancelToken? cancelToken}) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<List<SendingEmail>> updateMultipleSendingEmail(AccountId accountId, UserName userName, List<SendingEmail> newSendingEmails) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<SendingEmail> updateSendingEmail(AccountId accountId, UserName userName, SendingEmail newSendingEmail) {
|
||||
throw UnimplementedError();
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored) {
|
||||
return Future.sync(() async {
|
||||
return _localStorageManager.get(keyStored);
|
||||
}).catchError(_exceptionThrower.throwException);
|
||||
}
|
||||
}
|
||||
@@ -902,7 +902,9 @@ class EmailAPI with HandleSetErrorMixin {
|
||||
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds) async {
|
||||
final requestBuilder = JmapRequestBuilder(_httpClient, ProcessingInvocation());
|
||||
final parseEmailMethod = ParseEmailMethod(accountId, blobIds);
|
||||
final parseEmailMethod = ParseEmailMethod(accountId, blobIds)
|
||||
..addProperties(ThreadConstants.propertiesParseEmailByBlobId)
|
||||
..addFetchHTMLBodyValues(true);
|
||||
final parseEmailInvocation = requestBuilder.invocation(parseEmailMethod);
|
||||
|
||||
final response = await (requestBuilder
|
||||
|
||||
@@ -32,6 +32,7 @@ import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/email_print.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/repository/email_repository.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/data/datasource/state_datasource.dart';
|
||||
@@ -486,6 +487,21 @@ class EmailRepositoryImpl extends EmailRepository {
|
||||
|
||||
@override
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds) {
|
||||
throw UnimplementedError();
|
||||
return emailDataSource[DataSourceType.network]!.parseEmailByBlobIds(accountId, blobIds);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest) {
|
||||
return emailDataSource[DataSourceType.network]!.generatePreviewEmailEMLContent(previewEmailEMLRequest);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent) {
|
||||
return emailDataSource[DataSourceType.local]!.sharePreviewEmailEMLContent(keyStored, previewEMLContent);
|
||||
}
|
||||
|
||||
@override
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored) {
|
||||
return emailDataSource[DataSourceType.local]!.getPreviewEmailEMLContentShared(keyStored);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
import 'package:equatable/equatable.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:jmap_dart_client/jmap/account_id.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/id.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/user_name.dart';
|
||||
import 'package:jmap_dart_client/jmap/mail/email/email.dart';
|
||||
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
|
||||
|
||||
class PreviewEmailEMLRequest with EquatableMixin {
|
||||
final AccountId accountId;
|
||||
final UserName userName;
|
||||
final Id blobId;
|
||||
final Email email;
|
||||
final Locale locale;
|
||||
final AppLocalizations appLocalizations;
|
||||
final String baseDownloadUrl;
|
||||
|
||||
PreviewEmailEMLRequest({
|
||||
required this.accountId,
|
||||
required this.userName,
|
||||
required this.blobId,
|
||||
required this.email,
|
||||
required this.locale,
|
||||
required this.appLocalizations,
|
||||
required this.baseDownloadUrl,
|
||||
});
|
||||
|
||||
String get keyStored => blobId.value;
|
||||
|
||||
@override
|
||||
List<Object?> get props => [
|
||||
accountId,
|
||||
userName,
|
||||
blobId,
|
||||
email,
|
||||
locale,
|
||||
appLocalizations,
|
||||
baseDownloadUrl,
|
||||
];
|
||||
}
|
||||
@@ -27,6 +27,7 @@ import 'package:tmail_ui_user/features/email/domain/model/detailed_email.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/email_print.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/restore_deleted_message_request.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/domain/model/create_new_mailbox_request.dart';
|
||||
|
||||
@@ -181,4 +182,10 @@ abstract class EmailRepository {
|
||||
EventActionType eventActionType);
|
||||
|
||||
Future<List<Email>> parseEmailByBlobIds(AccountId accountId, Set<Id> blobIds);
|
||||
|
||||
Future<String> generatePreviewEmailEMLContent(PreviewEmailEMLRequest previewEmailEMLRequest);
|
||||
|
||||
Future<void> sharePreviewEmailEMLContent(String keyStored, String previewEMLContent);
|
||||
|
||||
Future<String> getPreviewEmailEMLContentShared(String keyStored);
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
|
||||
class GettingPreviewEmailEMLContentShared extends LoadingState {}
|
||||
|
||||
class GetPreviewEmailEMLContentSharedSuccess extends UIState {
|
||||
|
||||
final String previewEMLContent;
|
||||
|
||||
GetPreviewEmailEMLContentSharedSuccess(this.previewEMLContent);
|
||||
|
||||
@override
|
||||
List<Object?> get props => [previewEMLContent];
|
||||
}
|
||||
|
||||
class GetPreviewEmailEMLContentSharedFailure extends FeatureFailure {
|
||||
|
||||
GetPreviewEmailEMLContentSharedFailure(dynamic exception) : super(exception: exception);
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/id.dart';
|
||||
import 'package:jmap_dart_client/jmap/mail/email/email.dart';
|
||||
|
||||
class ParsingEmailByBlobId extends LoadingState {}
|
||||
@@ -7,11 +8,12 @@ class ParsingEmailByBlobId extends LoadingState {}
|
||||
class ParseEmailByBlobIdSuccess extends UIState {
|
||||
|
||||
final Email email;
|
||||
final Id blobId;
|
||||
|
||||
ParseEmailByBlobIdSuccess(this.email);
|
||||
ParseEmailByBlobIdSuccess(this.email, this.blobId);
|
||||
|
||||
@override
|
||||
List<Object> get props => [email];
|
||||
List<Object> get props => [email, blobId];
|
||||
}
|
||||
|
||||
class ParseEmailByBlobIdFailure extends FeatureFailure {
|
||||
|
||||
@@ -0,0 +1,19 @@
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
|
||||
class PreviewingEmailFromEmlFile extends LoadingState {}
|
||||
|
||||
class PreviewEmailFromEmlFileSuccess extends UIState {
|
||||
|
||||
final String storeKey;
|
||||
|
||||
PreviewEmailFromEmlFileSuccess(this.storeKey);
|
||||
|
||||
@override
|
||||
List<Object?> get props => [storeKey];
|
||||
}
|
||||
|
||||
class PreviewEmailFromEmlFileFailure extends FeatureFailure {
|
||||
|
||||
PreviewEmailFromEmlFileFailure(dynamic exception) : super(exception: exception);
|
||||
}
|
||||
+24
@@ -0,0 +1,24 @@
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/repository/email_repository.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/get_preview_email_content_shared_state.dart';
|
||||
|
||||
class GetPreviewEmailEMLContentSharedInteractor {
|
||||
final EmailRepository _emailRepository;
|
||||
|
||||
const GetPreviewEmailEMLContentSharedInteractor(this._emailRepository);
|
||||
|
||||
Stream<Either<Failure, Success>> execute(String keyStored) async* {
|
||||
try {
|
||||
yield Right<Failure, Success>(GettingPreviewEmailEMLContentShared());
|
||||
|
||||
final previewEMLContent = await _emailRepository
|
||||
.getPreviewEmailEMLContentShared(keyStored);
|
||||
|
||||
yield Right<Failure, Success>(GetPreviewEmailEMLContentSharedSuccess(previewEMLContent));
|
||||
} catch (e) {
|
||||
yield Left<Failure, Success>(GetPreviewEmailEMLContentSharedFailure(e));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -20,7 +20,10 @@ class ParseEmailByBlobIdInteractor {
|
||||
{blobId},
|
||||
);
|
||||
|
||||
yield Right<Failure, Success>(ParseEmailByBlobIdSuccess(emailParsed.first));
|
||||
yield Right<Failure, Success>(ParseEmailByBlobIdSuccess(
|
||||
emailParsed.first,
|
||||
blobId,
|
||||
));
|
||||
} catch (e) {
|
||||
yield Left<Failure, Success>(ParseEmailByBlobIdFailure(e));
|
||||
}
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/repository/email_repository.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/preview_email_from_eml_file_state.dart';
|
||||
|
||||
class PreviewEmailFromEmlFileInteractor {
|
||||
final EmailRepository _emailRepository;
|
||||
|
||||
const PreviewEmailFromEmlFileInteractor(this._emailRepository);
|
||||
|
||||
Stream<Either<Failure, Success>> execute(
|
||||
PreviewEmailEMLRequest previewEmailEMLRequest,
|
||||
) async* {
|
||||
try {
|
||||
yield Right<Failure, Success>(PreviewingEmailFromEmlFile());
|
||||
|
||||
final previewEMLContent = await _emailRepository
|
||||
.generatePreviewEmailEMLContent(previewEmailEMLRequest);
|
||||
|
||||
final keyStored = previewEmailEMLRequest.keyStored;
|
||||
|
||||
await _emailRepository.sharePreviewEmailEMLContent(keyStored, previewEMLContent);
|
||||
|
||||
yield Right<Failure, Success>(PreviewEmailFromEmlFileSuccess(keyStored));
|
||||
} catch (e) {
|
||||
yield Left<Failure, Success>(PreviewEmailFromEmlFileFailure(e));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,11 +1,13 @@
|
||||
import 'package:core/core.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/base_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
@@ -20,6 +22,8 @@ import 'package:tmail_ui_user/features/email/domain/usecases/get_stored_email_st
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/mark_as_email_read_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/mark_as_star_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/move_to_mailbox_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/parse_email_by_blob_id_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/preview_email_from_eml_file_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/print_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/store_event_attendance_status_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/store_opened_email_interactor.dart';
|
||||
@@ -70,6 +74,8 @@ class EmailBindings extends BaseBindings {
|
||||
Get.find<StoreOpenedEmailInteractor>(),
|
||||
Get.find<PrintEmailInteractor>(),
|
||||
Get.find<StoreEventAttendanceStatusInteractor>(),
|
||||
Get.find<ParseEmailByBlobIdInteractor>(),
|
||||
Get.find<PreviewEmailFromEmlFileInteractor>(),
|
||||
));
|
||||
}
|
||||
|
||||
@@ -118,6 +124,9 @@ class EmailBindings extends BaseBindings {
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -148,6 +157,8 @@ class EmailBindings extends BaseBindings {
|
||||
Get.lazyPut(() => StoreOpenedEmailInteractor(Get.find<EmailRepository>()));
|
||||
Get.lazyPut(() => PrintEmailInteractor(Get.find<EmailRepository>()));
|
||||
Get.lazyPut(() => StoreEventAttendanceStatusInteractor(Get.find<EmailRepository>()));
|
||||
Get.lazyPut(() => ParseEmailByBlobIdInteractor(Get.find<EmailRepository>()));
|
||||
Get.lazyPut(() => PreviewEmailFromEmlFileInteractor(Get.find<EmailRepository>()));
|
||||
IdentityInteractorsBindings().dependencies();
|
||||
}
|
||||
|
||||
@@ -169,7 +180,8 @@ class EmailBindings extends BaseBindings {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>()
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
|
||||
@@ -7,10 +7,12 @@ import 'package:core/core.dart';
|
||||
import 'package:core/presentation/utils/html_transformer/text/sanitize_autolink_unescape_html_transformer.dart';
|
||||
import 'package:core/presentation/utils/html_transformer/text/new_line_transformer.dart';
|
||||
import 'package:core/presentation/utils/html_transformer/text/standardize_html_sanitizing_transformers.dart';
|
||||
import 'package:core/utils/html/html_utils.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:dio/dio.dart';
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:jmap_dart_client/jmap/account_id.dart';
|
||||
@@ -46,6 +48,7 @@ import 'package:tmail_ui_user/features/email/domain/model/event_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/mark_read_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_to_mailbox_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/preview_email_eml_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/send_receipt_to_sender_request.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/calendar_event_accept_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/calendar_event_maybe_state.dart';
|
||||
@@ -59,6 +62,8 @@ import 'package:tmail_ui_user/features/email/domain/state/mark_as_email_read_sta
|
||||
import 'package:tmail_ui_user/features/email/domain/state/mark_as_email_star_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/move_to_mailbox_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/parse_calendar_event_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/parse_email_by_blob_id_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/preview_email_from_eml_file_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/print_email_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/send_receipt_to_sender_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/store_event_attendance_status_state.dart';
|
||||
@@ -74,6 +79,8 @@ import 'package:tmail_ui_user/features/email/domain/usecases/get_email_content_i
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/mark_as_email_read_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/move_to_mailbox_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/parse_calendar_event_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/parse_email_by_blob_id_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/preview_email_from_eml_file_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/print_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/send_receipt_to_sender_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/store_event_attendance_status_interactor.dart';
|
||||
@@ -138,6 +145,8 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
final StoreOpenedEmailInteractor _storeOpenedEmailInteractor;
|
||||
final PrintEmailInteractor _printEmailInteractor;
|
||||
final StoreEventAttendanceStatusInteractor _storeEventAttendanceStatusInteractor;
|
||||
final ParseEmailByBlobIdInteractor _parseEmailByBlobIdInteractor;
|
||||
final PreviewEmailFromEmlFileInteractor _previewEmailFromEmlFileInteractor;
|
||||
|
||||
CreateNewEmailRuleFilterInteractor? _createNewEmailRuleFilterInteractor;
|
||||
SendReceiptToSenderInteractor? _sendReceiptToSenderInteractor;
|
||||
@@ -191,6 +200,8 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
this._storeOpenedEmailInteractor,
|
||||
this._printEmailInteractor,
|
||||
this._storeEventAttendanceStatusInteractor,
|
||||
this._parseEmailByBlobIdInteractor,
|
||||
this._previewEmailFromEmlFileInteractor,
|
||||
);
|
||||
|
||||
@override
|
||||
@@ -246,6 +257,10 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
calendarEventSuccess(success);
|
||||
} else if (success is StoreEventAttendanceStatusSuccess) {
|
||||
_showToastMessageEventAttendanceSuccess(success);
|
||||
} else if (success is ParseEmailByBlobIdSuccess) {
|
||||
_handleParseEmailByBlobIdSuccess(success);
|
||||
} else if (success is PreviewEmailFromEmlFileSuccess) {
|
||||
_handlePreviewEmailFromEMLFileSuccess(success);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -269,6 +284,10 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
} else if (failure is CalendarEventReplyFailure
|
||||
|| failure is StoreEventAttendanceStatusFailure) {
|
||||
_calendarEventFailure(failure);
|
||||
} else if (failure is ParseEmailByBlobIdFailure) {
|
||||
_handleParseEmailByBlobIdFailure(failure);
|
||||
} else if (failure is PreviewEmailFromEmlFileFailure) {
|
||||
_handlePreviewEmailFromEMLFileFailure(failure);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1896,16 +1915,12 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
}
|
||||
|
||||
void handleViewAttachmentAction(BuildContext context, Attachment attachment) {
|
||||
if (PlatformInfo.isWeb) {
|
||||
if (PlatformInfo.isCanvasKit && attachment.validatePDFIcon()) {
|
||||
previewPDFFileAction(context, attachment);
|
||||
} else {
|
||||
downloadAttachmentForWeb(attachment);
|
||||
}
|
||||
} else if (PlatformInfo.isMobile) {
|
||||
exportAttachment(context, attachment);
|
||||
if (PlatformInfo.isWeb && PlatformInfo.isCanvasKit && attachment.isPDFFile) {
|
||||
previewPDFFileAction(context, attachment);
|
||||
} else if (attachment.isEMLFile) {
|
||||
previewEMLFileAction(attachment, AppLocalizations.of(context));
|
||||
} else {
|
||||
log('EmailView::_handleViewAttachmentAction: THE PLATFORM IS SUPPORTED');
|
||||
handleDownloadAttachmentAction(context, attachment);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1936,6 +1951,80 @@ class SingleEmailController extends BaseController with AppLoaderMixin {
|
||||
);
|
||||
}
|
||||
|
||||
void previewEMLFileAction(Attachment attachment, AppLocalizations appLocalizations) {
|
||||
SmartDialog.showLoading(
|
||||
msg: appLocalizations.loadingPleaseWait,
|
||||
maskColor: Colors.black38,
|
||||
);
|
||||
|
||||
if (accountId == null) {
|
||||
consumeState(Stream.value(Left(ParseEmailByBlobIdFailure(NotFoundAccountIdException()))));
|
||||
return;
|
||||
}
|
||||
|
||||
if (attachment.blobId == null) {
|
||||
consumeState(Stream.value(Left(ParseEmailByBlobIdFailure(NotFoundBlobIdException([])))));
|
||||
return;
|
||||
}
|
||||
|
||||
consumeState(_parseEmailByBlobIdInteractor.execute(
|
||||
accountId!,
|
||||
attachment.blobId!,
|
||||
));
|
||||
}
|
||||
|
||||
void _handleParseEmailByBlobIdSuccess(ParseEmailByBlobIdSuccess success) {
|
||||
if (session == null) {
|
||||
consumeState(Stream.value(Left(PreviewEmailFromEmlFileFailure(NotFoundSessionException()))));
|
||||
return;
|
||||
}
|
||||
|
||||
if (accountId == null) {
|
||||
consumeState(Stream.value(Left(PreviewEmailFromEmlFileFailure(NotFoundAccountIdException()))));
|
||||
return;
|
||||
}
|
||||
|
||||
if (currentContext == null) {
|
||||
consumeState(Stream.value(Left(PreviewEmailFromEmlFileFailure(NotFoundContextException()))));
|
||||
return;
|
||||
}
|
||||
|
||||
consumeState(_previewEmailFromEmlFileInteractor.execute(
|
||||
PreviewEmailEMLRequest(
|
||||
accountId: accountId!,
|
||||
userName: userName!,
|
||||
blobId: success.blobId,
|
||||
email: success.email,
|
||||
locale: Localizations.localeOf(currentContext!),
|
||||
appLocalizations: AppLocalizations.of(currentContext!),
|
||||
baseDownloadUrl: session!.getDownloadUrl(jmapUrl: dynamicUrlInterceptors.jmapUrl),
|
||||
),
|
||||
));
|
||||
}
|
||||
|
||||
void _handleParseEmailByBlobIdFailure(ParseEmailByBlobIdFailure failure) {
|
||||
SmartDialog.dismiss();
|
||||
toastManager.showMessageFailure(failure);
|
||||
}
|
||||
|
||||
void _handlePreviewEmailFromEMLFileFailure(PreviewEmailFromEmlFileFailure failure) {
|
||||
SmartDialog.dismiss();
|
||||
toastManager.showMessageFailure(failure);
|
||||
}
|
||||
|
||||
void _handlePreviewEmailFromEMLFileSuccess(PreviewEmailFromEmlFileSuccess success) {
|
||||
SmartDialog.dismiss();
|
||||
|
||||
if (PlatformInfo.isWeb) {
|
||||
HtmlUtils.openNewWindowByUrl(
|
||||
RouteUtils.createUrlWebLocationBar(
|
||||
AppRoutes.emailEMLPreviewer,
|
||||
previewId: success.storeKey
|
||||
).toString(),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void handleMailToAttendees(CalendarOrganizer? organizer, List<CalendarAttendee>? attendees) {
|
||||
final listEmailAddressAttendees = attendees
|
||||
?.map((attendee) => EmailAddress(attendee.name?.name, attendee.mailto?.mailAddress.value))
|
||||
|
||||
@@ -1,9 +1,11 @@
|
||||
import 'package:core/presentation/extensions/media_type_extension.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:model/email/attachment.dart';
|
||||
import 'package:tmail_ui_user/features/upload/domain/extensions/media_type_extension.dart';
|
||||
|
||||
extension AttachmentExtension on Attachment {
|
||||
String getIcon(ImagePaths imagePaths) => type?.getIcon(imagePaths, fileName: name) ?? imagePaths.icFileEPup;
|
||||
|
||||
bool validatePDFIcon() => type?.validatePDFIcon(fileName: name) ?? false;
|
||||
bool get isPDFFile => type?.isPDFFile(fileName: name) ?? false;
|
||||
|
||||
bool get isEMLFile => type?.isEMLFile ?? false;
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
|
||||
import 'package:core/data/model/source_type/data_source_type.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:core/utils/file_utils.dart';
|
||||
import 'package:core/utils/print_utils.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/base_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/network/email_api.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/repository/email_repository_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/repository/email_repository.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/get_preview_email_eml_content_shared_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email_previewer/email_previewer_controller.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/data/datasource/state_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/data/datasource_impl/state_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/mailbox/data/local/state_cache_manager.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/manager/new_email_cache_manager.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/manager/new_email_cache_worker_queue.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/manager/opened_email_cache_manager.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/manager/opened_email_cache_worker_queue.dart';
|
||||
import 'package:tmail_ui_user/features/offline_mode/manager/sending_email_cache_manager.dart';
|
||||
import 'package:tmail_ui_user/features/thread/data/local/email_cache_manager.dart';
|
||||
import 'package:tmail_ui_user/main/exceptions/cache_exception_thrower.dart';
|
||||
import 'package:tmail_ui_user/main/exceptions/remote_exception_thrower.dart';
|
||||
import 'package:tmail_ui_user/main/utils/ios_sharing_manager.dart';
|
||||
|
||||
class EmailPreviewerBindings extends BaseBindings {
|
||||
|
||||
@override
|
||||
void bindingsController() {
|
||||
Get.lazyPut(() => EmailPreviewerController(
|
||||
Get.find<GetPreviewEmailEMLContentSharedInteractor>()));
|
||||
}
|
||||
|
||||
@override
|
||||
void bindingsDataSource() {
|
||||
Get.lazyPut<EmailDataSource>(() => Get.find<EmailDataSourceImpl>());
|
||||
Get.lazyPut<HtmlDataSource>(() => Get.find<HtmlDataSourceImpl>());
|
||||
Get.lazyPut<StateDataSource>(() => Get.find<StateDataSourceImpl>());
|
||||
Get.lazyPut<PrintFileDataSource>(() => Get.find<PrintFileDataSourceImpl>());
|
||||
}
|
||||
|
||||
@override
|
||||
void bindingsDataSourceImpl() {
|
||||
Get.lazyPut(() => EmailDataSourceImpl(
|
||||
Get.find<EmailAPI>(),
|
||||
Get.find<RemoteExceptionThrower>()));
|
||||
Get.lazyPut(() => HtmlDataSourceImpl(
|
||||
Get.find<HtmlAnalyzer>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => StateDataSourceImpl(
|
||||
Get.find<StateCacheManager>(),
|
||||
Get.find<IOSSharingManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => PrintFileDataSourceImpl(
|
||||
Get.find<PrintUtils>(),
|
||||
Get.find<ImagePaths>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<HtmlAnalyzer>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailHiveCacheDataSourceImpl(
|
||||
Get.find<NewEmailCacheManager>(),
|
||||
Get.find<OpenedEmailCacheManager>(),
|
||||
Get.find<NewEmailCacheWorkerQueue>(),
|
||||
Get.find<OpenedEmailCacheWorkerQueue>(),
|
||||
Get.find<EmailCacheManager>(),
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
}
|
||||
|
||||
@override
|
||||
void bindingsInteractor() {
|
||||
Get.lazyPut(() => GetPreviewEmailEMLContentSharedInteractor(
|
||||
Get.find<EmailRepository>()));
|
||||
}
|
||||
|
||||
@override
|
||||
void bindingsRepository() {
|
||||
Get.lazyPut<EmailRepository>(() => Get.find<EmailRepositoryImpl>());
|
||||
}
|
||||
|
||||
@override
|
||||
void bindingsRepositoryImpl() {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
Get.find<PrintFileDataSource>()));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/base_controller.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/exceptions/email_exceptions.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/get_preview_email_content_shared_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/get_preview_email_eml_content_shared_interactor.dart';
|
||||
import 'package:tmail_ui_user/main/routes/route_utils.dart';
|
||||
|
||||
class EmailPreviewerController extends BaseController {
|
||||
|
||||
final GetPreviewEmailEMLContentSharedInteractor _getPreviewEmailEMLContentSharedInteractor;
|
||||
|
||||
EmailPreviewerController(
|
||||
this._getPreviewEmailEMLContentSharedInteractor,
|
||||
);
|
||||
|
||||
@override
|
||||
void onReady() {
|
||||
super.onReady();
|
||||
_getPreviewEmailEMLContentShared();
|
||||
}
|
||||
|
||||
void _getPreviewEmailEMLContentShared() {
|
||||
final parameters = Get.parameters;
|
||||
|
||||
if (parameters.isEmpty) {
|
||||
consumeState(Stream.value(Left(GetPreviewEmailEMLContentSharedFailure(
|
||||
NotFoundBlobIdException([])))));
|
||||
return;
|
||||
}
|
||||
|
||||
final keyStored = parameters[RouteUtils.paramID];
|
||||
if (keyStored?.trim().isNotEmpty == true) {
|
||||
consumeState(_getPreviewEmailEMLContentSharedInteractor.execute(keyStored!));
|
||||
} else {
|
||||
consumeState(Stream.value(Left(GetPreviewEmailEMLContentSharedFailure(
|
||||
NotFoundBlobIdException([])))));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
|
||||
import 'package:core/presentation/views/html_viewer/html_content_viewer_on_web_widget.dart';
|
||||
import 'package:core/presentation/views/loading/cupertino_loading_widget.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/get_preview_email_content_shared_state.dart';
|
||||
import 'package:tmail_ui_user/features/email_previewer/email_previewer_controller.dart';
|
||||
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
|
||||
|
||||
class EmailPreviewerView extends GetWidget<EmailPreviewerController> {
|
||||
|
||||
const EmailPreviewerView({super.key});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Scaffold(
|
||||
backgroundColor: Colors.white,
|
||||
body: Obx(() {
|
||||
final viewState = controller.viewState.value;
|
||||
return viewState.fold(
|
||||
(failure) {
|
||||
if (viewState is GetPreviewEmailEMLContentSharedFailure) {
|
||||
return Center(
|
||||
child: Text(AppLocalizations.of(context).previewEmailFromEMLFileFailed),
|
||||
);
|
||||
} else {
|
||||
return const Center(
|
||||
child: CupertinoLoadingWidget(),
|
||||
);
|
||||
}
|
||||
},
|
||||
(success) {
|
||||
if (success is GetPreviewEmailEMLContentSharedSuccess) {
|
||||
return HtmlContentViewerOnWeb(
|
||||
widthContent: context.width,
|
||||
heightContent: context.height,
|
||||
contentHtml: success.previewEMLContent,
|
||||
);
|
||||
} else {
|
||||
return const Center(
|
||||
child: CupertinoLoadingWidget(),
|
||||
);
|
||||
}
|
||||
});
|
||||
}),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,2 +1,6 @@
|
||||
|
||||
class NotFoundSessionException implements Exception {}
|
||||
class NotFoundSessionException implements Exception {}
|
||||
|
||||
class NotFoundAccountIdException implements Exception {}
|
||||
|
||||
class NotFoundContextException implements Exception {}
|
||||
+7
-1
@@ -7,6 +7,7 @@ import 'package:core/utils/print_utils.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/base_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/clients/recent_search_cache_client.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/composer/data/repository/contact_repository_impl.dart';
|
||||
import 'package:tmail_ui_user/features/composer/domain/repository/contact_repository.dart';
|
||||
import 'package:tmail_ui_user/features/composer/domain/usecases/send_email_interactor.dart';
|
||||
@@ -15,6 +16,7 @@ import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dar
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
@@ -254,6 +256,9 @@ class MailboxDashBoardBindings extends BaseBindings {
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => RemoteServerSettingsDataSourceImpl(
|
||||
Get.find<ServerSettingsAPI>(),
|
||||
Get.find<RemoteExceptionThrower>()
|
||||
@@ -340,7 +345,8 @@ class MailboxDashBoardBindings extends BaseBindings {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>()
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
|
||||
@@ -4,12 +4,14 @@ import 'package:core/utils/file_utils.dart';
|
||||
import 'package:core/utils/print_utils.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/interactors_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/composer/domain/usecases/send_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
@@ -89,6 +91,9 @@ class SendEmailInteractorBindings extends InteractorsBindings {
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => RemoteServerSettingsDataSourceImpl(
|
||||
Get.find<ServerSettingsAPI>(),
|
||||
Get.find<RemoteExceptionThrower>()));
|
||||
@@ -111,7 +116,8 @@ class SendEmailInteractorBindings extends InteractorsBindings {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>()
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
|
||||
@@ -4,11 +4,13 @@ import 'package:core/utils/file_utils.dart';
|
||||
import 'package:core/utils/print_utils.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/base/interactors_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/email_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/html_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource/print_file_datasource.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_local_storage_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/html_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/datasource_impl/print_file_datasource_impl.dart';
|
||||
import 'package:tmail_ui_user/features/email/data/local/html_analyzer.dart';
|
||||
@@ -127,6 +129,9 @@ class FcmInteractorBindings extends InteractorsBindings {
|
||||
Get.find<SendingEmailCacheManager>(),
|
||||
Get.find<FileUtils>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
Get.lazyPut(() => EmailLocalStorageDataSourceImpl(
|
||||
Get.find<LocalStorageManager>(),
|
||||
Get.find<CacheExceptionThrower>()));
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -180,7 +185,8 @@ class FcmInteractorBindings extends InteractorsBindings {
|
||||
Get.lazyPut(() => EmailRepositoryImpl(
|
||||
{
|
||||
DataSourceType.network: Get.find<EmailDataSource>(),
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>()
|
||||
DataSourceType.hiveCache: Get.find<EmailHiveCacheDataSourceImpl>(),
|
||||
DataSourceType.local: Get.find<EmailLocalStorageDataSourceImpl>(),
|
||||
},
|
||||
Get.find<HtmlDataSource>(),
|
||||
Get.find<StateDataSource>(),
|
||||
|
||||
@@ -2,10 +2,10 @@ import 'package:core/presentation/state/failure.dart';
|
||||
import 'package:core/presentation/state/success.dart';
|
||||
import 'package:dartz/dartz.dart';
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:jmap_dart_client/jmap/core/session/session.dart';
|
||||
import 'package:model/oidc/oidc_configuration.dart';
|
||||
import 'package:model/oidc/token_oidc.dart';
|
||||
import 'package:tip_dialog/tip_dialog.dart';
|
||||
import 'package:tmail_ui_user/features/base/reloadable/reloadable_controller.dart';
|
||||
import 'package:tmail_ui_user/features/home/domain/state/get_session_state.dart';
|
||||
import 'package:tmail_ui_user/features/login/data/network/config/oidc_constant.dart';
|
||||
@@ -44,7 +44,7 @@ class TwakeWelcomeController extends ReloadableController {
|
||||
}
|
||||
|
||||
void onClickSignIn(BuildContext context) {
|
||||
TipDialogHelper.loading(AppLocalizations.of(context).loadingPleaseWait);
|
||||
SmartDialog.showLoading(msg: AppLocalizations.of(context).loadingPleaseWait);
|
||||
|
||||
final baseUri = Uri.tryParse(AppConfig.saasJmapServerUrl);
|
||||
|
||||
@@ -64,7 +64,7 @@ class TwakeWelcomeController extends ReloadableController {
|
||||
}
|
||||
|
||||
void onSignUpTwakeWorkplace(BuildContext context) {
|
||||
TipDialogHelper.loading(AppLocalizations.of(context).loadingPleaseWait);
|
||||
SmartDialog.showLoading(msg: AppLocalizations.of(context).loadingPleaseWait);
|
||||
|
||||
final baseUri = Uri.tryParse(AppConfig.saasJmapServerUrl);
|
||||
|
||||
@@ -115,7 +115,7 @@ class TwakeWelcomeController extends ReloadableController {
|
||||
|
||||
@override
|
||||
void handleReloaded(Session session) {
|
||||
TipDialogHelper.dismiss();
|
||||
SmartDialog.dismiss();
|
||||
|
||||
popAndPush(
|
||||
RouteUtils.generateNavigationRoute(AppRoutes.dashboard),
|
||||
@@ -124,7 +124,7 @@ class TwakeWelcomeController extends ReloadableController {
|
||||
|
||||
@override
|
||||
void handleGetSessionFailure(GetSessionFailure failure) {
|
||||
TipDialogHelper.dismiss();
|
||||
SmartDialog.dismiss();
|
||||
|
||||
toastManager.showMessageFailure(failure);
|
||||
}
|
||||
@@ -147,13 +147,13 @@ class TwakeWelcomeController extends ReloadableController {
|
||||
}
|
||||
|
||||
void _handleSignInTwakeWorkplaceFailure(SignInTwakeWorkplaceFailure failure) {
|
||||
TipDialogHelper.dismiss();
|
||||
SmartDialog.dismiss();
|
||||
|
||||
toastManager.showMessageFailure(failure);
|
||||
}
|
||||
|
||||
void _handleSignUpTwakeWorkplaceFailure(SignUpTwakeWorkplaceFailure failure) {
|
||||
TipDialogHelper.dismiss();
|
||||
SmartDialog.dismiss();
|
||||
|
||||
toastManager.showMessageFailure(failure);
|
||||
}
|
||||
|
||||
@@ -3,7 +3,6 @@ import 'package:flutter/services.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:linagora_design_flutter/linagora_design_flutter.dart';
|
||||
import 'package:tip_dialog/tip_dialog.dart';
|
||||
import 'package:tmail_ui_user/features/starting_page/presentation/twake_welcome/twake_welcome_controller.dart';
|
||||
import 'package:tmail_ui_user/features/starting_page/presentation/twake_welcome/twake_welcome_view_style.dart';
|
||||
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
|
||||
@@ -19,42 +18,29 @@ class TwakeWelcomeView extends GetWidget<TwakeWelcomeController> {
|
||||
DeviceOrientation.portraitDown
|
||||
]);
|
||||
|
||||
return Stack(
|
||||
children: [
|
||||
TwakeWelcomeScreen(
|
||||
logo: Padding(
|
||||
padding: const EdgeInsetsDirectional.only(bottom: 16),
|
||||
child: SvgPicture.asset(
|
||||
controller.imagePaths.icLogoTwakeWelcome,
|
||||
fit: BoxFit.fill,
|
||||
),
|
||||
),
|
||||
focusColor: Colors.transparent,
|
||||
hoverColor: Colors.transparent,
|
||||
highlightColor: Colors.transparent,
|
||||
overlayColor: WidgetStateProperty.all(Colors.transparent),
|
||||
signInTitle: AppLocalizations.of(context).signIn.capitalizeFirst ?? '',
|
||||
onSignInOnTap: () => controller.onClickSignIn(context),
|
||||
onCreateTwakeIdOnTap: () => controller.onSignUpTwakeWorkplace(context),
|
||||
createTwakeIdTitle: AppLocalizations.of(context).createTwakeId,
|
||||
useCompanyServerTitle: AppLocalizations.of(context).useCompanyServer,
|
||||
description: AppLocalizations.of(context).descriptionWelcomeTo,
|
||||
descriptionTextStyle: TwakeWelcomeViewStyle.descriptionTextStyle,
|
||||
privacyPolicy: AppLocalizations.of(context).privacyPolicy,
|
||||
descriptionPrivacyPolicy: AppLocalizations.of(context).byContinuingYouAreAgreeingToOur,
|
||||
onPrivacyPolicyOnTap: controller.onClickPrivacyPolicy,
|
||||
onUseCompanyServerOnTap: controller.handleUseCompanyServer,
|
||||
return TwakeWelcomeScreen(
|
||||
logo: Padding(
|
||||
padding: const EdgeInsetsDirectional.only(bottom: 16),
|
||||
child: SvgPicture.asset(
|
||||
controller.imagePaths.icLogoTwakeWelcome,
|
||||
fit: BoxFit.fill,
|
||||
),
|
||||
TipDialogContainer(
|
||||
duration: const Duration(seconds: 2),
|
||||
outsideTouchable: true,
|
||||
onOutsideTouch: (tipDialog) {
|
||||
if (tipDialog is TipDialog && tipDialog.type == TipDialogType.LOADING) {
|
||||
TipDialogHelper.dismiss();
|
||||
}
|
||||
}
|
||||
)
|
||||
],
|
||||
),
|
||||
focusColor: Colors.transparent,
|
||||
hoverColor: Colors.transparent,
|
||||
highlightColor: Colors.transparent,
|
||||
overlayColor: WidgetStateProperty.all(Colors.transparent),
|
||||
signInTitle: AppLocalizations.of(context).signIn.capitalizeFirst ?? '',
|
||||
onSignInOnTap: () => controller.onClickSignIn(context),
|
||||
onCreateTwakeIdOnTap: () => controller.onSignUpTwakeWorkplace(context),
|
||||
createTwakeIdTitle: AppLocalizations.of(context).createTwakeId,
|
||||
useCompanyServerTitle: AppLocalizations.of(context).useCompanyServer,
|
||||
description: AppLocalizations.of(context).descriptionWelcomeTo,
|
||||
descriptionTextStyle: TwakeWelcomeViewStyle.descriptionTextStyle,
|
||||
privacyPolicy: AppLocalizations.of(context).privacyPolicy,
|
||||
descriptionPrivacyPolicy: AppLocalizations.of(context).byContinuingYouAreAgreeingToOur,
|
||||
onPrivacyPolicyOnTap: controller.onClickPrivacyPolicy,
|
||||
onUseCompanyServerOnTap: controller.handleUseCompanyServer,
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -84,4 +84,28 @@ class ThreadConstants {
|
||||
|
||||
static const int defaultMaxHeightEmailItemOnBrowser = 40;
|
||||
static const int defaultMaxHeightBrowser = 1200;
|
||||
|
||||
static final propertiesParseEmailByBlobId = Properties({
|
||||
EmailProperty.id,
|
||||
EmailProperty.blobId,
|
||||
EmailProperty.subject,
|
||||
EmailProperty.from,
|
||||
EmailProperty.to,
|
||||
EmailProperty.cc,
|
||||
EmailProperty.bcc,
|
||||
EmailProperty.keywords,
|
||||
EmailProperty.size,
|
||||
EmailProperty.receivedAt,
|
||||
EmailProperty.sentAt,
|
||||
EmailProperty.preview,
|
||||
EmailProperty.hasAttachment,
|
||||
EmailProperty.replyTo,
|
||||
EmailProperty.mailboxIds,
|
||||
EmailProperty.bodyValues,
|
||||
EmailProperty.htmlBody,
|
||||
EmailProperty.attachments,
|
||||
EmailProperty.headers,
|
||||
EmailProperty.messageId,
|
||||
EmailProperty.references,
|
||||
});
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
import 'package:core/domain/extensions/media_type_extension.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:http_parser/http_parser.dart';
|
||||
|
||||
extension MediaTypeExtension on MediaType {
|
||||
String getIcon(ImagePaths imagePaths, {String? fileName}) {
|
||||
if (validatePDFIcon(fileName: fileName) == true) {
|
||||
return imagePaths.icFilePdf;
|
||||
} else if (isDocFile()) {
|
||||
return imagePaths.icFileDocx;
|
||||
} else if (isExcelFile()) {
|
||||
return imagePaths.icFileXlsx;
|
||||
} else if (isPowerPointFile()) {
|
||||
return imagePaths.icFilePptx;
|
||||
} else if (isPdfFile()) {
|
||||
return imagePaths.icFilePdf;
|
||||
} else if (isZipFile()) {
|
||||
return imagePaths.icFileZip;
|
||||
} else if (isImageFile()) {
|
||||
return imagePaths.icFilePng;
|
||||
} else {
|
||||
return imagePaths.icFileEPup;
|
||||
}
|
||||
}
|
||||
|
||||
bool validatePDFIcon({required String? fileName}) => mimeType == 'application/pdf' ||
|
||||
(mimeType == 'application/octet-stream' && fileName?.endsWith('.pdf') == true);
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
|
||||
import 'package:core/presentation/extensions/media_type_extension.dart';
|
||||
import 'package:core/presentation/resources/image_paths.dart';
|
||||
import 'package:core/utils/app_logger.dart';
|
||||
import 'package:dio/dio.dart';
|
||||
@@ -6,7 +7,6 @@ import 'package:equatable/equatable.dart';
|
||||
import 'package:http_parser/http_parser.dart';
|
||||
import 'package:model/email/attachment.dart';
|
||||
import 'package:model/upload/file_info.dart';
|
||||
import 'package:tmail_ui_user/features/upload/domain/extensions/media_type_extension.dart';
|
||||
import 'package:tmail_ui_user/features/upload/domain/model/upload_task_id.dart';
|
||||
import 'package:tmail_ui_user/features/upload/presentation/model/upload_file_status.dart';
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
{
|
||||
"@@last_modified": "2025-01-09T04:35:09.125475",
|
||||
"@@last_modified": "2025-01-10T23:14:09.007935",
|
||||
"initializing_data": "Initializing data...",
|
||||
"@initializing_data": {
|
||||
"type": "text",
|
||||
@@ -4089,5 +4089,17 @@
|
||||
"type": "text",
|
||||
"placeholders_order": [],
|
||||
"placeholders": {}
|
||||
},
|
||||
"parseEmailByBlobIdFailed": "Cannot parse email by blob id",
|
||||
"@parseEmailByBlobIdFailed": {
|
||||
"type": "text",
|
||||
"placeholders_order": [],
|
||||
"placeholders": {}
|
||||
},
|
||||
"previewEmailFromEMLFileFailed": "Cannot preview this eml file",
|
||||
"@previewEmailFromEMLFileFailed": {
|
||||
"type": "text",
|
||||
"placeholders_order": [],
|
||||
"placeholders": {}
|
||||
}
|
||||
}
|
||||
+4
-1
@@ -3,6 +3,7 @@ import 'package:core/utils/app_logger.dart';
|
||||
import 'package:core/utils/build_utils.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_localizations/flutter_localizations.dart';
|
||||
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:tmail_ui_user/features/caching/config/hive_cache_config.dart';
|
||||
import 'package:tmail_ui_user/main/bindings/main_bindings.dart';
|
||||
@@ -74,6 +75,8 @@ class TMailApp extends StatelessWidget {
|
||||
unknownRoute: AppPages.unknownRoutePage,
|
||||
defaultTransition: Transition.noTransition,
|
||||
initialRoute: AppRoutes.home,
|
||||
getPages: AppPages.pages);
|
||||
getPages: AppPages.pages,
|
||||
builder: FlutterSmartDialog.init(),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -7,12 +7,14 @@ import 'package:core/utils/application_manager.dart';
|
||||
import 'package:core/utils/config/app_config_loader.dart';
|
||||
import 'package:core/utils/file_utils.dart';
|
||||
import 'package:core/utils/platform_info.dart';
|
||||
import 'package:core/utils/preview_eml_file_utils.dart';
|
||||
import 'package:core/utils/print_utils.dart';
|
||||
import 'package:device_info_plus/device_info_plus.dart';
|
||||
import 'package:flutter_secure_storage/flutter_secure_storage.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:shared_preferences/shared_preferences.dart';
|
||||
import 'package:tmail_ui_user/features/base/before_reconnect_manager.dart';
|
||||
import 'package:tmail_ui_user/features/caching/utils/local_storage_manager.dart';
|
||||
import 'package:tmail_ui_user/features/sending_queue/presentation/utils/sending_queue_isolate_manager.dart';
|
||||
import 'package:tmail_ui_user/main/utils/app_config.dart';
|
||||
import 'package:tmail_ui_user/main/utils/email_receive_manager.dart';
|
||||
@@ -72,6 +74,7 @@ class CoreBindings extends Bindings {
|
||||
if (PlatformInfo.isIOS) {
|
||||
Get.put(IOSNotificationManager());
|
||||
}
|
||||
Get.put(PreviewEmlFileUtils());
|
||||
}
|
||||
|
||||
void _bindingIsolate() {
|
||||
@@ -88,5 +91,6 @@ class CoreBindings extends Bindings {
|
||||
accessibility: KeychainAccessibility.first_unlock_this_device
|
||||
)
|
||||
));
|
||||
Get.put(LocalStorageManager());
|
||||
}
|
||||
}
|
||||
@@ -4294,4 +4294,17 @@ class AppLocalizations {
|
||||
);
|
||||
}
|
||||
|
||||
String get parseEmailByBlobIdFailed {
|
||||
return Intl.message(
|
||||
'Cannot parse email by blob id',
|
||||
name: 'parseEmailByBlobIdFailed',
|
||||
);
|
||||
}
|
||||
|
||||
String get previewEmailFromEMLFileFailed {
|
||||
return Intl.message(
|
||||
'Cannot preview this eml file',
|
||||
name: 'previewEmailFromEMLFileFailed',
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@ import 'package:tmail_ui_user/features/composer/presentation/composer_view.dart'
|
||||
import 'package:tmail_ui_user/features/contact/presentation/contact_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/destination_picker/presentation/destination_picker_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/destination_picker/presentation/destination_picker_view.dart' deferred as destination_picker;
|
||||
import 'package:tmail_ui_user/features/email_previewer/email_previewer_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/email_recovery/presentation/email_recovery_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/home/presentation/home_bindings.dart';
|
||||
import 'package:tmail_ui_user/features/home/presentation/home_view.dart';
|
||||
@@ -36,6 +37,7 @@ import 'package:tmail_ui_user/main/routes/app_routes.dart';
|
||||
import 'package:tmail_ui_user/features/search/mailbox/presentation/search_mailbox_view.dart' deferred as search_mailbox_view;
|
||||
import 'package:tmail_ui_user/features/mailto/presentation/mailto_url_view.dart' deferred as mailto_url_view;
|
||||
import 'package:tmail_ui_user/features/email_recovery/presentation/email_recovery_view.dart' deferred as email_recovery;
|
||||
import 'package:tmail_ui_user/features/email_previewer/email_previewer_view.dart' deferred as email_previewer_view;
|
||||
|
||||
class AppPages {
|
||||
static final pages = [
|
||||
@@ -82,6 +84,14 @@ class AppPages {
|
||||
contact_view.loadLibrary,
|
||||
() => contact_view.ContactView()),
|
||||
binding: ContactBindings()),
|
||||
GetPage(
|
||||
name: AppRoutes.emailEMLPreviewer,
|
||||
page: () => DeferredWidget(
|
||||
email_previewer_view.loadLibrary,
|
||||
() => email_previewer_view.EmailPreviewerView(),
|
||||
),
|
||||
binding: EmailPreviewerBindings(),
|
||||
),
|
||||
unknownRoutePage,
|
||||
if (PlatformInfo.isMobile)
|
||||
...[
|
||||
|
||||
@@ -16,4 +16,5 @@ abstract class AppRoutes {
|
||||
static const searchMailbox = '/search_mailbox';
|
||||
static const mailtoURL = '/mailto';
|
||||
static const emailRecovery = '/email_recovery';
|
||||
static const emailEMLPreviewer = '/mail/eml/preview';
|
||||
}
|
||||
@@ -83,12 +83,22 @@ abstract class RouteUtils {
|
||||
return servicePath;
|
||||
}
|
||||
|
||||
static ServicePath _createEmailEMLPreviewerServicePath(String route, {String? previewId}) {
|
||||
ServicePath servicePath = ServicePath(route);
|
||||
if (previewId?.trim().isNotEmpty == true) {
|
||||
servicePath = servicePath.withQueryParameters([
|
||||
StringQueryParameter(paramID, previewId!)
|
||||
]);
|
||||
}
|
||||
return servicePath;
|
||||
}
|
||||
|
||||
static ServicePath _createServicePath(String route) {
|
||||
ServicePath servicePath = ServicePath(route);
|
||||
return servicePath;
|
||||
}
|
||||
|
||||
static Uri createUrlWebLocationBar(String route, {NavigationRouter? router}) {
|
||||
static Uri createUrlWebLocationBar(String route, {NavigationRouter? router, String? previewId}) {
|
||||
if (route == AppRoutes.dashboard) {
|
||||
final servicePath = _createDashboardServicePath(
|
||||
'$baseOriginUrl$route',
|
||||
@@ -98,6 +108,12 @@ abstract class RouteUtils {
|
||||
} else if (route == AppRoutes.settings) {
|
||||
final servicePath = _createSettingServicePath('$baseOriginUrl$route', router: router);
|
||||
return Uri.parse(servicePath.path);
|
||||
} else if (route == AppRoutes.emailEMLPreviewer) {
|
||||
final servicePath = _createEmailEMLPreviewerServicePath(
|
||||
'$baseOriginUrl$route',
|
||||
previewId: previewId,
|
||||
);
|
||||
return Uri.parse(servicePath.path);
|
||||
} else {
|
||||
final servicePath = _createServicePath('$baseOriginUrl$route');
|
||||
return Uri.parse(servicePath.path);
|
||||
|
||||
@@ -5,6 +5,8 @@ import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:model/email/email_action_type.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/model/move_action.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/parse_email_by_blob_id_state.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/state/preview_email_from_eml_file_state.dart';
|
||||
import 'package:tmail_ui_user/features/home/data/exceptions/session_exceptions.dart';
|
||||
import 'package:tmail_ui_user/features/home/domain/state/get_session_state.dart';
|
||||
import 'package:tmail_ui_user/features/login/data/network/oidc_error.dart';
|
||||
@@ -84,6 +86,10 @@ class ToastManager {
|
||||
} else {
|
||||
message = AppLocalizations.of(currentContext!).createTwakeIdFailed;
|
||||
}
|
||||
} else if (failure is ParseEmailByBlobIdFailure) {
|
||||
message = AppLocalizations.of(currentContext!).parseEmailByBlobIdFailed;
|
||||
} else if (failure is PreviewEmailFromEmlFileFailure) {
|
||||
message = AppLocalizations.of(currentContext!).previewEmailFromEMLFileFailed;
|
||||
}
|
||||
|
||||
if (message?.isNotEmpty == true) {
|
||||
|
||||
@@ -64,6 +64,16 @@ extension EmailExtension on Email {
|
||||
return '';
|
||||
}
|
||||
|
||||
String getSentAt({required String newLocale, String? pattern}) {
|
||||
if (sentAt != null) {
|
||||
return sentAt!.formatDateToLocal(
|
||||
pattern: pattern ?? sentAt!.value.toLocal().toPattern(),
|
||||
locale: newLocale
|
||||
);
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
Set<String> getRecipientEmailAddressList() {
|
||||
final listEmailAddress = <String>{};
|
||||
final listToAddress = to.getListAddress() ?? [];
|
||||
|
||||
+8
-16
@@ -1021,6 +1021,14 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "3.1.0"
|
||||
flutter_smart_dialog:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: flutter_smart_dialog
|
||||
sha256: d7b915461fdc9bb8111d23a709b4ce910dbc4b9bef0fbd941655f74bf7de09a6
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.9.8+5"
|
||||
flutter_staggered_grid_view:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@@ -1337,14 +1345,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "2.1.1"
|
||||
loading_view:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: loading_view
|
||||
sha256: "3d31c2c5293c2e3518b7330ffdc2fab5c83daaa9218cc45d4406c875f08f0795"
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.1.0"
|
||||
logging:
|
||||
dependency: transitive
|
||||
description:
|
||||
@@ -2023,14 +2023,6 @@ packages:
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "1.0.1"
|
||||
tip_dialog:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: tip_dialog
|
||||
sha256: edc1ebbb4b9f9575220c85206cf6986921c2b63d173744be0babac00c2e48bd0
|
||||
url: "https://pub.dev"
|
||||
source: hosted
|
||||
version: "4.0.0"
|
||||
typed_data:
|
||||
dependency: transitive
|
||||
description:
|
||||
|
||||
+1
-1
@@ -247,7 +247,7 @@ dependencies:
|
||||
|
||||
web_socket_channel: 2.4.3
|
||||
|
||||
tip_dialog: 4.0.0
|
||||
flutter_smart_dialog: 4.9.8+5
|
||||
|
||||
flutter_web_auth_2: 3.1.1
|
||||
|
||||
|
||||
@@ -47,7 +47,7 @@ void main() {
|
||||
result,
|
||||
emitsInOrder([
|
||||
Right<Failure, Success>(ParsingEmailByBlobId()),
|
||||
Right<Failure, Success>(ParseEmailByBlobIdSuccess(parsedEmail)),
|
||||
Right<Failure, Success>(ParseEmailByBlobIdSuccess(parsedEmail, blobId)),
|
||||
]),
|
||||
);
|
||||
|
||||
|
||||
@@ -39,6 +39,8 @@ import 'package:tmail_ui_user/features/email/domain/usecases/mark_as_email_read_
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/mark_as_star_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/move_to_mailbox_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/parse_calendar_event_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/parse_email_by_blob_id_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/preview_email_from_eml_file_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/print_email_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/store_event_attendance_status_interactor.dart';
|
||||
import 'package:tmail_ui_user/features/email/domain/usecases/store_opened_email_interactor.dart';
|
||||
@@ -98,6 +100,8 @@ const fallbackGenerators = {
|
||||
MockSpec<MaybeCalendarEventInteractor>(),
|
||||
MockSpec<RejectCalendarEventInteractor>(),
|
||||
MockSpec<StoreEventAttendanceStatusInteractor>(),
|
||||
MockSpec<ParseEmailByBlobIdInteractor>(),
|
||||
MockSpec<PreviewEmailFromEmlFileInteractor>(),
|
||||
MockSpec<PrintUtils>(),
|
||||
MockSpec<ApplicationManager>(),
|
||||
MockSpec<ToastManager>(),
|
||||
@@ -134,6 +138,8 @@ void main() {
|
||||
final uuid = MockUuid();
|
||||
final printEmailInteractor = MockPrintEmailInteractor();
|
||||
final storeEventAttendanceStatusInteractor = MockStoreEventAttendanceStatusInteractor();
|
||||
final parseEmailByBlobIdInteractor = MockParseEmailByBlobIdInteractor();
|
||||
final previewEmailFromEmlFileInteractor = MockPreviewEmailFromEmlFileInteractor();
|
||||
final printUtils = MockPrintUtils();
|
||||
final applicationManager = MockApplicationManager();
|
||||
final mockToastManager = MockToastManager();
|
||||
@@ -191,6 +197,8 @@ void main() {
|
||||
storeOpenedEmailInteractor,
|
||||
printEmailInteractor,
|
||||
storeEventAttendanceStatusInteractor,
|
||||
parseEmailByBlobIdInteractor,
|
||||
previewEmailFromEmlFileInteractor,
|
||||
);
|
||||
});
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import 'package:core/core.dart';
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
import 'package:http_parser/http_parser.dart';
|
||||
import 'package:model/email/attachment.dart';
|
||||
import 'package:tmail_ui_user/features/upload/domain/extensions/media_type_extension.dart';
|
||||
|
||||
void main() {
|
||||
final attachmentA = Attachment(
|
||||
@@ -34,7 +34,7 @@ void main() {
|
||||
'WHEN perform call `attachmentA.isDisplayedPDFIcon()`\n'
|
||||
'SHOULD return true',
|
||||
() {
|
||||
bool result = attachmentA.type!.validatePDFIcon(fileName: null);
|
||||
bool result = attachmentA.type!.isPDFFile(fileName: null);
|
||||
|
||||
expect(result, isTrue);
|
||||
});
|
||||
@@ -45,7 +45,7 @@ void main() {
|
||||
'WHEN perform call `attachmentB.isDisplayedPDFIcon()`\n'
|
||||
'SHOULD return true',
|
||||
() {
|
||||
bool result = attachmentB.type!.validatePDFIcon(fileName: 'attachmentB.pdf');
|
||||
bool result = attachmentB.type!.isPDFFile(fileName: 'attachmentB.pdf');
|
||||
|
||||
expect(result, isTrue);
|
||||
});
|
||||
@@ -56,7 +56,7 @@ void main() {
|
||||
'WHEN perform call `attachmentC.isDisplayedPDFIcon()`\n'
|
||||
'SHOULD return false',
|
||||
() {
|
||||
bool result = attachmentC.type!.validatePDFIcon(fileName: 'attachmentC.docx');
|
||||
bool result = attachmentC.type!.isPDFFile(fileName: 'attachmentC.docx');
|
||||
|
||||
expect(result, isFalse);
|
||||
});
|
||||
@@ -67,7 +67,7 @@ void main() {
|
||||
'WHEN perform call `attachmentD.isDisplayedPDFIcon()`\n'
|
||||
'SHOULD return false',
|
||||
() {
|
||||
bool result = attachmentD.type!.validatePDFIcon(fileName: 'attachmentD.png');
|
||||
bool result = attachmentD.type!.isPDFFile(fileName: 'attachmentD.png');
|
||||
|
||||
expect(result, isFalse);
|
||||
});
|
||||
@@ -78,7 +78,7 @@ void main() {
|
||||
'WHEN perform call `attachmentE.isDisplayedPDFIcon()`\n'
|
||||
'SHOULD return false',
|
||||
() {
|
||||
bool result = attachmentE.type!.validatePDFIcon(fileName: 'attachmentE.pdf');
|
||||
bool result = attachmentE.type!.isPDFFile(fileName: 'attachmentE.pdf');
|
||||
|
||||
expect(result, isFalse);
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user