Pair programming is not a new concept. But there are still tons of teams out there who either don’t practice it or are making a few mistakes while doing it, preventing them from cashing in on the benefits.
I have a ton of experience with both pair and mob programming so I wanted to share my thoughts and experiences, and hopefully help other people avoid some common mistakes I’ve seen a lot.
First, let me explain my background. For almost 3 years now I’ve been working at a Vehikl, a software consultancy that specializes in web application development usually using Laravel, a robust and extremely popular PHP framework.
I’ve practiced pair and mob programming before coming to Vehikl but since being here, I’ve done a ton of pairing with not only our own internal staff, but with our clients too. I’ve also done a ton of mobbing with mobs from 3 people all the way up to almost 20. I’ve mobbed and paired on client work or “real world” work, internal projects, as well as plenty of code katas or just random deep dives into new technologies for the sake of learning.
So in the past few years I’ve tried a lot of different approaches for structuring these collaborative sessions and I’ve seen a lot of things not work out too well. I’ve also seen a lot of developers who push back on the concept, and have even gone through periods where I’ve questioned the benefits too. But I’m certain that with the right mindset, understanding and skills that any team can use both pair and mob programming to win some serious long term awards.
Before we look at the hows and the whats lets make sure we’re all on the same page.
Pair programming is really just when two developers work together on delivering a feature. The idea being, that two brains and two sets of eyes is more productive. But there’s a bit more to it, and there are a lot of nuances.
Usually pair programming is thought of as two developers sitting at the same keyboard but this doesn’t always have to be the case. If you’re working remotely this definitely won’t be case!
There are also two categories of pairing that I see happen: structured and un-structured. The latter being the one I see practiced most often when the team hasn’t had any training or been shown what structured pairing looks like.
Unstructured pairing is when you have two developers working on the same task, remotely or at the same keyboard or whatever. And there aren’t any rules to it other than they’re working together. It can be a great way to knowledge share, avoid silos, increase productivity on the team in the long run and increase team cohesiveness.
It also has its problems which I’ll get into later.
Same basic premise in that two developers are working on the same task only now you add some rules. Specifically a timer. Traditionally each developer is assigned a role, either navigator or driver. Every n minutes they switch roles. How long you set the timer depends on a number of factors, but 5, 10 and 15 are pretty popular at Vehikl.
The simplest rule is that the person navigating chooses the high level intentions for the current rotation. So if the timer is set to 5 minutes, the navigator’s job is to set a high level intention to complete something that is achievable in 5 minutes.
The driver works like a smart input/output system. Meaning they run with the high level intention as far as they can and ask for help, or explanation as they need it.
Which segways into my first mistake I see. Either not understanding how structured pairing works, or not sticking to the guidelines and letting dismantle into an unstructured session.
But first lets explore how to do structured pairing and what tools you can use.
First you have a timer. Lets say it’s set to 5 minutes. Each time the timer goes off you and the person your pairing with switches roles. The roles are “navigator” and “driver”. Before you can practice structured pairing you have to understand how these roles work.
The analogy is that if I were to drive from my house to yours, but I’ve never been, I’ll need you to navigate me. You might start with a fairly high level direction like, “head to the freeway”. I don’t need you to tell me how to turn my car on, or how to back out of my driveway. I also know how to get to the freeway so I don’t need you to explain every turn required to get there.
As we come closer you might need to tell me which onramp to get on. You might say “get on the eastbound lane, and then stay on the freeway for 20 minutes”. I don’t need any more than that. I know how to merge onto a freeway, and I know how to switch lanes, pass cars etc…
What I might need from you is to know which exit to take. So as we get closer to the exit you say, “work your way over to the right lane now, the exit is coming up soon, you want 215”. Again, you don’t need to tell me how to merge lanes and take an exit, but once I take the exit I’m going to start asking for more detailed directions until we show up to your house.
This is essentially what structured pairing should feel like. The navigator states a high level intention like “my high level intention is to write a test for our users controller”. The driver then follows through and does as much as she can do without the navigators assistance.
If the driver has questions about the code base or anything, then the navigator answers. If the navigator notices the driver did something he didn’t mean for her to do, then he says something. The important thing is that the navigator only gets as detailed as the driver needs.
If the navigator notices the driver used their mouse to do something but knows of a keyboard shortcut it’s totally cool to say something. Just try not to fall for the trap of dictating every keystroke — unless the driver asks for it of course.
Once the timer is up you just switch roles. The new navigator states her high level intention, and the new driver proceeds as best as they can without help, asking for questions and feedback along the way.
You should make sure you have a predefined time to stop the session. Whatever that time is, stop 5 minutes early. If you scheduled one hour of pairing, stop at 55 minutes. Take 5 minutes to do a mini retrospective. How did it go? What went well? What didn’t? What can be improved next time? That kinda thing. Practicing this will help ensure that the pairing process is continually improved and reevaluated.
This is where pairing can get more nuanced.
One way to pair is you share the same physical computer. Obviously this only works if you’re in the same office. This also only works out ok if you both use the same OS, IDE, DBMS, key bindings, have the same CLI tools etc. And for some companies this will be true, because developers are forced to use the same tools.
I definitely understand the merritt of being unified on tools. However I think it prevents creativity and innovation. Developers might become super proficient at the tools they’re forced to use, but they’re also less likely to experiment with other tools meaning the team stagnates.
Lots of companies allow developers to choose the tools they use. So you might not be using the same IDE as the person you’re pairing with. This makes pairing on the same machine pretty challenging.
Use your own computers. To do this you just push your changes to your central repository when you’re done driving. When you switch back to the driver seat you pull the latest changes down.
This is my preferred way to both pair and mob. It works well both remotely and in the office plus you don’t run into people stumbling on machines they’re not comfortable with. Which also helps reduce performance anxiety.
- Cloud IDE’s or Liveshare. VS Code’s Liveshare option works really well. It allows one developer to run and host the project while others can remote in and edit the code simultaneously. This can also work great remotely too. I find this option more useful during a mob session but it can it work out ok while pairing too.
- Remote desktop. Vehikl uses a tool called AnyDesk which allows developers to remote into Mac’s running at our office. Because of the corona virus we’re all remote these days so most teams are opting for the AnyDesk solution. You run into similar problems stated in option 1.
Whatever you decide to use is just preference. I’ve used all four options for both pairing and mobbing and they can all work. My preference just happens to be option 2. But you should experiment and see what works for you and your team.
How long each rotation lasts is just up to you and the people you pair with. 5 minutes is pretty common especially when you’re just starting out. It’s good to just get into the practice of switching roles. Once you get good at it, I find I like to work in 10 and sometimes even 15 minute rotations but everyone is different.
A great tool you can use for tracking your pair programming sessions by the way is https://mobti.me. It’s intended for mob programming, but a two person mob is just pair programming so it still works for that too!
Ok so we know what it is, and how to do it, but what are some of the mistakes and pitfalls?
Lets focus on not practicing structured pairing at all, and then we’ll look at how it’s sometimes practiced but just poorly.
Like I mentioned earlier, unstructured pairing can be a great tool. But it does come with some problems. The first is that the person at the keyboard tends to end up doing most of the thinking. It’s usually not intentional either. It’s just how our brains work. It’s a lot harder to follow along and keep engaged with something when you’re not the one who has to take physical action.
Have you ever been the passenger in a car while a friend drives you to a place you’ve never been before? How likely are you able to make that same trip without GPS on your own? Most people have a hard time remembering directions as a passenger. But if you’re the one to actually drive to that new place, and your friend navigates you there, you’re far more likely to remember the directions. You’re also far more likely to pay attention to the road the entire time (at least ideally).
Programming is the same. If you’re just sitting there watching someone else code, your attention kind of ebs in and out. You only really become engaged when they actually need your help. Like maybe they’re debugging something and they need your eyes. Or they don’t know whether to do one approach or another, or they’re unsure how to proceed with the current feature.
If there’s no immediate need for your attention it tends to wander and it’s easy to just sort of sit there on auto-pilot nodding and agreeing even though you’re not totally present in the moment.
This is bad.
If you want to collect dividends on your investment in pairing you need to be focusing on the benefits which are:
- Realtime feedback and review on the code and the design.
- Fewer blockers. If one developer is stuck usually the other can figure it out.
- Knowledge transfer.
As soon as one developer checks out (unintentionally remember), then you’re not getting any of those three benefits. They’re just gone. Which means you now essentially have two developers doing what one could have done. So you’ve doubled the cost of your software development — awesome! (not awesome…)
Unstructured definitely has its place. Sometimes it’s just too stressful or tiring to constantly worry about the timer. Like if both developers don’t really know what they’re doing and they’re more in a research phase, reading docs, experimenting with API’s etc…
But it’s important to remember that during your pairing sessions you really need to be working as a team to make sure they’re structured most of the time.
Now that a team understands how to do structured pairing the next mistake I see happen is they tend to let the structure slip and fall back into unstructured pairing.
It’s pretty easy to let this happen; structured pairing is hard at first!
The first reason I see that this happens is the pair is unsure of the direction they want to go. The timer starts to feel like it’s in the way and becomes a nuisance so they ignore it or shut it off. This is actually an ok reason to pause the timer.
Pausing the timer but never turning it back on
Sometimes you just need to read documentation, or you just want to figure out why something isn’t behaving the way you expected it to. You’re both just too invested in solving the problem at hand to bother switching and that’s ok.
The problem is if once you fix the problem you were stuck on, you don’t go back to the timer and fire it back up. Because now you’re not just taking a break from it, you’re actively not practicing a structured session anymore.
The other more problematic reason I see is when one developer is more experienced than the other, or just has more domain knowledge of the specific feature.
Allowing one person to navigate too much
The one with less knowledge tends to have to ask a lot more questions and needs more detailed instructions when they’re sitting in the driver seat. Once the more experienced one is driving, they tend to just crush through everything they already know needs to be done, but the navigator doesn’t have much to say because she doesn’t really know what needs to be done.
This can be challenging because on one hand you want to get the task completed in a reasonable amount of time. Both the less experienced and the more experienced dev tend to see that things move faster if the more experienced one just does the work.
On the other hand, you’re not practicing knowledge sharing. Remember pairing is a long term investment. If you want to see the compounds you need to slow down when this imbalance happens. The more knowledgeable developer needs to make sure that she’s helping the other get up to her level. If she just bulldozes a path and carries the task to completion mostly on her own, the other developer won’t get up to speed as quickly. It just means those pairing sessions take longer to pay off.
One side effect of pairing, especially if it’s structured is that it forces both developers to be extremely engaged in the work. After a while the intensity can be exhausting but the intensity also makes time fly by. If you’re planning on pairing for longer than an hour, make sure you schedule short 5-10 minute breaks.
Without them, people tend to just go go go until all of a sudden they’re out of gas and their brain is just completely done for they day. You’ve got to control that burn man. You and your partner don’t want to be burnt out with 3 hours left in the work day.
Even if you can go like that for an entire day, and lots of people can, by the second or third straight in a row, you’re suddenly burning out hard. And next thing you know you’re abandoning the structured pairing because you’re both too damn tired to do it, so you throw your headphones on for the day and next thing you know it’s been two weeks since you last paired.
So please. Take. Breaks.
Note: If you’re just getting started with pair programming the following section may seem like a lot to take in and maybe even discouraging. Just know that these things don’t necessarily make or break the practice. They’re usually more subtle and over the long run you can iteratively improve on. These topics are also always present whether you pair program or not, it’s just that pairing can make them seem more a little more obvious.
This is the hardest part about pair programming. People are complicated, and rounding them up into a group, calling them a team and having them deliver software is hard. People have differences in personalities, communication patterns, learning preferences and even social and systemic inequalities. People perform differently under pressure, or in front of people they aspire to be. They struggle to explain themselves and they struggle to understand others. There are just so many reasons why pairing can go very wrong when one or more people don’t understand each others differences.
We don’t all have to become psychologists to become more aware of these things and sometimes just acknowledging that they are there is enough to make a big impact.
Here are just a few things you have to consider when pairing with someone, and not in order of importance.
Have you ever had shaky hands at the keyboard? I sure have. It’s an awful feeling. One of the first times I switched jobs I had this happen to me. It was the first time I had my hands on the keyboard at this company while pairing.
I didn’t even see it coming. I was feeling a little nervous to be honest, but I thought I had my nerves under control. But once my hands had to physically type in front of a new colleague my hands started shaking. I don’t know if the guy I was pairing with noticed or not, but it made me panic inside. I was making typing mistakes I wouldn’t normally make, then I was caught up in my head about what he would think, which made it worse and I started thinking unclearly and it just spiraled into a bit of a mess, at least internally anyway.
I eventually snapped out of it and things worked out, but it was a rough day for me.
Years later after I thought I was long passed that, it happened to me again. This time in front of someone that I respected a lot for their technical prowess. I wanted to get to where he was one day, and I wanted to impress him. But those thoughts got in my head and I actually completely collapsed while trying to pair with him. And at the time he was technically my manager. It sucked dude.
Both situations I didn’t get any empathy from the other person, and I also was too embarrassed to admit that it was happening to me. They both probably didn’t even notice it was happening either.
Remember to be aware that performance anxiety is a real thing and happens. Some people never have an issue with it, but most people experience it at least during their first few experiences with pair programming. But it can happen in other situations too.
It can happen because you’re more senior than they are and they’re nervous around you, or because it’s a job interview, or maybe just because it’s their first day and they’re worried they’ll make a bad impression with someone.
Simply by being aware of it I find I can recognize it easily when it happens. If they make a mistake and seem worried or frustrated about it I assure them everyone gets sloppy at the keyboard when others are watching and it’s totally normal. Sometimes this helps people relax a bit.
And that’s an important bit. Relax. If you recognize your partner is experiencing some performance anxiety you have to work with them to set the tone of the session. Make sure they don’t feel under pressure and that you’re not judging them. A pairing session should be a safe environment where people make mistakes. Things gotta be chill and calm. Unintuitive perhaps, but it’ll help things move faster.
Also note, that for some people performance anxiety is not a situational thing. It’s a constant. You might have to spend some time informing yourself about it, and see if you can work with them to get through it. It may even have to be in collaboration with a therapist. Remember it doesn’t make them incompetent. There’s just a fear they’re struggling to get past and as a good teammate you need to do what you can to help.
We all experience it. That feeling that you don’t measure up with your peers, and somehow they’re going to find out you’re a fraud and it’ll all be over. You’ll lose your job, then your home, your family will leave you… it’s an awful feeling.
But it happens to us all at least once in a while, and for some people it’s a chronic issue. Everyone experiences it for different reasons and expresses it in different ways. Be mindful of it. It seems similar to performance anxiety but this is deeper. People can suffer from imposter syndrome while being capable of performing extremely well in front of others.
It can manifest itself in a lot of ways. Some people get quite and can seem less engaged. Others might react by being hyper engaged and intense which can sometimes increase pressure on the task at hand (increasing the performance anxiety in the other person). They can become overly excited and have unrealistic expectations for the pairing session and their partner. It all just depends on where the imposter syndrome stems from, and what personality type they are. There is a ton of research on the topic and it’s worth getting familiar with: https://en.wikipedia.org/wiki/Impostor_syndrome
Power dynamics can be a problem on homogeneous teams, but it can be a really big problem on heterogeneous teams. This doesn’t come from experience mind you, just research. Vehikl has a heterogenous team and we successfully pair and mob all the time!
Power dynamics can be structural, like a senior developer has more authority than a junior for example. But they can be hidden too. Maybe you’re a CIS male and you’re pairing with a women or a person of color. Whether intentionally or not, people tend to treat others differently when they feel like they’re valued less or more.
Obviously if your the lead on a project or are the more senior developer you should have more authority. At the end of the day you have to help make sure the code that ships meets certain standards since you’re likely accountable for the output. But you also need to make sure the less senior developer understands your suggestions and the direction you lead them. And that’s accomplished through teaching and being respectful.
Respect means you speak to the other person like their ideas matter just as much as yours. They might not have the experience you do, and maybe have holes in their knowledge but the ideas they have are just as important.
Power dynamics can also be invisible, hidden or unspoken. If you didn’t know, our individual differences are often perceived through shared assumptions about power passed down to us by the histories of our own societies.1 🤯 Mind blowing I know…
If the power dynamic is hidden, and you recognize that there is a power imbalance, like if you’re a white man, pairing with a black woman for example, then there are other things you should consider. Just because you’re not intentionally gender biased and you’re not racist doesn’t mean the other person hasn’t experienced it with other people.
People who experience power imbalances from the lower end are used to not having their ideas heard, or being dismissed. They may have a history of being treated like they don’t matter or are unwelcome. So they may be hesitant to critique you. They might not give you feedback when they should, or they won’t ask for explanation when they need to. This sucks because now you’re not learning from them, and they’re not learning as much as they can from you. Knowledge sharing is lost.
So you just have to make sure you’re not wearing blinders. Recognize the dynamic and make sure it’s clear that you welcome and respect their input. Show them that they’re valued.
And don’t go out of your way to treat them differently! Just go out of your way to make sure you’re not accidentally interrupting anyone in general. Make sure you treat people with respect in general. Make sure you listen when others are speaking in general. If you’re a white, straight dude but are truly not sexist or racist that’s all you have to do. Otherwise you’ve got more really hard work to do and I’m not the one to help you there, sorry.
We are all different. Including you, you shinney little snowflake ❄. We all have our quirks and quarks and different perspectives. Your uniqueness is was makes you so valuable. You bring something to the table that only you can bring. But all the glorious variance of personality can also cause a lot of friction on a team or in a pair programming session when not understood.
Saying the same thing; just differently
People have a tendency to say the same thing two different ways. When you first start pairing with someone this is bound to happen. Try not to get frustrated with each other. Over time you’ll get to understand each other better and you’ll develop a local language.
Different learning styles
Some people are visual learners, some audio, others learn best through reading and writing while others learn best by doing. Most of us are a combination of each of these, but we all have at least one we’re strongest at.
When you’re pairing with someone you need to share with each other what your preferred learning styles are. It’ll help you communicate. Rather than getting frustrated that you’ve had to explain something four times, maybe try another tool. Is your partner more of a visual learner? Try diagraming the concept. More of a hands on learner? Make sure you get their hands on the keyboard while you share whatever knowledge you’re trying to transfer.
Assertive vs Turbulent
Where Assertive individuals tend to be calm, relaxed, and free from worry, Turbulent types are more likely to be self-conscious perfectionists, concerned about their abilities or about how others perceive them.2 One isn’t better than the other and both have their own strengths.
You can find out more about these two personality types (actually “identity types”) here: https://www.16personalities.com/articles/identity-assertive-vs-turbulent
They key point is they manifest and handle stress differently. A turbulent personality is more likely to be a perfectionist and stress about whether or not the work is good enough. Again it’s not good or bad, but if you’re the opposite, the two of you have to learn to work with each others strengths and weaknesses. And recognize each other for what your strong at.
Definitely helps to educate yourself a bit on the different personality types, and if the people you pair with regularly happen to know what they are, focus on learning those types and understanding the adjustments in your behaviour that you need to make in order to pair effectively with them.
I use this website all the time to asses myself and study other personality types: https://www.16personalities.com/
Pair programming is actually one of the ten principles in XP (Extreme Programming)3, so often when people talk about it the idea they have in their head is that developers are pair programming all the time and never running solo.
That might not work for you and your team. At Vehikl lots of teams are practicing the XP version of pairing but some don’t. I don’t personally believe in pairing 100% of the time. I think some people just need alone time. Sometimes you’re able to learn more by coding alone than with someone else. I find I’m also able to focus way more intensely when I’m alone with my headphones on. Problem is I’m creating a silo on the team by doing that.
So I feel that having developers pair or mob at least once a day pays back in huge dividends over the lifetime of a project. Every project I’ve been on that doesn’t make it a regular practice has been burned by siloing.
I also mentioned the word “mob” a lot in this article. If you’re unfamiliar, mobbing is exactly the same as pairing only you add more people. Every single point I mentioned applies to mobbing but mob programming also adds additional complexity which I didn’t explore. If you want to know more about mobbing let me know in the comments!
Also, if you have any questions about anything at all, or if you disagree with any of my points I also want to hear from you! If you disagree just keep it respectful. I still have a lot to learn, and if you think differently than me, I might have a lot to learn from you!