Shouldn't we open an issue? Is it not a "sin", for a given module A, to publicly extend a type defined in another module B with methods whose signature does not involve types from A?
// In module A
import B
extension B.SomeType {
// Well-behaved
public func doStuff(_ x: A.Stuff) // OK
// Mis-behaved
public func doStuff()
public func doStuff(_ x: Swift.Int)
public func doStuff(_ x: Foundation.IndexSet)
public func doStuff(_ x: SomeOtherModule.Stuff)
}
To me, it looks like SwiftUI may well use this extension internally, no problem, but that it should not be public.
Am I correct? Or do I forget things like inlining and ABI stability?
No. The "sin" is in conforming types you don't own to protocols you don't own. Extending a protocol with new methods is not considered problematic, whether you own any of the types involved.
You are right @Avi, you have described the classic sin.
But aren't we looking at another sin, then? Consider this other current discussion, which talks about removing indices. What will happen when the Standard Library defines the same extension, and a user imports Foundation? Or, more precisely, if Foundation defines the same extension (after all, IndexSet is Foundation's property)? Won't the compiler complain with ambiguity errors, due to two conflicting implementations?
Should SwiftUI be allowed to step on Foundation's "natural" territory?
Yes, that's another situation we have with the ability to extend types we don't own. We would need to overhaul, in a very source-breaking way, the current access controls to close this hole. Any two libraries can extend a common type (from the stdlib or any other source) in incompatible ways. This isn't limited to just the type owner and a consuming framework.
Or we need a way to disambiguate at the call site.
Both SwiftUI and Foundation are being owned by apple, so they can remove the extension from SwiftUI at the same time they add it to Foundation. I have no idea how that would affect ABI, but it should be source compatible because SwiftUI and Foundation are always shipped together
What problems does this create? I have run into several situations where it would be extremely convenient to add conformances in a separate module, and it's always been a point of frustration not to be able to do this.
You can do that, so I'm not sure what trouble you ran into.
The reason it's considered a sin is that your code is brittle, as the owners of the types can't possibly consider your extensions when changing their code.
I think that's because it's superfluous. If the protocol is public, the conformance will be, and if it's not, you can't make the extension public anyway.
Actually, with a little more digging, it appears the remove(atOffsets:) method is implemented in the Foundation framework. So, the documentation's listing of the method raises the question: Should the "official" Swift Standard Library documentation include references to methods contained in extensions implemented via frameworks? The documentation notes that the method is part of the SwiftUI framework, but that approach to documentation seems awkward--perhaps a bit Apple-centric.
The applying(_:) method is anticipated to be included in the Standard Library, but the pending amendment has not yet been accepted AFIK (Active Review (June 19 - 25 2019). Of course, it is a sure thing that it will be accepted. Certainly, the formality of acceptance will catch up soon. @Douglas_Gregor
I suppose it is convenient to handle the documentation in that fashion, but it sure feels like a fork in the language. One language set when working with Apple OS, and another set when elsewhere.
I love SwiftUI and Combine, and admire the incredible, herculean work that those teams presently are engaged in. But, I am concerned about the implications of their decisions on the future development of the language.
For instance, one could imagine a future in which there would exist a UserInterface framework, with that framework providing (i) types to specify universal UI elements, and (ii) a set of protocols to provide an interface between those universal types and any given OS, with the platform provider (or the Swift-on-Linux project) to write types that conform to the interface protocols. SwiftUI may be a big step down that road; or it may, through inertia and/or due to naming collisions and/or for other reasons, become an impediment to growth in that sort of direction or other directions. I'd appreciate the thoughts of the community on that topic, but perhaps that discussion should be saved for some other thread.