如何在颤振中创建 SharedPreferences 的 Singleton 类

Posted

技术标签:

【中文标题】如何在颤振中创建 SharedPreferences 的 Singleton 类【英文标题】:How to create Singleton class of SharedPreferences in flutter 【发布时间】:2020-02-11 19:36:01 【问题描述】:

SharedPreferences 始终是必需的对象,但我们使用 await Like 访问。

await SharedPreferences.getInstance();

这就是为什么我想创建 SharedPreferences 的 Singleton 类并在 SharedPreferences 中为 GET 和 SET 数据创建静态方法。

但我不知道该怎么做,我尝试但无法成功 请帮帮我

【问题讨论】:

【参考方案1】:

对于处理单例​​类SharedPreference,请遵循 3 个步骤 -

1.把这个类放到你的项目中

    import 'dart:async' show Future;
    import 'package:shared_preferences/shared_preferences.dart';

    class PreferenceUtils 
      static Future<SharedPreferences> get _instance async => _prefsInstance ??= await SharedPreferences.getInstance();
      static SharedPreferences _prefsInstance;

      // call this method from iniState() function of mainApp().
      static Future<SharedPreferences> init() async 
        _prefsInstance = await _instance;
        return _prefsInstance;
      

      static String getString(String key, [String defValue]) 
        return _prefsInstance.getString(key) ?? defValue ?? "";
      

      static Future<bool> setString(String key, String value) async 
        var prefs = await _instance;
        return prefs?.setString(key, value) ?? Future.value(false);
      
    

2。从你的主类的 initState() 初始化这个类

PreferenceUtils.init();

3.访问您的方法,例如

PreferenceUtils.setString(AppConstants.USER_NAME, "");
String username = PreferenceUtils.getString(AppConstants.USER_NAME);

【讨论】:

很好的答案!我发现了一个问题:静态 SharedPreferences _prefs;应该删除并且 _instance 应该使用 _prefsInstance。而不是 _prefs 未处理的异常:NoSuchMethodError:方法 'getString' 在 null 上被调用。 E/flutter (11362): 接收者: null E/flutter (11362): 尝试调用: getString("token") _prefsInstance 为 null Null 安全引发未处理的异常:LateInitializationError:字段“_prefsInstance@1023372235”尚未初始化。由于静态后期 SharedPreferences _prefsInstance;有什么解决办法吗?【参考方案2】:

您可以使用以下非常简单的类来获取没有awaitSharedPreferences 实例:

import 'package:shared_preferences/shared_preferences.dart';

class SharedPrefs 
  static late final SharedPreferences instance;

  static Future<SharedPreferences> init() async =>
      instance = await SharedPreferences.getInstance();

    可能在main()函数中初始化instance,如下:
void main() async 
  // Required for async calls in `main`
  WidgetsFlutterBinding.ensureInitialized();

  // Initialize SharedPrefs instance.
  await SharedPrefs.init();

  runApp(MyApp());

    SharedPrefs.instance 上的访问方法,例如:
final someString = SharedPrefs.instance.getString('someString') ?? 'defaultValue';
await SharedPrefs.instance.setBool('someBool', true);

额外: 如果愿意,可以通过重新定义这些方法(getBoolsetString 等)或在SharedPrefs 类本身中定义新方法(getUsersetUsersetAccessToken 等)来进一步抽象并制作instance_instance 这样的私有字段。

一个这样的例子如下:

// Getter
static bool? getBool(String key) => _instance.getBool(key);

// Setter
static Future<bool> setBool(String key, bool value) => _instance.setBool(key, value);

// More abstraction
static const _kAccessToken = 'accessToken';

static Future<bool> setAccessToken(String value) => _instance.setString(_kAccessToken, value);

static String? getAccessToken() => _instance.getString(_kAccessToken);

之后,就可以简单的调用这些方法了,如下:

final someBool = SharedPrefs.getBool('someBool') ?? false;
await SharedPrefs.setBool('someBool', someBool);

final accessToken = SharedPrefs.getAccessToken();

【讨论】:

【参考方案3】:

这是我的首选项解决方案:

class Storage 
  static const String _some_field = 'some_field';

  static Future<SharedPreferences> get prefs => SharedPreferences.getInstance();

  static Future<String> getSomeStringData() async =>
      (await prefs).getString(_some_field) ?? '';

  static Future setSomeStringData(String phone) async =>
      (await prefs).setString(_some_field, phone);

  static Future clear() async 
    await getSomeStringData(null);
  

【讨论】:

【参考方案4】:

我将此代码用于单身偏好

static Future<SharedPreferences>  getInstance() async
  
    SharedPreferences preferences ;
    preferences = await SharedPreferences.getInstance();
    return preferences;
  

然后用它来恢复你的数据,这里我恢复userId。

 /// ----------------------------------------------------------
  /// Method that saves/restores the userId
  /// ----------------------------------------------------------
   static Future<String>  getUserId() async 
    return getInstance().then((pref) 
      return pref.get(Constants.userId);
    );
  

希望对你有帮助:)

【讨论】:

【参考方案5】:
class YourClass 
    static final YourClass _singleton = 
           new YourClass._internal();

    factory YourClass()
            return _singleton;
    

    YourClass._internal()
            //initialization your logic here
    

//主代码环境

YourClass mClass = new YourClass(); //把单例还给你

【讨论】:

问题是关于单例中的 SharedPreferences,而不是一般的单例类。

以上是关于如何在颤振中创建 SharedPreferences 的 Singleton 类的主要内容,如果未能解决你的问题,请参考以下文章

如何在android中使用SharedPreference存储动态表值[重复]

Android 如何从 SharedPreference 设置 EditTextPreference 的默认值?

StrictMode:创建 SharedPreference 时的 StrictModeDiskReadViolation

如何存储数组到sharedpreference中

如何在颤振中创建网页视图

如何在颤振中创建超链接图标?