SamehDos
SamehDos

Reputation: 1203

Can not add class with generic type to swift realm

I need to save a class in realm, this class contains a generic type as the following:-

@objcMembers
class ClassA<T: Object & Codable>: Object, Codable {
    dynamic var key: String?
    dynamic var type: T?

    override class func primaryKey() -> String {
        return "key"
    }

}

@objcMembers
class ClassB: Object, Codable {    
}

let object: ClassA<ClassB> 

realm.add(object, update: true)

But this code unfortunately save only ClassA.key in realm and ignors ClassA.type.

I have googled about this issue but without any result unfortunately. It seems that nobody uses a generic type inside a realm class.

Upvotes: 1

Views: 517

Answers (2)

SamehDos
SamehDos

Reputation: 1203

Finally I’ve reached the proper solution. I have used the advantage of the generic realm list type, then I have modified the “type” variable to be a list of generic instead of single generic object. It is now working fine with me. Now I can easily use a generic type inside a class and save this class to realm without any problem.

@objcMembers
class ClassA<T: Object & Codable>: Object, Codable {
    dynamic var key: String?
    var type: List<T>()

    override class func primaryKey() -> String {
        return "key"
    }

}

@objcMembers
class ClassB: Object, Codable {    
}

let object: ClassA<ClassB>

realm.add(object, update: true)

Upvotes: 1

keji
keji

Reputation: 5990

@objcMembers only exposes compatible members to Objective-C. Swift generics do not get included with this as they are not compatible with Objective-C. Realm works off of exposing the members to Objective-C.

Possible solution:

@objcMembers
class ClassA<T: Object & Codable>: Object, Codable {
    dynamic var key: String?
    var type: T?

    override class func primaryKey() -> String {
        return "key"
    }

}

@objcMembers
class ClassB: Object, Codable {

}

class ClassABComposite: ClassA<ClassB> {
    // T can be realized as ClassB here
    override var type: ClassB? {
        set {
            backingType = newValue
        }
        get {
            return backingType
        }
    }

    // This will work because it's not generic
    @objc dynamic var backingType: ClassB?
}

Upvotes: 0

Related Questions