我正在编写一个jetpack compose android应用程序,我需要永久存储一些设置。
我决定使用androidx.datastore:datastore-preferences:1.0.0库,我已将其添加到我的类路径中。
根据https://developer.android.com/topic/libraries/architecture/datastore描述,我已将这行代码添加到顶层的 kotlin 文件中:
val Context.prefsDataStore:按preferencesDataStore(name =“settings”)的数据存储
但我得到一个编译错误:
e: ...SettingsViewModel.kt: (13, 50): Property delegate must have a 'getValue(Context, KProperty<*>)' method. None of the following functions is suitable:
public abstract operator fun getValue(thisRef: Context, property: KProperty<*>): DataStore<Preferences> defined in kotlin.properties.ReadOnlyProperty
Run Code Online (Sandbox Code Playgroud)
如何使用数据存储首选项?
我的 build.gradle 文件:
plugins {
id 'com.android.application'
id 'kotlin-android'
id 'kotlin-kapt'
}
apply plugin: 'dagger.hilt.android.plugin'
apply plugin: 'kotlinx-serialization'
android {
compileSdk 31
defaultConfig {
applicationId "hu.homedashboard.mobile"
minSdk 22
targetSdk 31
versionCode 1
versionName …Run Code Online (Sandbox Code Playgroud) android kotlin android-jetpack-compose android-jetpack-datastore
我想使用 DataStore 存储一些首选项。但问题是我的应用程序可以有多个用户,因此需要将这些首选项存储在单独的文件中。我得到了一个仅使用一个用户的工作示例,但我正在努力支持多个用户。
这是我的代码的示例:
class DataStorageRepository(private val context: Context, private val userRepository: UserRepository) {
private object PreferencesKeys {
val SETTING_ONE = intPreferencesKey("setting_one")
}
// retrieve datastore for currently logged in user.
private val Context.dataStore: DataStore<Preferences> by preferencesDataStore(name = userRepository.currentRegistration().name)
val userPreferencesFlow: Flow<UserPreferences> = context.dataStore.data.map { preferences ->
val settingOne = preferences[PreferencesKeys.SETTING_ONE] ?: 0
UserPreferences(settingOne)
}
suspend fun storeSettingOne(settingOne: Int) {
context.dataStore.edit { preferences ->
preferences[PreferencesKeys.SETTING_ONE] = settingOne
}
}
data class UserPreferences(val lastUsedToAccountTab: Int)
}
Run Code Online (Sandbox Code Playgroud)
我正在使用Koin并尝试卸载DataStorageRepository注销并在登录时重新创建它,但数据存储似乎一直保持活动状态,直到应用程序被终止并且出现以下崩溃: …
android koin android-jetpack coroutinescope android-jetpack-datastore
我正在尝试新的 jetpack DataStore库。我使用库保存了数据。这在应用程序数据目录 (/data/data/my.package.name/files/datastore/settings.preferences_pb) 中创建了一个文件settings.preferences_pb 。setting是我给的文件名。使用文本查看器无法正确显示数据。我可以辨认出键名,但值是垃圾。如何打开该文件并查看它?
我从 Android 开发者平台关注了这个 Codelab:https ://developer.android.com/codelabs/android-proto-datastore#4
添加了与 Codelab 中所示完全相同的依赖项,在尝试同步时出现以下 gradle 异常
A problem occurred configuring project ':app'.
Could not get unknown property 'source' for generate-proto-generateDebugProto of type org.gradle.api.internal.file.DefaultSourceDirectorySet.
at org.jetbrains.plugins.gradle.model.ProjectImportAction.execute(ProjectImportAction.java:125)
at org.jetbrains.plugins.gradle.model.ProjectImportAction.execute(ProjectImportAction.java:42)
Caused by: groovy.lang.MissingPropertyException: Could not get unknown property 'source' for generate-proto-generateDebugProto of type org.gradle.api.internal.file.DefaultSourceDirectorySet.
at com.google.protobuf.gradle.ProtobufPlugin$_linkGenerateProtoTasksToSourceCompile_closure25$_closure39.doCall(ProtobufPlugin.groovy:472)
at com.google.protobuf.gradle.ProtobufPlugin$_linkGenerateProtoTasksToSourceCompile_closure25.doCall(ProtobufPlugin.groovy:469)
at com.google.protobuf.gradle.ProtobufPlugin.linkGenerateProtoTasksToSourceCompile(ProtobufPlugin.groovy:468)
at com.google.protobuf.gradle.ProtobufPlugin$_doApply_closure5.doCall(ProtobufPlugin.groovy:153)
at jdk.proxy1/jdk.proxy1.$Proxy56.afterEvaluate(Unknown Source)
at org.jetbrains.plugins.gradle.model.ProjectImportAction.execute(ProjectImportAction.java:125)
at org.jetbrains.plugins.gradle.model.ProjectImportAction.execute(ProjectImportAction.java:42)
Run Code Online (Sandbox Code Playgroud)
我不知道问题是什么,尝试升级 Codelab 中显示的版本,到处查找问题,但似乎找不到任何经历过同样事情的人。任何想法?
android-gradle-plugin protobuf-java android-jetpack-compose android-jetpack-datastore
我只能找到通过Kotlin实现数据存储的方法。我尝试使用它来创建它
DataStore<Preferences> datastore = new Datastore<Preferences>,但一旦继续使用它,它就会覆盖方法,即 save 和 loadData,但传入它们的参数也在 Kotlin 中。我应该只继续使用 Sharedpreferences 吗?
我是否遗漏了某些内容,或者是否无法将侦听器附加到新的 Android Jetpack 首选项数据存储?我认为使用 Flow 的全部意义在于我们可以在首选项数据存储上调用 flow.toLiveData() 并观察值变化的变化。
以下是我从数据存储区获取流程的方法。
val taxRatePreferenceFlow: Flow<TaxRate> = dataStore.data
.catch { exception ->
if (exception is IOException){
emit(emptyPreferences())
} else {
throw exception
}
}.map { preferences ->
val name = preferences[PreferencesKeys.TAX_LABEL] ?: "Tax"
val rate = preferences[PreferencesKeys.TAX_RATE] ?: Constants.DEFAULT_TAX_RATE.toFloat()
val type = TaxType.valueOf(preferences[PreferencesKeys.TAX_TYPE] ?: TaxType.ON_ITEMS.name)
TaxRate(name, rate, type)
}
Run Code Online (Sandbox Code Playgroud)
我希望将 Flow 转换为 LiveData,就像在 ViewModel 中一样,并监听更改,直到观察者被删除。
totalAmountLiveData.addSource(taxRateFlow.asLiveData()){ taxtRate ->
taxtRate?.let {
updateTaxAmount(it)
}
}
Run Code Online (Sandbox Code Playgroud)
然而,该观察者仅发出保存的值,并且不会随着值的更新而更新。退出并重新进入屏幕将显示更新后的值。
这是我更新数据存储中每个值的方法
suspend fun updateTaxLabel(newTaxLabel: String){
dataStore.edit { preferences ->
preferences[PreferencesKeys.TAX_LABEL] …Run Code Online (Sandbox Code Playgroud) 我之前按照 Google 在文档中的建议,用新的 DataStore 替换了我的应用程序中的 SharedPreferences,以获得一些明显的好处。然后是添加设置屏幕的时候了,我找到了首选项库。当我看到库默认使用 SharedPreferences 而没有切换到 DataStore 的选项时,困惑就来了。您可以使用setPreferenceDataStore提供自定义存储实现,但 DataStore 没有实现 PreferenceDataStore 接口,由开发人员决定。是的,这个命名也非常令人困惑。当我发现没有关于将 DataStore 与 Preferences Library 一起使用的文章或问题时,我变得更加困惑,所以我觉得我错过了一些东西。人们是否同时使用这两种存储解决方案?还是其中之一?如果我要在 DataStore 中实现 PreferenceDataStore,有什么我应该注意的问题/陷阱吗?
android sharedpreferences preferencescreen android-jetpack-datastore
我遇到了一个情况,我可以通过 SharedPreferences 解决。但现在我正在迁移到 kotlin 和 DataStore。
我遇到了这个问题。
我有一个字符串值存储在共享首选项以及其他键值对中。此字符串是一个 URL,用于 Retrofit 调用的 baseUrl 参数中。
我的问题是,当我在 ViewModel 中运行时,检索 Fragment 值的正确方法是什么。
这是我的代码的一部分:
@Singleton
class PreferencesManager @Inject constructor(
@ApplicationContext context: Context,
anioDao: AnioDao
) {
val baseUrlFlow = dataStore.data
.catch { exception ->
if (exception is IOException) {
Log.e(TAG, "Error reading preferences: ", exception)
emit(emptyPreferences())
} else {
throw exception
}
}
.map {
it[PreferencesKeys.BASER_URL] ?: "http://192.168.2.109:1337"
}
}
Run Code Online (Sandbox Code Playgroud)
然后在 ViewModel 类中
class EnsayosViewModel @ViewModelInject constructor(
private val ensayoRepository: EnsayoRepository,
private val anioRepository: AnioRepository, …Run Code Online (Sandbox Code Playgroud) 因此,在新的 alpha07 版本中,Android 放弃了 . private val dataStore = context.createDataStore(name = "settings_pref"),但是他们使用数据存储的新方式对我不起作用。
由于从“androidx.datastore:datastore-core:1.0.0-alpha06”升级到 alpha07,我似乎无法在没有获得红色代码的情况下使我的数据存储语法正常工作(当我添加 context.dataStore.edit 时出现错误)。同样降级回 alpha06,以前工作的代码现在不再工作(使用 createDataStore)。
我使用的是他们在主页面上的示例,但在其他任何地方,除了这个示例之外,他们仍然没有更新他们的示例。
@Singleton
class PreferencesManager @Inject constructor(@ApplicationContext context: Context) {
val Context.dataStore: DataStore<Preferences> by preferencesDataStore(name = "settings")
val EXAMPLE_COUNTER = intPreferencesKey("example_counter")
val exampleCounterFlow: Flow<Int> = context.dataStore.data
.map { preferences ->
// No type safety.
preferences[EXAMPLE_COUNTER] ?: 0
}
suspend fun incrementCounter() {
context.dataStore.edit { settings ->
val currentCounterValue = settings[EXAMPLE_COUNTER] ?: 0
settings[EXAMPLE_COUNTER] = currentCounterValue + 1
}
}
} …Run Code Online (Sandbox Code Playgroud) 执行从 SharedPrefs 到 DataStore 的迁移非常简单并且有很好的文档记录。但是,当我想要从 DataStore 到静态 DataStore 进行简单的“版本碰撞”迁移时,这意味着某些键可能已更改等。应该如何执行此操作?
就我现在看来,我们需要在创建DataStore时在migrations参数中手动实现这些功能。
PreferenceDataStoreFactory.create(
migrations = listOf(
object : DataMigration<Preferences> {
override suspend fun cleanUp() {
TODO("Not yet implemented")
}
override suspend fun migrate(currentData: Preferences): Preferences {
TODO("Not yet implemented")
}
override suspend fun shouldMigrate(currentData: Preferences): Boolean {
TODO("Not yet implemented")
}
},
),
produceFile = {
get<Context>().preferencesDataStoreFile("filename")
}
)
Run Code Online (Sandbox Code Playgroud)
我还没有看到有人谈论它,或者不幸的是它是 Codelab 的一部分,这对我来说是一个很大的惊喜。有人可以指出我可以在哪里寻找一些有关如何正确执行此操作的灵感吗?
android sharedpreferences android-jetpack android-jetpack-datastore