Skip to content

Commit 624cc49

Browse files
committedMay 24, 2019
Add release notes for NSCoder and NSSortDescriptor.

File tree

1 file changed

+55
-0
lines changed

1 file changed

+55
-0
lines changed
 

‎Docs/ReleaseNotes_Swift5.md

+55
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,61 @@
22

33
swift-corelibs-foundation contains new features and API in the Swift 5.x family of releases. These release notes complement the [Foundation release notes](https://developer.apple.com/documentation/ios_release_notes/ios_12_release_notes/foundation_release_notes) with information that is specific to swift-corelibs-foundation. Check both documents for a full overview.
44

5+
## Improvements to NSCoder
6+
7+
In this release, the implementation of `NSCoder` and related classes has been brought closer to the behavior of their Darwin counterparts. There are a number of differences from previous versions of swift-corelibs-foundation that you should keep in mind while writing code that uses `NSKeyedArchiver` and `NSKeyedUnarchiver`:
8+
9+
* In previous versions of swift-corelibs-foundation, the `decodingFailurePolicy` setting was hardcoded to `.setAndReturnError`; however, failure in decoding would crash the process (matching the behavior of the `.raiseException` policy). This has been corrected; you can now set the `decodingFailurePolicy` to either policy. To match Darwin, the default behavior has been changed to `.raiseException`.
10+
11+
* On Darwin, in certain rare cases, invoking `failWithError(_:)` could stop execution of an initializer or `encode(with:)` method and unwind the stack, while still continuing program execution (by translating the exception to a `NSError` to a top-level caller). Swift does not support this. The `NSCoder` API documented to do this (`decodeTopLevelObject…`) is not available on swift-corelibs-foundation, and it has been annotated with diagnostics pointing you to cross-platform replacements.
12+
13+
* The following Foundation classes that conform to `NSCoding` and/or `NSSecureCoding` now correctly implement archiving in a way that is compatible with archives produced by their Darwin counterparts:
14+
15+
- `NSCharacterSet`
16+
- `NSOrderedSet`
17+
- `NSSet`
18+
- `NSIndexSet`
19+
- `NSTextCheckingResult` (only for results whose type is `.regularExpression`)
20+
- `ISO8601DateFormatter`
21+
- `DateIntervalFormatter`
22+
23+
* The following Foundation classes require features not available in swift-corelibs-foundation. Therefore, they do not conform to `NSCoding` and/or `NSSecureCoding` in swift-corelibs-foundation. These classes may have conformed to `NSCoding` or `NSSecureCoding` in prior versions of swift-corelibs-foundation, even though they weren't complete prior to this release.
24+
25+
- `NSSortDescriptor` (requires key-value coding)
26+
- `NSPredicate` (requires key-value coding)
27+
- `NSExpression` (requires key-value coding)
28+
- `NSFileHandle` (requires `NSXPCConnection` and related subclasses, which are not available outside of Darwin)
29+
30+
While the type system may help you find occurrences of usage of these classes in a `NSCoding` context, they can still be, incorrectly, passed to the `decodeObjects(of:…)` method that takes a `[AnyClass]` argument. You will need to audit your code to ensure you are not attempting to decode these objects; if you need to decode an archive that contains these objects from Darwin, you should skip decoding of the associated keys in your swift-corelibs-foundation implementation.
31+
32+
## NSSortDescriptor Changes
33+
34+
swift-corelibs-foundation now contains an implementation of `NSSortDescriptor` that is partially compatible with its Objective-C counterpart. You may need to alter existing code that makes use of the following:
35+
36+
- Initializers that use string keys or key paths (e.g.: `init(key:…)`) are not available in swift-corelibs-foundation. You should migrate to initializers that take a Swift key path instead (`init(keyPath:…)`).
37+
38+
- Initializers that take or invoke an Objective-C selector are not available in swift-corelibs-foundation. If your class implemented a `compare(_:)` method for use with the `init(keyPath:ascending:)` initializer, you should add a `Swift.Comparable` conformance to it, which will be used in swift-corelibs-foundation in place of the method. The conformance can invoke the method, like so:
39+
40+
```swift
41+
extension MyCustomClass: Comparable {
42+
public static func <(_ lhs: MyCustomClass, _ rhs: MyCustomClass) {
43+
return lhs.compare(rhs) == .orderedAscending
44+
}
45+
}
46+
```
47+
48+
Note that swift-corelibs-foundation's version of `init(keyPath:ascending:)` is annotated with diagnostics that will cause your code to fail to compile if your custom type isn't `Comparable`; code that uses that constructor with Foundation types that implement a `compare(_:)` method, like `NSString`, `NSNumber`, etc., should still compile and work correctly.
49+
50+
If you were using a selector other than `compare(_:)`, you should migrate to passing a closure to `init(keyPath:ascending:comparator:)` instead. That closure can invoke the desired method. For example:
51+
52+
```swift
53+
let descriptor = NSSortDescriptor(keyPath: \Person.name, ascending: true, comparator: { (lhs, rhs) in
54+
return (lhs as! NSString).localizedCompare(rhs as! String)
55+
})
56+
```
57+
58+
- Archived sort descriptors make use of string keys and key paths, and Swift key paths cannot be serialized outside of Darwin. `NSSortDescriptor` does not conform to `NSSecureCoding` in swift-corelibs-foundation as a result. See the section on `NSCoding` for more information on coding differences in this release.
59+
560
## Improved Scanner API
661

762
The `Scanner` class now has additional API that is more idiomatic for use by Swift code, and doesn't require casting or using by-reference arguments. Several of the new methods have the same name as existing ones, except without the `into:` parameter: `scanInt32()`, `scanString(_:)`, `scanUpToCharacters(from:)`, etc. These invocations will return `nil` if scanning fails, where previous methods would return `false`.

0 commit comments

Comments
 (0)
Please sign in to comment.