DEV Community

Discussion on: Repository Pattern in Laravel, it's worth?

Collapse
 
javiertoledos profile image
Javier Toledo

One example of what Pavel is menttioning is the scenario where your application needs to introduce a caching layer when obtaining information, since your code is tied to eloquent models, you have to search every place where the model is queried or persisted to add that cache layer. If a new developer comes and uses the model without considering the caching layer, he or she can create an invalid caching state where the new data is persisted but old data is being presented by the caching layer because the code doesn't prevent you to do this kind of things.

When the business logic depends on a repository this would abstract this logic and the business won't be aware of that cache logic. Maybe some domain entities could be something that makes sense to be stored in a object based storage like a AWS S3, and the repository can just be swapped to work with it and keep the rest of the logic as it is.

The reason of why people use Active Record to persists behind the repository methods is because it's the easiest way to achieve it in many frameworks. Instead, you would have to use the DBAL without the ORM an create your own data mapper (as mentioned by Pavel) to convert the DTO coming from database to the business model that is represented by it. This sounds a lot more harder, and this is because the frameworks aren't usually built to simplify that, not because it's worse.

Other consequence of using Active record models as business models is that they tend to be used as mere DTO to the persistense layer and the business logic is usually (and wrongly implemented in Controllers). In this scenario everything looks fine, until you find repeating business validations across controllers, or when a new entrypoint for your app is added (i.e. cli or queues) you face the fact that you have to move the business logic to somewhere else (the so called services or use cases).

Active record helps for fast prototyping and small applications, but the pattern exists to solve issues usually found in big enterprise architectures.

Functional testing is nice in Laravel and it's quite fast, however, when you need more layers and different persistence mechanism, you will start seeing that your functional tests leak implementation details making the tests harder to maintain and slower. Unit testing becomes a feasible option under these scenarios.

TL; DR; Implementing repositories using active record persistence methods is wrong and it's not the way the repositories should be implemented, and the repository pattern doesn't exists for the sole purpose of mocking during testing but for decoupling the business logic of how the data is persisted as Pavel mentions.