enable lint use_test_throws_matchers (#83943)

This commit is contained in:
Alexandre Ardhuin 2021-06-04 07:14:03 +02:00 committed by GitHub
parent f890e9ca2b
commit cfc08594d9
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 553 additions and 556 deletions

View File

@ -228,6 +228,7 @@ linter:
- use_rethrow_when_possible - use_rethrow_when_possible
# - use_setters_to_change_properties # not yet tested # - use_setters_to_change_properties # not yet tested
# - use_string_buffers # has false positives: https://github.com/dart-lang/sdk/issues/34182 # - use_string_buffers # has false positives: https://github.com/dart-lang/sdk/issues/34182
- use_test_throws_matchers
# - use_to_and_as_if_applicable # has false positives, so we prefer to catch this by code-review # - use_to_and_as_if_applicable # has false positives, so we prefer to catch this by code-review
- valid_regexps - valid_regexps
- void_checks - void_checks

View File

@ -14,22 +14,18 @@ void main() {
end: Object(), end: Object(),
); );
FlutterError? error; expect(
try { () => objectTween.transform(0.1),
objectTween.transform(0.1); throwsA(isA<FlutterError>().having(
} on FlutterError catch (err) { (FlutterError error) => error.diagnostics.map((DiagnosticsNode node) => node.toString()),
error = err; 'diagnostics',
} <String>[
'Cannot lerp between "Instance of \'Object\'" and "Instance of \'Object\'".',
if (error == null) { 'The type Object might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
fail('Expected Tween.transform to throw a FlutterError'); 'There may be a dedicated "ObjectTween" for this type, or you may need to create one.',
} ],
)),
expect(error.diagnostics.map((DiagnosticsNode node) => node.toString()), <String>[ );
'Cannot lerp between "Instance of \'Object\'" and "Instance of \'Object\'".',
'The type Object might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
'There may be a dedicated "ObjectTween" for this type, or you may need to create one.',
]);
}); });
test('throws flutter error when tweening types that do not fully satisfy tween requirements - Color', () { test('throws flutter error when tweening types that do not fully satisfy tween requirements - Color', () {
@ -38,22 +34,18 @@ void main() {
end: const Color(0xFFFFFFFF), end: const Color(0xFFFFFFFF),
); );
FlutterError? error; expect(
try { () => colorTween.transform(0.1),
colorTween.transform(0.1); throwsA(isA<FlutterError>().having(
} on FlutterError catch (err) { (FlutterError error) => error.diagnostics.map((DiagnosticsNode node) => node.toString()),
error = err; 'diagnostics',
} <String>[
'Cannot lerp between "Color(0xff000000)" and "Color(0xffffffff)".',
if (error == null) { 'The type Color might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
fail('Expected Tween.transform to throw a FlutterError'); 'To lerp colors, consider ColorTween instead.',
} ],
)),
expect(error.diagnostics.map((DiagnosticsNode node) => node.toString()), <String>[ );
'Cannot lerp between "Color(0xff000000)" and "Color(0xffffffff)".',
'The type Color might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
'To lerp colors, consider ColorTween instead.',
]);
}); });
test('throws flutter error when tweening types that do not fully satisfy tween requirements - Rect', () { test('throws flutter error when tweening types that do not fully satisfy tween requirements - Rect', () {
@ -62,22 +54,18 @@ void main() {
end: const Rect.fromLTWH(2, 2, 2, 2), end: const Rect.fromLTWH(2, 2, 2, 2),
); );
FlutterError? error; expect(
try { () => rectTween.transform(0.1),
rectTween.transform(0.1); throwsA(isA<FlutterError>().having(
} on FlutterError catch (err) { (FlutterError error) => error.diagnostics.map((DiagnosticsNode node) => node.toString()),
error = err; 'diagnostics',
} <String>[
'Cannot lerp between "Rect.fromLTRB(0.0, 0.0, 10.0, 10.0)" and "Rect.fromLTRB(2.0, 2.0, 4.0, 4.0)".',
if (error == null) { 'The type Rect might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
fail('Expected Tween.transform to throw a FlutterError'); 'To lerp rects, consider RectTween instead.',
} ],
)),
expect(error.diagnostics.map((DiagnosticsNode node) => node.toString()), <String>[ );
'Cannot lerp between "Rect.fromLTRB(0.0, 0.0, 10.0, 10.0)" and "Rect.fromLTRB(2.0, 2.0, 4.0, 4.0)".',
'The type Rect might not fully implement `+`, `-`, and/or `*`. $kApiDocsLink',
'To lerp rects, consider RectTween instead.',
]);
}); });
test('throws flutter error when tweening types that do not fully satisfy tween requirements - int', () { test('throws flutter error when tweening types that do not fully satisfy tween requirements - int', () {
@ -86,22 +74,18 @@ void main() {
end: 1, end: 1,
); );
FlutterError? error; expect(
try { () => colorTween.transform(0.1),
colorTween.transform(0.1); throwsA(isA<FlutterError>().having(
} on FlutterError catch (err) { (FlutterError error) => error.diagnostics.map((DiagnosticsNode node) => node.toString()),
error = err; 'diagnostics',
} <String>[
'Cannot lerp between "0" and "1".',
if (error == null) { 'The type int returned a double after multiplication with a double value. $kApiDocsLink',
fail('Expected Tween.transform to throw a FlutterError'); 'To lerp int values, consider IntTween or StepTween instead.',
} ],
)),
expect(error.diagnostics.map((DiagnosticsNode node) => node.toString()), <String>[ );
'Cannot lerp between "0" and "1".',
'The type int returned a double after multiplication with a double value. $kApiDocsLink',
'To lerp int values, consider IntTween or StepTween instead.',
]);
}); });
test('Can chain tweens', () { test('Can chain tweens', () {

View File

@ -371,24 +371,23 @@ void main() {
}); });
testWidgets('CrossAxisAlignment.baseline is not allowed', (WidgetTester tester) async { testWidgets('CrossAxisAlignment.baseline is not allowed', (WidgetTester tester) async {
try { expect(
MaterialApp( () {
home: Material( MaterialApp(
child: ExpansionTile( home: Material(
initiallyExpanded: true, child: ExpansionTile(
title: const Text('title'), initiallyExpanded: true,
expandedCrossAxisAlignment: CrossAxisAlignment.baseline, title: const Text('title'),
expandedCrossAxisAlignment: CrossAxisAlignment.baseline,
),
), ),
), );
); },
} on AssertionError catch (error) { throwsA(isA<AssertionError>().having((AssertionError error) => error.toString(), '.toString()', contains(
expect(error.toString(), contains(
'CrossAxisAlignment.baseline is not supported since the expanded' 'CrossAxisAlignment.baseline is not supported since the expanded'
' children are aligned in a column, not a row. Try to use another constant.', ' children are aligned in a column, not a row. Try to use another constant.',
)); ))),
return; );
}
fail('AssertionError was not thrown when expandedCrossAxisAlignment is CrossAxisAlignment.baseline.');
}); });
testWidgets('expandedCrossAxisAlignment and expandedAlignment default values', (WidgetTester tester) async { testWidgets('expandedCrossAxisAlignment and expandedAlignment default values', (WidgetTester tester) async {

View File

@ -485,11 +485,10 @@ void main() {
), ),
), ),
); );
try { await expectLater(
await tester.pumpWidget(boilerplate); () => tester.pumpWidget(boilerplate),
} catch (e) { returnsNormally,
fail('Expected no error, but got $e'); );
}
}); });
group('Accessibility (a11y/Semantics)', () { group('Accessibility (a11y/Semantics)', () {

View File

@ -128,16 +128,15 @@ void main() {
]); ]);
}, },
); );
try { expect(
await channel.invokeMethod<dynamic>('sayHello', 'hello'); () => channel.invokeMethod<dynamic>('sayHello', 'hello'),
fail('Exception expected'); throwsA(
} on PlatformException catch (e) { isA<PlatformException>()
expect(e.code, equals('bad')); .having((PlatformException e) => e.code, 'code', equals('bad'))
expect(e.message, equals('Something happened')); .having((PlatformException e) => e.message, 'message', equals('Something happened'))
expect(e.details, equals(<String, dynamic>{'a': 42, 'b': 3.14})); .having((PlatformException e) => e.details, 'details', equals(<String, dynamic>{'a': 42, 'b': 3.14})),
} catch (e) { ),
fail('PlatformException expected'); );
}
}); });
test('can invoke unimplemented method', () async { test('can invoke unimplemented method', () async {
@ -145,15 +144,16 @@ void main() {
'ch7', 'ch7',
(ByteData? message) async => null, (ByteData? message) async => null,
); );
try { expect(
await channel.invokeMethod<void>('sayHello', 'hello'); () => channel.invokeMethod<void>('sayHello', 'hello'),
fail('Exception expected'); throwsA(
} on MissingPluginException catch (e) { isA<MissingPluginException>()
expect(e.message, contains('sayHello')); .having((MissingPluginException e) => e.message, 'message', allOf(
expect(e.message, contains('ch7')); contains('sayHello'),
} catch (e) { contains('ch7'),
fail('MissingPluginException expected'); )),
} ),
);
}); });
test('can invoke unimplemented method (optional)', () async { test('can invoke unimplemented method (optional)', () async {
@ -218,15 +218,14 @@ void main() {
await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage('ch7', call, (ByteData? result) { await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage('ch7', call, (ByteData? result) {
envelope = result; envelope = result;
}); });
try { expect(
jsonMethod.decodeEnvelope(envelope!); () => jsonMethod.decodeEnvelope(envelope!),
fail('Exception expected'); throwsA(
} on PlatformException catch (e) { isA<PlatformException>()
expect(e.code, equals('bad')); .having((PlatformException e) => e.code, 'code', equals('bad'))
expect(e.message, equals('sayHello failed')); .having((PlatformException e) => e.message, 'message', equals('sayHello failed')),
} catch (e) { ),
fail('PlatformException expected'); );
}
}); });
test('can handle method call with other error result', () async { test('can handle method call with other error result', () async {
@ -238,15 +237,14 @@ void main() {
await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage('ch7', call, (ByteData? result) { await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage('ch7', call, (ByteData? result) {
envelope = result; envelope = result;
}); });
try { expect(
jsonMethod.decodeEnvelope(envelope!); () => jsonMethod.decodeEnvelope(envelope!),
fail('Exception expected'); throwsA(
} on PlatformException catch (e) { isA<PlatformException>()
expect(e.code, equals('error')); .having((PlatformException e) => e.code, 'code', equals('error'))
expect(e.message, equals('Invalid argument(s): bad')); .having((PlatformException e) => e.message, 'message', equals('Invalid argument(s): bad')),
} catch (e) { ),
fail('PlatformException expected'); );
}
}); });
test('can check the mock handler', () async { test('can check the mock handler', () async {

View File

@ -686,16 +686,20 @@ void main() {
}; };
} }
try { expect(
await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage( () async {
SystemChannels.keyEvent.name, await TestDefaultBinaryMessengerBinding.instance!.defaultBinaryMessenger.handlePlatformMessage(
SystemChannels.keyEvent.codec.encodeMessage(keyEventMessage), SystemChannels.keyEvent.name,
(ByteData? data) { }, SystemChannels.keyEvent.codec.encodeMessage(keyEventMessage),
); (ByteData? data) { },
fail('Expected an exception, but did not get one.'); );
} on AssertionError catch (error) { },
expect(error.toString(), contains('Attempted to send a key down event when no keys are in keysPressed')); throwsA(isA<AssertionError>().having(
} (AssertionError error) => error.toString(),
'.toString()',
contains('Attempted to send a key down event when no keys are in keysPressed'),
)),
);
}); });
}); });

View File

@ -1303,24 +1303,27 @@ void main() {
}); });
testWidgets('minLines cannot be greater than maxLines', (WidgetTester tester) async { testWidgets('minLines cannot be greater than maxLines', (WidgetTester tester) async {
try { expect(
await tester.pumpWidget( () async {
overlay( await tester.pumpWidget(
child: SizedBox( overlay(
width: 300.0, child: SizedBox(
child: SelectableText( width: 300.0,
'abcd', child: SelectableText(
minLines: 4, 'abcd',
maxLines: 3, minLines: 4,
maxLines: 3,
),
), ),
), ),
), );
); },
} on AssertionError catch (e) { throwsA(isA<AssertionError>().having(
expect(e.toString(), contains("minLines can't be greater than maxLines")); (AssertionError error) => error.toString(),
return; '.toString()',
} contains("minLines can't be greater than maxLines"),
fail('An assert should be triggered when minLines is greater than maxLines'); )),
);
}); });
testWidgets('Selectable height with minLine', (WidgetTester tester) async { testWidgets('Selectable height with minLine', (WidgetTester tester) async {

View File

@ -81,31 +81,25 @@ void main() {
group('Setters', () { group('Setters', () {
testWithoutContext('setInputDirectory fails if the directory does not exist', () { testWithoutContext('setInputDirectory fails if the directory does not exist', () {
try { expect(
LocalizationsGenerator.inputDirectoryFromPath(fs, 'lib', fs.directory('bogus')); () => LocalizationsGenerator.inputDirectoryFromPath(fs, 'lib', fs.directory('bogus')),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('Make sure that the correct path was provided')); (L10nException e) => e.message,
return; 'message',
} contains('Make sure that the correct path was provided'),
)),
fail(
'LocalizationsGenerator.setInputDirectory should fail if the '
'directory does not exist.'
); );
}); });
testWithoutContext('setting className fails if input string is empty', () { testWithoutContext('setting className fails if input string is empty', () {
_standardFlutterDirectoryL10nSetup(fs); _standardFlutterDirectoryL10nSetup(fs);
try { expect(
LocalizationsGenerator.classNameFromString(''); () => LocalizationsGenerator.classNameFromString(''),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('cannot be empty')); (L10nException e) => e.message,
return; 'message',
} contains('cannot be empty'),
)),
fail(
'LocalizationsGenerator.className should fail if the '
'input string is null.'
); );
}); });
@ -179,8 +173,8 @@ void main() {
.writeAsStringSync(singleEsMessageArbFileString); .writeAsStringSync(singleEsMessageArbFileString);
// Project path should be intentionally a directory that does not exist. // Project path should be intentionally a directory that does not exist.
try { expect(
LocalizationsGenerator( () => LocalizationsGenerator(
fileSystem: fs, fileSystem: fs,
projectPathString: 'absolute/path/to/flutter_project', projectPathString: 'absolute/path/to/flutter_project',
inputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
@ -188,15 +182,12 @@ void main() {
templateArbFileName: defaultTemplateArbFileName, templateArbFileName: defaultTemplateArbFileName,
outputFileString: defaultOutputFileString, outputFileString: defaultOutputFileString,
classNameString: defaultClassNameString, classNameString: defaultClassNameString,
); ),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('Directory does not exist')); (L10nException e) => e.message,
return; 'message',
} contains('Directory does not exist'),
)),
fail(
'An exception should be thrown when the directory '
'specified in projectPathString does not exist.'
); );
}); });
@ -206,54 +197,46 @@ void main() {
}); });
testWithoutContext('fails on string with spaces', () { testWithoutContext('fails on string with spaces', () {
try { expect(
LocalizationsGenerator.classNameFromString('String with spaces'); () => LocalizationsGenerator.classNameFromString('String with spaces'),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('is not a valid public Dart class name')); (L10nException e) => e.message,
return; 'message',
} contains('is not a valid public Dart class name'),
fail( )),
'LocalizationsGenerator.className should fail if the '
'input string is not a valid Dart class name.'
); );
}); });
testWithoutContext('fails on non-alphanumeric symbols', () { testWithoutContext('fails on non-alphanumeric symbols', () {
try { expect(
LocalizationsGenerator.classNameFromString('TestClass@123'); () => LocalizationsGenerator.classNameFromString('TestClass@123'),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('is not a valid public Dart class name')); (L10nException e) => e.message,
return; 'message',
} contains('is not a valid public Dart class name'),
fail( )),
'LocalizationsGenerator.className should fail if the '
'input string is not a valid public Dart class name.'
); );
}); });
testWithoutContext('fails on camel-case', () { testWithoutContext('fails on camel-case', () {
try { expect(
LocalizationsGenerator.classNameFromString('camelCaseClassName'); () => LocalizationsGenerator.classNameFromString('camelCaseClassName'),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('is not a valid public Dart class name')); (L10nException e) => e.message,
return; 'message',
} contains('is not a valid public Dart class name'),
fail( )),
'LocalizationsGenerator.className should fail if the '
'input string is not a valid public Dart class name.'
); );
}); });
testWithoutContext('fails when starting with a number', () { testWithoutContext('fails when starting with a number', () {
try { expect(
LocalizationsGenerator.classNameFromString('123ClassName'); () => LocalizationsGenerator.classNameFromString('123ClassName'),
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('is not a valid public Dart class name')); (L10nException e) => e.message,
return; 'message',
} contains('is not a valid public Dart class name'),
fail( )),
'LocalizationsGenerator.className should fail if the '
'input string is not a valid public Dart class name.'
); );
}); });
}); });
@ -339,20 +322,22 @@ void main() {
.writeAsStringSync(singleMessageArbFileString); .writeAsStringSync(singleMessageArbFileString);
l10nDirectory.childFile('app_localizations_en_CA_foo.arb') l10nDirectory.childFile('app_localizations_en_CA_foo.arb')
.writeAsStringSync(singleMessageArbFileString); .writeAsStringSync(singleMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
fileSystem: fs,
inputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: 'app_localizations_en.arb', templateArbFileName: 'app_localizations_en.arb',
outputFileString: defaultOutputFileString, outputFileString: defaultOutputFileString,
classNameString: defaultClassNameString, classNameString: defaultClassNameString,
).loadResources(); ).loadResources();
} on L10nException catch (e) { },
expect(e.message, contains("The following .arb file's locale could not be determined")); throwsA(isA<L10nException>().having(
return; (L10nException e) => e.message,
} 'message',
contains("The following .arb file's locale could not be determined"),
fail('Using app_en_CA_foo.arb should fail as it is not a valid locale.'); )),
);
}); });
testWithoutContext('correctly creates an untranslated messages file (useSyntheticPackage = true)', () { testWithoutContext('correctly creates an untranslated messages file (useSyntheticPackage = true)', () {
@ -775,23 +760,25 @@ void main() {
..childFile(esArbFileName).writeAsStringSync(singleEsMessageArbFileString) ..childFile(esArbFileName).writeAsStringSync(singleEsMessageArbFileString)
..childFile('header.txt').writeAsStringSync('/// Sample header in a text file'); ..childFile('header.txt').writeAsStringSync('/// Sample header in a text file');
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
headerString: '/// Sample header for localizations file.', classNameString: defaultClassNameString,
headerFile: 'header.txt', headerString: '/// Sample header for localizations file.',
); headerFile: 'header.txt',
} on L10nException catch (e) { );
expect(e.message, contains('Cannot accept both header and header file arguments')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('Setting both headerFile and headerString should fail'); contains('Cannot accept both header and header file arguments'),
)),
);
}); });
testWithoutContext('setting a headerFile that does not exist should fail', () { testWithoutContext('setting a headerFile that does not exist should fail', () {
@ -804,22 +791,24 @@ void main() {
l10nDirectory.childFile('header.txt') l10nDirectory.childFile('header.txt')
.writeAsStringSync('/// Sample header in a text file'); .writeAsStringSync('/// Sample header in a text file');
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
headerFile: 'header.tx', // Intentionally spelled incorrectly classNameString: defaultClassNameString,
); headerFile: 'header.tx', // Intentionally spelled incorrectly
} on L10nException catch (e) { );
expect(e.message, contains('Failed to read header file')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('Setting headerFile that does not exist should fail'); contains('Failed to read header file'),
)),
);
}); });
group('generateLocalizations', () { group('generateLocalizations', () {
@ -1022,27 +1011,23 @@ flutter:
.writeAsStringSync(singleZhMessageArbFileString); .writeAsStringSync(singleZhMessageArbFileString);
const List<String> preferredSupportedLocale = <String>['am', 'es']; const List<String> preferredSupportedLocale = <String>['am', 'es'];
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
preferredSupportedLocales: preferredSupportedLocale, classNameString: defaultClassNameString,
).loadResources(); preferredSupportedLocales: preferredSupportedLocale,
} on L10nException catch (e) { ).loadResources();
expect( },
e.message, throwsA(isA<L10nException>().having(
(L10nException e) => e.message,
'message',
contains("The preferred supported locale, 'am', cannot be added."), contains("The preferred supported locale, 'am', cannot be added."),
); )),
return;
}
fail(
'Should fail since an unsupported locale was added '
'to the preferredSupportedLocales list.'
); );
}, },
); );
@ -1149,25 +1134,22 @@ flutter:
l10nDirectory.childFile('app_am.arb') l10nDirectory.childFile('app_am.arb')
.writeAsStringSync(arbFileWithZhLocale); .writeAsStringSync(arbFileWithZhLocale);
LocalizationsGenerator generator; expect(
try { () {
generator = LocalizationsGenerator( LocalizationsGenerator(
fileSystem: fs, fileSystem: fs,
inputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
outputPathString: defaultL10nPathString, outputPathString: defaultL10nPathString,
templateArbFileName: 'app_es.arb', templateArbFileName: 'app_es.arb',
outputFileString: defaultOutputFileString, outputFileString: defaultOutputFileString,
classNameString: defaultClassNameString, classNameString: defaultClassNameString,
); ).loadResources();
generator.loadResources(); },
} on L10nException catch (e) { throwsA(isA<L10nException>().having(
expect(e.message, contains('The locale specified in @@locale and the arb filename do not match.')); (L10nException e) => e.message,
return; 'message',
} contains('The locale specified in @@locale and the arb filename do not match.'),
)),
fail(
'An exception should occur if the @@locale and the filename extensions are '
'defined but not matching.'
); );
}); });
@ -1176,23 +1158,22 @@ flutter:
..createSync(recursive: true) ..createSync(recursive: true)
..childFile('app.arb') ..childFile('app.arb')
.writeAsStringSync(singleMessageArbFileString); .writeAsStringSync(singleMessageArbFileString);
try { expect(
final LocalizationsGenerator generator = LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: 'app.arb', outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: 'app.arb',
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
); classNameString: defaultClassNameString,
generator.loadResources(); ).loadResources();
} on L10nException catch (e) { },
expect(e.message, contains('locale could not be determined')); throwsA(isA<L10nException>().having(
return; (L10nException e) => e.message,
} 'message',
fail( contains('locale could not be determined'),
'Since locale is not specified, setting languages and locales ' )),
'should fail'
); );
}); });
testWithoutContext('throws when the same locale is detected more than once', () { testWithoutContext('throws when the same locale is detected more than once', () {
@ -1211,23 +1192,22 @@ flutter:
l10nDirectory.childFile('app2_en.arb') l10nDirectory.childFile('app2_en.arb')
.writeAsStringSync(secondMessageArbFileString); .writeAsStringSync(secondMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: 'app_en.arb', outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: 'app_en.arb',
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
).loadResources(); classNameString: defaultClassNameString,
} on L10nException catch (e) { ).loadResources();
expect(e.message, contains("Multiple arb files with the same 'en' locale detected")); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail( contains("Multiple arb files with the same 'en' locale detected"),
'Since en locale is specified twice, setting languages and locales ' )),
'should fail'
); );
}); });
@ -1237,23 +1217,22 @@ flutter:
l10nDirectory.childFile('app_en_US.arb') l10nDirectory.childFile('app_en_US.arb')
.writeAsStringSync(singleMessageArbFileString); .writeAsStringSync(singleMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: 'app_en_US.arb', outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: 'app_en_US.arb',
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
).loadResources(); classNameString: defaultClassNameString,
} on L10nException catch (e) { ).loadResources();
expect(e.message, contains('Arb file for a fallback, en, does not exist')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail( contains('Arb file for a fallback, en, does not exist'),
'Since en_US.arb is specified, but en.arb is not, ' )),
'the tool should throw an error.'
); );
}); });
}); });
@ -1544,24 +1523,28 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(singleDateMessageArbFileString); .writeAsStringSync(singleDateMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
templateArbFileName: defaultTemplateArbFileName, inputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('asdf')); },
expect(e.message, contains('springStartDate')); throwsA(isA<L10nException>().having(
expect(e.message, contains('does not have a corresponding DateFormat')); (L10nException e) => e.message,
return; 'message',
} allOf(
contains('asdf'),
fail('Improper date formatting should throw an exception'); contains('springStartDate'),
contains('does not have a corresponding DateFormat'),
),
)),
);
}); });
testWithoutContext('throws an exception when no format attribute is passed in', () { testWithoutContext('throws an exception when no format attribute is passed in', () {
@ -1582,23 +1565,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(singleDateMessageArbFileString); .writeAsStringSync(singleDateMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('the "format" attribute needs to be set')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('Improper date formatting should throw an exception'); contains('the "format" attribute needs to be set'),
)),
);
}); });
}); });
@ -1658,25 +1643,29 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(singleDateMessageArbFileString); .writeAsStringSync(singleDateMessageArbFileString);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('asdf')); },
expect(e.message, contains('progress')); throwsA(isA<L10nException>().having(
expect(e.message, contains('does not have a corresponding NumberFormat')); (L10nException e) => e.message,
return; 'message',
} allOf(
contains('asdf'),
fail('Improper date formatting should throw an exception'); contains('progress'),
contains('does not have a corresponding NumberFormat'),
),
)),
);
}); });
}); });
@ -1695,22 +1684,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(pluralMessageWithoutPlaceholdersAttribute); .writeAsStringSync(pluralMessageWithoutPlaceholdersAttribute);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Check to see if the plural message is in the proper ICU syntax format')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
fail('Generating class methods without placeholders should not succeed'); 'message',
contains('Check to see if the plural message is in the proper ICU syntax format'),
)),
);
}); });
testWithoutContext('should throw attempting to generate a plural message with an empty placeholders map', () { testWithoutContext('should throw attempting to generate a plural message with an empty placeholders map', () {
@ -1728,22 +1720,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(pluralMessageWithEmptyPlaceholdersMap); .writeAsStringSync(pluralMessageWithEmptyPlaceholdersMap);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Check to see if the plural message is in the proper ICU syntax format')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
fail('Generating class methods without placeholders should not succeed'); 'message',
contains('Check to see if the plural message is in the proper ICU syntax format'),
)),
);
}); });
testWithoutContext('should throw attempting to generate a plural message with no resource attributes', () { testWithoutContext('should throw attempting to generate a plural message with no resource attributes', () {
@ -1757,22 +1752,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(pluralMessageWithoutResourceAttributes); .writeAsStringSync(pluralMessageWithoutResourceAttributes);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Resource attribute "@helloWorlds" was not found')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
fail('Generating plural class method without resource attributes should not succeed'); 'message',
contains('Resource attribute "@helloWorlds" was not found'),
)),
);
}); });
testWithoutContext('should throw attempting to generate a plural message with incorrect format for placeholders', () { testWithoutContext('should throw attempting to generate a plural message with incorrect format for placeholders', () {
@ -1789,23 +1787,28 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(pluralMessageWithIncorrectPlaceholderFormat); .writeAsStringSync(pluralMessageWithIncorrectPlaceholderFormat);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('is not properly formatted')); },
expect(e.message, contains('Ensure that it is a map with string valued keys')); throwsA(isA<L10nException>().having(
return; (L10nException e) => e.message,
} 'message',
fail('Generating class methods with incorrect placeholder format should not succeed'); allOf(
contains('is not properly formatted'),
contains('Ensure that it is a map with string valued keys'),
),
)),
);
}); });
}); });
@ -2190,27 +2193,28 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(arbFileWithTrailingComma); .writeAsStringSync(arbFileWithTrailingComma);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('app_en.arb')); },
expect(e.message, contains('FormatException')); throwsA(isA<L10nException>().having(
expect(e.message, contains('Unexpected character')); (L10nException e) => e.message,
return; 'message',
} allOf(
contains('app_en.arb'),
fail( contains('FormatException'),
'should fail with an L10nException due to a trailing comma in the ' contains('Unexpected character'),
'arb file.' ),
)),
); );
}, },
); );
@ -2225,26 +2229,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(arbFileWithMissingResourceAttribute); .writeAsStringSync(arbFileWithMissingResourceAttribute);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
areResourceAttributesRequired: true, classNameString: defaultClassNameString,
) areResourceAttributesRequired: true,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Resource attribute "@title" was not found')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail( contains('Resource attribute "@title" was not found'),
'should fail with a FormatException due to a trailing comma in the ' )),
'arb file.'
); );
}); });
@ -2262,23 +2265,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(nonAlphaNumericArbFile); .writeAsStringSync(nonAlphaNumericArbFile);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Invalid ARB resource name')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('should fail due to non-alphanumeric character.'); contains('Invalid ARB resource name'),
)),
);
}); });
testWithoutContext('must start with lowercase character', () { testWithoutContext('must start with lowercase character', () {
@ -2294,23 +2299,25 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(nonAlphaNumericArbFile); .writeAsStringSync(nonAlphaNumericArbFile);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
outputPathString: defaultL10nPathString, inputPathString: defaultL10nPathString,
templateArbFileName: defaultTemplateArbFileName, outputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Invalid ARB resource name')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('should fail since key starts with a non-lowercase.'); contains('Invalid ARB resource name'),
)),
);
}); });
testWithoutContext('cannot start with a number', () { testWithoutContext('cannot start with a number', () {
@ -2326,22 +2333,24 @@ import 'output-localization-file_en.dart' deferred as output-localization-file_e
l10nDirectory.childFile(defaultTemplateArbFileName) l10nDirectory.childFile(defaultTemplateArbFileName)
.writeAsStringSync(nonAlphaNumericArbFile); .writeAsStringSync(nonAlphaNumericArbFile);
try { expect(
LocalizationsGenerator( () {
fileSystem: fs, LocalizationsGenerator(
inputPathString: defaultL10nPathString, fileSystem: fs,
templateArbFileName: defaultTemplateArbFileName, inputPathString: defaultL10nPathString,
outputFileString: defaultOutputFileString, templateArbFileName: defaultTemplateArbFileName,
classNameString: defaultClassNameString, outputFileString: defaultOutputFileString,
) classNameString: defaultClassNameString,
..loadResources() )
..writeOutputFiles(BufferLogger.test()); ..loadResources()
} on L10nException catch (e) { ..writeOutputFiles(BufferLogger.test());
expect(e.message, contains('Invalid ARB resource name')); },
return; throwsA(isA<L10nException>().having(
} (L10nException e) => e.message,
'message',
fail('should fail since key starts with a number.'); contains('Invalid ARB resource name'),
)),
);
}); });
}); });
}); });