The Word Counter is my biggest software project so far, and it’s growing. To add features, I discovered the use of Swift modules with joy. I can write code for all levels of the new feature in isolation in a new project that compiles fast. Later I plug the resulting project and module into the Word Counter, et voilà: feature finished.
The Builder design pattern is often overlooked, I find. Apart from plain builders, in Ruby I found that some us it like a configurator. You can use a configuration object in Swift in the for of block parameters, for example: This would make the internals of ComplexThing configuratable through the block. Instead of messing around with an instance of a ComplexThing, you can do atuff with the configurator which determines how the instance will look.
I got angry at NSOpenPanel the other day for visually blocking NSAlerts, and for staying in the way when the debugger hits a breakpoint. Silly me, I used ye olde runModal. When you use the block-based API of NSSavePanel or its decendant NSOpenPanel, all of a sudden they will display on top, but only per application. Also, alerts seem to have a higher display level in these cases.
East-Oriented programming can, for example, be implemented through delegates or callback blocks. “East” is all about Tell, Don’t Ask: don’t query for values; instead, pass a handler around so the flow of information doesn’t return to your current scope.
A repository pattern is used to model a central place in your domain to fetch model instances. It usually hides database-related stuff behind a collection-like interface. You don’t have to worry about caching or database query optimization in client code – the concrete repository implementation will handle that.
When you reason about objects in your system and their means of communication, you can differentiate between three messaging flavors according to Mathias Verraes: imperative, interrogatory, and informational messages. Before we can talk about informational messages and their value, let’s recap the other two and see what the difference is, because them calling for being extracted is not easy to spot.
In Swift, there’s no exception handling or throwing. If you can’t use exceptions for control flow like you would in Java, what else are you going to do if you (a) write library code which executes a failing subroutine, and (b) you find unwrapping optionals too cumbersome? I played with the thought of keeping Swift code clean, avoiding the use of optionals, while maintaining their intent to communicate failing operations.