Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Standardize HTML sanitizing when preview email #3223

Merged
merged 9 commits into from
Oct 24, 2024
9 changes: 9 additions & 0 deletions contact/pubspec.lock
Original file line number Diff line number Diff line change
@@ -992,6 +992,15 @@ packages:
url: "https://pub.dev"
source: hosted
version: "3.2.1"
sanitize_html:
dependency: transitive
description:
path: sanitize_html
ref: support_mail
resolved-ref: fda32cde4d4baadaa988477f498ab6622ee79987
url: "https://github.com/linagora/dart-neats.git"
source: git
version: "2.1.0"
shelf:
dependency: transitive
description:
Original file line number Diff line number Diff line change
@@ -23,13 +23,12 @@ class MessageContentTransformer {
Map<String, String>? mapUrlDownloadCID
}) async {
await Future.wait([
if (_configuration.domTransformers.isNotEmpty)
..._configuration.domTransformers.map((domTransformer) async =>
domTransformer.process(
document: document,
dioClient: _dioClient,
mapUrlDownloadCID: mapUrlDownloadCID,
)
..._configuration.domTransformers.map((domTransformer) async =>
domTransformer.process(
document: document,
dioClient: _dioClient,
mapUrlDownloadCID: mapUrlDownloadCID,
)
)
]);
}
@@ -38,24 +37,32 @@ class MessageContentTransformer {
required String message,
Map<String, String>? mapUrlDownloadCID
}) async {
final document = parse(message);
await _transformDocument(
document: document,
mapUrlDownloadCID: mapUrlDownloadCID,
);
final newMessage = _configuration.textTransformers.isNotEmpty
? _transformMessage(message)
: message;

final document = parse(newMessage);

if (_configuration.domTransformers.isNotEmpty) {
await _transformDocument(
document: document,
mapUrlDownloadCID: mapUrlDownloadCID,
);
}

return document;
}

String _transformMessage(String message) {
if (_configuration.textTransformers.isNotEmpty) {
for (var transformer in _configuration.textTransformers) {
message = transformer.process(message, _htmlEscape);
}
for (var transformer in _configuration.textTransformers) {
message = transformer.process(message, _htmlEscape);
}
return message;
}

String toMessage(String message) {
return _transformMessage(message);
return _configuration.textTransformers.isNotEmpty
? _transformMessage(message)
: message;
}
}
16 changes: 16 additions & 0 deletions core/lib/presentation/utils/html_transformer/sanitize_html.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import 'package:sanitize_html/sanitize_html.dart';

class SanitizeHtml {
String process({
required String inputHtml,
List<String>? allowAttributes,
List<String>? allowTags,
}) {
final outputHtml = sanitizeHtml(
inputHtml,
allowAttributes: allowAttributes,
allowTags: allowTags,
);
return outputHtml;
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import 'package:core/utils/app_logger.dart';
import 'package:get/get.dart';

class SanitizeUrl {
@@ -24,7 +23,6 @@ class SanitizeUrl {
} else {
originalUrl = '';
}
log('SanitizeUrl::process:originalUrl = $originalUrl');
return originalUrl;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import 'dart:convert';
import 'package:core/presentation/utils/html_transformer/base/text_transformer.dart';
import 'package:core/presentation/utils/html_transformer/sanitize_html.dart';

class StandardizeHtmlSanitizingTransformers extends TextTransformer {

static const List<String> mailAllowedHtmlAttributes = [
'style',
'public-asset-id',
'data-filename',
'bgcolor',
'id',
'class',
];

static const List<String> mailAllowedHtmlTags = [
'font',
'u',
'center',
'style',
'body',
];

const StandardizeHtmlSanitizingTransformers();

@override
String process(String text, HtmlEscape htmlEscape) =>
SanitizeHtml().process(
inputHtml: text,
allowAttributes: mailAllowedHtmlAttributes,
allowTags: mailAllowedHtmlTags,
);
}
Original file line number Diff line number Diff line change
@@ -15,7 +15,7 @@ import 'package:core/presentation/utils/html_transformer/dom/remove_tooltip_link
import 'package:core/presentation/utils/html_transformer/dom/sanitize_hyper_link_tag_in_html_transformers.dart';
import 'package:core/presentation/utils/html_transformer/dom/script_transformers.dart';
import 'package:core/presentation/utils/html_transformer/dom/signature_transformers.dart';
import 'package:core/presentation/utils/html_transformer/text/sanitize_autolink_html_transformers.dart';
import 'package:core/presentation/utils/html_transformer/text/standardize_html_sanitizing_transformers.dart';
import 'package:core/utils/platform_info.dart';

/// Contains the configuration for all transformations.
@@ -37,7 +37,9 @@ class TransformConfiguration {

factory TransformConfiguration.fromDomTransformers(List<DomTransformer> domTransformers) => TransformConfiguration(domTransformers, []);

factory TransformConfiguration.empty() => const TransformConfiguration([], []);
factory TransformConfiguration.fromTextTransformers(
List<TextTransformer> textTransformers
) => TransformConfiguration([], textTransformers);

factory TransformConfiguration.forReplyForwardEmail() => TransformConfiguration.fromDomTransformers([
if (PlatformInfo.isWeb)
@@ -46,10 +48,15 @@ class TransformConfiguration {
const RemoveCollapsedSignatureButtonTransformer(),
]);

factory TransformConfiguration.forDraftsEmail() => TransformConfiguration.fromDomTransformers([const ImageTransformer()]);
factory TransformConfiguration.forEditDraftsEmail() => TransformConfiguration.fromDomTransformers([
...TransformConfiguration.forDraftsEmail().domTransformers,
const HideDraftSignatureTransformer()]);
factory TransformConfiguration.forDraftsEmail() => TransformConfiguration.create(
customDomTransformers: [const ImageTransformer()]
);
factory TransformConfiguration.forEditDraftsEmail() => TransformConfiguration.create(
customDomTransformers: [
...TransformConfiguration.forDraftsEmail().domTransformers,
const HideDraftSignatureTransformer()
]
);

factory TransformConfiguration.forPreviewEmailOnWeb() => TransformConfiguration.create(
customDomTransformers: [
@@ -65,7 +72,9 @@ class TransformConfiguration {

factory TransformConfiguration.forPreviewEmail() => TransformConfiguration.standardConfiguration;

factory TransformConfiguration.forRestoreEmail() => TransformConfiguration.fromDomTransformers([const ImageTransformer()]);
factory TransformConfiguration.forRestoreEmail() => TransformConfiguration.create(
customDomTransformers: [const ImageTransformer()]
);

factory TransformConfiguration.forPrintEmail() => TransformConfiguration.fromDomTransformers([
if (PlatformInfo.isWeb)
@@ -115,6 +124,6 @@ class TransformConfiguration {
];

static const List<TextTransformer> standardTextTransformers = [
SanitizeAutolinkHtmlTransformers()
StandardizeHtmlSanitizingTransformers(),
];
}
9 changes: 9 additions & 0 deletions core/pubspec.lock
Original file line number Diff line number Diff line change
@@ -945,6 +945,15 @@ packages:
url: "https://pub.dev"
source: hosted
version: "3.0.1"
sanitize_html:
dependency: "direct main"
description:
path: sanitize_html
ref: support_mail
resolved-ref: fda32cde4d4baadaa988477f498ab6622ee79987
url: "https://github.com/linagora/dart-neats.git"
source: git
version: "2.1.0"
shelf:
dependency: transitive
description:
9 changes: 9 additions & 0 deletions core/pubspec.yaml
Original file line number Diff line number Diff line change
@@ -34,6 +34,15 @@ dependencies:
url: https://github.com/dab246/languagetool_textfield.git
ref: twake-supported

# Sanitize_html is restricting Tags and Attributes. So some of our own tags and attributes (signature, public asset,...) will be lost when sanitizing html.
# TODO: We will change it when the PR in upstream repository will be merged
# https://github.com/google/dart-neats/pull/259
sanitize_html:
git:
url: https://github.com/linagora/dart-neats.git
ref: support_mail
path: sanitize_html

### Dependencies from pub.dev ###
cupertino_icons: 1.0.6

52 changes: 52 additions & 0 deletions core/test/utils/standardize_html_sanitizing_transformers_test.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import 'package:core/presentation/utils/html_transformer/text/standardize_html_sanitizing_transformers.dart';
import 'package:flutter_test/flutter_test.dart';
import 'dart:convert';

void main() {
group('StandardizeHtmlSanitizingTransformers::test', () {
const transformer = StandardizeHtmlSanitizingTransformers();
const htmlEscape = HtmlEscape();

test('SHOULD remove attributes of IMG tag WHEN they are invalid', () {
const inputHtml = '<img src="1" href="1" onerror="javascript:alert(1)">';
final result = transformer.process(inputHtml, htmlEscape);

expect(result, equals('<img src="1">'));
});

test('SHOULD remove all SCRIPTS tags', () {
const inputHtml = '<script>alert("This is an alert message!");</script>';
final result = transformer.process(inputHtml, htmlEscape).trim();

expect(result, equals(''));
});

test('SHOULD remove all IFRAME tags', () {
const inputHtml = '<iframe style="xg-p:absolute;top:0;left:0;width:100%;height:100%" onmouseover="prompt(1)">';
final result = transformer.process(inputHtml, htmlEscape);

expect(result, equals(''));
});

test('SHOULD remove href attribute of A tag WHEN it is invalid', () {
const inputHtml = '<a href="javascript:alert(1)" id="id1">test</a>';
final result = transformer.process(inputHtml, htmlEscape);

expect(result, equals('<a id="id1">test</a>'));
});

test('SHOULD persist value src attribute of IMG tag WHEN it is base64 string', () {
const inputHtml = '<img src="data:image/jpeg;base64,iVBORw0KGgoAAAANSUhEUgAAAAUA">';
final result = transformer.process(inputHtml, htmlEscape);

expect(result, equals('<img src="data:image/jpeg;base64,iVBORw0KGgoAAAANSUhEUgAAAAUA">'));
});

test('SHOULD persist value src attribute of IMG tag WHEN it is CID string', () {
const inputHtml = '<img src="cid:email123">';
final result = transformer.process(inputHtml, htmlEscape);

expect(result, equals('<img src="cid:email123">'));
});
});
}
17 changes: 17 additions & 0 deletions lib/features/base/upgradeable/upgrade_hive_database_steps_v12.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@

import 'package:tmail_ui_user/features/base/upgradeable/upgrade_database_steps.dart';
import 'package:tmail_ui_user/features/caching/caching_manager.dart';

class UpgradeHiveDatabaseStepsV12 extends UpgradeDatabaseSteps {

final CachingManager _cachingManager;

UpgradeHiveDatabaseStepsV12(this._cachingManager);

@override
Future<void> onUpgrade(int oldVersion, int newVersion) async {
if (oldVersion > 0 && oldVersion < newVersion && newVersion == 12) {
await _cachingManager.clearEmailCacheAndAllStateCache();
}
}
}
4 changes: 3 additions & 1 deletion lib/features/caching/caching_manager.dart
Original file line number Diff line number Diff line change
@@ -106,18 +106,20 @@ class CachingManager {
return Future.wait([
_stateCacheClient.deleteItem(StateType.email.getTupleKeyStored(accountId, session.username)),
_emailCacheClient.clearAllData(),
if (PlatformInfo.isMobile) clearAllFileInStorage(),
], eagerError: true);
}

Future<void> clearEmailCacheAndAllStateCache() {
return Future.wait([
_stateCacheClient.clearAllData(),
_emailCacheClient.clearAllData(),
if (PlatformInfo.isMobile) clearAllFileInStorage(),
], eagerError: true);
}

Future<bool> storeCacheVersion(int newVersion) async {
log('CachingManager::storeCacheVersion()');
log('CachingManager::storeCacheVersion():newVersion = $newVersion');
return _hiveCacheVersionClient.storeVersion(newVersion);
}

2 changes: 1 addition & 1 deletion lib/features/caching/config/cache_version.dart
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@

class CacheVersion {
static const int hiveDBVersion = 11;
static const int hiveDBVersion = 12;
}
2 changes: 2 additions & 0 deletions lib/features/caching/config/hive_cache_config.dart
Original file line number Diff line number Diff line change
@@ -8,6 +8,7 @@ import 'package:hive/hive.dart';
import 'package:path_provider/path_provider.dart' as path_provider;
import 'package:tmail_ui_user/features/base/upgradeable/upgrade_hive_database_steps_v10.dart';
import 'package:tmail_ui_user/features/base/upgradeable/upgrade_hive_database_steps_v11.dart';
import 'package:tmail_ui_user/features/base/upgradeable/upgrade_hive_database_steps_v12.dart';
import 'package:tmail_ui_user/features/base/upgradeable/upgrade_hive_database_steps_v7.dart';
import 'package:tmail_ui_user/features/caching/caching_manager.dart';
import 'package:tmail_ui_user/features/caching/config/cache_version.dart';
@@ -67,6 +68,7 @@ class HiveCacheConfig {
await UpgradeHiveDatabaseStepsV7(cachingManager).onUpgrade(oldVersion, newVersion);
await UpgradeHiveDatabaseStepsV10(cachingManager).onUpgrade(oldVersion, newVersion);
await UpgradeHiveDatabaseStepsV11(cachingManager).onUpgrade(oldVersion, newVersion);
await UpgradeHiveDatabaseStepsV12(cachingManager).onUpgrade(oldVersion, newVersion);

if (oldVersion != newVersion) {
await cachingManager.storeCacheVersion(newVersion);
5 changes: 4 additions & 1 deletion lib/features/email/data/local/html_analyzer.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import 'package:collection/collection.dart';
import 'package:core/data/constants/constant.dart';
import 'package:core/presentation/utils/html_transformer/html_transform.dart';
import 'package:core/presentation/utils/html_transformer/text/sanitize_autolink_html_transformers.dart';
import 'package:core/presentation/utils/html_transformer/transform_configuration.dart';
import 'package:core/utils/app_logger.dart';
import 'package:dartz/dartz.dart';
@@ -35,7 +36,9 @@ class HtmlAnalyzer {
case EmailContentType.textPlain:
final message = _htmlTransform.transformToTextPlain(
content: emailContent.content,
transformConfiguration: transformConfiguration
transformConfiguration: TransformConfiguration.fromTextTransformers([
const SanitizeAutolinkHtmlTransformers()
]),
);
return EmailContent(emailContent.type, message);
default:
9 changes: 9 additions & 0 deletions model/pubspec.lock
Original file line number Diff line number Diff line change
@@ -969,6 +969,15 @@ packages:
url: "https://pub.dev"
source: hosted
version: "3.2.1"
sanitize_html:
dependency: transitive
description:
path: sanitize_html
ref: support_mail
resolved-ref: fda32cde4d4baadaa988477f498ab6622ee79987
url: "https://github.com/linagora/dart-neats.git"
source: git
version: "2.1.0"
shelf:
dependency: transitive
description:
9 changes: 9 additions & 0 deletions pubspec.lock
Original file line number Diff line number Diff line change
@@ -1714,6 +1714,15 @@ packages:
url: "https://pub.dev"
source: hosted
version: "0.27.7"
sanitize_html:
dependency: transitive
description:
path: sanitize_html
ref: support_mail
resolved-ref: fda32cde4d4baadaa988477f498ab6622ee79987
url: "https://github.com/linagora/dart-neats.git"
source: git
version: "2.1.0"
server_settings:
dependency: "direct main"
description:

Unchanged files with check annotations Beta

final listFileInfo = await onDragDone(context: context, details: details);
await _uploadMultipleFilesToPublicAsset(
context,

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (contact)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (email_recovery)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (forward)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (server_settings)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (fcm)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (model)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (core)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (rule_filter)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously

Check notice on line 883 in lib/features/identity_creator/presentation/identity_creator_controller.dart

GitHub Actions / analyze-test (default)

Don't use 'BuildContext's across async gaps. For more details, see https://dart.dev/tools/diagnostic-messages#use_build_context_synchronously
listFileInfo,
maxWidth: maxWidth);
}
import 'package:contact/contact/model/capability_contact.dart';

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_method.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:contact/contact/model/contact_filter.dart';
import 'package:contact/core/method/request/autocomplete_method.dart';
import 'package:jmap_dart_client/http/converter/account_id_converter.dart';
import 'package:contact/contact/model/tmail_contact.dart';

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/autocomplete/autocomplete_tmail_contact_response.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:contact/core/method/response/autocomplete_response.dart';
import 'package:jmap_dart_client/http/converter/account_id_converter.dart';
import 'package:jmap_dart_client/http/converter/unsigned_int_nullable_converter.dart';

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/capability_contact.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:jmap_dart_client/jmap/core/capability/capability_identifier.dart';
final tmailContactCapabilityIdentifier = CapabilityIdentifier(Uri.parse('com:linagora:params:jmap:contact:autocomplete'));

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:equatable/equatable.dart';
abstract class Contact with EquatableMixin {
import 'package:jmap_dart_client/jmap/core/filter/filter.dart';

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/contact_filter.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:json_annotation/json_annotation.dart';
part 'contact_filter.g.dart';

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact/model/tmail_contact.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:contact/contact/model/contact.dart';
import 'package:jmap_dart_client/jmap/mail/email/email_address.dart';
import 'package:json_annotation/json_annotation.dart';
library contact_module;

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/contact_module.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
export 'contact/model/contact.dart';
export 'contact/model/contact_filter.dart';
import 'package:jmap_dart_client/jmap/account_id.dart';

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/request/autocomplete_method.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:jmap_dart_client/jmap/core/filter/filter.dart';
import 'package:jmap_dart_client/jmap/core/method/method.dart';
import 'package:jmap_dart_client/jmap/core/method/request/query_method.dart';
import 'package:jmap_dart_client/jmap/account_id.dart';

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/core/method/response/autocomplete_response.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:jmap_dart_client/jmap/core/method/method_response.dart';
import 'package:jmap_dart_client/jmap/core/unsigned_int.dart';

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (contact)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (email_recovery)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (forward)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (server_settings)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (fcm)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (model)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (core)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (rule_filter)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting

Check warning on line 1 in contact/lib/data/datasource/auto_complete_datasource.dart

GitHub Actions / analyze-test (default)

Invalid format. For more details, see https://dart.dev/guides/language/effective-dart/style#formatting
import 'package:jmap_dart_client/jmap/mail/email/email_address.dart';
import 'package:model/autocomplete/auto_complete_pattern.dart';