gpt4 book ai didi

ios - 对 Transformable 属性采用 NSSecureUnarchiveFromDataTransformer 时发生崩溃

转载 作者:行者123 更新时间:2023-12-01 23:52:54 31 4
gpt4 key购买 nike

在 iOS 12 中,Apple 引入了 NSSecureUnarchiveFromDataTransformerName 用于 CoreData 模型实体的 Transformable 属性。我曾经将转换器名称字段保留为空,这隐式使用了 NSKeyedUnarchiveFromDataTransformerName。此转换器现已弃用,将来将该字段保留为空将意味着 NSSecureUnarchiveFromDataTransformerName

在 iOS 13 中,如果该字段为空,您现在会收到一条运行时警告,告诉您上述内容。我在任何地方都找不到任何相关文档,我得到的唯一引用是 WWDC 2018 核心数据最佳实践演讲,其中简要提到了我刚才所说的内容。

现在我有一个模型,其中的实体直接将 HTTPURLResponse 对象存储在 Transformable 属性中。它符合 NSSecureCoding,并且我在运行时检查了 supportsSecureCodingtrue

为转换器名称设置 NSSecureUnarchiveFromDataTransformerName 会崩溃,并显示以下消息:

Object of class NSHTTPURLResponse is not among allowed top level class list (
NSArray,
NSDictionary,
NSSet,
NSString,
NSNumber,
NSDate,
NSData,
NSURL,
NSUUID,
NSNull
) with userInfo of (null)

所以听起来 Transformable 属性只能属于这些顶级对象。

我尝试按照文档的建议对安全转换器进行子类化并覆盖 allowedTopLevelClasses 属性:

@available(iOS 12.0, *)
public class NSSecureUnarchiveHTTPURLResponseFromDataTransformer: NSSecureUnarchiveFromDataTransformer {

override public class var allowedTopLevelClasses: [AnyClass] {
return [HTTPURLResponse.self]
}
}

然后我想我可以创建一个自定义转换器名称,在模型中设置它并为该名称调用 setValueTransformer(_:forName:) ,但我找不到要设置的 API如果我使用的是 iOS 11,则为我的自定义名称默认的 NSKeyedUnarchiveFromDataTransformer

请记住,我正在使用 Xcode 11 Beta 5,但如果我要接受我所得到的错误的含义,这似乎并不相关。

欣赏任何想法。

最佳答案

我编写了一个简单的模板类,它可以轻松地为任何实现 NSSecureCoding 的类创建和注册转换器。它在 iOS 12 和 13 中对我来说工作得很好,至少在我使用 UIColor 作为可转换属性的简单测试中是这样。

使用它(以 UIColor 为例):

// Make UIColor adopt ValueTransforming
extension UIColor: ValueTransforming {
static var valueTransformerName: NSValueTransformerName {
.init("UIColorValueTransformer")
}
}

// Register the transformer somewhere early in app startup.
NSSecureCodingValueTransformer<UIColor>.registerTransformer()

核心数据模型中使用的转换器的名称是UIColorValueTransformer

import Foundation

public protocol ValueTransforming: NSSecureCoding {
static var valueTransformerName: NSValueTransformerName { get }
}

public class NSSecureCodingValueTransformer<T: NSSecureCoding & NSObject>: ValueTransformer {
public override class func transformedValueClass() -> AnyClass { T.self }
public override class func allowsReverseTransformation() -> Bool { true }

public override func transformedValue(_ value: Any?) -> Any? {
guard let value = value as? T else { return nil }
return try? NSKeyedArchiver.archivedData(withRootObject: value, requiringSecureCoding: true)
}

public override func reverseTransformedValue(_ value: Any?) -> Any? {
guard let data = value as? NSData else { return nil }
let result = try? NSKeyedUnarchiver.unarchivedObject(
ofClass: T.self,
from: data as Data
)
return result
}

/// Registers the transformer by calling `ValueTransformer.setValueTransformer(_:forName:)`.
public static func registerTransformer() {
let transformer = NSSecureCodingValueTransformer<T>()
ValueTransformer.setValueTransformer(transformer, forName: T.valueTransformerName)
}
}

关于ios - 对 Transformable 属性采用 NSSecureUnarchiveFromDataTransformer 时发生崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57304922/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com