1

我正在尝试 Widget 测试我的 WelcomeScreen()。WelcomeScreen 有一个 BlocProvider 和一个 BlocBuilder。在我加载 WelcomeBloc() 后,它会使用构建器中的 if 语句检查状态是否为 WelcomeLoadSuccessState。

如果语句为真,我如何在 if 语句下找到某些内容?

我的欢迎屏幕:

Widget build(BuildContext context) {
  return BlocProvider(
   create: (context) => WelcomeBloc(),
   child: BlocBuilder<WelcomeBloc, WelcomeState>(
     builder: (context, state) {
       if (state is WelcomeLoadSuccessState) {
         return Scaffold(
           body: Container(
            child: Column(
              children: [
                Wrap(
                  direction: Axis.vertical,
                  crossAxisAlignment: WrapCrossAlignment.center,
                  children: [
                    Padding(
                      padding: EdgeInsets.all(8),
                      child: ShowUp(
                          delay: _delay + 200,
                          child: Text('Welcome user’,        // <——— I want to find this one
                              )),
                    ),
                  
                  ],
                ),
              ],
            )),
      );
    }

    // return LoadingWidget();
    return Text('Something');       // <——— This one I can find
  },
),
);
}

我现在的测试:

    main() {
  WelcomeBloc welcomeBloc;
  WelcomeService welcomeService;
  final Brand brand = Brand();

  setUp(() {
    setUpMocks();
    welcomeService = localServices<WelcomeService>();
    welcomeBloc = MockWelcomeBloc();
  });

 _createWidget(WidgetTester tester) async {
    when(welcomeService.getBrand(id: '609a88d324a01928242d1ca9')).thenAnswer((realInvocation) => Future.value(brand));
    welcomeBloc.add(WelcomeLoadRequestEvent(id: '609a88d324a01928242d1ca9'));
    when(welcomeBloc.state).thenAnswer((_) => WelcomeLoadSuccessState(brand: brand));

    print(welcomeBloc.state); //Correct State (WelcomeLoadSuccessState)

    await tester.pumpWidget(
        MaterialApp(
          title: 'Flutter Demo',
          home: WelcomeScreen(),
        )
    );

    await tester.pump();
  }

  testWidgets('Welcome Screen Test', (WidgetTester tester) async {
    await _createWidget(tester);
    await tester.pump();

    //expect(find.textContaining('Welcome user'), findsOneWidget); //What I want
    expect(find.text('Something'), findsOneWidget);  //This works
  });

  tearDown(() {
    welcomeBloc?.close();
  });
}

谢谢你的帮忙。

4

1 回答 1

0

我解决了它:

改变:

create: (context) => WelcomeBloc()

到:

create: (context) => WelcomeBloc()..add(WelcomeLoadRequestEvent(id: '609a88d324a01928242d1ca9')),

我的测试现在是这样的:

main() {
  WelcomeBloc welcomeBloc;
  WelcomeService welcomeService;
  final Brand brand = Brand();

  setUp(() {
    setUpMocks();
    welcomeService = localServices<WelcomeService>();
    welcomeBloc = MockWelcomeBloc();
  });

  _createWidget(WidgetTester tester) async {
    await tester.pumpWidget(MaterialApp(
      title: 'Flutter Demo',
      home: WelcomeScreen(),
    ));

   await tester.pump(Duration(seconds: 10));
  }

  testWidgets('Welcome Screen Test', (WidgetTester tester) async {
    when(welcomeService.getBrand(id: '609a88d324a01928242d1ca9'))
        .thenAnswer((realInvocation) => Future.value(brand));
    whenListen(
        welcomeBloc,
        Stream.fromIterable([
      WelcomeLoadInProgressState(),
      WelcomeLoadSuccessState(brand: brand),
    ]));

    await _createWidget(tester);
    await tester.pump(Duration(seconds: 5));

    expect(find.textContaining('Welcome user'), findsOneWidget);
  });

 tearDown(() {
    welcomeBloc?.close();
    unRegister();
  });
}

编辑添加:

对于我的其他页面,将 blocProvider 和 blocBuilder 分开很有用。这样我就可以用 MockMyBloc() 模拟我的 blocProvider ,然后给孩子屏幕。

我真正的小部件:

MyWidgetMakeBlocProviders(
    Widget build(context) {
        return BlocProvider<MyBloc>(
            create: (context) => MyBloc(),
            child: MyScreen(),
        );
    }
)


MyScreen(
    Widget build(context) {
        return BlocBuilder<MyBloc, MyBlocState>(
            builder: (context, state) {...}
        );
    }
)

我的测试:

testWidgets('', (tester) async {
    whenListen(MockMyBloc, Stream.fromIterable([
        InitState(),
        LoadedState()
    ]));

    await _createWidget(tester);
    await tester.pump();
    
    //expect()
});

_createWidget(tester) async {
    await tester.pumpWidget(
        MaterialApp(
            title: '',
            home: BlocProvider<MockMyBloc>(
                create: (context) => MockMyBloc(),
                child: MyScreen(),
            )
        )
    );

    await tester.pump();
}
于 2021-05-19T12:12:56.983 回答