Software Craftsmanship North America is an annual conference bringing together software craftsmen—developers who are interested in improving their own ability to program. In his opening remarks at SCNA 2012, 8th Light’s co-founder, Micah Martin described the conference as the “yearly attitude adjustment” for software craftsmen.
The speakers covered topics ranging from professional and product development, to engineering practices like testing and architecture, to theoretical CS concepts like monoids and logic programming. I have a complete-ish set of notes on my Flickr but here are some highlights.
Cory Foy talked about a model for teaching programmers (slides) that starts with work that has low context and low cognitive demand (such as katas, koans) and brings them up to doing work with high context, high cognitive demand (such as adding features and listening to code). This mirrors closely the 8th Light apprenticeship model. He also talked about how we need to learn to listen to the code and not try to force it to do things that it is not suited for; to listen requires understanding, to understand requires practice, and to practice requires context.
There were several discussions about apprenticeship. My sense is that 3 months is enough time to train people in basic craftsmanship suitable for basic web development (the equivalent of a semester, so maybe 4 courses worth). It obviously isn’t the ten thousand hours necessary to produce a master. The successes described also suggests that apprenticeship is not necessarily good at producing developers that can be hired for other companies. Of the 20 or so apprentices trained by apprentice.io (a program at Thoughtbot to try to commercialize apprenticeships), only one has been actually placed in an external company despite over a hundred companies interested in hiring out of the apprentice pool. On the other hand, they’ve hired about eight themselves. 8th Light has similarly grown much of its current 20+ craftsmen through its internal apprenticeship program.
8th Light has shared their internal syllabus for training craftsmen. Thoughtbot, the team behind apprentice.io, has also produced a set of basic trailmaps for learning basic techniques that the community can contribute to on GitHub.
I’m curious about adopting a more formal apprenticeship/mentoring program at places not primarily doing web app development, and in particular at systems-y companies like Hadapt (where time and money is limited) and VMware (where there is both more existing training, and where resources are less scarce). Certainly, some of the basic skills and culture do need to be acquired, but so does the knowledge necessary to build a distributed query execution engine or a shadow page table walker.
Uncle Bob’s talk (video/summary) spoke more broadly. He argued that we need to behave professionally because, one day, some software glitch will result in lots of deaths (think Therac-25) and the world will demand an answer from the tech industry. If we don’t want government regulation, we better behave professionally. As Uncle Bob put it, to be professional means that we do not ship shit. That we say no. That we work as a team. And that we learn continuously: Uncle Bob proposed upwards of 20 hours a week on our own.
There were many talks about aspects of testing. Michael Feathers gave a talk that sort of questioned some of ones assumptions about testing by focusing on the value delivered by tests. He talked about, for example, deleting tests—if they no longer provide value. Value of tests can come from many places: guiding the design of objects, detecting changes in behavior, acting as documentation, guiding acceptance criteria. The value of a test can change over time and we should not over-venerate any specific test. He argued that it is more appropriate to set a time budget for testing.
Gary Bernhardt gave a beautiful talk about mixing functional programming and object oriented programming. He noted that mocks and stubs cause tests to become isolated from reality but that purely functional code does not require mocking: it always behaves the same way given the same inputs. Thus, he argued that code should be structured to have a functional core surrounded by a more imperative/OO shell that sequences the results with actions, a style he called “Faux-O”. By focusing on providing values (functional results), we free the computation from the execution model (for example, how Java Callable’s can be plugged into a variety of ExecutorServices).
Justin Searls took a different tack to testing, bridging Michael and Gary’s talks in a sense. His big picture observation is that different kinds of testing deliver different amounts of reality and we should choose tests that give us the amount of reality we need. (He has a nice taxonomy of tests on his blog.) One takeaway from his talk is that we should adopt a standard for what kind of testing we do and stick to it: he liked the GOOS style of using isolation tests to guide design and more end-to-end acceptance tests to prove functionality, but listed a few others.
Drilling down into more specific tools/techniques, Brian Marick gave a talk about generating data for tests using logic programming, using an example in Clojure. His goal was to ensure that he only says as much about the data used for a test as is absolutely necessary for the test and to allow other aspects of that data to vary; this can be achieved by writing a logic program to state the test’s requirements and allowing the runtime to solve for the right data. In fact, you could imagine automatically testing all valid values that the logic program generated, instead of just one (much like Guava’s Collections test suite builder does more imperatively). We have explored this idea for system-level testing at both VMware and Hadapt, where it would be useful for tests to declare their dependencies on the system (e.g., requires a system configured in a particular way) and have the test framework automatically satisfy those dependencies in some way that the test does not care about. Logic programming would provide a way to bind the resulting dependencies to variables that could be used by the test.
Susan Potter gave a talk about monoids at a very theoretical level, but they have a practical impact on code expressiveness. A nice way to understand monoids is to see how monoids apply to FizzBuzz. At a more systems level, monoids are used by Twitter in their services stack to compose asynchronous results. As we develop tools at Hadapt for provisioning systems or manipulating internal plan trees, I expect to apply monoids to help ensure composable abstractions.
The last talk of the conference was by Leon Gersing and was a great motivational talk about personal development. You should watch it.
The talks were only half the time at SCNA. Networking with other developers made up the rest, as well as being intermixed with fun activities like kata battles (wherein two developers race to complete a basic coding kata live on screen in front of the audience) and Jeopardy. There was also a re-factoring kata fishbowl where I narrowly missed an opportunity to pair with Uncle Bob. While I got a lot of value from the talks, I wished there had been more time for pairing and working on code with the other developers there. On the last day, I got a tutorial from Randy Coulman, who has been programming in SmallTalk for 10 years, as he did the coin changer kata in SmallTalk. More explicit time for that sort of impromptu practice (not just chatting about work) would have made the conference even better.
Overall, SCNA was a great conference and I hope to be able to spend more time with software craftsmen in the future.