How can I properly copy objects from one Realm object to another object
What you want to do is use:
for record in postsDB.objects(PostModel.self) {
if !combinedDB.objects(PostModel.self).filter("postId == \(record.parentId)").isEmpty {
combinedDB.create(PostModel.self, value: record, update: false)
}
}
The create method is inherited from Object. It tells the target to create a new object. Use true if you want it to look to see if there is already a record there, and update it if there is.
PostModel is the Object type, record is what you want copied.
Edit: I added the if statement to provide more context. You didn't show your class definitions, so I was guessing. This is a working example. I ask for a set of records from DatabaseA and copy it to DatabaseB (postsDB to combinedDB).
So if the type of the object you're trying to insert is a List, I'd recommend you define a subclass of Object, and have at least the list you need as a property.
class TagList: Object {
dynamic var tag = ""
var list = List<PostModel>()
override class func primaryKey() -> String? {
return "tag"
}
}
Full working example illustrating: creating new objects, copying all objects to a second list, deleting from second list after copying, adding to first list (which didn't get anything deleted from it.
import Foundation
import RealmSwift
class Letter: Object {
dynamic var letter = "a"
}
class Letters: Object {
var letterList = List<Letter>()
}
class ListExample {
let listRealmStore = try! Realm() // swiftlint:disable:this force_try
func testThis() {
print(Realm.Configuration.defaultConfiguration.fileURL!)
listRealmStore.beginWrite()
addSingleItems() // add 3 objects to the DB
let firstList = Letters()
let allObjects = listRealmStore.objects(Letter.self)
for item in allObjects {
firstList.letterList.append(item)
}
let secondList = Letters()
let itemsToCopy = firstList.letterList
for item in itemsToCopy {
let obj = listRealmStore.create(Letter.self)
obj.letter = item.letter
secondList.letterList.append(obj)
}
let third = Letter()
third.letter = "Z"
listRealmStore.add(third)
firstList.letterList.append(third)
secondList.letterList.removeLast()
do {
try listRealmStore.commitWrite()
} catch let error {
print("couldn't commit db writes: \(error.localizedDescription)")
}
print("list one:\n\(firstList)")
print("list two:\n\(secondList)")
}
func addSingleItems() {
for letter in ["a", "b", "c"] {
let objectToInsert = Letter()
objectToInsert.letter = letter
listRealmStore.add(objectToInsert)
}
}
}
Results in:
list one:
Letters {
letterList = List<Letter> (
[0] Letter {
letter = a;
},
[1] Letter {
letter = b;
},
[2] Letter {
letter = c;
},
[3] Letter {
letter = Z;
}
);
}
list two:
Letters {
letterList = List<Letter> (
[0] Letter {
letter = a;
},
[1] Letter {
letter = b;
}
);
}
How to copy objects from the default local realm to a MongoDB synced realm using Swift?
Update
Found a potential workaround for this issue in "How can I easily duplicate/copy an existing realm object" using Codable
with JSONEncoder
and JSONDecoder
, https://stackoverflow.com/a/65436546/2226315
Found another function in GitHub Gist migrates local realm to a synced realm, however, the code seems already outdated.
Found a GitHub issue raised in 2014 about how to move/copy objects between realms, https://github.com/realm/realm-cocoa/issues/1076. createInRealm:withObject:
was suggested in the comment.
However, after digging into the source code only createInRealm:withValue:
is available in Objective-C API, https://github.com/realm/realm-cocoa/blob/84179b4e0b54e11f73723c283c4567c565da62f5/Realm/RLMObject.h#L174
In the official guide on "Add Sync to a Local-Only App", there is a section about "Copy Existing Data" which outlines the flow to copy data from a local realm to a synced realm.
Relevant Info
- Converting local realms to synced realm
- https://github.com/realm/realm-cocoa/issues/5381
RealmSwift: Detach an object from Realm, including its properties of List type
This is not yet supported natively by Realm, but a requested feature tracked by issue #3381.
For now, you would need to implement your own deep copy constructor. A common strategy is to do that on every model and call the deep copy constructors of related objects. You need to pay attention though that you don't run into cycles.
Deep copy Realm object in Kotlin
can you please provide more context and appropriate information as I do not see and array's in your code statement. Thank you.
EDIT
Because Money is not a data class, you do not have the auto-generated copy() function available, that leaves you with two options:
- Create an custom copy() function in the Money class. This could be mundane if there are huge amount of fields in the class.
- Use 3rd party libraries, in which case you'll add external dependency to your RealmObject.
What I will suggest is a no brainer: Try to convert your Money.class to a Data class. You will get auto generated functions and idiomatically it will work as RealmObjects should be key-values pairs.
EDIT
You can use GSON library's serialization/deserialization and hack your way to solve your problem (although this is a hacky way but will do its job):
fun clone(): Money {
val stringMoney = Gson().toJson(this, Money::class.java)
return Gson().fromJson<Money>(stringMoney, Money::class.java)
}
usage:
val originalMoney = Money()
val moneyClone = originalMoney.clone()
Proper way of avoiding duplicate object in Realm?
Depending on whether you want to update the existing object with new data or do nothing if it exists already, you have two alternatives.
If you want to do nothing if it already exists, you can use Realm.object(ofType:,forPrimaryKey:)
.
let existingPerson = realm.object(ofType: Person.self, forPrimaryKey: primaryKey)
if let existingPerson = existingPerson {
// Person already exists, act accordingly
} else {
// Add person
}
If you want to update the object if it exists and add it if it doesn't, you can simply use realm.add(_:,update:)
.
do {
try realm.write {
realm.add(personObject,update:true)
}
}
RealmList addAll duplicating object with same primary key
A RealmList works just like an ArrayList
, so the same item can be there multiple times. If you want to update SomeObject
you should just do that directly. The objects
RealmList will reflect those changes.
It isn't clear exactly what you are trying to do, so from the given information it is hard to give more advice.
Realm Swift - Duplicate existing nested Objects
Have an unique property for your store. For example an UUID.
dynamic var uuid = UUID().uuidString
Override the primaryKey
function for your Store model, and returns the previously created unique property.
override class func primaryKey() -> String? {
return "uuid"
}
It should do the trick.
Related Topics
How to Display an Activity Indicator With Text on iOS 8 With Swift
Saving Picked Image to Coredata
Why Can't I Pass a Protocol.Type to a Generic T.Type Parameter
Multiple Functions With the Same Name
Access Firebase Variable Outside Closure
Checking If an Object Is a Given Type in Swift
How to Detect If an Skspritenode Has Been Touched
How to Create a Segue That Can Be Called from a Button That Is Created Programmatically
Programmatically Detect Tab Bar or Tabview Height in Swiftui
How to Convert Array of Bytes [Uint8] into Hexa String in Swift
Trapping Signals in a Swift Command Line Application
Extra Arguments At Positions #11, #12 in Call Swiftui
Swift - Validating Uitextfield
Selecting Global or Object Print Function