Swift development realities

Swift 3 is going to break your code. It’s a given. It was a given when the Swift team presented swift.org, opened the Swift evolution repo and mailing list, and allowed an early peek into already accepted proposals. If you’re not living in beta land, you will see it when 2.2 starts to warn what 3.x will break.

It’s a given when you see how Swift is reworking the way it interfaces with Foundation and adopting new guidelines for translating Objective-C APIs. It’s a given when there are still active and lively discussions about how the error system will evolve, how the standard library is going to change, and what default inheritance rules should be.

With this reality, you can choose one of the following approaches:

  1. Avoid Swift. C and Objective-C and their C++, web, and cross-platform friends can still help you build and sell product.
  2. Cautiously test the Swift waters but delay full adoption.
  3. Embrace Swift and fight to maintain the language’s immediate integrity for production code.
  4. Embrace Swift and try to get as much pottery broken and re-geared in the 3 update to ensure that the 4 update and later involve relatively minor changes, adding features instead of breaking them.

I vote for option 4.

All changes are costly but large early changes are ultimately less expensive than slow yearly language updates. That’s not to say that changes aren’t traumatic or expensive, regardless of when they happen. They are.

Imagining that all the important changes can be adopted at once is a fantasy. But the sooner the language approaches stability, the more both the developer community and your customers will benefit. You can complain from the sidelines or get involved in setting the direction.

You can’t properly develop in Swift without preparing for refactors. The two core realities of adopting Swift right now are writing tests and documenting the hell out of everything[1]. Allocating time and building tests and comments are part and parcel of getting ready for the next big flood.

The flood is gonna happen. Will you be there?

[1] If the tests work, great. If not, your comments address the “what was I thinking when I wrote this” bit that moves beyond “self documenting code” and “obvious method names”


  • Excellent! I vote for option 4 as well.

  • Erica, firstly thank you for having the presence of mind to understand the need to openly discuss “Swift development realities”.

    To get right to the points:

    1) If the authors of Swift are going to break something in an upgrade, then please provide a clear and un-ambiguous example(s) of how to code the “new” Swift.

    What Swift developer has not spent countess hours searching on the web and downloading examples
    trying to “please” the Swift compiler because something that used to work in Swift now is deprecated
    or just won’t compile anymore.

    And the Xcode help/documentation is of no real help, because it has not been annotated regarding the change to Swift.

    Let’s not so quickly forget – Swift (and Objective-C) stand on the shoulders of Cocoa, the real workhorse.
    Many of the iOS API are coded is C/C++, and they may never be re-written, so Swift should play nice
    with the API layer.

    The amount and quality of the examples/documentation available regarding coding in Swift and Objective-C
    (using both languages together/separately on a daily basis in the real-world to do real work) is lacking/lackluster.

    2) iOS Developers no longer have a choice, or are being asked to make recommendation of when should to jump/switch to Swift.

    — hmmm. I can code this is Objective-C in a few hours, but if I do it in Swift, i might get caught up in some of it’s compiler “shenanigans”
    and figuring out how too make sometimes even simple stuff work, and loose a few days (and make me look bad at my job,
    because Apple says “it easy” on their website and managers believe that).

    I think sometimes there is over-engineering in Swift (coding the 10-20% case) , and it looses it “general” programming capability,
    for the sake of being “evolutionary”.

    come on don’t take away my –, ++. i love those operators. there. I said it!

    I don’t need/expect the compiler to solve programming tasks for me that have well-known programming patterns,
    and if it does allow some “avant garde, clever, powerful” way of accomplishing said programming task,
    don’t do so at the sake of breaking/abandoning a standard way of doing things in compiled languages for the last 50 years.

    3) Suggestion: Has anyone considered a ANSI-C compatible switch? maybe at the module level.

    • Well, I completely disagree with your statements. Directly to your points:

      1. I’ve upgraded projects from Swift 1.0 to 1.2 to 2.0 and 2.1. Only for the last one (2.0 -> 2.1) I did use the aid of the updater. It takes me around 20 minutes per 1000 lines of code and is pretty much straight-forward. Updates generally cannot introduce bugs.

      2. I actually love the stability Swift brings to projects. I’ve been doing serious development (projects above 50,000-100,000 lines of code) in C, C#, C++, JavaScript, Objective-C. And in the teams I’ve been, I am the one who cleans up shit after all kinds of senior and junior “expert developers” finish their tasks.

      From my point of view I can tell you Swift is magic! Since version 1.2 the benefits far outweigh any “compiler shenanigans” slowdowns. Common null references, non-initialized memory just vanishes. Circular references are way easier to find.

      I’ve spent weeks searching for memory leaks in WPF/C# code. A single debug session spanning multiple days, if you can imagine. I do have similar stories with C++ and all kinds of smart pointers, by the way. In this respect Objective-C is no better.

      I also like the — and ++ operators, but I won’t shed a tear when they are gone.

      Compiler warnings and error messages need to be seriously improved, I can’t argue with that. But that doesn’t mean the language is at fault.

      3. ANSI-C switch? Are you kidding? There is nothing a Swift switch-case cannot accomplish that ANSI-C switch can. But it is way safer as it does not automatically fall through multiple cases just because somebody forgot to put a “break” statement.

      I’ve seen far more bugs coming from a forgotten break statement than the number of instances where a fall through is actually the correct behavior. Oh, and I’ve seen bugs introduced during code reviews by adding “break” statements where the code needs to actually fall through.

      So, the Swift approach of breaking by default and requiring an explicit “fallthrough” statement is the ONLY sane approach. It is unambiguous and shows intent.

  • 3.0 is when most languages achieve stability. This is a great argument if you work for a startup, a bad one if you work for a large corporation and have a lot of code. Let me be blunt: the language needs to stop changing, other than tiny little increments and framework add ons. If Apple wants it to be taken seriously, start acting like grownups with responsibilities instead of a bunch of excited kids taking acid. Right now it’s a laboratory, and I don’t build my apps in a laboratory.

    • I totally disagree that Swift the languages needs to stabilize much at all, the improvements that have come from the language enhancements have far outweighed the minimal cost so far (a few hours for each new version of Swift after running the updater) of adapting code to new updates. I say that as someone working on enterprise apps for a medium sized company… and has been working for small to huge companies for over two decades now.

      For too long the computer world has been ruled by an irrational fear of change, which has ossified too many development teams and led to rigid thinking and inflexible development. The language evolving gives the developers the kick they need to learn new ideas over time and prevents them from falling into a mental ditch where nothing new is ever done.

      If you want to talk about grownups, they are the ones who have to learn to adapt to a changing world quickly rather than playing in a sandbox with toy that never alter through the years.

    • No, they have to make the breaking changes now. There will be no chance to fix mistakes later. Right now everybody knows Swift is new and changing a lot. Apple has communicated this clearly and people simply have to plan for it. Swift isn’t old enough for people to have huge Swift code bases yet. But at Swift 6.0 there will be too much Swift code out there to make even tiny changes. They got to get stuff right now. Otherwise we end up like Java and pay for design mistakes for years to come. Or we end up like Python 3. A major change coming too late, when there was too much Python 2 code around to upgrade.

      I think with Swift 3.0 they should have fixed 99.99% of all issues developers have had with Swift, except the story on concurrency. But I suspect if C# was able to add a nice concurrency system years later Swift should be capable as well. Whether it is actually nice or not I don’t know but given how C# developers rave about it I assume it must be really nice.

  • I’ve been working in Swift in a production (enterprise) app pretty much since the release of Swift… yes we’ve had to change some code, but overall the migration time has been very little even as the language has gone through some big changes.

    One of the things we did do though is be somewhat careful about using more esoteric features, letting them bake fully as it were before adopting them (that said we started using guard and try almost after they came out).

    Even with the potential for some refactoring from Swift updates I think at this point you would be a lot better off on a new project starting with swift, or in an existing project figuring out who to include Swift for some parts of the app going forward.