Remembering what it's like to begin

Spending my time teaching Mozilla development, as opposed to doing it, gives me a unique perspective of the process.  Sure it's hard watching all the interesting projects going on around me, not being able to get involved directly.  And yet in my not-doing I have come to understand one thing more clearly: what is involved in the process of starting work on Mozilla.

Working with my students I've learned a great deal about how to improve this initial ramp-up, what to avoid, how to change things in order to straighten otherwise circuitous routes, the perils of build environments, etc.  Many of the people in the community I interact with are so far beyond this initial zero point that it is hard for them to relate to the needs of the beginner.  Many, but not all.

Shaver has been working with a couple of my students, helping them to figure out where to add some new functionality they've written.  Just so we're clear, the Mozilla codebase is not a happy place to enter for the beginner.  If you disagree with me, I'll take this opportunity to point out that you, fair reader, are clearly not a beginner any more.  Neither is Shaver.  But my students, they're new to this game and they asked what I think is an important and appropriate question: now that we've got some working code for feature XYZ, how do we integrate it into Firefox?

I've heard this same question asked and answered enough on IRC, via email, during casual chats, etc. to know that many, many people are wondering the same thing.  And so, in appreciation for the help that was given to my students, I want to take the time to share the answer Shaver gave.

First, if you're hoping that the answer includes source filenames and line numbers, be warned that this is not the blog post for you.  There is no answer like this until you've completed your work and can look back.  I'm convinced that one can only speak about 'how' in the past tense.  Rather, what is offered is permission to try, and more importantly to fail, confidence and encouragement to try again, and patience.

Now, here's his advice.  I'll paraphrase to protect the innocent.  The particular feature he was discussing with the students turned out to have some baggage around it in terms of how different people thought it should be done.  The bug is littered with argumentative comments, unhelpful asides, and a complete lack of code.  Trying to determine who has ownership of the code is difficult, and trying to determine who might know something about it even harder.  And so, as the saying goes, because he couldn't give them supper, Shaver decided to teach them how to fish.

He suggested a pattern of development for adding new capabilities to Firefox that need to work with/around existing code:

1) Go Native

Get the functionality limping along outside Firefox, if possible, so that you have some decent familiarity with the framework in question.

2) Duct-tape it onto the Fox

Hack it into Firefox with utter disregard for modularity, cleanliness, cross-platform issues, or backwards compatibility.  Goal: bringing up a Firefox build that uses feature XYZ in the most direct possible fashion.  This will give you a number of valuable things:

  • a patch you can attach to a bug (more about that below)
  • the crazy-ass high of seeing Firefox do your new thing
  • a test build that you can give to other people in order to get them to tell you about
  • problems on other platforms, configuration issues, etc.
  • a stake in the ground against which you can write or describe tests
    3) Tell the world

Post far and wide about that progress, and propose a direction for the next steps of integration.  Maybe your feature can be done as an extension rather than in the tree; maybe you can tie into something else that wasn't known to you when you began; etc.

3.1) Now that the world knows, be careful not to listen to everyone

Prepare yourself for people with more of a sense of entitlement than ability to contribute (read "to deluge you with") 'must haves' regarding the ability for other extensions to override your work, a bazillion configuration options ("you have to be able to disable/enable feature XYZ use on a per-tab basis, or Firefox will fail"), and such like.  People have been imagining their perfect implementation of XYZ for years, and now they'll be expecting all their dreams to come true.

As the one doing the actual work, you have the driver's seat here, and the people you really need to negotiate with are the module and product owners.  Remember to focus on asking yourself whether people will be better off with what they have today, or what you're doing.  If they'll be better off with your work, then you should go ahead with it.  The perfect is the enemy of the good, the time value of working code is high, etc.

3.2) Don't stop working for fear of doing the wrong thing

Work while processing that feedback!  Mozilla is a very asynchronous project, and that's critical to our ability to move forward.  Prefer to spend time writing code rather than waiting.  In the worst (and historically unlikely) case, you will have to throw some work away, but that's basically the same as having waited and not written it, except that you'll know more about the problem space.  It's important that you actively preserve your momentum while waiting for responses to emails, reviews, etc.

4) Keep the bug hot

Provide frequent updates to the patches in whatever bug you take over for this purpose.  Even if it doesn't compile, checkpoint your work there for safety and (importantly) so that interested parties can give you feedback as soon as possible.

What I think is most important about this list is that it helps someone new, like my students, understand that it's ok to not know how to do something.  I don't think Shaver would mind me saying that he doesn't know how to do XYZ either.  That's not the same as saying he couldn't figure it out.  This is the second most important piece, that knowing how to do something is not the same as doing it.  What is needed is a certain hubris and a stubborn, single-minded motion forward, even if it's done on hands and knees.