Another issue of scale - I had to switch to a native mail client as replying 
inline severely broke my webmail client. ;-)

Again, lots of love here. Responses inline.

> On Mar 15, 2017, at 6:40 PM, Itai Ferber via swift-evolution 
> <[email protected]> wrote:
> Proposed solution
> We will be introducing the following new types:
> 
> protocol Codable: Adopted by types to opt into archival. Conformance may be 
> automatically derived in cases where all properties are also Codable.
FWIW I think this is acceptable compromise. If the happy path is derived 
conformances, only-decodable or only-encodable types feel like a lazy way out 
on the part of a user of the API, and builds a barrier to proper testing.
> [snip]
> 
> Structured types (i.e. types which encode as a collection of properties) 
> encode and decode their properties in a keyed manner. Keys may be 
> String-convertible or Int-convertible (or both), and user types which have 
> properties should declare semantic key enums which map keys to their 
> properties. Keys must conform to the CodingKey protocol:
> public protocol CodingKey { <##snip##> }

A few things here:

The protocol leaves open the possibility of having both a String or Int 
representation, or neither. What should a coder do in either case? Are the 
representations intended to be mutually exclusive, or not? The protocol design 
doesn’t seem particularly matching with the flavor of Swift; I’d expect 
something along the lines of a CodingKey enum and the protocol 
CodingKeyRepresentable. It’s also possible that the concerns of the two are 
orthogonal enough that they deserve separate container(keyedBy:) requirements.

Speaking of the mutually exclusive representations - what above serializations 
that doesn’t code as one of those two things? YAML can have anything be a 
“key”, and despite that being not particularly sane, it is a use case.
> For most types, String-convertible keys are a reasonable default; for 
> performance, however, Int-convertible keys are preferred, and Encoders may 
> choose to make use of Ints over Strings. Framework types should provide keys 
> which have both for flexibility and performance across different types of 
> Encoders. It is generally an error to provide a key which has neither a 
> stringValue nor an intValue.
> 

Could you speak a little more to using Int-convertible keys for performance? I 
get the feeling int-based keys parallel the legacy of NSCoder’s older design, 
and I don’t really see anyone these days supporting non-keyed archivers. They 
strike me as fragile. What other use cases are envisioned for ordered archiving 
than that?
> [snip]
> 
> Keyed Encoding Containers
> 
> Keyed encoding containers are the primary interface that most Codable types 
> interact with for encoding and decoding. Through these, Codable types have 
> strongly-keyed access to encoded data by using keys that are semantically 
> correct for the operations they want to express.
> 
> Since semantically incompatible keys will rarely (if ever) share the same key 
> type, it is impossible to mix up key types within the same container (as is 
> possible with Stringkeys), and since the type is known statically, keys get 
> autocompletion by the compiler.
> 
> open class KeyedEncodingContainer<Key : CodingKey> {

Like others, I’m a little bummed about this part of the design. Your reasoning 
up-thread is sound, but I chafe a bit on having to reabstract and a little more 
on having to be a reference type. Particularly knowing that it’s got a bit more 
overhead involved… I /like/ that NSKeyedArchiver can simply push some state and 
pass itself as the next encoding container down the stack.

>     open func encode<Value : Codable>(_ value: Value?, forKey key: Key) throws

Does this win anything over taking a Codable?

>     open func encode(_ value: Bool?,   forKey key: Key) throws
>     open func encode(_ value: Int?,    forKey key: Key) throws
>     open func encode(_ value: Int8?,   forKey key: Key) throws
>     open func encode(_ value: Int16?,  forKey key: Key) throws
>     open func encode(_ value: Int32?,  forKey key: Key) throws
>     open func encode(_ value: Int64?,  forKey key: Key) throws
>     open func encode(_ value: UInt?,   forKey key: Key) throws
>     open func encode(_ value: UInt8?,  forKey key: Key) throws
>     open func encode(_ value: UInt16?, forKey key: Key) throws
>     open func encode(_ value: UInt32?, forKey key: Key) throws
>     open func encode(_ value: UInt64?, forKey key: Key) throws
>     open func encode(_ value: Float?,  forKey key: Key) throws
>     open func encode(_ value: Double?, forKey key: Key) throws
>     open func encode(_ value: String?, forKey key: Key) throws
>     open func encode(_ value: Data?,   forKey key: Key) throws

What is the motivation behind abandoning the idea of “primitives” from the 
Alternatives Considered? Performance? Being unable to close the protocol?

What ways is encoding a value envisioned to fail? I understand wanting to allow 
maximum flexibility, and being symmetric to `decode` throwing, but there are 
plenty of “conversion” patterns the are asymmetric in the ways they can fail 
(Date formatters, RawRepresentable, LosslessStringConvertible, etc.).

>     /// For `Encoder`s that implement this functionality, this will only 
> encode the given object and associate it with the given key if it encoded 
> unconditionally elsewhere in the archive (either previously or in the future).
>     open func encodeWeak<Object : AnyObject & Codable>(_ object: Object?, 
> forKey key: Key) throws

Is this correct that if I send a Cocoa-style object graph (with weak backrefs), 
an encoder could infinitely recurse? Or is a coder supposed to detect that?

>     open var codingKeyContext: [CodingKey]
> }
> [snippity snip]
> 
Alright, those are just my first thoughts. I want to spend a little time 
marinating in the code from PR #8124 before I comment further. Cheers! I owe 
you, Michael, and Tony a few drinks for sure.

Zach Waldowski
[email protected]

_______________________________________________
swift-evolution mailing list
[email protected]
https://lists.swift.org/mailman/listinfo/swift-evolution

Reply via email to