I love throws. I know many people don’t, and I get it. It’s immature, and I’m very impatient for coroutines. Without async/await, throws is a weird little cul-de-sac that you have to constantly lift into Result. (If you’re lifting into (Value?, Error?), just stop it. Stop it. Unless you have the unusual case where both could be non-nil, that’s just wrong.)

I write a lot of Result-based code, and it’s cool and all, and I teach it because it’s an important part of Swift today (and deep down it’s a very beautiful idea). But all those beautiful composition features require closures and closures mean what-kind-of-self-oh-no-weak hell, and frankly I think it’s a mess in Swift and I think it will always be a mess in Swift because Swift will (I’m pretty willing to bet) never be garbage collected, and all those FP composition techniques were designed on a Lisp machine where cyclic garbage collection is like breathing. (I’m not making any argument here for GC. That’s its own can of worms.)

But when you have a whole system that uses throws (and is synchronous, and doesn’t have to interact with anything that doesn’t use throws), I love it. All that weird ?? and guard let that you have all over the place in Optional code evaporate. Low-level things generate errors. High level things handle errors. Mid-level things get to ignore it.

And I’m glad that throws currently is untyped. I love types. I love them so much. And I hope some day Swift has a typed throws for the cases where it’s useful (and there are important cases where it is). But for most of my systems, untyped throws is so much better. So thanks for that.

So anyway, I don’t get to use throws as often as I’d like, because “a little” throws is obnoxious. It’s a pain to convert to-and-from other systems, and it’s annoying to have to create a special Error type for every little thing. You don’t get any of that cost back if you only have one or two methods doing it. But when you have a whole system…yeah, it’s a nice design.

Please coroutines soon. Please.