mirror of
https://github.com/oxen-io/session-android.git
synced 2024-11-29 04:55:15 +00:00
feat: adding a force new configs flag and logic for timestamp handling / forced configs, fix issue with handling legacy messages
This commit is contained in:
parent
371fb20b6e
commit
9c206bad64
@ -94,14 +94,8 @@ import network.loki.messenger.libsession_util.util.Contact as LibSessionContact
|
|||||||
open class Storage(context: Context, helper: SQLCipherOpenHelper, private val configFactory: ConfigFactory) : Database(context, helper), StorageProtocol,
|
open class Storage(context: Context, helper: SQLCipherOpenHelper, private val configFactory: ConfigFactory) : Database(context, helper), StorageProtocol,
|
||||||
ThreadDatabase.ConversationThreadUpdateListener {
|
ThreadDatabase.ConversationThreadUpdateListener {
|
||||||
|
|
||||||
// TODO: maybe add time here from formation / creation message
|
|
||||||
override fun threadCreated(address: Address, threadId: Long) {
|
override fun threadCreated(address: Address, threadId: Long) {
|
||||||
if (!getRecipientApproved(address)) return // don't store unapproved / message requests
|
if (!getRecipientApproved(address)) return // don't store unapproved / message requests
|
||||||
if (getUserPublicKey() == address.serialize()) {
|
|
||||||
Log.d("Loki-DBG", "NTS created, context:\n${Thread.currentThread().stackTrace.joinToString("\n")}")
|
|
||||||
} else {
|
|
||||||
Log.d("Loki-DBG", "Thread created ${address.serialize()}")
|
|
||||||
}
|
|
||||||
|
|
||||||
val volatile = configFactory.convoVolatile ?: return
|
val volatile = configFactory.convoVolatile ?: return
|
||||||
if (address.isGroup) {
|
if (address.isGroup) {
|
||||||
@ -491,7 +485,7 @@ open class Storage(context: Context, helper: SQLCipherOpenHelper, private val co
|
|||||||
private fun updateUserGroups(userGroups: UserGroupsConfig) {
|
private fun updateUserGroups(userGroups: UserGroupsConfig) {
|
||||||
val threadDb = DatabaseComponent.get(context).threadDatabase()
|
val threadDb = DatabaseComponent.get(context).threadDatabase()
|
||||||
val localUserPublicKey = getUserPublicKey() ?: return Log.w(
|
val localUserPublicKey = getUserPublicKey() ?: return Log.w(
|
||||||
"Loki-DBG",
|
"Loki",
|
||||||
"No user public key when trying to update user groups from config"
|
"No user public key when trying to update user groups from config"
|
||||||
)
|
)
|
||||||
val communities = userGroups.allCommunityInfo()
|
val communities = userGroups.allCommunityInfo()
|
||||||
|
@ -596,6 +596,8 @@ public class SQLCipherOpenHelper extends SQLiteOpenHelper {
|
|||||||
db.execSQL(ConfigDatabase.CREATE_CONFIG_TABLE_COMMAND);
|
db.execSQL(ConfigDatabase.CREATE_CONFIG_TABLE_COMMAND);
|
||||||
db.execSQL(ConfigurationMessageUtilities.DELETE_INACTIVE_GROUPS);
|
db.execSQL(ConfigurationMessageUtilities.DELETE_INACTIVE_GROUPS);
|
||||||
db.execSQL(ConfigurationMessageUtilities.DELETE_INACTIVE_ONE_TO_ONES);
|
db.execSQL(ConfigurationMessageUtilities.DELETE_INACTIVE_ONE_TO_ONES);
|
||||||
|
// TODO: remove this for release
|
||||||
|
TextSecurePreferences.setForceNewConfig(context);
|
||||||
}
|
}
|
||||||
|
|
||||||
db.setTransactionSuccessful();
|
db.setTransactionSuccessful();
|
||||||
|
@ -6,13 +6,14 @@ import network.loki.messenger.libsession_util.Contacts
|
|||||||
import network.loki.messenger.libsession_util.ConversationVolatileConfig
|
import network.loki.messenger.libsession_util.ConversationVolatileConfig
|
||||||
import network.loki.messenger.libsession_util.UserGroupsConfig
|
import network.loki.messenger.libsession_util.UserGroupsConfig
|
||||||
import network.loki.messenger.libsession_util.UserProfile
|
import network.loki.messenger.libsession_util.UserProfile
|
||||||
|
import org.session.libsession.snode.SnodeAPI
|
||||||
import org.session.libsession.utilities.ConfigFactoryProtocol
|
import org.session.libsession.utilities.ConfigFactoryProtocol
|
||||||
import org.session.libsession.utilities.ConfigFactoryUpdateListener
|
import org.session.libsession.utilities.ConfigFactoryUpdateListener
|
||||||
|
import org.session.libsession.utilities.TextSecurePreferences
|
||||||
import org.session.libsignal.protos.SignalServiceProtos.SharedConfigMessage
|
import org.session.libsignal.protos.SignalServiceProtos.SharedConfigMessage
|
||||||
import org.session.libsignal.utilities.Log
|
import org.session.libsignal.utilities.Log
|
||||||
import org.thoughtcrime.securesms.database.ConfigDatabase
|
import org.thoughtcrime.securesms.database.ConfigDatabase
|
||||||
import org.thoughtcrime.securesms.util.ConfigurationMessageUtilities
|
import org.thoughtcrime.securesms.util.ConfigurationMessageUtilities
|
||||||
import java.util.concurrent.Executors
|
|
||||||
|
|
||||||
class ConfigFactory(
|
class ConfigFactory(
|
||||||
private val context: Context,
|
private val context: Context,
|
||||||
@ -39,6 +40,8 @@ class ConfigFactory(
|
|||||||
private val userGroupsLock = Object()
|
private val userGroupsLock = Object()
|
||||||
private var _userGroups: UserGroupsConfig? = null
|
private var _userGroups: UserGroupsConfig? = null
|
||||||
|
|
||||||
|
private val isConfigForcedOn = TextSecurePreferences.hasForcedNewConfig(context)
|
||||||
|
|
||||||
private val listeners: MutableList<ConfigFactoryUpdateListener> = mutableListOf()
|
private val listeners: MutableList<ConfigFactoryUpdateListener> = mutableListOf()
|
||||||
fun registerListener(listener: ConfigFactoryUpdateListener) {
|
fun registerListener(listener: ConfigFactoryUpdateListener) {
|
||||||
listeners += listener
|
listeners += listener
|
||||||
@ -50,7 +53,7 @@ class ConfigFactory(
|
|||||||
|
|
||||||
override val user: UserProfile?
|
override val user: UserProfile?
|
||||||
get() = synchronized(userLock) {
|
get() = synchronized(userLock) {
|
||||||
if (!ConfigBase.isNewConfigEnabled) return null
|
if (!ConfigBase.isNewConfigEnabled(isConfigForcedOn, SnodeAPI.nowWithOffset)) return null
|
||||||
if (_userConfig == null) {
|
if (_userConfig == null) {
|
||||||
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
||||||
val userDump = configDatabase.retrieveConfigAndHashes(
|
val userDump = configDatabase.retrieveConfigAndHashes(
|
||||||
@ -70,7 +73,7 @@ class ConfigFactory(
|
|||||||
|
|
||||||
override val contacts: Contacts?
|
override val contacts: Contacts?
|
||||||
get() = synchronized(contactsLock) {
|
get() = synchronized(contactsLock) {
|
||||||
if (!ConfigBase.isNewConfigEnabled) return null
|
if (!ConfigBase.isNewConfigEnabled(isConfigForcedOn, SnodeAPI.nowWithOffset)) return null
|
||||||
if (_contacts == null) {
|
if (_contacts == null) {
|
||||||
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
||||||
val contactsDump = configDatabase.retrieveConfigAndHashes(
|
val contactsDump = configDatabase.retrieveConfigAndHashes(
|
||||||
@ -90,7 +93,7 @@ class ConfigFactory(
|
|||||||
|
|
||||||
override val convoVolatile: ConversationVolatileConfig?
|
override val convoVolatile: ConversationVolatileConfig?
|
||||||
get() = synchronized(convoVolatileLock) {
|
get() = synchronized(convoVolatileLock) {
|
||||||
if (!ConfigBase.isNewConfigEnabled) return null
|
if (!ConfigBase.isNewConfigEnabled(isConfigForcedOn, SnodeAPI.nowWithOffset)) return null
|
||||||
if (_convoVolatileConfig == null) {
|
if (_convoVolatileConfig == null) {
|
||||||
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
||||||
val convoDump = configDatabase.retrieveConfigAndHashes(
|
val convoDump = configDatabase.retrieveConfigAndHashes(
|
||||||
@ -111,7 +114,7 @@ class ConfigFactory(
|
|||||||
|
|
||||||
override val userGroups: UserGroupsConfig?
|
override val userGroups: UserGroupsConfig?
|
||||||
get() = synchronized(userGroupsLock) {
|
get() = synchronized(userGroupsLock) {
|
||||||
if (!ConfigBase.isNewConfigEnabled) return null
|
if (!ConfigBase.isNewConfigEnabled(isConfigForcedOn, SnodeAPI.nowWithOffset)) return null
|
||||||
if (_userGroups == null) {
|
if (_userGroups == null) {
|
||||||
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
val (secretKey, publicKey) = maybeGetUserInfo() ?: return@synchronized null
|
||||||
val userGroupsDump = configDatabase.retrieveConfigAndHashes(
|
val userGroupsDump = configDatabase.retrieveConfigAndHashes(
|
||||||
@ -174,7 +177,7 @@ class ConfigFactory(
|
|||||||
else -> throw UnsupportedOperationException("Can't support type of ${forConfigObject::class.simpleName} yet")
|
else -> throw UnsupportedOperationException("Can't support type of ${forConfigObject::class.simpleName} yet")
|
||||||
}
|
}
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
Log.e("Loki-DBG", e)
|
Log.e("Loki", "failed to persist ${forConfigObject.javaClass.simpleName}", e)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -354,7 +354,8 @@ class HomeActivity : PassphraseRequiredActionBarActivity(),
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun updateLegacyConfigView() {
|
private fun updateLegacyConfigView() {
|
||||||
binding.configOutdatedView.isVisible = ConfigBase.isNewConfigEnabled && textSecurePreferences.getHasLegacyConfig()
|
binding.configOutdatedView.isVisible = ConfigBase.isNewConfigEnabled(textSecurePreferences.hasForcedNewConfig(), SnodeAPI.nowWithOffset)
|
||||||
|
&& textSecurePreferences.getHasLegacyConfig()
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun onResume() {
|
override fun onResume() {
|
||||||
|
@ -18,6 +18,7 @@ import org.session.libsession.messaging.jobs.JobQueue
|
|||||||
import org.session.libsession.messaging.messages.Destination
|
import org.session.libsession.messaging.messages.Destination
|
||||||
import org.session.libsession.messaging.messages.control.ConfigurationMessage
|
import org.session.libsession.messaging.messages.control.ConfigurationMessage
|
||||||
import org.session.libsession.messaging.sending_receiving.MessageSender
|
import org.session.libsession.messaging.sending_receiving.MessageSender
|
||||||
|
import org.session.libsession.snode.SnodeAPI
|
||||||
import org.session.libsession.utilities.Address
|
import org.session.libsession.utilities.Address
|
||||||
import org.session.libsession.utilities.GroupUtil
|
import org.session.libsession.utilities.GroupUtil
|
||||||
import org.session.libsession.utilities.TextSecurePreferences
|
import org.session.libsession.utilities.TextSecurePreferences
|
||||||
@ -25,7 +26,6 @@ import org.session.libsession.utilities.WindowDebouncer
|
|||||||
import org.session.libsignal.utilities.Hex
|
import org.session.libsignal.utilities.Hex
|
||||||
import org.session.libsignal.utilities.toHexString
|
import org.session.libsignal.utilities.toHexString
|
||||||
import org.thoughtcrime.securesms.database.GroupDatabase
|
import org.thoughtcrime.securesms.database.GroupDatabase
|
||||||
import org.thoughtcrime.securesms.database.GroupMemberDatabase
|
|
||||||
import org.thoughtcrime.securesms.database.ThreadDatabase
|
import org.thoughtcrime.securesms.database.ThreadDatabase
|
||||||
import org.thoughtcrime.securesms.dependencies.DatabaseComponent
|
import org.thoughtcrime.securesms.dependencies.DatabaseComponent
|
||||||
import java.util.Timer
|
import java.util.Timer
|
||||||
@ -53,7 +53,9 @@ object ConfigurationMessageUtilities {
|
|||||||
fun syncConfigurationIfNeeded(context: Context) {
|
fun syncConfigurationIfNeeded(context: Context) {
|
||||||
// add if check here to schedule new config job process and return early
|
// add if check here to schedule new config job process and return early
|
||||||
val userPublicKey = TextSecurePreferences.getLocalNumber(context) ?: return
|
val userPublicKey = TextSecurePreferences.getLocalNumber(context) ?: return
|
||||||
if (ConfigBase.isNewConfigEnabled) {
|
val forcedConfig = TextSecurePreferences.hasForcedNewConfig(context)
|
||||||
|
val currentTime = SnodeAPI.nowWithOffset
|
||||||
|
if (ConfigBase.isNewConfigEnabled(forcedConfig, currentTime)) {
|
||||||
scheduleConfigSync(userPublicKey)
|
scheduleConfigSync(userPublicKey)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
@ -81,7 +83,9 @@ object ConfigurationMessageUtilities {
|
|||||||
fun forceSyncConfigurationNowIfNeeded(context: Context): Promise<Unit, Exception> {
|
fun forceSyncConfigurationNowIfNeeded(context: Context): Promise<Unit, Exception> {
|
||||||
// add if check here to schedule new config job process and return early
|
// add if check here to schedule new config job process and return early
|
||||||
val userPublicKey = TextSecurePreferences.getLocalNumber(context) ?: return Promise.ofFail(NullPointerException("User Public Key is null"))
|
val userPublicKey = TextSecurePreferences.getLocalNumber(context) ?: return Promise.ofFail(NullPointerException("User Public Key is null"))
|
||||||
if (ConfigBase.isNewConfigEnabled) {
|
val forcedConfig = TextSecurePreferences.hasForcedNewConfig(context)
|
||||||
|
val currentTime = SnodeAPI.nowWithOffset
|
||||||
|
if (ConfigBase.isNewConfigEnabled(forcedConfig, currentTime)) {
|
||||||
// schedule job if none exist
|
// schedule job if none exist
|
||||||
// don't schedule job if we already have one
|
// don't schedule job if we already have one
|
||||||
scheduleConfigSync(userPublicKey)
|
scheduleConfigSync(userPublicKey)
|
||||||
|
@ -25,7 +25,11 @@ sealed class ConfigBase(protected val /* yucky */ pointer: Long) {
|
|||||||
is UserGroupsConfig -> Kind.GROUPS
|
is UserGroupsConfig -> Kind.GROUPS
|
||||||
}
|
}
|
||||||
|
|
||||||
const val isNewConfigEnabled = true
|
// TODO: time in future to activate (hardcoded to 1st jan 2024 for testing, change before release)
|
||||||
|
private const val ACTIVATE_TIME = 1704027600
|
||||||
|
|
||||||
|
fun isNewConfigEnabled(forced: Boolean, currentTime: Long) =
|
||||||
|
forced || currentTime >= ACTIVATE_TIME
|
||||||
|
|
||||||
const val PRIORITY_HIDDEN = -1
|
const val PRIORITY_HIDDEN = -1
|
||||||
const val PRIORITY_VISIBLE = 0
|
const val PRIORITY_VISIBLE = 0
|
||||||
|
@ -2,14 +2,13 @@ package org.session.libsession.messaging.jobs
|
|||||||
|
|
||||||
import network.loki.messenger.libsession_util.ConfigBase
|
import network.loki.messenger.libsession_util.ConfigBase
|
||||||
import network.loki.messenger.libsession_util.ConfigBase.Companion.protoKindFor
|
import network.loki.messenger.libsession_util.ConfigBase.Companion.protoKindFor
|
||||||
import nl.komponents.kovenant.functional.bind
|
|
||||||
import org.session.libsession.messaging.MessagingModuleConfiguration
|
import org.session.libsession.messaging.MessagingModuleConfiguration
|
||||||
import org.session.libsession.messaging.messages.Destination
|
import org.session.libsession.messaging.messages.Destination
|
||||||
import org.session.libsession.messaging.messages.control.SharedConfigurationMessage
|
import org.session.libsession.messaging.messages.control.SharedConfigurationMessage
|
||||||
import org.session.libsession.messaging.sending_receiving.MessageSender
|
import org.session.libsession.messaging.sending_receiving.MessageSender
|
||||||
import org.session.libsession.messaging.utilities.Data
|
import org.session.libsession.messaging.utilities.Data
|
||||||
import org.session.libsession.snode.RawResponse
|
|
||||||
import org.session.libsession.snode.SnodeAPI
|
import org.session.libsession.snode.SnodeAPI
|
||||||
|
import org.session.libsession.utilities.TextSecurePreferences
|
||||||
import org.session.libsignal.utilities.Log
|
import org.session.libsignal.utilities.Log
|
||||||
import java.util.concurrent.atomic.AtomicBoolean
|
import java.util.concurrent.atomic.AtomicBoolean
|
||||||
|
|
||||||
@ -25,12 +24,14 @@ data class ConfigurationSyncJob(val destination: Destination): Job {
|
|||||||
|
|
||||||
override suspend fun execute(dispatcherName: String) {
|
override suspend fun execute(dispatcherName: String) {
|
||||||
val storage = MessagingModuleConfiguration.shared.storage
|
val storage = MessagingModuleConfiguration.shared.storage
|
||||||
|
val forcedConfig = TextSecurePreferences.hasForcedNewConfig(MessagingModuleConfiguration.shared.context)
|
||||||
|
val currentTime = SnodeAPI.nowWithOffset
|
||||||
val userEdKeyPair = MessagingModuleConfiguration.shared.getUserED25519KeyPair()
|
val userEdKeyPair = MessagingModuleConfiguration.shared.getUserED25519KeyPair()
|
||||||
val userPublicKey = storage.getUserPublicKey()
|
val userPublicKey = storage.getUserPublicKey()
|
||||||
val delegate = delegate
|
val delegate = delegate
|
||||||
if (destination is Destination.ClosedGroup // TODO: closed group configs will be handled in closed group feature
|
if (destination is Destination.ClosedGroup // TODO: closed group configs will be handled in closed group feature
|
||||||
// if we haven't enabled the new configs don't run
|
// if we haven't enabled the new configs don't run
|
||||||
|| !ConfigBase.isNewConfigEnabled
|
|| !ConfigBase.isNewConfigEnabled(forcedConfig, currentTime)
|
||||||
// if we don't have a user ed key pair for signing updates
|
// if we don't have a user ed key pair for signing updates
|
||||||
|| userEdKeyPair == null
|
|| userEdKeyPair == null
|
||||||
// this will be useful to not handle null delegate cases
|
// this will be useful to not handle null delegate cases
|
||||||
|
@ -149,8 +149,11 @@ private fun handleConfigurationMessage(message: ConfigurationMessage) {
|
|||||||
|
|
||||||
TextSecurePreferences.setConfigurationMessageSynced(context, true)
|
TextSecurePreferences.setConfigurationMessageSynced(context, true)
|
||||||
TextSecurePreferences.setLastProfileUpdateTime(context, message.sentTimestamp!!)
|
TextSecurePreferences.setLastProfileUpdateTime(context, message.sentTimestamp!!)
|
||||||
if (ConfigBase.isNewConfigEnabled) {
|
val isForceSync = TextSecurePreferences.hasForcedNewConfig(context)
|
||||||
|
val currentTime = SnodeAPI.nowWithOffset
|
||||||
|
if (ConfigBase.isNewConfigEnabled(isForceSync, currentTime)) {
|
||||||
TextSecurePreferences.setHasLegacyConfig(context, true)
|
TextSecurePreferences.setHasLegacyConfig(context, true)
|
||||||
|
if (!firstTimeSync) return
|
||||||
}
|
}
|
||||||
val allClosedGroupPublicKeys = storage.getAllClosedGroupPublicKeys()
|
val allClosedGroupPublicKeys = storage.getAllClosedGroupPublicKeys()
|
||||||
for (closedGroup in message.closedGroups) {
|
for (closedGroup in message.closedGroups) {
|
||||||
|
@ -151,7 +151,7 @@ class Poller(private val configFactory: ConfigFactoryProtocol, debounceTimer: Ti
|
|||||||
val (message, _) = MessageReceiver.parse(data = envelope.toByteArray(), openGroupServerID = null)
|
val (message, _) = MessageReceiver.parse(data = envelope.toByteArray(), openGroupServerID = null)
|
||||||
// sanity checks
|
// sanity checks
|
||||||
if (message !is SharedConfigurationMessage) {
|
if (message !is SharedConfigurationMessage) {
|
||||||
Log.w("Loki-DBG", "shared config message handled in configs wasn't SharedConfigurationMessage but was ${message.javaClass.simpleName}")
|
Log.w("Loki", "shared config message handled in configs wasn't SharedConfigurationMessage but was ${message.javaClass.simpleName}")
|
||||||
return@forEach
|
return@forEach
|
||||||
}
|
}
|
||||||
forConfigObject.merge(hash!! to message.data)
|
forConfigObject.merge(hash!! to message.data)
|
||||||
@ -213,11 +213,11 @@ class Poller(private val configFactory: ConfigFactoryProtocol, debounceTimer: Ti
|
|||||||
if (personalResponseIndex >= 0) {
|
if (personalResponseIndex >= 0) {
|
||||||
responseList.getOrNull(personalResponseIndex)?.let { rawResponse ->
|
responseList.getOrNull(personalResponseIndex)?.let { rawResponse ->
|
||||||
if (rawResponse["code"] as? Int != 200) {
|
if (rawResponse["code"] as? Int != 200) {
|
||||||
Log.e("Loki-DBG", "Batch sub-request for personal messages had non-200 response code, returned code ${(rawResponse["code"] as? Int) ?: "[unknown]"}")
|
Log.e("Loki", "Batch sub-request for personal messages had non-200 response code, returned code ${(rawResponse["code"] as? Int) ?: "[unknown]"}")
|
||||||
} else {
|
} else {
|
||||||
val body = rawResponse["body"] as? RawResponse
|
val body = rawResponse["body"] as? RawResponse
|
||||||
if (body == null) {
|
if (body == null) {
|
||||||
Log.e("Loki-DBG", "Batch sub-request for personal messages didn't contain a body")
|
Log.e("Loki", "Batch sub-request for personal messages didn't contain a body")
|
||||||
} else {
|
} else {
|
||||||
processPersonalMessages(snode, body)
|
processPersonalMessages(snode, body)
|
||||||
}
|
}
|
||||||
@ -230,12 +230,12 @@ class Poller(private val configFactory: ConfigFactoryProtocol, debounceTimer: Ti
|
|||||||
requestSparseArray.keyIterator().withIndex().forEach { (requestIndex, key) ->
|
requestSparseArray.keyIterator().withIndex().forEach { (requestIndex, key) ->
|
||||||
responseList.getOrNull(requestIndex)?.let { rawResponse ->
|
responseList.getOrNull(requestIndex)?.let { rawResponse ->
|
||||||
if (rawResponse["code"] as? Int != 200) {
|
if (rawResponse["code"] as? Int != 200) {
|
||||||
Log.e("Loki-DBG", "Batch sub-request had non-200 response code, returned code ${(rawResponse["code"] as? Int) ?: "[unknown]"}")
|
Log.e("Loki", "Batch sub-request had non-200 response code, returned code ${(rawResponse["code"] as? Int) ?: "[unknown]"}")
|
||||||
return@forEach
|
return@forEach
|
||||||
}
|
}
|
||||||
val body = rawResponse["body"] as? RawResponse
|
val body = rawResponse["body"] as? RawResponse
|
||||||
if (body == null) {
|
if (body == null) {
|
||||||
Log.e("Loki-DBG", "Batch sub-request didn't contain a body")
|
Log.e("Loki", "Batch sub-request didn't contain a body")
|
||||||
return@forEach
|
return@forEach
|
||||||
}
|
}
|
||||||
if (key == Namespace.DEFAULT) {
|
if (key == Namespace.DEFAULT) {
|
||||||
|
@ -180,6 +180,8 @@ interface TextSecurePreferences {
|
|||||||
fun setThemeStyle(themeStyle: String)
|
fun setThemeStyle(themeStyle: String)
|
||||||
fun setFollowSystemSettings(followSystemSettings: Boolean)
|
fun setFollowSystemSettings(followSystemSettings: Boolean)
|
||||||
fun autoplayAudioMessages(): Boolean
|
fun autoplayAudioMessages(): Boolean
|
||||||
|
fun setForceNewConfig()
|
||||||
|
fun hasForcedNewConfig(): Boolean
|
||||||
fun hasPreference(key: String): Boolean
|
fun hasPreference(key: String): Boolean
|
||||||
fun clearAll()
|
fun clearAll()
|
||||||
|
|
||||||
@ -268,6 +270,7 @@ interface TextSecurePreferences {
|
|||||||
const val SELECTED_ACCENT_COLOR = "selected_accent_color"
|
const val SELECTED_ACCENT_COLOR = "selected_accent_color"
|
||||||
|
|
||||||
const val HAS_RECEIVED_LEGACY_CONFIG = "has_received_legacy_config"
|
const val HAS_RECEIVED_LEGACY_CONFIG = "has_received_legacy_config"
|
||||||
|
const val HAS_FORCED_NEW_CONFIG = "has_forced_new_config"
|
||||||
|
|
||||||
const val GREEN_ACCENT = "accent_green"
|
const val GREEN_ACCENT = "accent_green"
|
||||||
const val BLUE_ACCENT = "accent_blue"
|
const val BLUE_ACCENT = "accent_blue"
|
||||||
@ -811,6 +814,16 @@ interface TextSecurePreferences {
|
|||||||
setIntegerPreference(context, NOTIFICATION_MESSAGES_CHANNEL_VERSION, version)
|
setIntegerPreference(context, NOTIFICATION_MESSAGES_CHANNEL_VERSION, version)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun setForceNewConfig(context: Context) {
|
||||||
|
setBooleanPreference(context, HAS_FORCED_NEW_CONFIG, true)
|
||||||
|
}
|
||||||
|
|
||||||
|
@JvmStatic
|
||||||
|
fun hasForcedNewConfig(context: Context): Boolean {
|
||||||
|
return getBooleanPreference(context, HAS_FORCED_NEW_CONFIG, false)
|
||||||
|
}
|
||||||
|
|
||||||
@JvmStatic
|
@JvmStatic
|
||||||
fun getBooleanPreference(context: Context, key: String?, defaultValue: Boolean): Boolean {
|
fun getBooleanPreference(context: Context, key: String?, defaultValue: Boolean): Boolean {
|
||||||
return getDefaultSharedPreferences(context).getBoolean(key, defaultValue)
|
return getDefaultSharedPreferences(context).getBoolean(key, defaultValue)
|
||||||
@ -1447,6 +1460,13 @@ class AppTextSecurePreferences @Inject constructor(
|
|||||||
setIntegerPreference(TextSecurePreferences.NOTIFICATION_MESSAGES_CHANNEL_VERSION, version)
|
setIntegerPreference(TextSecurePreferences.NOTIFICATION_MESSAGES_CHANNEL_VERSION, version)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun setForceNewConfig() {
|
||||||
|
setBooleanPreference(TextSecurePreferences.HAS_FORCED_NEW_CONFIG, true)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun hasForcedNewConfig(): Boolean =
|
||||||
|
getBooleanPreference(TextSecurePreferences.HAS_FORCED_NEW_CONFIG, false)
|
||||||
|
|
||||||
override fun getBooleanPreference(key: String?, defaultValue: Boolean): Boolean {
|
override fun getBooleanPreference(key: String?, defaultValue: Boolean): Boolean {
|
||||||
return getDefaultSharedPreferences(context).getBoolean(key, defaultValue)
|
return getDefaultSharedPreferences(context).getBoolean(key, defaultValue)
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user