Page MenuHomePhabricator

D11045.id37007.diff
No OneTemporary

D11045.id37007.diff

diff --git a/native/cpp/CommonCpp/DatabaseManagers/DatabaseManager.cpp b/native/cpp/CommonCpp/DatabaseManagers/DatabaseManager.cpp
--- a/native/cpp/CommonCpp/DatabaseManagers/DatabaseManager.cpp
+++ b/native/cpp/CommonCpp/DatabaseManagers/DatabaseManager.cpp
@@ -1,5 +1,8 @@
#include "DatabaseManager.h"
#include "../Notifications/BackgroundDataStorage/NotificationsCryptoModule.h"
+#ifdef __APPLE__
+#include "../Tools/CommMMKV.h"
+#endif
#include "../Tools/CommSecureStore.h"
#include "Logger.h"
#include "PlatformSpecificTools.h"
@@ -36,6 +39,9 @@
CommSecureStore::set(CommSecureStore::commServicesAccessToken, "");
SQLiteQueryExecutor::clearSensitiveData();
PlatformSpecificTools::removeBackupDirectory();
+#ifdef __APPLE__
+ CommMMKV::clearSensitiveData();
+#endif
NotificationsCryptoModule::clearSensitiveData();
DatabaseManager::setDatabaseStatusAsWorkable();
}
diff --git a/native/cpp/CommonCpp/Tools/CommMMKV.h b/native/cpp/CommonCpp/Tools/CommMMKV.h
new file mode 100644
--- /dev/null
+++ b/native/cpp/CommonCpp/Tools/CommMMKV.h
@@ -0,0 +1,15 @@
+#pragma once
+
+#include <optional>
+#include <string>
+
+namespace comm {
+class CommMMKV {
+
+public:
+ static void initialize();
+ static void clearSensitiveData();
+ static bool setString(std::string key, std::string value);
+ static std::optional<std::string> getString(std::string key);
+};
+} // namespace comm
diff --git a/native/ios/Comm.xcodeproj/project.pbxproj b/native/ios/Comm.xcodeproj/project.pbxproj
--- a/native/ios/Comm.xcodeproj/project.pbxproj
+++ b/native/ios/Comm.xcodeproj/project.pbxproj
@@ -84,6 +84,8 @@
CB90951F29534B32002F2A7F /* CommSecureStore.mm in Sources */ = {isa = PBXBuildFile; fileRef = 71D4D7CB26C50B1000FCDBCD /* CommSecureStore.mm */; };
CBA5F8852B6979F7005BE700 /* SQLiteConnectionManager.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CBA5F8842B6979ED005BE700 /* SQLiteConnectionManager.cpp */; };
CBAAA4702B459181007599DA /* BackupOperationsExecutor.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CBAAA46E2B459181007599DA /* BackupOperationsExecutor.cpp */; };
+ CBB0DF602B768007008E22FF /* CommMMKV.mm in Sources */ = {isa = PBXBuildFile; fileRef = CBB0DF5F2B768007008E22FF /* CommMMKV.mm */; };
+ CBB0DF612B768007008E22FF /* CommMMKV.mm in Sources */ = {isa = PBXBuildFile; fileRef = CBB0DF5F2B768007008E22FF /* CommMMKV.mm */; };
CBCA09062A8E0E7400F75B3E /* StaffUtils.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CBCA09052A8E0E6B00F75B3E /* StaffUtils.cpp */; };
CBCA09072A8E0E7D00F75B3E /* StaffUtils.cpp in Sources */ = {isa = PBXBuildFile; fileRef = CBCA09052A8E0E6B00F75B3E /* StaffUtils.cpp */; };
CBDEC69B28ED867000C17588 /* GlobalDBSingleton.mm in Sources */ = {isa = PBXBuildFile; fileRef = CBDEC69A28ED867000C17588 /* GlobalDBSingleton.mm */; };
@@ -291,6 +293,8 @@
CBA784382B28AC4300E9F419 /* CommServicesAuthMetadataEmitter.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CommServicesAuthMetadataEmitter.h; sourceTree = "<group>"; };
CBAAA46E2B459181007599DA /* BackupOperationsExecutor.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = BackupOperationsExecutor.cpp; path = PersistentStorageUtilities/BackupOperationsUtilities/BackupOperationsExecutor.cpp; sourceTree = "<group>"; };
CBAAA46F2B459181007599DA /* BackupOperationsExecutor.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = BackupOperationsExecutor.h; path = PersistentStorageUtilities/BackupOperationsUtilities/BackupOperationsExecutor.h; sourceTree = "<group>"; };
+ CBB0DF5E2B767FDF008E22FF /* CommMMKV.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = CommMMKV.h; sourceTree = "<group>"; };
+ CBB0DF5F2B768007008E22FF /* CommMMKV.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = CommMMKV.mm; path = Comm/CommMMKV.mm; sourceTree = "<group>"; };
CBCA09042A8E0E6B00F75B3E /* StaffUtils.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = StaffUtils.h; sourceTree = "<group>"; };
CBCA09052A8E0E6B00F75B3E /* StaffUtils.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = StaffUtils.cpp; sourceTree = "<group>"; };
CBCF57AB2B05096F00EC4BC0 /* AESCryptoModuleObjCCompat.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = AESCryptoModuleObjCCompat.h; path = Comm/CommAESCryptoUtils/AESCryptoModuleObjCCompat.h; sourceTree = "<group>"; };
@@ -392,6 +396,7 @@
71B8CCB626BD30EC0040C0A2 /* CommCoreImplementations */ = {
isa = PBXGroup;
children = (
+ CBB0DF5F2B768007008E22FF /* CommMMKV.mm */,
CB74AB1B2B2AFF6E00CBB494 /* CommServicesAuthMetadataEmitter.mm */,
DFD5E77D2B05264000C32B6A /* AESCrypto.mm */,
CBCF57A92B05091D00EC4BC0 /* CommAESCryptoUtils */,
@@ -436,6 +441,7 @@
71BE84382636A944002849D2 /* Tools */ = {
isa = PBXGroup;
children = (
+ CBB0DF5E2B767FDF008E22FF /* CommMMKV.h */,
DFD5E7802B05264F00C32B6A /* AESCrypto.h */,
CBCA09052A8E0E6B00F75B3E /* StaffUtils.cpp */,
CBCA09042A8E0E6B00F75B3E /* StaffUtils.h */,
@@ -1134,6 +1140,7 @@
718DE99E2653D41C00365824 /* WorkerThread.cpp in Sources */,
8B99BAAE28D511FF00EB5ADB /* lib.rs.cc in Sources */,
71CA4AEC262F236100835C89 /* Tools.mm in Sources */,
+ CBB0DF602B768007008E22FF /* CommMMKV.mm in Sources */,
71762A75270D8AAE00F565ED /* PlatformSpecificTools.mm in Sources */,
71BF5B7126B3FF0900EDE27D /* Session.cpp in Sources */,
8EF7756E2A7513F40046A385 /* MessageStore.cpp in Sources */,
@@ -1185,6 +1192,7 @@
CB1648AF27CFBE6A00394D9D /* CryptoModule.cpp in Sources */,
CB4821AE27CFB187001AB7E1 /* Tools.cpp in Sources */,
CB4821AC27CFB17C001AB7E1 /* Session.cpp in Sources */,
+ CBB0DF612B768007008E22FF /* CommMMKV.mm in Sources */,
CB4821A927CFB153001AB7E1 /* WorkerThread.cpp in Sources */,
CB4821AA27CFB153001AB7E1 /* Tools.mm in Sources */,
CB3C621227CE65030054F24C /* CommSecureStoreIOSWrapper.mm in Sources */,
diff --git a/native/ios/Comm/AppDelegate.mm b/native/ios/Comm/AppDelegate.mm
--- a/native/ios/Comm/AppDelegate.mm
+++ b/native/ios/Comm/AppDelegate.mm
@@ -40,6 +40,7 @@
#import "CommConstants.h"
#import "CommCoreModule.h"
+#import "CommMMKV.h"
#import "CommRustModule.h"
#import "CommUtilsModule.h"
#import "GlobalDBSingleton.h"
@@ -88,6 +89,7 @@
willFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
[self attemptDatabaseInitialization];
[self registerForNewMessageInfosNotifications];
+ comm::CommMMKV::initialize();
return YES;
}
diff --git a/native/ios/Comm/CommMMKV.mm b/native/ios/Comm/CommMMKV.mm
new file mode 100644
--- /dev/null
+++ b/native/ios/Comm/CommMMKV.mm
@@ -0,0 +1,109 @@
+#import "CommMMKV.h"
+#import "../../cpp/CommonCpp/CryptoTools/Tools.h"
+#import "CommSecureStore.h"
+#import "Logger.h"
+#import "Tools.h"
+
+#import <Foundation/Foundation.h>
+#import <MMKV.h>
+
+namespace comm {
+
+const int commMMKVEncryptionKeySize = 16;
+const std::string secureStoreMMKVEncryptionKeyID = "comm.MMKVEncryptionKey";
+const NSString *commMMKVId = @"comm.MMKV";
+
+static NSString *mmkvEncryptionKey;
+
+MMKV *getMMKVInstance(NSString *mmkvID, NSString *encryptionKey) {
+ MMKV *mmkv =
+ [MMKV mmkvWithID:mmkvID
+ cryptKey:[encryptionKey dataUsingEncoding:NSUTF8StringEncoding]
+ mode:MMKVMultiProcess];
+ if (!mmkv) {
+ throw std::runtime_error("Failed to instantiate MMKV object.");
+ }
+ return mmkv;
+}
+
+void assignEncryptionKey() {
+ std::string encryptionKey =
+ crypto::Tools::generateRandomString(commMMKVEncryptionKeySize);
+ CommSecureStore::set(secureStoreMMKVEncryptionKeyID, encryptionKey);
+ mmkvEncryptionKey = [NSString stringWithCString:encryptionKey.c_str()
+ encoding:NSUTF8StringEncoding];
+}
+
+void CommMMKV::initialize() {
+ static dispatch_once_t onceToken;
+ dispatch_once(&onceToken, ^{
+ auto maybeEncryptionKey =
+ CommSecureStore::get(secureStoreMMKVEncryptionKeyID);
+
+ bool isRunningInAppExtension =
+ [[[NSBundle mainBundle] bundlePath] hasSuffix:@".appex"];
+
+ if (maybeEncryptionKey.hasValue()) {
+ mmkvEncryptionKey =
+ [NSString stringWithCString:maybeEncryptionKey.value().c_str()
+ encoding:NSUTF8StringEncoding];
+ } else if (!isRunningInAppExtension) {
+ assignEncryptionKey();
+ } else {
+ throw std::runtime_error("NSE can't initialize MMKV encryption key.");
+ }
+
+ [MMKV initializeMMKV:nil
+ groupDir:[Tools getAppGroupDirectoryPath]
+ logLevel:MMKVLogNone];
+ getMMKVInstance(commMMKVId.copy, mmkvEncryptionKey);
+ });
+}
+
+void CommMMKV::clearSensitiveData() {
+ CommMMKV::initialize();
+
+ @synchronized(mmkvEncryptionKey) {
+ BOOL storageRemoved = [MMKV removeStorage:commMMKVId.copy
+ mode:MMKVMultiProcess];
+ if (!storageRemoved) {
+ throw std::runtime_error("Failed to remove mmkv storage.");
+ }
+
+ assignEncryptionKey();
+ [MMKV initializeMMKV:nil
+ groupDir:[Tools getAppGroupDirectoryPath]
+ logLevel:MMKVLogNone];
+ getMMKVInstance(commMMKVId.copy, mmkvEncryptionKey);
+ }
+}
+
+bool CommMMKV::setString(std::string key, std::string value) {
+ CommMMKV::initialize();
+ MMKV *mmkv = getMMKVInstance(commMMKVId.copy, mmkvEncryptionKey);
+
+ BOOL result =
+ [mmkv setString:[NSString stringWithCString:value.c_str()
+ encoding:NSUTF8StringEncoding]
+ forKey:[NSString stringWithCString:key.c_str()
+ encoding:NSUTF8StringEncoding]];
+ if (!result) {
+ Logger::log("Attempt to write in background or failure during write.");
+ }
+ return result;
+}
+
+std::optional<std::string> CommMMKV::getString(std::string key) {
+ CommMMKV::initialize();
+ MMKV *mmkv = getMMKVInstance(commMMKVId.copy, mmkvEncryptionKey);
+
+ NSString *value =
+ [mmkv getStringForKey:[NSString stringWithCString:key.c_str()
+ encoding:NSUTF8StringEncoding]];
+ if (!value) {
+ return std::nullopt;
+ }
+ return std::string([value UTF8String]);
+}
+
+} // namespace comm
diff --git a/native/ios/Comm/Tools.h b/native/ios/Comm/Tools.h
--- a/native/ios/Comm/Tools.h
+++ b/native/ios/Comm/Tools.h
@@ -4,5 +4,6 @@
@interface Tools : NSObject
+ (NSString *)getSQLiteFilePath;
++ (NSString *)getAppGroupDirectoryPath;
+ (NSString *)getAppGroupSQLiteFilePath;
@end
diff --git a/native/ios/Comm/Tools.mm b/native/ios/Comm/Tools.mm
--- a/native/ios/Comm/Tools.mm
+++ b/native/ios/Comm/Tools.mm
@@ -2,6 +2,10 @@
#import <Foundation/Foundation.h>
#import <stdexcept>
+@interface Tools ()
++ (NSURL *)getAppGroupDirectoryURL;
+@end
+
@implementation Tools
+ (NSString *)getSQLiteFilePath {
@@ -22,13 +26,23 @@
return [documentsUrl URLByAppendingPathComponent:@"comm.sqlite"].path;
}
-+ (NSString *)getAppGroupSQLiteFilePath {
++ (NSURL *)getAppGroupDirectoryURL {
NSURL *groupUrl = [NSFileManager.defaultManager
containerURLForSecurityApplicationGroupIdentifier:@"group.app.comm"];
if (groupUrl == nil) {
throw std::runtime_error(
- "Failed to resolve database path - could not find groupUrl");
+ "Failed to resolve app group path - could not find groupUrl");
}
+ return groupUrl;
+}
+
++ (NSString *)getAppGroupDirectoryPath {
+ NSURL *groupUrl = [Tools getAppGroupDirectoryURL];
+ return groupUrl.path;
+}
+
++ (NSString *)getAppGroupSQLiteFilePath {
+ NSURL *groupUrl = [Tools getAppGroupDirectoryURL];
return [groupUrl URLByAppendingPathComponent:@"comm.sqlite"].path;
}
diff --git a/native/ios/Podfile b/native/ios/Podfile
--- a/native/ios/Podfile
+++ b/native/ios/Podfile
@@ -46,6 +46,7 @@
common_comm_target_pods
pod 'ReactNativeKeyboardTrackingView', :path => '../../node_modules/react-native-keyboard-tracking-view'
pod 'ReactNativeKeyboardInput', :path => '../node_modules/react-native-keyboard-input'
+ pod 'MMKV'
react_native_config
end
@@ -55,6 +56,7 @@
pod 'OLMKit', :path => "../node_modules/olm"
pod 'RCT-Folly', :podspec => "../../node_modules/react-native/third-party-podspecs/RCT-Folly.podspec"
pod 'CommExpoPackage', :path => "../expo-modules/comm-expo-package/ios"
+ pod 'MMKVAppExtension'
react_native_config
end
diff --git a/native/ios/Podfile.lock b/native/ios/Podfile.lock
--- a/native/ios/Podfile.lock
+++ b/native/ios/Podfile.lock
@@ -158,6 +158,11 @@
- lottie-react-native (5.1.4):
- lottie-ios (~> 3.4.0)
- React-Core
+ - MMKV (1.3.3):
+ - MMKVCore (~> 1.3.3)
+ - MMKVAppExtension (1.3.3):
+ - MMKVCore (~> 1.3.3)
+ - MMKVCore (1.3.3)
- mobile-ffmpeg-min (4.3.1.LTS)
- OLMKit (3.2.14):
- OLMKit/olmc (= 3.2.14)
@@ -604,6 +609,8 @@
- hermes-engine (from `../../node_modules/react-native/sdks/hermes/hermes-engine.podspec`)
- libevent (~> 2.1.12)
- lottie-react-native (from `../node_modules/lottie-react-native`)
+ - MMKV
+ - MMKVAppExtension
- OLMKit (from `../node_modules/olm`)
- RCT-Folly (from `../../node_modules/react-native/third-party-podspecs/RCT-Folly.podspec`)
- RCTRequired (from `../../node_modules/react-native/Libraries/RCTRequired`)
@@ -668,6 +675,9 @@
- libvmaf
- libwebp
- lottie-ios
+ - MMKV
+ - MMKVAppExtension
+ - MMKVCore
- mobile-ffmpeg-min
- OpenSSL-Universal
- SDWebImage
@@ -885,6 +895,9 @@
libwebp: f62cb61d0a484ba548448a4bd52aabf150ff6eef
lottie-ios: 8f97d3271e155c2d688875c29cd3c74908aef5f8
lottie-react-native: b702fab740cdb952a8e2354713d3beda63ff97b0
+ MMKV: f902fb6719da13c2ab0965233d8963a59416f911
+ MMKVAppExtension: fcf23c6b250cc87db63507bc57be8e6ed378168d
+ MMKVCore: d26e4d3edd5cb8588c2569222cbd8be4231374e9
mobile-ffmpeg-min: d5d22dcef5c8ec56f771258f1f5be245d914f193
OLMKit: a13e1a20579e88d03971c5821360be24949a1a09
OpenSSL-Universal: 84efb8a29841f2764ac5403e0c4119a28b713346
@@ -946,6 +959,6 @@
Yoga: dc109b79db907f0f589fc423e991b09ec42d2295
ZXingObjC: fdbb269f25dd2032da343e06f10224d62f537bdb
-PODFILE CHECKSUM: 8b75c667b4679ba1a92a975823401ba7614ea7a1
+PODFILE CHECKSUM: fa3cbc5d9308882a5b32f37839d5ed4c00a41eab
COCOAPODS: 1.14.3

File Metadata

Mime Type
text/plain
Expires
Fri, Dec 20, 10:48 PM (16 h, 28 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
2683598
Default Alt Text
D11045.id37007.diff (14 KB)

Event Timeline