๐๐ผ๐ ๐ ๐๐ถ๐๐ฒ ๐๐ถ๐ป๐ฒ ๐๐ฟ๐ฐ๐ต๐ถ๐๐ฒ๐ฐ๐๐๐ฟ๐ฒ ๐ง๐ฒ๐๐ ๐๐ฎ๐๐ด๐ต๐ ๐ ๐๐ฎ๐๐ฎ ๐๐ฒ๐ฎ๐ธ
A human code review missed a major security flaw.
Our team had a rule. Every model with tenant data must use the BelongsToTenant trait. This trait prevents one client from seeing another client's data.
A new developer joined the team. They added a new model but forgot the trait. The reviewer focused on the business logic. They did not notice the missing trait. The code went live.
For two days, one clinic saw fragments of another clinic's data. A support ticket found the error. Our tests did not.
That day, we started using architecture tests.
Most tests check behavior. They check if input produces the right output. Architecture tests check structure. They check how you organize your code.
Pest PHP has a function for this. You can write rules like these:
- Tenant models must use the BelongsToTenant trait.
- Controllers cannot use the DB facade directly.
- Services cannot depend on the HTTP request.
- No env calls outside config files.
These tests run in your CI pipeline on every commit. If a developer breaks a rule, the build fails. It tells you exactly which file broke the rule.
The tenant trait test caught four more data leaks in the following months. That one test paid for itself.
The env test prevents a common Laravel trap. Calling env directly works in development but returns null in production when you cache your config. This test makes that mistake impossible.
If you add these tests to an old codebase, do not add them all at once. A wall of red failures makes teams angry. Do this instead:
- Start with one rule. Pick your most important rule.
- Fix the existing violations for that rule.
- Add one new rule per week.
- Use the ignoring method for legacy code.
This enforces the rule for new code while you fix the old code slowly.
Architecture tests make your code predictable. Isolation becomes a fact instead of a hope. The machine checks the rules on every commit so humans do not have to remember them.
A rule in a wiki is a suggestion. A rule in CI is real.
What rule would you turn into a test first?