Skip to content

You Can't Learn Agentic Engineering from the Sidelines

Recently, someone sent me Rachel Laycock's article Why are good developers so wary of agentic development?. I agree with quite a lot of it. Experienced developers have good reasons to be skeptical when somebody claims that an agent can now build an entire application. Making something run is one thing. Making it reliable, maintainable, secure, and actually useful in production is another.

But the article also reminded me of something that has been bothering me for a while. Not so much the skepticism itself, but what some developers seem to do with it.

Our software wasn't that great before AI either

When we discuss the quality of agent-generated code, I sometimes get the impression that we are comparing it to a rather idealized version of traditional software development. As if the systems we built before AI were always well-designed, thoroughly tested, carefully documented, and easy to maintain.

Well, they weren't - we have been dealing with technical debt, questionable architecture decisions, missing tests, and systems nobody really understands for a long time. I certainly have not worked exclusively on codebases that would win awards for craftsmanship. This does not mean we should lower our standards for AI-generated software. Quite the opposite. But we should at least compare it against the reality of how software is built, not against how we wish it had always been built. And perhaps we should also ask why so many of these problems existed in the first place.

Writing code was never the real problem

I have always considered writing code to be only one part of software engineering. Often not even the most difficult one. Understanding what a system is supposed to do, deciding where responsibilities belong, dealing with dependencies, finding the right abstractions, and figuring out what will break when something changes: that is where much of the work happens.

Agents do not make those problems disappear. They can actually make them more obvious. If an agent changes a dozen files in a few minutes, I cannot rely on having written every line myself to understand the result. And if I never had a good overview of the system to begin with, blaming the agent for that missing overview seems a little convenient.

Of course, there is a new problem here. Agents can produce changes faster than we can reasonably inspect and understand them. That is a real risk, not just an excuse made up by skeptical developers. But to me, that is an argument for improving the way we maintain system understanding: architecture documentation, traceable decisions, useful tests, codemaps, and ways to see what changed and why. It is not an argument for avoiding the tools.

You can't optimize an experience you haven't had

What I find frustrating is something else. I keep hearing discussions about how to use agents efficiently from people who have barely tried them. Which model should we use? How should we structure the context? How do we avoid wasting tokens? What is the perfect workflow? Those are perfectly reasonable questions. I ask them myself.

But sometimes the discussion seems to happen instead of using the tool. We want to understand the optimal way of doing something before we have even found out what happens when we try. I do not see how that is supposed to work.

I have probably spent more on coding-agent tokens than most people around me. That is not a badge of quality, and I would not claim that spending more automatically produces better software. Some of those tokens were undoubtedly wasted.

But I have learned a lot from using the tools, including what does not work. And that knowledge is difficult to acquire from a presentation about prompt engineering. Experience does not mean always knowing the right solution. Quite often, it means having tried the wrong one and understanding why it failed.

To be clear, I am not suggesting that everybody should hand an autonomous agent production credentials and see what happens. Security constraints, confidentiality, review requirements, and operational risks are real. There is a huge difference between a controlled experiment on a branch and letting an agent loose on a critical production system. But surely there is enough room between those two extremes to actually start learning.

What went wrong when I tried it

Over the last months, I have been building an agentic software development lifecycle with specialized agents, task routing, and shared architectural knowledge. The design looked fairly reasonable on paper, until I started using it.

Flow from orchestrator to router to agent to tools, with four numbered failure points: a missing file-read tool, wrong routing, a stale codemap, and unclear failure reports

One agent was supposed to inspect a repository but did not have the tools required to read its files. Another task ended up with the wrong specialist. And the codemap I had introduced to help agents understand the repository was only useful as long as it stayed up to date. None of these problems were particularly mysterious once I found them. But that is the point: I had to encounter them first.

The missing file-access tool, for example, was not a model-quality issue. The agent could not do its job because the surrounding system did not give it the necessary capabilities. Improving its prompt would not have fixed that. Task routing was similar. Giving a task to the wrong agent can produce a perfectly plausible failure that looks like bad reasoning, when the real problem is that the task should never have been assigned to that agent. And I have written about giving Copilot a CODEMAP before. A map that is not maintained alongside the code eventually becomes another source of misinformation.

These experiences changed what I want from the architecture. Agents should be able to reject tasks outside their scope, report missing tools or permissions, and tell the orchestrator what went wrong. Ideally, they should also suggest which agent should handle the next step. That is a design direction, not a claim that I have already solved all of these problems. I could have spent another month refining the initial design. I doubt I would have identified the same issues with the same clarity.

Experienced developers should be the ones doing this

This is where I agree strongly with Laycock. Experienced developers know what can go wrong in software systems. They have seen the consequences of poor boundaries, weak tests, hidden dependencies, and questionable deployment decisions. That experience is incredibly useful when working with agents. But it needs to be applied.

If we want to establish good practices for agentic engineering, somebody has to try things, measure the results, and share what went wrong. We need to look at review effort, defects, maintainability, recovery from failures, and the actual quality of the resulting systems. Counting generated lines of code is not particularly useful. Neither is counting tokens. I may use agents more than a colleague and still produce worse results. That is entirely possible, and we should be able to find out rather than just argue about it.

What I find difficult to accept is the idea that we should wait until the tools and best practices are mature before getting involved. Who exactly is supposed to develop those practices in the meantime?

So, where does that leave us?

A dashed arrow of waiting for mature best practices, compared with a loop of small experiment, watching where it breaks, and fixing the system around the agent

I am not convinced that agentic development is already a solved problem. My own experiments are evidence to the contrary. But I also do not believe that standing on the sidelines will make us better at it.

Good developers should be skeptical. They should question results, insist on verification, and be aware of the risks, and then they should try the tools. Not every new technology deserves blind enthusiasm. But engineering judgment develops through contact with real problems, and we will not learn how to build reliable agentic systems by waiting for somebody else to figure it all out.