Interactor is a sweet little gem that you can mix in to the classes implementing your business logic to expose a common interface:
context = MyInteractor.call
Following a conventional ‘service object’ pattern, a class method ‘call’ is defined for you. This returns a ‘context’ object, which we can query like so:
You can think of ‘context’ as representing the life of the interaction – and, as we shall see, the lifespan of an interaction can be greater than that of a single interactor.
As our interactor has no behaviour, this context has had no reason to report a failure. Let’s give it some behaviour by overriding the instance method `call` to cause the interactor to fail if it is given a number that is not even.
context.fail!(error: context.value.to_s + ‘ is not an even number!’) if context.value.odd?
context = MyInteractor.call(value: 3)
context = MyInteractor.call(value: 4)
One thing I’ve learned from playing with interactors so far is that calling on the `context` object all over your class quickly gets confusing. The convention I’ve adopted is to limit access to values on `context` to the `before` hook provided by interactor (alternatively you could override initialize, but using `before` feels a little more interactor-y):
@value = context.value
`Before` is run prior to the instance method `call`.
There’s a second problem with `context`, however, which is that as it is a subclass of OpenStruct you’re open to a lot of NilClass errors throughout your interactor. Misspell ‘value’ when calling `context.value`, for example, and rather than getting an easy-to-fix unknown variable error you’ll get nil silently flowing through your domain layer (in this case blowing up on `odd?`).
There are some extensions out there that provide some quasi-type-safety for your interactors, but a quick way of ensuring that the attributes you need in the `before` block are available is to convert the context to a hash and use fetch to assert the presence of the desired attributes:
attributes = context.to_h
@value = attributes.fetch(:value)
This way, you’ll get a KeyError if a parameter is missing. You can also easily provide a default as the second argument to `fetch`.
Interactors get more interesting when you start chaining them together with `Interactor::Organizer`. An organizer allows you to quickly compose interactors into novel sequences without having to manually wire them together. With an organizer, interactors are threaded through with a single ‘context’ object and the failure of an interactor triggers the ‘rollback’ method on those preceding it.
There are some criticisms of the Interactor gem out there:
The ‘context’ variable is a glorified global variable. The way the interactor gem encourages you to access parameters through the `context` object is potentially open to abuse. I haven’t settled on using the `before` block as a kind of constructor but it seems like some convention such as this would mitigate this danger. Notably Rack uses a very similar pattern to `context`, allowing you to pass a single “env” hash through a stack of Rack middleware.
Failures are silent. Interactor doesn’t catch your errors, so I’m not sure what this criticism is about.
Class names are verbs. Interactor encourages you to follow the service object pattern of encapsulating actions within classes that are named something like CreateUser or GenerateImage. This naming convention doesn’t cleave entirely to Rails’ concept of a resource, and so can be confusing. However, I don’t think this convention was ever supposed to determine the public interface of your domain layer. You could, if you choose, hide all invocations of ‘call’ behind meaningfully named methods defined on your models. So for example, you might have a `user.upgrade_account` method that is in fact implemented with a series of interactors.
Just over four months ago I crash-landed back in England after 3 years abroad. I went straight from the airport to Makers Academy to attend the graduation of the August cohort and, 3 days later, was starting out a junior myself.
The challenges of abruptly ending one life to dive headlong into another have, for me, prompted a period of deep introspection. The reason I mention this is as a note to incoming students: starting out as a struggling novice at something you really want to be good at, and having to deal with all the (mostly self-directed) negativity inevitably arising from that, is a great opportunity to challenge negative thought processes in all areas of your life.*
Or, as Lao Tzu wrote a long time ago:
Always we hope
someone else has the answer,
some other place will be better,
some other time,
it will turn out.
This is it.
No one else has the answer,
no other place will be better,
and it has already turned out.
At the center of your being,
you have the answer:
you know who you are and
you know what you want.
There is no need to run outside
for better seeing,
nor to peer from a window.
Rather abide at the center of your being:
for the more you leave it,
the less you learn.
Search your heart and see
the way to do is to be.
Abide at the center of your being.
Anyway, that’s the past. Happily from next Monday I will be joining the coaching team at Makers! It is a logical move for me, given my background in education, and I am very excited. Makers is a company run by some of the most talented and forward-thinking people I have ever met.
I plan to use this blog to trial some ideas I have about the best ways of coaching students in test driven development so stay tuned if you’re interested in that.
* I recommend John Hargrave’s (free) book Mind Hacking for a techy perspective on how you might go about this.
My time as a student at Makers Academy wrapped up over a week ago now, but I was invited to come back as an “Alumni Helper” and coach the new cohort of juniors. Before Makers I was a teacher, so it’s been a natural and enjoyable reversion to form.
I’ve been thinking recently about the idea of “context switching”. In programming, context switching is when you change from one language to another. This might happen because different projects are best written in different languages, or because you segue from one part of the stack to another.
“Language interference”, the accidental use of syntax or conventions of one language when writing another, makes context switching difficult. In my previous life as a teacher, I taught elementary-age children whose first language was Korean. Their struggle with language interference was constant, commonly manifesting as inappropriate discourse indicators. When pausing for thought, exclaiming, or about to say something, they would often make very Korean sounding utterances.
Just as with bad style, misnaming, or unnecessary complexity, context switching contributes to mental dissonance. It’s jarring to have to jump from one language to another. So programmers generally try to minimize context switching by keeping the language consistent across the stack, or at least organizing blocks of work so as not to be straddling the language-fault-lines in the codebase. Context switching is also talked about as a kind of “design smell” – indicative of code that’s breaking encapsulation.
At the same time, sometimes we have to change languages and so we might call “context switching” a skill, a measure of how readily someone can readjust to working at a different point in the codebase or in a different language.
More broadly, being able to “context switch” from focusing for hours on a few dozen lines of code to scrumming with others in the team is vitally important. Many times over the past few months I have found myself struggling to go back to being my normal sociable self after a long stretch of focus.
At Makers, pair programming helps with keeping the work within a social context. And fortunately there is Dana, the party creator, yogi, guru, therapist, and broad-smiling face of Makers Academy. Through her yoga classes in particular I have learned the discipline of pulling myself out of one frame of mind to be immersed in another.
The final project, weeks 10 and 11 at makers, whipped by. My team was made up of Danielle, Gus, Charlie, India, and myself:
In the past few months Makers have been inviting external clients, usually charities, to pitch ideas at the jamboree in Week 9. Charities were selected this time around too: the Snow Angels group, for example, worked with a Sussex village charity to automate the organization of support for elderly people during times of adverse weather.
My team’s project, though, came from Tom and Amar, two ideators local to Shoreditch. “I Am Me” is born of the frustration of spending Saturday mornings scanning TimeOut and similar sites for suggestions of what to do on the weekend. Though such sites have a lot of content, it’s presented within a cluttered interface and without regard to the particular user’s interests. To boil it down, “I Am Me” is an event discovery website that has the form of a calendar. My team and I had some concerns going into the project: which features could we fulfill on in the two weeks available? Should we stick to the design brief or experiment?
In the end, we turned out a product that we could all be proud of. Users of the site can browse and create events with a visually appealing UI, and we even implemented some event-discovery, albeit of a primitive kind. Our presentation at the graduation event on got a good reaction.
As this post is titled ‘Reflections’, here are my takeaways from the project:
We did a good job of getting it clear in our heads from Day 1 what we were designing and what kind of user it was for. We didn’t think so deeply about the flow of the user’s experience through the site. Storyboards would have helped in this regard.
Use technical language carefully; make sure everyone is on the same page. People have different assumptions about what certain design decisions would entail. It always helps to have people rephrase what they mean, or think they mean.
Never Rails scaffold! Bad Things will ensue.
There were many highlights. I was blessed again with a team of fun and talented people from whom I learned a lot.
The weekend of Feb 21/22 I rather recklessly signed up for a hackerthon called “UN Influx”, which was organized by a charity, the Influx Trust. ‘Reckless’ because I was coming out of a week’s introduction to Ruby on Rails, a web framework, and about to go into the final project of my time at Maker’s.
The problem statement was this: “How can digital innovation help the UN and the public work together more effectively?” Soon after arriving at the venue, a colourful workspace across the road from Tower of London, I met Toby Beresford, who offered to let me use his “gamification platform” for any project I could think of. I pitched an idea that I thought could realistically be built in 48 hours and fortunately, found a great team.
Irina, a designer, was the first one to join the team. She had a lot of ideas about how to present on the front end. She also managed to both attend a hackerthon and move house in one weekend. Remarkable.
There was a moment after the round of pitching on the Friday, when “ideas” people (who I had somehow become) were supposed to gather a team, when I was about to give up. Then Sandra, frontend developer, offered to do the frontend and ended up doing so some technology (Meteor) she hadn’t used before. She’s also travelled to over 40 countries and introduced me to BDD (“beer driven development”).
Ozo, a programmer originating from Nigeria, doubled as architect and visionary. He very generously agreed to using my language of choice, node.js, above any he is familiar with and also put more thought than anyone else over the weekend into what we were building, why we were building it, who it as for, and how we should pitch it.
Our project, UN Frontliners, a platform for volunteers to tell their stories of working in the field, was given the “hearts” prize by a panel of judged which included a former UN Deputy Secretary General. Thanks to my team and some of the amazing mentors in attendance, I learned a lot at the UN Influx hackerthon and had a great experience. UN Influx are planning to hold another in Autumn and I recommend attending to any fellow junior devs out there.
It began with a talk by Charles Davies, CTO of TomTom, who condensed some of his immense experience in the tech sector into manageable drops of wisdom: read a lot, keep it simple, and hire the best even if you can’t afford them. TomTom’s revenue runs close to a billion euros, but they question was still put to him: Why buy the kind of navigation utility that TomTom sell when a modern smartphone can do all the same things and more?
His answer touched on a key concept of this week: user stories. User stories are 3-line narratives used by developers to evaluate whether a proposed feature is worth the time required to implement it. I’ll come back to them in a moment.
Time was precious this week as it was the week of the Makerthon. The Makerthon is a mini-team-based project, a practice run for the final projects. My team’s project, dreamed up by the very talented Jacob Mitchinson, was to create a bot that sits in the Makers Academy slack channel (slack is a messaging program we use to communicate) and answers students’ questions about lecture times, talks, course material, etc., basically anything we could implement in time.
So a real user story from our project was: As a student at Makers, when there is a lunchtime talk, I want to be reminded of it in advance. User stories might seem so short as to be trivial, but their importance is in being public narratives around which to discuss whether a proposed feature satisfied a real need. They’re a working hypothesis rather than a panacea for the problem of making something people want.
The Makerbot ended up doing a lot of things we hadn’t originally planned: it can tell you knock knock jokes, where to go for lunch in Shoreditch , and even the answer to “What is the average flight velocity of an unladen swallow?”. Massive thanks to my team: Jin, Danielle, Clint, and Jacob for making the week so much fun.
Imagine a teacher wants to test his students’ math ability. He gets them to stand in a line and he starts at the top, asking the first student: “What is 8 * 9?” The student replies with the correct answer almost immediately and can sit down. Things are going well. Except the teacher now asks a really difficult question to the next student and she has think for a whole minute. Meanwhile, all remaining students are idly waiting in line. Eventually the teacher gets to the end of the line, but the math test took up the whole class.
This is how blocking processes work.
A different teacher conducts her math tests like this: She lines up the students, quickly moves down the line giving each a card with the problem to be solved, and she then stands by the whiteboard ready to write down their answers. The students are now working on their problems simultaneously and nobody is idle.
This seems like a very fast and effective way of conducting a math test and things are going well. Except these students, though brilliant at math, have zero common sense (much like computer programs). They solve their problems but then don’t know to report their answers to the teacher. Fortunately, the teacher foresaw this and wrote what to do on the back of the card. After completing their problems, the students turn over their cards and follow the instructions to move to the board and tell the teacher the answer. In programming this secondary instruction is called a “callback”.
Though this “non-blocking” style is a little more complicated than the previous “blocking” style, the math test has been completed in a fraction of the time and the class can get on with doing something else. Great, right? No wonder Twitter switched over from Ruby, a blocking language, to Node, non-blocking.
Okay this time, imagine a slightly different scenario. The class is studying Japanese and wants to learn the language for days of the week. The teacher, however, doesn’t speak Japanese and so instructs the students to look up the words in their dictionaries. To speed up the process, she delegates each day, Monday through Sunday, to a different student. Their secondary, “callback”, instruction is to move to the board and report the answer to the teacher.
Here we hit a snag: some students are faster with the dictionary than others. In fact, the student looking up “Friday” returns to the board first and his answers gets written down first. In the end the class has a list of seven Japanese words but no idea which of the days of the week each corresponds to. Clearly the “callback” instruction to the students was inadequate: they should, perhaps, have been told to report the English word given to them along with the Japanese translation.
I hope this elaborate metaphor has given you some insight into the relative merits of blocking and non-blocking processes. =)
Congratulations to the October cohort of makers! They graduated and presented on their final projects last Friday. Some teams had decided to run with ideas pitched at them by charities. There was Oodles, a service for connecting people with surplus food to charities that need surplus food to distribute, and Lookup, an app that allows you to assess roofs for potential yield of solar energy.
Lightbox is a secure messaging service for doctors to communicate patient data and discuss. Lastly, Hipspot uses twitter location data as a proxy for the popularity of restaurants, bars, nightclubs, etc.
Given the December cohort and I will be starting our final projects in a couple of weeks, it was a very inspirational, albeit a little intimidating, performance.
I caught some conversation from the many scrum-meetings that went into developing these projects and was impressed by all groups attention to process. Good process, so I have learned, is about writing clear user-stories, getting thorough test coverage, and adhering to best practices in naming and style conventions. This may sound boring compared to slapping together a feature-rich app. My hunch is there’s art and discipline in good process and if you do it right it makes the whole thing much more fun. We’ll see.
One highlight of the past week was a talk by Paul Carke, CTO of Ocado. It turns out that Ocado is not an online supermarket as many of have been led to believe, but is firstly and at heart a technology company. Paul Carke illustrated this point with a couple of incredible infographics, the first a virtual-lightshow of neon-coloured units, presumably representing individual customer orders, tracking back and forth along kilometers of conveyor belt in a warehouse. The second showed delivery routes unspooling from distribution centers across England. These two representations alone were extremely impressive (though I did notice that Norfolk and Cornwall were completely dark) and attest to the rapid pace at which Ocado is unsettling the grocery market with automation.
Lunchtime talks are the jet propellant of Makers. Usually there are phrases and acronyms that are over my head, but it’s motivational to be exposed to these vast areas of unknown technology, many still in the process of being hashed out.
Week 4 at Makers! You can see in this photograph that Ana the MA marketing wizard snapped of me, screens are a big deal. I took advantage of having two, plugging both into my Macbook for extra acreage. It’s useful now we’re quickly moving from working with a single page of code to a whole suite of controllers, models, feature tests, and an involved directory structure.
An interesting subject that came up this week in my conversations at Makers was pain in the learning process. Nobody likes to be in pain, even if it’s just the mental kind that you get when trying to fix an error you’ve never encountered before, yet it seems to be inescapable when getting to grips with something difficult and new.
It’s a controversial topic. Occasionally this week myself and many among the December cohort have felt out of depth, floundering in the unknown, and it seems to be a coach putting us in this position. “Aren’t they supposed to help you?” I hear you ask. Indeed, one reaction to this is to blame the coach for not fully explaining whatever the source of the frustration is. Another approach, which a lot of coders believe in, is to take pain as a sign (a sort of “code smell”, in the lingo) that your going about things the wrong way.
Though it’s true that if you’re fully driving your development with tests, making only incremental and necessary additions, and following all the SOLID, RESTful, (there are a lot of acronyms for good coding practices) decisions, frustration should be kept to a minimum. Stay zen! Factor out your emotions! These phrases are used a lot.
Even if it were so easy, is that really what we want? One coach, a graduate of Makers, made the point to me this past week though that if students don’t test the limits of their mental endurance while at Makers, they never will. At Makers we get to make mistakes, break things, get out of our depth, without really having to worry about the consequences.
Perhaps there are hidden dangers to playing it safe. I heard a story recently about Daniel Kish, President of World Access for the Blind, a man who has taught at least 500 children (as well as himself) to echolocate. In the anecdote, he persuades a blind boy who typically relies on other people for mobility to climb a tree. The boy hates it but Daniel keeps working on him, taking away the option of coming back down. Eventually the boy learns to climb trees and a great deal else too, but not without some pain along the way.
Alright enough musings, on to Fun Friday! Friday was fun for three main reasons:
1) My team and I won the first CodeJam. A coach organised “CodeJam”, a kind of rapid coding competition. Four teams of four had 15 minutes to solve code ‘katas’ – short problems designed to be repeated again and again for fluency. The time limit made it intense and we had some communication issues on the first problem which meant we didn’t quite get a solution in time.. but fortunately neither had any of the other teams. The second round we communicated a bit better and almost aced it, which was enough to go 2 for 0. No prize but lots of bragging rights, were that my style.
2) I presented at the first Makers Pecha Kucha of 2015. At 5pm Steve, a teacher at Makers, held a Pecha Kucha. My favourite presentation was by Canadian and fellow student Danielle, who introduced us to her far-flung hometown that I forget the name of. Mine was about Jeju-do, a beautiful island province of South Korea, and my residence until very recently. It was a great experience, though I felt that it was people already confident in public speaking who got up. Hopefully next time there will be more of a mix.
3) It was Friday!