如何模拟 SharedPreferences.getInstance()?

huangapple go评论125阅读模式
英文:

How to mock SharedPreferences.getInstance()?

问题

如何在Flutter测试中模拟SharedPreferences.getInstance()?
我在Google上搜索了一下,没有找到答案。
我还尝试了ChatGPT,并得到了以下答案:

import 'package:flutter_test/flutter_test.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:mocktail/mocktail.dart';

class MockSharedPreferences extends Mock implements SharedPreferences {}

void main() {
  group(
    'Login Tests',
    () {
      testWidgets('Login', (WidgetTester tester) async {
        final mockSharedPreferences = MockSharedPreferences();
        // Not working.
        when(() => MockSharedPreferences.getInstance()).thenAnswer((_) => Future.value(mockSharedPreferences));
      });    
    }
  );
}

必须完全执行的lib中的登录函数:(它在SharedPreferences.getInstance()行卡住了,这就是为什么我想要模拟它的原因)

void login() {
    if (
      username.isNotEmpty
      && password.isNotEmpty
    ) {
      dio.post(
        '${Config.url}/api/users/login/',
        data: {
          'username': username,
          'password': password
        }
      ).then(
        (Response<dynamic> response) async {
          if (response.statusCode == 200) {
            String token = response.data['key'];
            SharedPreferences sharedPreferences = await SharedPreferences.getInstance();
            sharedPreferences.setString('token', token);
            BlocProvider.of<AccountBloc>(context).add(LoginEvent(token));
            Future.delayed(
              Duration.zero, 
              () async {
                Navigator.of(context).popAndPushNamed('/');
              }
            );                  
          } else {
            throw 'Data: ${response.data}. Code: ${response.statusCode}. Message: ${response.statusMessage}';
          }
        }
      ).catchError(
        (dynamic error) {
          print('Login error: ${error}');
        }
      );
    }
  }
英文:

How to mock SharedPreferences.getInstance() in Flutter Test?
I have searched on Google and found no answers.
I also tried ChatGPT and came up with this:

import &#39;package:flutter_test/flutter_test.dart&#39;;
import &#39;package:shared_preferences/shared_preferences.dart&#39;;
import &#39;package:mocktail/mocktail.dart&#39;;

class MockSharedPreferences extends Mock implements SharedPreferences {}

void main() {
  group(
    &#39;Login Tests&#39;, 
    () {
      testWidgets(&#39;Login&#39;, (WidgetTester tester) async {
        final mockSharedPreferences = MockSharedPreferences();
        // Not working.
        when(() =&gt; MockSharedPreferences.getInstance()).thenAnswer((_) =&gt; Future.value(mockSharedPreferences));
      });    
    }
  );
}

The login function in the lib that has to be executed fully: (It gets stuck at the SharedPreferences.getInstance() line, that's why I want to mock it)

  void login() {
    if (
      username.isNotEmpty
      &amp;&amp; password.isNotEmpty
    ) {
      dio.post(
        &#39;${Config.url}/api/users/login/&#39;,
        data: {
          &#39;username&#39;: username,
          &#39;password&#39;: password
        }
      ).then(
        (Response&lt;dynamic&gt; response) async {
          if (response.statusCode == 200) {
            String token = response.data[&#39;key&#39;];
            SharedPreferences sharedPreferences = await SharedPreferences.getInstance();
            sharedPreferences.setString(&#39;token&#39;, token);
            BlocProvider.of&lt;AccountBloc&gt;(context).add(LoginEvent(token));
            Future.delayed(
              Duration.zero, 
              () async {
                Navigator.of(context).popAndPushNamed(&#39;/&#39;);
              }
            );                  
          } else {
            throw &#39;Data: ${response.data}. Code: ${response.statusCode}. Message: ${response.statusMessage}&#39;;
          }
        }
      ).catchError(
        (dynamic error) {
          print(&#39;Login error: ${error}&#39;);
        }
      );
    }
  }

答案1

得分: 1

在测试中正确使用SharedPreferences的方法是使用setMockInitialValues()方法,正如官方包文档所述:https://pub.dev/packages/shared_preferences。

此外,可以查看这个完整示例:https://blog.victoreronmosele.com/mocking-shared-preferences-flutter

示例代码:

test('Mock data in SharedPreferences', () async {

  SharedPreferences.setMockInitialValues({'test': 1});
  SharedPreferences sp = await SharedPreferences.getInstance();
  expect(sp.getInt('test'), 1);

});
英文:

The right way to use SharedPreferences in tests is to use the setMockInitialValues() method, as reported on the official package: https://pub.dev/packages/shared_preferences.

Also, look at this for a complete example: https://blog.victoreronmosele.com/mocking-shared-preferences-flutter

An example:

test(&#39;Mock data in SharedPreferences&#39;, () async {

  SharedPreferences.setMockInitialValues({&#39;test&#39;: 1});
  SharedPreferences sp = await SharedPreferences.getInstance();
  expect(sp.getInt(&#39;test&#39;), 1);

});

huangapple
  • 本文由 发表于 2023年8月11日 00:31:00
  • 转载请务必保留本文链接:https://go.coder-hub.com/76877676.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定