I've got a skill that drastically improves code quality and architecture and it's powered by defects. I'm sure you've already had many scenarios where you've had your agent fix the same bug 3-4 times. That's not just a defect, it's a systemic failure. Sure, we want to fix the bug -- but it's even better to fix the problem that caused the problem: to learn what went wrong and what conditions made…
Here's a question: if you were told you were going to get the biggest, worst codebase that you had to work on, sight-unseen, but you could magically apply one refactoring to it, what would that refactoring be? good naming? no god classes? tabs instead of spaces? 🙃 I think it's a good question, because: The magic largely exists all of a sudden in the way of LLMs. I want to be reading less agentic…
One of the main reasons I see people getting poor results from agentic coding is that they're not managing their context properly. They're getting results like: The AI forgets clear instructions you gave multiple times. It keeps suggesting an idea you've rejected multiple times. It gets desperate about completing the task at hand quickly rather than doing it well. It assumes fundamental things…
One thing I've noticed when working with others while coding with agents is that many people are still working at too low of a level by default. Level 0: Line-by-line dictation Obviously if you're telling it line by line what to type (and no one is -- this is a straw man), you're not getting the value out of the LLM that you could be. Level 1: Technical solutions The next level up is specifiying…
Steve Yegge shipped 225,000 lines of Go code he's never read. I just hit 170k lines on a side project without looking at the code. Vibe-coding is old news at this point, but what about vibe-reviewing? And possibly more terrifying: Can we build software without reading the code at all? In the vibe-coding book , Yegge describes reviewing 10,000 lines of code a day. But he's not reading for elegance…
My software engineering background colors my management style in many ways. Here’s an example that’s a cornerstone for my definition of good management: Most people in software know a “200 OK” is a web server response that says that the request was successful, or a 400 Bad Request error that something went wrong. Less common is a “202 Accepted” response, but it’s worth explaining: A 202 Accepted…
(special thanks to Deepa Joshi for her input!) This is the fourth and final part of my series on work breakdown (WBD) for large software efforts. In the last post I chatted in detail about what constitutes a good piece of work in the breakdown, but in this post I'd like to get more holistic and talk about what the entire WBD will look like when it's done well, and how the pieces of it should…
(special thanks to Deepa Joshi for her input!) I introduced the concept of thin vertical slices for work breakdowns (WBD) in my last post but the idea is by no means new, and I didn't invent it; thin vertical slices have been the state-of-the-art for work breakdown (WBD) for decades. People often don't spend time studying the state-of-the-art though, and they're more comfortable breaking things…
(special thanks to Deepa Joshi for her input!) I previously explained why you should care about a good work breakdown (WBD), and gave some examples of common ways to do work breakdown that we should try to avoid. None of that is much help unless you know what we’re really trying to achieve. I’ll explain that here. The whole point of the WBD is manageability. We break work down because a single big…
(special thanks to Deepa Joshi for her input!) A critical skill for senior engineers is knowing how to break down a bunch of work into smaller, more manageable pieces. You need to make sure you’re spending your time and effort on the right things, and that the rest of the organization is in agreement. This isn’t always the most exciting part of software development, but I’ve seen a proper work…
I’ve stumbled upon a style of estimation that I’ve seen be pretty successful. I’ll call it “2W+ Estimation”. I've mentioned it before , but without much detail. There are two possible estimates given for any work that the team is about to take on: “more than 2 weeks” and “less than 2 weeks”. An estimate is not provided at all if the work seems like less than 2 weeks. It is assumed to be less than…
It can sometimes feel like TDD is pretty dead in 2022. I’m not sure what happened, because I think it’s a genius way to work, but most programmers I talk to seem to think that it’s a waste of time. We don’t really have to be dogmatic about it though. It’s not equally valuable at all times, and there are even rare times when a total kool-aid drinker like me doesn’t do it. This post is meant to chat…
How you do QA is probably terrible. Of course I don’t know you, but most software development shops that I’ve worked on or chatted with “do QA” in a way that is pretty terrible. Almost everyone does it, and almost everyone considers it a “best practice”, and yet somehow it never even got a name. I’m going to call it “block-testing” because it’s the kind of testing that unfortunately makes…
I’ve seen this pattern a number of times in my years as a software developer, and it’s always hard to watch: (1) “We don’t need automated tests on this stuff. It’s way too simple.” ( The codebase grows until it’s more and more out of control. We’re getting scared to make changes and manual testing is taking forever. ) (2) “It turns out that we need tests, but this stuff isn’t very testable, so the…
I think that the most important thing I've learned while trying to improve my abilities as an organizational change agent (read: a programmer that likes to get his way), is to never ever present some idea as a best practice. If you don't know the reasoning well enough to explain it with that reasoning alone, you don't understand the problem or the practice well enough to suggest it. Escaping…
Evergreen Update ( 2022-01-35 ): After some time working with Typescript, I'm actually completely sold on its usefulness and value, which I certainly was not at the time of this writing. I was surprised that none of the usual explanations seemed really true, eg it didn't reduce the number of tests or types of test that I wrote at all. What it did do though is it greatly sped up my feedback loop:…
I've always worked most heavily with dynamically-typed languages. They're a great choice for me and the teams that I've worked on because of the kinds of work that we're doing. It's pretty normal though for these teams to add team-members that are completely unaccustomed to working with dynamically-typed languages because they come from backgrounds where they worked mainly in statically-typed…
One of my favourite ways to tackle tech debt is to fix it as I work through product requirements. There are some great advantages to it: It automatically prioritizes tech debt burndown in areas that you’re probably going to touch again soon, which is where it’s most valuable. It doesn’t require blocking any product development flow. It just slows it down (probably imperceptibly). It doesn’t even…
In my experience, cross-functional teams align people to business goals best, and so they can get to real results much faster and much easier than teams made up of a single function. They really don't seem to be that popular, so I thought I'd talk about them a bit. Here's some common chatter across mono-functional teams: The Engineering team: "We should never be taking on tech debt. Tech debt…
Too often when I see a team trying to replace a bad/old/deprecated pattern that is widespread in a codebase, they default to what I call The Hero Solution : One person on the team goes through and fixes every case of it themselves. This can work for very small efforts, but it's almost always a terrible solution in larger efforts for a few reasons: When the bad pattern is widespread this is the…
I always try to think about what exactly it is about experience that makes a software developer better. Are there aspects of experience that are teachable, but we don't understand them yet well enough to teach them? Can we do better to pass on "experience" rather than have every developer suffer through the same mistakes that we suffered through? I know I've had a couple of hard-won lessons over…
The 4th criteria of the Joel Test of quality on a software team is: Do you have a bug database? You probably do. The test was written almost 20 years ago and if I recall correctly almost everyone had one anyway. Joel was even selling one. On the surface it seems like common sense. Quality is something you want to manage. So naturally you'll also tend to want to log things... measure things...…
I've had a chance to get back to coding after a couple of months' hiatus so I thought I'd write about something a bit more fun and way down in the details. Conditionals add complexity -- they seem like a tiny bit of complexity in the singular case, but they really do add up quickly to make code unpredictable and difficult to follow. Your debugger and your unit tests are probably great at managing…
I've been developing software for a few years without doing much estimation at all, and the estimation I've been doing has been really vague, eg "You know that feature is a lot of work, right?". I've recently been reading more and more from the #noestimates movement on The Twitter , so I thought I'd chime in a bit with my rationale and experience as well. "Is the company crazy?" Yes, but I don't…
I've recently seen a case of spontaneous waterfall-style development emerging where the team was generally empowered to avoid it or at least to correct against it, and certainly wanted to, and yet did not. From the outside it seemed like waterfall was a kind of steady-state for them that they'd trended toward and didn't have the escape-velocity to move toward anything else. They weren't happy with…
"Engineer" really is a very silly term for people that make software. Engineering is supposed to be a predictable application of science toward predictable results. Software development is really anything but that. The biggest problem in our profession is and always has been getting predictable results. The key difference between a junior engineer and those that are more senior is that the more…
Special thanks to my friends Deepa Joshi and Sam DeCesare for input/feedback! The 80/20 Rule, otherwise known as the Pareto Principle has wide-reaching implications for productivity. If you can get 80% of the results you want for 20% of the effort in a given endeavour it really lets you consider an efficiency/thoroughness trade-off that's right for your desired results. There's a real opportunity…
Special thanks to my colleagues Sam Chaudhary, Lexi Ross and Stuart Reavley for feedback/criticism! I’m not a management guru, and I’ve never taken a management class. I have done some management, and a hell of a lot more coaching (which is often more powerful than traditional management) though, and I’ve worked with and for managers of varying degrees of effectiveness and I’ve picked up a few…
A lot of engineering management and product development process conversation tends to be based on a fundamental assumption that product quality and development speed are always opposing forces. Time and again however I find myself learning and relearning that speed and quality can instead be symbiotic and improving one can also improve the other. These win-win scenarios are actually everywhere as…
One pattern that I've seen work well in software development management is one I call The Atomic Team pattern. Basically what it means is that ideally the smallest indivisible unit for management is the team. I think it's a cornerstone of healthy service-oriented architecture, but it's rarely talked about because it's on the more touchy-feely and less-technical side. Management of such a team ends…
Obviously from the title, I think software engineering management is in a Stone Age. Before I get into my arguments though, I'd like to say that this isn't really about any particular manager or managers that I've had in the past. It's really about counter-productive patterns that I've seen that I really think we need to evolve from. I've also been responsible for some of these mistakes myself as…
(Thanks to Chris Frank and Sam Decesare for the feedback!) Bugs and outages happen. If the team can learn from them though, it's possible to reclaim some of that lost effectiveness, sometimes even to the point that the learning is more valuable than the effectiveness lost. The best mechanism I've seen to drive that learning is for the team to meet after the outage or defect is no longer an…
Last week I had the pleasure of being on a panel about Continuous Testing put on by Electric Cloud . There's video of the discussion if you're interested, here . Additionally, I posted a blog post on the subject on the ClassDojo Engineering blog here . For posterity, I'll x-post here as well: Continuous Testing at ClassDojo We have thousands of tests and regularly deploy to production multiple…
It's been over a year since I've been on a team that does Sprints as part of its engineering process, and I've really changed my mind on their usefulness. I'm probably pretty old-school "agile" by most standards, so I still think Scrum is better than what most teams out there are doing, but I think it's lost me as a proponent for a few reasons, with the most surprising reason (to me) being its use…
This is the last part of my 3-part series on production-quality node.js web applications. I've decided to leave error-prevention to the end, because while it's super-important, it's often the only strategy developers employ to ensure customers have the most defect-free experience as possible. It's definitely worth checking out part I and part II if you're curious about other strategies and really…
This is the second part of a three part series on making node.js web apps that are (what I would consider to be) production quality. The first part really just covered the basics, so if you're missing some aspect covered in the basics, you're likely going to have some issues with the approaches discussed here. First, I'm going to talk about a few major classes of defects and how to detect them. I…
I've been working on production-quality node.js web applications for a couple of years now, and I thought it'd be worth writing down some of the more interesting tricks that I've learned along the way. I'm mostly going to talk about maintaining a low-defect rate and high availability, rather than get into the details about scaling that are covered in a lot of other places. In particular, I’ll be…
I've been reading the 37 signals book Remote lately and it's got me thinking a lot about the advantages and disadvantages of working remotely. While they clearly acknowledge that there are trade-offs to working remotely, I personally don't think they paint a very clear picture of just how expensive those trade-offs are. I can only really speak from a software development perspective, but I think…
So you’re thinking about versioning your web API somehow. Versioning is how we annotate and manage changes in software libraries, so it seems natural to re-apply this solution to changes in web APIs. Most web APIs are versioned in order to… ( A ) “freeze” an older version somehow so that it doesn’t change for older clients, or at least it is subjected to much less change than newer versions, so…
If you’ve ever seen a laundry list of the types of non-functional requirements like testability, accessibility, reliability, etc, (often called “ilities” because of their common suffix) you probably haven’t seen “rewritability”, but I really want to add it to the pile. I’ve often found in software engineering that counterintuitively, if something is difficult or scary there’s a lot to be gained by…
I once asked an interviewee “Ever work on a high-performing team?” and he answered “Yeah…” and then went on to explain how his team profiled and optimized their code-base all the time to give it very high performance. That’s not what I meant, but in his defence, I really don’t think many developers have had the opportunity to work on high-performing teams and so they don’t know what they don’t…
First a little background I’ve always been a big fan of REST the way Roy intended it for two major reasons: It uses HTTP the way HTTP was intended, playing on its strengths and not wasting any time re-inventing what HTTP already has. The state of HTTP APIs these days is really ridiculously bad, given what we should have learned from the unfathomable success of the WWW. I was also envious as hell…
I’ve seen these anti-patterns in a lot of web APIs, so I thought I’d detail why they’re bad and what to do instead. Using a 200 status code for every response: This anti-pattern is common for SOAP-like RPC APIs. Using a 200 status code for all your responses is silly because you end up having to reinvent an error-indication in your response body instead, and nobody in the world knows your new…
If you consider the number of packages on pypi , npm , and rubygems , and the release dates of python (1991), ruby (1995) and node.js (2009), it looks a lot like those communities are getting new packages at the following rates, per year: python: 29,720 packages / 22 years = 1351 packages per year ruby: 54,385 packages / 18 years = 3022 packages per year node.js 26,966 packages / 4 years = 6742…
If you’ve developed SaaS in a large organization (or even a small organization that acts like one), you’ve probably seen some of the symptoms of fear of releasing software: Off-hours deployments and weekend deployments Infrequent releases extended code-freeze and testing cycles Reluctance to refactor Feature branches for the purpose of ‘cherry-picking’ release managers many non-customer-facing…
Version control branches come with costs. I’m at the point now that I don’t think it’s possible to get away without spending a couple of days every month managing issues with version control and merging if you’re using feature branches liberally as is common with DVCS (like git) users. I’ve spent days myself in the past months, so I felt compelled to write this because those were days I could’ve…
Let’s just forget about story points, pigs, chickens, daily stand-ups, burndown charts, sprints and scrummasters for a second. In my experience all of that weird jargon is really hurting Agile’s adoption among the no-nonsense type of developer that doesn’t have time for fluff and wants to know the real benefits of something before investing time in learning about it (instead of a million other…
One fine day in the trenches, a junior engineer was tasked with optimizing a particular web service call that was way too slow (sometimes slower than 20 seconds!). I had just figured out how to use a performance profiler for that particular platform, so I thought I’d offer to show him how to use it. His response was that he was on a tight deadline and didn’t have time to learn to use the profiler,…
Prototyping is a design methodology that basically involves “trying stuff out and seeing what works”. It’s meant to be iterative in that you continue to create prototypes (possibly by alterring previous prototypes) until you’ve got all the information you need to say your design is complete. If we were building cars, we would probably first prototype a body design with CGI to be able to collect…
“We will encourage you to develop the three great virtues of a programmer: laziness, impatience, and hubris.” — Larry Wall In this quote Larry Wall makes some great points about what it means to be a great programmer in a zen-like, toungue-in-cheek sort-of-way. Let’s look at one aspect of the Virtue of Laziness. Every reasonable developer knows that he should write his code to be easily…