Luis Lobo
Luis Lobo

Reputation: 261

How can I fix this issue and properly test the CustomWidget to ensure it displays the correct translation for both English and Spanish locales?

I have an English file, int_en.arb, which contains: {"yes": "Yes" }

And a Spanish file, int_es.arb, which contains: {"yes": "Sí" }

I also have the following CustomWidget:

class CustomWidget extends StatelessWidget {
  const CustomWidget({super.key});

  @override
  Widget build(BuildContext context) {
    return Column(children: [Text(Translate.of(context).yes)]);
  }
}

I want to write a unit test for this widget to ensure it displays the correct translation based on the locale. I tried the following code, but it didn't work:

class Translate {
  final Locale locale;

  Translate(this.locale);

  static Translate of(BuildContext context) {
    return Localizations.of<Translate>(context, Translate)!;
  }

  String get yes {
    switch (locale.languageCode) {
      case 'es':
        return 'sí';
      case 'en':
      default:
        return 'yes';
    }
  }
}

class _TestLocalizationsDelegate extends LocalizationsDelegate<Translate> {
  final Translate translate;

  _TestLocalizationsDelegate(this.translate);

  @override
  bool isSupported(Locale locale) => true;

  @override
  Future<Translate> load(Locale locale) => SynchronousFuture<Translate>(translate);

  @override
  bool shouldReload(_TestLocalizationsDelegate old) => false;
}

class MockBuildContext extends Mock implements BuildContext {}

void main() {
  testWidgets('CustomWidget displays correct translation for English', (WidgetTester tester) async {
    const locale = Locale('en');
    final translate = Translate(locale);

    await tester.pumpWidget(
      MaterialApp(
        locale: locale,
        supportedLocales: const [
          Locale('en', 'US'),
        ],
        localizationsDelegates: [
          _TestLocalizationsDelegate(translate),
        ],
        home: const CustomWidget(),
      ),
    );
    expect(find.text('yes'), findsOneWidget);
  });

  testWidgets('CustomWidget displays correct translation for Spanish', (WidgetTester tester) async {
    const locale = Locale('es');
    final translate = Translate(locale);

    await tester.pumpWidget(
      MaterialApp(
        locale: locale,
        supportedLocales: const [
          Locale('es', 'ES'),
        ],
        localizationsDelegates: [
          _TestLocalizationsDelegate(translate),
        ],
        home: const CustomWidget(),
      ),
    );

    expect(find.text('sí'), findsOneWidget);
  });
}

When running the test, I encounter the following error:

══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY ╞═══════════════════════════════════════════════════════════ The following _TypeError was thrown building CustomWidget(dirty, dependencies: [_LocalizationsScope-[GlobalKey#bb8d6]]): Null check operator used on a null value

The relevant error-causing widget was: CustomWidget CustomWidget:file:///Users/.../app/core/components/custom_widget_test.dart:59:21

When the exception was thrown, this was the stack: ... (elided 5 frames from dart:async and package:stack_trace)

════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY FLUTTER TEST FRAMEWORK ╞════════════════════════════════════════════════════ The following TestFailure was thrown running a test: Expected: exactly one matching candidate Actual: _TextWidgetFinder:<Found 0 widgets with text "yes": []> Which: means none were found but one was expected

When the exception was thrown, this was the stack: #4 main.<anonymous closure (file:///Users/...test/app/core/components/custom_widget_test.dart:62:5) #5 testWidgets.. (package:flutter_test/src/widget_tester.dart:189:15) #6 TestWidgetsFlutterBinding._runTestBody (package:flutter_test/src/binding.dart:1027:5) (elided one frame from package:stack_trace)

This was caught by the test expectation on the following line: file:///Users/.../test/app/core/components/custom_widget_test.dart line 62 The test description was: CustomWidget displays correct translation for English ════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY FLUTTER TEST FRAMEWORK ╞════════════════════════════════════════════════════ The following message was thrown: Multiple exceptions (2) were detected during the running of the current test, and at least one was unexpected. ════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY WIDGETS ╞═══════════════════════════════════════════════════════════════════ The following message was thrown: Warning: This application's locale, es_ES, is not supported by all of its localization delegates.

• A MaterialLocalizations delegate that supports the es_ES locale was not found. • A CupertinoLocalizations delegate that supports the es_ES locale was not found.

The declared supported locales for this app are: es_ES

See https://flutter.dev/to/internationalization/ for more information about configuring an app's locale, supportedLocales, and localizationsDelegates parameters. ════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY WIDGETS LIBRARY ╞═══════════════════════════════════════════════════════════ The following _TypeError was thrown building CustomWidget(dirty, dependencies: [_LocalizationsScope-[GlobalKey#20413]]): Null check operator used on a null value

The relevant error-causing widget was: CustomWidget CustomWidget:file:///Users/.../test/app/core/components/custom_widget_test.dart:78:21

When the exception was thrown, this was the stack: #0 Translate.of (package:consultoria_mobile/translate.dart:121:75) #1 CustomWidget.build(file:///Users/.../test/app/core/components/custom_widget.dart:9:45) ... (elided 5 frames from dart:async and package:stack_trace)

════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY FLUTTER TEST FRAMEWORK ╞════════════════════════════════════════════════════ The following TestFailure was thrown running a test: Expected: exactly one matching candidate Actual: _TextWidgetFinder:<Found 0 widgets with text "sí": []> Which: means none were found but one was expected

When the exception was thrown, this was the stack: #4 main. (file:///Users/.../test/app/core/components/custom_widget_test.dart:82:5) #5 testWidgets.. (package:flutter_test/src/widget_tester.dart:189:15) #6 TestWidgetsFlutterBinding._runTestBody (package:flutter_test/src/binding.dart:1027:5) (elided one frame from package:stack_trace)

This was caught by the test expectation on the following line: file:///Users/.../test/app/core/components/custom_widget_test.dart line 82 The test description was: CustomWidget displays correct translation for Spanish ════════════════════════════════════════════════════════════════════════════════════════════════════ ══╡ EXCEPTION CAUGHT BY FLUTTER TEST FRAMEWORK ╞════════════════════════════════════════════════════ The following message was thrown: Multiple exceptions (3) were detected during the running of the current test, and at least one was unexpected. ════════════════════════════════════════════════════════════════════════════════════════════════════

Additional Context

I already have executed flutter clean, flutter pub get, and flutter pub run build_runner build but it didn`t fix the issue,

Upvotes: 0

Views: 25

Answers (0)

Related Questions