swiftswiftdata

How to fetch with new #Predicate macro by Enum property


I'm trying to fetch some results with the new #Predicate macro. The problem appears when I try to use an enum property inside the predicate. Does anyone know if it can be done or if this is a bug?

XCode 15 beta 4

Fetch 1:

let predicate = #Predicate<ModelA> { $0.type == ModelA.ModelAType.a }

Fetch 2:

let predicate = #Predicate<ModelA> { $0.type.rawValue == ModelA.ModelAType.a.rawValue }

Model:

@Model final class ModelA: Codable {
    @Attribute(.unique) var id: Int64 = 0
    enum ModelAType: Int, CaseIterable, Codable { case a = 1, b }
    var type: ModelAType = ModelAType.a
}

Errors:

Type 'ModelA.Type' cannot conform to 'StandardPredicateExpression'
Type 'ModelA.Type' cannot conform to 'PredicateExpression'
Cannot infer key path type from context; consider explicitly specifying a root type


Solution

  • As of Xcode 15.2 this doesn't seem to work at all if you want to use an enum in a predicate, a workaround is to store the raw value of the enum directly and use a computed property to convert between the stored value and the enum type.


    What worked for me in this situation was to define a constant for the raw value and use that constant in the predicate

    let aValue = ModelA.ModelAType.a.rawValue
    let predicate = #Predicate<ModelA> { $0.type.rawValue == aValue }
    

    I am not sure why this is needed but hopefully it’s a beta thing that will change soon