Resources for PHP developers: What to learn when AI writes the code
We send this list to every developer who interviews with us, including the ones we say no to. If someone spends an hour on our task and an hour on a call with us, they have earned something back, and honest feedback plus a real reading list is what we have to give. Here is the list, unchanged from the version we send by email, with the reasoning I usually only give on the call.
Key takeaways
- Writing or generating code is no longer the main challenge. The real job is deciding what to build and evaluating whether the generated code is correct. You cannot judge what you do not understand.
- AI reads well-structured systems easily but struggles with messy ones. Low coupling, high cohesion, and meaningful naming are now essential operational requirements.
- Begin with object-oriented PHP rather than a framework.
- Know what the language can and can't do, and what's happening beneath the framework.
- "There's a package for that" works only until the package doesn't fit.
- Patterns help you explain what you want and judge what you receive. They are the vocabulary you share with the model.
- A modern IDE is not optional.
- Build something reusable, not better prompts. If you do something more than twice, turn it into a process.
- Get good at reading code you did not write.
- Read a little, build a lot, get stuck, and then return to a book for the part you are stuck on.
Why we still send a reading list
We hardly write code by hand anymore. AI runs through every stage of delivery at ThinkWeb; we built our own skills and rule files to drive it, and we don't spend time hand-coding a value object or a class. So the fair question is: why do we give you a stack of books about writing code? Two reasons.
You are the one reviewing the code. You cannot judge what you do not understand. A model will give you a green test suite and a class that reads fine. Maybe the invariant is enforced in the handler instead of the aggregate, the entity is a bag of public setters, and changing one rule means touching six files. Catching that at review time is what the books train you for. Spotting these was always the important part; it just used to arrive bundled with the typing, so nobody had to name it separately.
AI reads a well-built system well and a messy one badly. Low coupling, high cohesion, names that carry domain meaning: these were ideals we argued for in code reviews and traded away when the sprint got tight. They are operational requirements now. Clean layering plus a small task gives the model one obvious place to put the code. Point the same prompt at a service class with nine constructor dependencies and a repository that leaks query builders, and you spend the afternoon undoing what you asked for.
Good code is no longer just written for the next human. It is the interface your tools work through now, which is why anyone who invested in clear boundaries has an edge with AI they were not planning for.
Writing / generating code is not hard anymore. Deciding what to build, and whether the generated code is right, is the job. This list is about that job.
Start with object-oriented PHP, not a framework
If you haven't really done object-oriented programming, start here and don't skip it. I recommend this to everyone, and it is the foundation the rest of the list sits on.
PHP OOP Way by Sergey Zhuk gives you solid foundations and walks through most of what a PHP developer should know. It starts at encapsulation and inheritance and ends at composition and design patterns. If you read one thing from this post, read this.
By OOP, I mean real object-oriented programming: using interfaces, preferring composition over inheritance, and creating objects that enforce their own rules and can’t be created in an invalid state. I don’t mean using classes just as namespaces for static helpers, or models with lots of public properties and business rules in controllers.
This is the gap we see most often in interviews, and deep framework knowledge often hides it. Someone might know Laravel very well but not understand PHP itself: how the container works, how facades resolve, or the cost of using __get. If every answer is 'there’s a package for that,' it works only until the package doesn’t fit. Know what the language can and can’t do, and what’s happening beneath the framework.
Front Line PHP by Brent Roose and Freek Van der Herten is short and really good for filling gaps.
Then patterns, SOLID, and tests
This is the minimum, not the goal. Nobody here has ever been impressed that a candidate can recite the five letters. We want you to spot the violation in the class on the screen: the handler that changes for three unrelated reasons, the interface that half its implementations satisfy by throwing BadMethodCallException.
- Refactoring Guru’s design patterns in PHP is very good, and the PHP examples make it concrete rather than academic.
- Design Patterns: Elements of Reusable Object-Oriented Software by the Gang of Four is the original. Heavier going, worth having read.
- SOLID Design Principles Explained: Building Better Software Architecture is a short article. Read it, then spend some time looking for places where you broke it.
- Test-Driven Development: By Example by Kent Beck. The value here is less the ritual than the pressure it puts on your design. Code that is painful to test is usually telling you something true.
- Clean Code by Robert C. Martin. A classic, and people still argue about it, which is fine. Read it and disagree with parts of it on purpose.
A quick note about patterns in the age of AI: It’s tempting to skip them because the model already knows them all. But that’s exactly why you need to know them too.
Ask vaguely, and you get an AbstractSellerFactoryInterface and three levels of indirection in front of one implementation. Someone has to see that and say no. Patterns are also the vocabulary you share with the model. “Put this behind a repository, strategy for the pricing rules, emit a domain event on upgrade” is a dozen words carrying a page of design intent, and it lands. Without the vocabulary, you describe the shape longhand, badly, and then accept the code it generates because you have no name for what is wrong with it.
Patterns help you explain what you want and judge what you receive. This was always important, but it matters even more now.
Where the shape of a system comes from
Once your objects are set up correctly, the next question is where everything belongs: which layer should own a rule, and what each module should know about others. This is where most of our interview discussions focus.
- Object Design Style Guide by Matthias Noback is a good foundation, and unusually practical: it is a set of decisions about how objects should behave, one page at a time.
- Advanced Web Application Architecture, by the same author, is a good foundation for how to do this. “Advanced” is overstated in my opinion, and I mean that as encouragement. It is more approachable than the title suggests.
- Hexagonal architecture. Keep this shape in mind: domain in the middle, HTTP and persistence as adapters at the edges, and dependencies pointing inward only.
Hexagonal is how we build most of our systems. No business logic depends on framework magic, and the database is an adapter you pick late rather than the diagram you start from. We call it Database-Last: solve the problem, model it, then decide whether the data lands in MySQL, a file, or a queue.
If you come from Database-First, this is the adjustment. Not because ports and adapters are hard to understand. Because it is hard to accept after years of starting from the migration and hanging the model off the database table.
When the basics are solid
Don’t start with this section. Read these resources only when you have a solid foundation; they’re about moving from just writing code to actually designing systems.
- Learning Domain-Driven Design by Vlad Khononov is the best introduction to DDD there is (in my personal opinion). Its subtitle, “Aligning Software Architecture and Business Strategy”, is the honest description of what DDD is for. If DDD has sounded like a cult to you from the outside, this is the book that fixes that.
- Patterns of Enterprise Application Architecture by Martin Fowler. Old and still correct. You will recognize half your framework in it.
- Designing Data-Intensive Applications by Martin Kleppmann. The one book on this list I would call essential regardless of language.
- Enterprise Integration Patterns by Gregor Hohpe and Bobby Woolf. Once systems talk to each other, this is the vocabulary.
- Greg Young’s CQRS documents. Short, and it clears up a topic that generates a lot of noise elsewhere.
The names in this section often sound scarier than the actual ideas. For example, a command bus is just a router. When you call $bus->dispatch(new UpgradeSeller($id)), it finds the right handler and calls it. That’s all there is to it. Most of DDD is like this, simple ideas with formal names.
You don’t need to know any of this to interview with us. Most people don’t, and that’s normal. Understanding DDD has never been the hard part.
A modern IDE is not optional
You need to use a modern IDE here, and this is the one requirement I insist on most.
- PhpStorm is what we use.
- PhpStorm Light is an experimental build that trims the heavy, slow parts and tunes startup and indexing. Everything you use day to day is still in it.
- The next version / Early Access Program builds are free (include EAP 30-day time-limited license) for major releases.
The reason has grown stronger since AI arrived. An IDE knows things about your code that a text editor and a language model are both guessing at. Find Usages resolves the interface to its implementations and the trait to the classes using it; grep matches a string and hopes. Rename refactors every call site, not the ones that happened to spell it the same way. Inspections flag the unhandled exception and the type that cannot be what you think it is, while you type. AI tools are catching up and are starting to use the built-in tools as MCPs.
That matters more when the diff is bigger than you have time to read. Reviewing generated code in an editor that cannot resolve a class or variable means reviewing it on vibes. The IDE turns “this looks fine” into “I checked.”
Learn to use the debugger. Xdebug, breakpoints, stepping into code, and watching the stack. Many developers never set it up and just use dd() and reload the page. When you take over a codebase you didn’t write, which happens often here, stepping through a single request will teach you more in ten minutes than an hour of reading.
What is worth learning that is not on the old list
The list above is almost the same as what I would have sent in 2019. What comes next is new, and it’s what now sets candidates apart in interviews.
Build something reusable, not better prompts
I ask everyone this question: How do you avoid explaining the same thing to the model every day?
The answers split people cleanly. Skills, workflows, rules, guardrails, something that persists and that a colleague could use, that is an answer. “I write good prompts” or “I keep some markdown files” is the same problem described back to me, unsolved, by someone who has not noticed it is a problem. If you do something more than twice, turn it into a process. That is why our own toolkit is a growing set of skills and rules rather than a folder of our favorite prompts.
Get good at reading code you did not write
This used to be a chore you did in your first week. It is the main thing now, because that is what reviewing generated code is. Tracing a call path you did not build, working out which module depends on which and why, reading the git history to find the constraint that explains a decision that looks wrong: that has quietly become the core skill.
Learn to ask
This is the rarest and most telling sign we see. If someone emails a question about scope before writing any code, they’re already doing the real work we value.
Most people don’t ask questions, often because they’ve worked in places where asking seemed like a weakness. That’s not the case here, and it’s not true when working with a model either. Half the battle in getting good results is knowing what to ask for.
Know what things cost
Do you know how much your system costs the client each month? What’s the p95 response time on your favorite endpoint? How many orders does it handle daily? Developers who know these numbers think like owners. Those who never ask are just closing tickets.
None of this replaces the reading list; it builds on top of it. You can’t design guardrails for a system if you don’t understand its core principles.
How to work through this without drowning
The list can feel overwhelming if you treat it like a to-do list. Don’t do that.
Start by reading PHP OOP Way carefully, then use it to build something real, even if it’s not perfect. Return to the Object Design Style Guide when you have code you’re not happy with. It will make more sense then. Save the advanced section for when you’re facing the problems those books address. Learning Domain-Driven Design is much more meaningful after you’ve built something that became messy and you understand why.
Read a little, build a lot, get stuck, and then return to the book for the part you are stuck on.
If you’re in the middle of this process and unsure how far you’ve come, that’s completely normal. Saying “I’ve read about SOLID but haven’t built something from scratch with it” is a good answer in an interview. It shows you judge yourself honestly, and we appreciate that.
Yes, for two reasons. You review the AI-generated code, and you cannot judge what you don't understand. Clean structure is also what makes a model useful: it reads a well-layered system well and a tangled one badly. Low coupling and high cohesion moved from ideals you argue for in review to operational requirements.
PHP OOP Way. Real OOP, meaning objects that enforce their own invariants rather than classes used as namespaces for helpers, is the foundation the rest of the list sits on. It is also the most common gap we see, usually hidden behind deep framework knowledge.
No. Most people arrive without it, and that is normal. Understanding aggregates and bounded contexts was never the hard part; accepting the Database-Last mindset after years of working Database-First is. What we need is that you are willing to work this way.
Why does a modern IDE matter so much?Not here. Know what the language does, what it cannot do, and what the framework is doing underneath: how the container autowires, how the facade resolves. The warning sign is when every question ends with “there is a package for that”, because that works until the package does not fit.
Building something reusable with AI rather than writing better prompts. Skills, workflows, and rules that persist and that a colleague can use. “I write good prompts” describes the problem rather than solving it.
Work with us
If this list sounds like the kind of job you want, then that’s what we offer. Each project here has one or two people, and you own the whole process. You’ll also direct a small team of AI agents and take responsibility for their work. There’s no project manager to break the work into pieces for you.
We’re based in Sofia, and we’d like you to join us in the office at first. It’s the fastest way to learn how we work.
Reach out and let us know what you’ve built.
We deliver outcomes, not code.
Why we hire problem solvers, not order takers, and what actually matters now that AI can write the code.
ThinkWeb at TechArena 2026
Last week, our CEO Theodosios Kariotis and CTO Goce Bonev represented ThinkWeb at TechArena 2026 in Stockholm,…
How to choose a custom PHP development company: The 2026 guide
Choosing the wrong PHP development company can cost you thousands in wasted development and forced rewrites. T…
Why early software estimates are wrong
In software development, the numbers given early are usually wrong. Not slightly wrong, but sometimes by month…
Discussing AI-ready security at WordCamp Sofia
Robert Jacobi, CXO at Blackwall, and Goce Bonev, CTO at ThinkWeb, joined the stage at WordCamp Sofia to talk a…
How to build secure healthcare applications with PHP and AWS
Goce Bonev, CTO at ThinkWeb, presented a practical guide to building healthcare applications with a high level…