Skip to content

Commit

Permalink
Allow opening synced realm in-memory.
Browse files Browse the repository at this point in the history
  • Loading branch information
dianaafanador3 committed Jan 23, 2024
1 parent 6a0054a commit aebbcaa
Show file tree
Hide file tree
Showing 5 changed files with 58 additions and 13 deletions.
6 changes: 5 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,10 @@ x.y.z Release notes (yyyy-MM-dd)
* The `baseURL` field of `AppConfiguration` can now be updated, rather than the
value being persisted between runs of the application in the metadata
storage. ([Core #7201](https://github.com/realm/realm-core/issues/7201))
* Allow in-memory synced Realms. This will allow setting and in-memory identifier on
flexible sync realms, this will not create a .realm file or its associated auxiliary
files for the synced realm and instead stores objects in memory while the realm is
open and discards them immediately when all instances are closed.

### Fixed
* `@Persisted`'s Encodable implementation did not allow the encoder to
Expand Down Expand Up @@ -9393,7 +9397,7 @@ Prebuilt frameworks are now built with Xcode 7.1.
the properties in a `RLMObject` subclass.
* Fix crash on IN query with several thousand items.
* Fix crash when querying indexed `NSString` properties.
* Fixed an issue which prevented in-memory Realms from being used accross multiple threads.
* Fixed an issue which prevented in-memory Realms from being used across multiple threads.
* Preserve the sort order when querying a sorted `RLMResults`.
* Fixed an issue with migrations where if a Realm file is deleted after a Realm is initialized,
the newly created Realm can be initialized with an incorrect schema version.
Expand Down
46 changes: 46 additions & 0 deletions Realm/ObjectServerTests/AsyncSyncTests.swift
Original file line number Diff line number Diff line change
Expand Up @@ -514,6 +514,52 @@ class AsyncFlexibleSyncTests: SwiftSyncTestCase {
checkCount(expected: 10, realm, SwiftPerson.self)
}

@MainActor
func testFlexibleSyncInitInMemory() async throws {
try await populateSwiftPerson(5)

let user = try await createUser()
try await Task {
var config = user.flexibleSyncConfiguration(initialSubscriptions: { subs in
subs.append(QuerySubscription<SwiftPerson> {
$0.age > 0 && $0.firstName == "\(#function)"
})
})
config.objectTypes = [SwiftPerson.self]
config.inMemoryIdentifier = "identifier"
let inMemoryRealm = try await Realm(configuration: config, downloadBeforeOpen: .always)
XCTAssertEqual(inMemoryRealm.objects(SwiftPerson.self).count, 5)
try! inMemoryRealm.write {
let person = SwiftPerson(firstName: "\(#function)",
lastName: "lastname_10",
age: 10)
inMemoryRealm.add(person)
}
XCTAssertEqual(inMemoryRealm.objects(SwiftPerson.self).count, 6)
try await inMemoryRealm.syncSession?.wait(for: .upload)
}.value

var config = user.flexibleSyncConfiguration(initialSubscriptions: { subs in
subs.append(QuerySubscription<SwiftPerson> {
$0.age > 5 && $0.firstName == "\(#function)"
})
})
config.objectTypes = [SwiftPerson.self]
config.inMemoryIdentifier = "identifier"
let inMemoryRealm = try await Realm(configuration: config, downloadBeforeOpen: .always)
XCTAssertEqual(inMemoryRealm.objects(SwiftPerson.self).count, 1)

var config2 = user.flexibleSyncConfiguration(initialSubscriptions: { subs in
subs.append(QuerySubscription<SwiftPerson> {
$0.age > 0 && $0.firstName == "\(#function)"
})
})
config2.objectTypes = [SwiftPerson.self]
config2.inMemoryIdentifier = "identifier2"
let inMemoryRealm2 = try await Realm(configuration: config2, downloadBeforeOpen: .always)
XCTAssertEqual(inMemoryRealm2.objects(SwiftPerson.self).count, 6)
}

@MainActor
func testStates() async throws {
let realm = try await openRealm()
Expand Down
6 changes: 3 additions & 3 deletions Realm/RLMRealmConfiguration.h
Original file line number Diff line number Diff line change
Expand Up @@ -75,13 +75,13 @@ typedef void(^RLMFlexibleSyncInitialSubscriptionsBlock)(RLMSyncSubscriptionSet *

#pragma mark - Properties

/// The local URL of the Realm file. Mutually exclusive with `inMemoryIdentifier`;
/// The local URL of the Realm file. Mutually exclusive with `inMemoryIdentifier`,
/// setting one of the two properties will automatically nil out the other.
@property (nonatomic, copy, nullable) NSURL *fileURL;

/// A string used to identify a particular in-memory Realm. Mutually exclusive with `fileURL`,
/// `seedFilePath`and `syncConfiguration`;
/// setting any one of the three properties will automatically nil out the other two.
/// `seedFilePath`.
/// setting an in-memory identifier will automatically nil out the other two.
@property (nonatomic, copy, nullable) NSString *inMemoryIdentifier;

/// A 64-byte key to use to encrypt the data, or `nil` if encryption is not enabled.
Expand Down
2 changes: 0 additions & 2 deletions Realm/RLMRealmConfiguration.mm
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,6 @@ - (void)setInMemoryIdentifier:(NSString *)inMemoryIdentifier {
if (inMemoryIdentifier.length == 0) {
@throw RLMException(@"In-memory identifier must not be empty");
}
_config.sync_config = nullptr;
_seedFilePath = nil;

RLMNSStringToStdString(_config.path, [NSTemporaryDirectory() stringByAppendingPathComponent:inMemoryIdentifier]);
Expand Down Expand Up @@ -367,7 +366,6 @@ - (void)setSyncConfiguration:(RLMSyncConfiguration *)syncConfiguration {
}

NSAssert(user.identifier, @"Cannot call this method on a user that doesn't have an identifier.");
_config.in_memory = false;
_config.sync_config = std::make_shared<realm::SyncConfig>(syncConfiguration.rawConfiguration);
_config.path = syncConfiguration.path;

Expand Down
11 changes: 4 additions & 7 deletions RealmSwift/RealmConfiguration.swift
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,9 @@ extension Realm {
/**
Creates a `Configuration` which can be used to create new `Realm` instances.
- note: The `fileURL`, `inMemoryIdentifier`, and `syncConfiguration` parameters are mutually exclusive. Only
- note: The `fileURL`, `inMemoryIdentifier`, parameters are mutually exclusive. Only
set one of them, or none if you wish to use the default file URL.
Synced Realms will set a unique file path unless is an in-memory realm.
- parameter fileURL: The local URL to the Realm file.
- parameter inMemoryIdentifier: A string used to identify a particular in-memory Realm.
Expand Down Expand Up @@ -106,15 +107,13 @@ extension Realm {
// MARK: Configuration Properties

/**
A configuration value used to configure a Realm for synchronization with Atlas App Services. Mutually
exclusive with `inMemoryIdentifier`.
A configuration value used to configure a Realm for synchronization with Atlas App Services.
*/
public var syncConfiguration: SyncConfiguration? {
get {
return _syncConfiguration
}
set {
_inMemoryIdentifier = nil
_syncConfiguration = newValue
}
}
Expand All @@ -128,15 +127,13 @@ extension Realm {
}
}

/// A string used to identify a particular in-memory Realm. Mutually exclusive with `fileURL` and
/// `syncConfiguration`.
/// A string used to identify a particular in-memory Realm. Mutually exclusive with `fileURL`.
public var inMemoryIdentifier: String? {
get {
return _inMemoryIdentifier
}
set {
fileURL = nil
_syncConfiguration = nil
_inMemoryIdentifier = newValue
}
}
Expand Down

0 comments on commit aebbcaa

Please sign in to comment.