'You must write docs. Docs must be in your repo. You must write tests. You must document your architecture. Etc. Etc.'
These were all best practices before LLMs existed and they remain so even now. I have been writing extensive documentation for all my software for something like twenty years now, whether it was for software I wrote for myself, for my tiny open source projects or for businesses. I will obviously continue to do so and it has nothing to do with:
> AI changes the game
The reason is simply that tests and documentation are useful to humans working on the codebase. They help people understand the system and maintain it over time. If these practices also benefit LLMs then that is certainly a bonus, but these practices were valuable long before LLMs existed and they remain valuable even now regardless of how AI may have changed the game.
It is also a bit funny that these considerations did not seem very common when the beneficiaries were fellow human collaborators, but are now being portrayed as very important once LLMs are involved. I'd argue that fellow humans and your future self deserved these considerations even more in the first place. Still, if LLMs are what finally motivate people to write good documentation and good tests, I suppose that is a good outcome since humans will end up benefiting from it too.
Maybe it's the speed of LLM iteration that makes the benefit more immediately obvious, vs seeing it unfold with a team of people over a longer time? It's almost like running a study?
I have a similar reaction to strong static types being advocated to help LLMs understanding/debugging code, catching bugs, refactoring... when it's obvious to me this helps humans as well.
Curious how "this practice helps LLMs be more productive" relates to studies that try to show this with human programmers, where running convincing human studies is really difficult. Besides problems with context sizes, are there best practices that help LLMs a lot but not humans?
I bet one of the next "revelations" is going to be: Avoid sprinkling side effects throughout your code. Prefer functional code, push side effects to the boundary (functional core, imperative shell).
About 95% of the work needed to make LLMs happy is just general purpose better engineering. Units tests? Integration tests? CI? API documentation? Good example? All great for humans too!
I consider this largely a good thing. It would be much worse if the changes needed for Happy LLMs were completely different than what you want for Happy Humans! Even worse would be if they were mutually exclusive.
It's a win. I'll take it.
It's another example where the reason for better engineering is to make machines (search engines) happy.
It has the effect of finally forcing people to think about the software they're making, assuming they care about quality. If they didn't, then it's not practically different from an insecure low-code app or something copy-pasted from 15 year old StackOverflow answers.
> It has the effect of finally forcing people to think about the software they're making,
Ah, and all this time I was reliably assured that waterfall, design-upfront, was a broken process...
Waterfall, as prescribed and as practiced, had feedback signals.
The reason might have been a cultural regression. At least with documentation, it seems to have been much better and a bigger priority a couple decades ago.
At the start of my career, teams produced documents as a part of their work, and there were even technical writers on staff. Then agile hit, the writers were laid off, much of what little documentation that was created was kept in various work-tracking systems and wikis that were periodically replaced, often with little to no migration.
Right now it's hosted externally (in our "blessed" knowledge base) but if it could be pulled into the repo, and we set an AI reviewer on every pull request to sanity check that if the changes we're doing have a material impact on the feature as described in those docs that it should be flagged (or changes proposed) that'd be a nice win for keeping them up-to-date, and it's easy enough to publish markdown as html or even script an update to the canonical site when we merge to main.
Everything regarding AI-assisted development is basically training wheels for the young people coming into the workplace.
> You should have a good, concise introduction to the codebase that allows anyone to write and test a simple patch in under 15 minutes.
Yeah, that's the CONTRIBUTING file.
Okay, so what, should I be moving my docs out of the repo or something?
How should I make it as hard as possible for LLMs to make any use of or suggestions about my documentation?
Many doomers are running around saying the future is grim because everything will be made for AI agents to use rather than humans. But so far everything done to push that agenda has looked more like a big de-enshittification.
Another one is Model Context Protocol, which brings forth the cutting edge (for 1970) idea of using a standard text based interface so that separate programs can interoperate through it.
If the cost of having non-user-hostile software is to let AI bros run around thinking they invented things like stdin and documentation, I'm all for it at this point.
If any AI bros are reading this here's another idea. Web pages that use a mostly static layout and a simple structure would probably be a lot easier for AI to parse. And google, it would be really beneficial to AI agents if their web searches weren't being interfered with by clickjacking sites such as Pinterest.
when things are tiny or resource constrained, the same people are doing each task regardless, but "technical writer" is a real job around documentation and manual writing, so there's at least sometimes some real decoupling between the code and outwards facing documents.
that also covers for cases where people can write code well, but who's english(or whatever the target documentation language is) is shaky at best.
GitHub Pages serving directly from a /docs folder makes it even simpler, no separate deploy, no separate CMS, no drift. The less infrastructure between writing and publishing, the more likely docs actually get maintained.
Our set up is:
packages/
↳ server
↳ app
↳ docs
Using mintlify for the docs, just points to the markdown files in the docs folder. And then a line in the claude.md to always check /docs for updates after adding new code.Polyrepos are workable, the way to do it is to actually version, ship, and document every subcomponent. When I mean ship, I really mean ship, as in a .deb package or python wheel with a version number, not a commit hash. AI can work with this as well, as long as it has access to the docs (which can also be AI-generated).
That means, a subcomponent can just make a needed change in the supercomponent as well, and test and the ship the subcomponent without excess ceremonies and releases.
GitHub Pages came out in 2008.
I get the principle but it seems like there are many other times to plant than now.
But let's be real, that's never going to happen. No matter what format you give someone, they're not going to write that kind of thing down. They will, however, encode why a firehose approach is necessary to both document it for future readers and to ensure that the program doesn't accidentally (or possibly on purpose by an eager junior dev) move to, say, a pull method that won't meet the business/technical requirements. Which LLMs can extract a natural language version from.
And, really, that's the only "why" that actually matters to other developers trying to get their job done. The forest, while perhaps full of fun stories that I am sure are entertaining to read, doesn't matter all that much.
I'm sure there's a ton of places where its been hard to do that in the past in a way where the docs are easily accessible where people are looking
but with agents, even just pulling the code package to get the docs is fine
I think the constructive information is mentioning Github Pages were built on .md file and they have existed for 10 years. That's true and useful.
The snarky part happens when phrasing the sentence "Ah you guys only doing this now? It has existed for 10 years" that part is talking about something constructive but it's also trying to diminish the discovery of someone else. We all find and develop at different times. In general is better to be constructive and happy someone else is joining you in using something than underline how it was already done in some way by you or others and this new discovery is irrelevant. Everything that exists already existed (in some other shape or smaller parts).
I don’t think this is a case of just finding something late, it’s finding something decades after it’s very common. And strange that the author didn’t reference this old practice.
My intent wasn’t snark, but more incredulity at how the post was written and how it states some very old, commonly accepted best practice was novel or finally time to use.
I’d make a similar comment if someone posted that now is the time to use object oriented programming. And I wouldn’t do so in a snarky way.
I used my software and R Markdown documents to help address such problems. In the source code, you have:
// DOC SNIPPET BEGAN: example_api_usage
/**
*/
function amazing_function( char life, long universe, string everything ) {
}
// DOC SNIPPET ENDED
In the R Markdown you write an R function to parse all snippets, then refer to snippets by name. If the snippet can't be found, building the documentation fails, and noisily breaks a CI/CD pipeline.What's nice is that you can then use this to parse C++ definitions into Markdown tables to render nicely formatted content.
The general idea is that you can have "living" documentation reference source code and break on mismatch. Whether you use knitr/pandoc or python or KeenWrite/R Markdown[1] is an implementation detail.
Now, at $job, there is a top-down directive for quickly documenting every part of every important workflow and every idiosyncrasy of our products.
So, developers knew that all along.
The great talk "No Vibes Allowed" put me to the far end of the other extreme - persistent long term state on disk is bad. Always force agents to rebuild, aggressively sub agent or use tools to compress context. The code should be self documenting as much as possible and structured in a way such that it's easy to grep through it. No inline docs trying to describe the structure of the tree (okay, maybe like, 3 at most).
I don't have the time to build such an elaborate testing harness as they do though. So instead I check in a markdown jungle in ROOT/docs/* . And garbage collect them aggressively. Most of these are not "look for where the code is", they are plans of varying length, ADRs, bug reports, etc. and they all can and *will" get GC'ed.
I still use persistent docs but they're very spare and often completely contractual. "Yes, I can enumerate the exact 97 cases I need to support, and we are tracking each of these in a markdown doc". That is fine IMO. Not "here let me explain what this code does". Or even ADRs - I love ADRs, but at least for my use case, I've thrown out the project and rewritten from scratch when too many of them got cluttered up... Lol.
I'm also re-implementing an open source project (with the intent of genuinely making it better as a daily user, licensed under the same license, and not just clean rooming it), which makes markdown spam less appealing to me. I kind of wish there was yet another git wrapper like jujutsu which easily layered and kept commits unified on the same branch but had multi-level purposes like this. Persistent History for some things is not needed, but git as a wrapper for everything is so convenient. Maybe I just submodule the notes....
Note: my approach isn't the best, heck, 1 month ago OpenAI wrote an article on harness engineering where they had many parallel agents working, including some which aggressively garbage collected. They garbage collected in the sense that yes, prolific docs point agents to places XYZ, but if something goes out of date, sync the docs. Again, That works if you have a huge compute basin. But for my use cases, my approach is how I combatted markdown spam.
With AI code assistants I personally spend 90% of time/tokens on design and understanding and that means creating docs that represent the feature and the changes needed to implement it so I can really see the value growing over time to this approach. Software engineering is evolving to be less about writing the code and more about designing the system and this is supporting that trend.
In the end I don't think AI hasn't fundamentally changed the benefit/detractor equation, it is just emphasizing that docs are part of the code and making it more obvious that putting them in the code is generally pretty beneficial.
However, in corporations, docs are often in Confluence or MS Sharepoint, separate from the code. Tech specs often require comments, discussion, or estimate/budget approvals from non-tech staff. Hence, some corporate AI coding tools can refer to docs in such corporate sites. That doesn't work too well yet, IMHO ... time will show.
> Non-engineers usually don't have repo access. [Answer:] (1) You can deploy your docs on an internal-only website. (2) There is clear trend with non-engineer code access (which poses some interesting security challenges).
Regarding (2): If, on the other hand, you have your agent use MCP to query, e.g., Confluence, anyone with access to Confluence could in theory do a prompt injection and possibly get access to your repo.
At least doc changes in the repo will undergo code review.
Some constraints are:
- Non-programmers are not used to working with Git.
- In practice, they (usually PMs or feature designers) need to write their documents somewhere else.
Possible solutions are:
- Make non-programmers use Git as a documentation tool (upgrade your tooling or GTFO).
- Build a two-way sync tool so that programmers and non-programmers can work from the same source.
- However, in practice, an SSOT (single source of truth) architecture is usually much simpler. Two-way sync tends to be quite difficult, especially across different platforms.Reviewing docs in Github isn't great - as the post mentions, Google Docs or similar is typically where review happens. Spectagon aims to change that so that you can submit PRs for docs and you get a great review experience as a layer on top of Github.
Then you ask marketing or support to open a PR. That is usually where the markdown honeymoon ends.
* redundancy with the code: if code samples can be generated from the code, why bother duplicating them? what do they add? can they not be llm-generated later? and possibly kept somewhere out of the way (like, a website) so as not to clutter the codebase with redundancy
* if you do go for this duplication, then you are on the hook for ensuring it's always up-to-date otherwise it becomes worse than duplicate: misleading
So my preference is, when adding something to the repo, think very hard whether this information is redundant or not. Handcrafted docs, notes, comments that add more context like why was this built that way after a ton of deliberation - yes. Anything that is trivially derived from the code itself - no.
I am all for using a source control system for your documents, I usually use RCS. But give AI access to your docs, no thanks. If I upload any of my docs to a public server (very rarely happens), they are compressed and encrypted to make sure only I and a few people can view them.
A) accept that my library exists, and has its uses (it's a tough world out there for canvas-focussed JS libraries that aren't Fabric.js, Konva.js or Pixi.js)
B) learn how to write code using my library in the best way possible (because the vibes ain't going away, so may as well teach the Agents how to do the work correctly)
Plus, writing the documentation[1] for a library I've been developing for over 10 years has turned into a useful brain-dumping activity to help justify all the decisions I've made along the way (such as my approach to the scene graph). I'm not going to be here forever, so might as well document as much as I can remember now.
[1] - https://scrawl-v8.rikweb.org.uk/docs/reference/index.html
The author at least acknowledges the point of files is to be read by humans.
Also the article is talking specifically about public docs mean to be used by others, not ones you’re specifically trying to keep private
Is the Linux Doc Projec part of the kernel?
No. For good reasons. The only people who insists all doc must live in the same repo as the code are the ones who does not value documentation.
Note, that in both examples above there is a documentation in the main repo, but not all documentation lives there.