Реализация Codable и NSManagedObject одновременно в Swift - PullRequest
0 голосов
/ 28 февраля 2019

У меня есть приложение для обработки заказов, над которым я работаю, для моих работодателей, которое изначально было разработано для динамического получения всех данных о заказах, продуктах и ​​клиентах из API.Таким образом, все объекты и все функции, связанные с этими объектами, взаимодействуют в приложении с ожиданием «передача по значению», используя структуры, соответствующие Codable.

Теперь мне нужно кэшировать почти всеэти объекты.Введите CoreData.

У меня нет желания создавать два файла для одного объекта (один в виде структуры Codable, а другой в качестве класса NSManagedObject), а затем пытаться выяснить, как преобразовать один в другой.Поэтому я хочу реализовать оба в одном и том же файле ... хотя я все еще могу использовать мой код "передачи по значению".

Возможно, это невозможно.

edit

Я ищу что-то более простое, чем восстановление всех моих структур данных с нуля.Я понимаю, что мне придется внести некоторые изменения, чтобы сделать структуру Codable совместимой с классом NSManagedObject.Я хотел бы избежать создания пользовательского инициализатора, который требует, чтобы я вводил каждое свойство вручную, потому что их сотни.

1 Ответ

0 голосов
/ 01 марта 2019

В конце концов, похоже, что не существует «хорошего» решения при переходе с динамического приложения API без кэширования в кэшированное приложение.

Я решил просто откусить пулю и попробовать метод в этомВопрос: Как использовать swift 4 Codable в Core Data?

РЕДАКТИРОВАТЬ:

Я не мог понять, как заставить это работать, поэтому я использовал следующее решение:

import Foundation
import CoreData

/*
 SomeItemData vs SomeItem:
 The object with 'Data' appended to the name will always be the codable struct. The other will be the NSManagedObject class.
 */

struct OrderData: Codable, CodingKeyed, PropertyLoopable
{
    typealias CodingKeys = CodableKeys.OrderData

    let writer: String,
    userID: String,
    orderType: String,
    shipping: ShippingAddressData
    var items: [OrderedProductData]
    let totals: PaymentTotalData,
    discount: Float

    init(json:[String:Any])
    {
        writer = json[CodingKeys.writer.rawValue] as! String
        userID = json[CodingKeys.userID.rawValue] as! String
        orderType = json[CodingKeys.orderType.rawValue] as! String
        shipping = json[CodingKeys.shipping.rawValue] as! ShippingAddressData
        items = json[CodingKeys.items.rawValue] as! [OrderedProductData]
        totals = json[CodingKeys.totals.rawValue] as! PaymentTotalData
        discount = json[CodingKeys.discount.rawValue] as! Float
    }
}

extension Order: PropertyLoopable //this is the NSManagedObject. PropertyLoopable has a default implementation that uses Mirror to convert all the properties into a dictionary I can iterate through, which I can then pass directly to the JSON constructor above
{
    convenience init(from codableObject: OrderData)
    {
        self.init(context: PersistenceManager.shared.context)

        writer = codableObject.writer
        userID = codableObject.userID
        orderType = codableObject.orderType
        shipping = ShippingAddress(from: codableObject.shipping)
        items = []
        for item in codableObject.items
        {
            self.addToItems(OrderedProduct(from: item))
        }
        totals = PaymentTotal(from: codableObject.totals)
        discount = codableObject.discount
    }
}
...