-1

I am working with a class which is both NSManagedObject and Codable. It's a Feed and it has multiple Albums. I want the ordered list of Albums but Core Data forces me to use Set instead, which is not ordered. I can use NSOrderedSet, but it doesn't work well with Codable. What would be the best way to get the ordered list in Core Data. Below is the Model I am trying to make work.

public class Feed: NSManagedObject, Codable {

    @nonobjc public class func fetchRequest() -> NSFetchRequest<Feed> {
        return NSFetchRequest<Feed>(entityName: "Feed")
    }

    @NSManaged public var title: String
    @NSManaged public var albums: Set<Album>
    @NSManaged public var feedContainer: FeedContainer?

    enum CodingKeys: String, CodingKey {
        case title
        case albums = "results"
        case feedContainer
    }

    public func encode(to encoder: Encoder) throws {
        var container = encoder.container(keyedBy: CodingKeys.self)
        try container.encode(title, forKey: .title)
        try container.encode(albums, forKey: .albums)
    }

    public required convenience init(from decoder: Decoder) throws {
        guard let contextUserInfoKey = CodingUserInfoKey.context,
            let managedObjectContext = decoder.userInfo[contextUserInfoKey] as? NSManagedObjectContext,
            let entity = NSEntityDescription.entity(forEntityName: "Feed", in: managedObjectContext) else {  fatalError("Failed to decode Subject!")  }
        self.init(entity: entity, insertInto: managedObjectContext)

        let container = try decoder.container(keyedBy: CodingKeys.self)
        title = try container.decodeIfPresent(String.self, forKey: .title) ?? ""
        albums = try container.decodeIfPresent(Set<Album>.self, forKey: .albums) ?? []
    }
}
Vandan Patel
  • 1,012
  • 1
  • 12
  • 23
  • Why can't you use an NSArray? And why doesn't NSOrderedSet work well with Codable? – BallpointBen Sep 12 '18 at 16:40
  • I'd recommend to use native Set<> and sort the items accordingly when being displayed. This is more efficient than using ordered sets – vadian Sep 12 '18 at 17:10
  • @vadian I have thought about that, but my data doesn't include any field to sort though. It's just a list of albums and it doesn't contain any field which would give us an order. – Vandan Patel Sep 12 '18 at 17:14

1 Answers1

1

I want the ordered list of Albums

It is your job to give the Album entity an attribute to sort by. Then, when you fetch, you can pass a sort descriptor to receive the Albums sorted on that attribute.

matt
  • 515,959
  • 87
  • 875
  • 1,141
  • I am not sure how I can do that though. How can I create an attribute which is consistent with the order of albums coming from network? – Vandan Patel Sep 12 '18 at 17:17
  • Your question says nothing about "coming from" a "network". You asked about how to make results from core data be "ordered" and I answered about how you do that. Core data results have no natural "order"; it is up to you to provide one, by means of an attribute. You can use a timestamp, an index number, whatever. – matt Sep 12 '18 at 17:35