In short, this is a few take-aways from my experience with the Rust ecosystem that we could adopt to make Swift even better:
- A toolchain manager for Swift
- A package registry
- More "Swifty" testing
- Generated documentation
- An online playground
- Command-line benchmarking
- Make Swift more "self-contained" from Xcode
- Reduce the size of the Swift toolchain (if possible)
Note that this isn't really a single proposal, but a number of discussion staters, each of which could be its own proposal.
Details
Recently, I've been learning Rust. It's a really great language and I can see why Swift pulled so much inspiration from it. For the most part, I think Swift just took the best parts of Rust and made them even better. Swift gains a lot of the safety of Rust, but with code that's easier to write, cleaner and more expressive. For the most part, I still prefer the experience of programming in Swift.
However, there is one area where Rust really shines over Swift: Rust has an amazing ecosystem. The experience of installing Rust, configuring it and getting projects started is a very cohesive, experience. Rust is IDE-agnostic, simple and straight-forward, and everything works well together. It's a self-contained, comprehensive suite of tools to write code.
Once setup and running, Swift shines. But, getting there is a bit clunkier. It's not hard, but it doesn't have that cohesive feel that Rust does. All of this isn't really an issue for traditional Swift programmers, who have primarily used Swift for iOS/Mac development and got it bundled with Xcode. However, we want to bring more types of Swift programmers to the table: those on other platforms, other IDEs, etc. As part of the "all are welcome" future of Swift, making the non-Xcode installation/setup process more friendly will reduce some of the barriers to getting new Swift adopters.
On Mac, Swift is very reliant on Xcode and has lots of ties to Xcode that feel a bit awkward. While Xcode is a great IDE and should be the best IDE for Swift development on Mac, Swift itself should feel more self-contained. On Linux, it is (because, of course, there is no Xcode on Linux). But this just makes the experience of installing Swift different on different platforms. To truly become a multi-purpose, multi-platform language, I really think we need Swift to be free of Xcode on all platforms. Xcode can embrace Swift and be an awesome Swift IDE, but Swift should be agnostic. A good example of this separation beginning to work is SourceKit, which Xcode uses, but allows other IDEs to provide the same experience as Xcode as well.
Another impediment to Swift is the size of the toolchain. The Rust toolchain is 117.5 MB. By contrast, the Swift 5.3 toolchain (Mac) is 1.61 GB. That's over 13 times larger. Why is it so much larger than the Rust toolchain? There may be a good reason, but it may be something to think about. The size makes Swift feel a bit heavy. Rust does a lot (compile code, manage packages, generate documentation, run tests, run benchmark, etc.) for a lot less. Can we go on a diet?
Here is a rundown of a few Rust ecosystem features I wanted to call out, along with some proposals about how we can adopt them in the Swift community:
Online playground
Rust: Rust has an online playground on its homepage.
Proposal
While Swift playgrounds are great, they only really work well in Xcode. Having an online playground right on swift.org would be a great way to get new Swift developers hooked before they even download the toolchain.
Installation process
Rust: Rust can be installed with rustup
, a tool that manages your Rust toolchains and keeps Rust up-to-date.
Proposal
I'd propose we add an official Swift toolchain manager like rustup
. Let's call it swiftup
(probably not what we'd actually call it, but as a placeholder for now). Like rustup
, downloading swiftup
this would be the first step for any OS. It could be by running a curl command like Rust, or via a package manager (Homebrew, etc.). Doing so would automatically download the latest Swift toolchain. swiftup
would also let you download/install alternative toolchains, keep Swift updated, allow toolchain switching (globally and per project), etc.
We actually already have a Swift tool that does most of this: swiftenv
(swiftenv Homepage). swiftenv
is great, but would be even better as an official part of Swift.
Many Mac users already get Swift by default with Xcode. While this would still appear to happen with swiftup
, Xcode would no longer bundle a Swift toolchain. Instead, Xcode would ensure swiftup
was installed and then use it to download/manage the preferred toolchain (downloading it to /Library/Developer/Toolchains vs. inside the Xcode package). Unlike today, setting your toolchain from within Xcode and from the command line would do the exact same thing. This would be a more unified approach, not just across platforms, but also on Mac.
Package registry
Rust: Rust has the cargo
tool and the crates.io as a package registry.
Proposal
I know this one is already in the works for Swift, but still worth calling out. Having an official registry to search, install from and publish to right from the swift package
command will be a big win. One thought: perhaps we could come up with a name to make it a bit less verbose than swift package
... something like spm
that would server as a "type alias" for swift package
.
Documentation
Rust: Rust has a rustdoc
tool to generate HTML documentation.
Proposal
Something like this would be a big win for Swift. Similar to Rust, this would pull markdown formatting from comments to generate HTML documentation.
Benchmarking
Rust: Rust has command-line benchmarking tools built in.
Proposal
Swift can do this in Xcode, but it might be a good addition to be able to do from command line as well.
Testing
Rust: There really isn't anything specific to call out about Rust testing. This one is just about Swift and XCTest
.
Proposal
While XCTest
is a perfectly acceptable testing tool, it doesn't feel particularly "Swifty" or expressive... it feels like a bit of a carry-over from Objective-C days. It's fine, just not cohesive with the rest of the Swift experience. I think Swift is due for a more expressive default testing package. There is already a great example out there called Spectre: (GitHub). It's very expressive and makes writing tests feel more like writing Swift. Again, great, but would be even better if it was the default.
Conclusion
So, all in all, Swift is the best language out there. But, there are a lot of developers who don't know that because they aren't iOS/Mac developers. I'd propose we start thinking a bit about the experience of the Swift ecosystemoutside of that iOS/Mac developer community and make Swift's ecosystem as cohesive and friendly as Rust.