Laravel the right way (PART 1) - 10 Laravel meetup

Recently, I have been to the Laravel meetup, and I had the pleasure to talk about good practices and common mistakes that newbies in Laravel make on a daily basis. We also had Guilherme Guitte’s talk, who spoke about how Elasticsearch works.

Laravel the right way

There are a few topics that I have come across over and over during my daily work as a developer using Laravel. This bothers me because some of them are so easy to understand and use that I decided to divide them into a few topics and try to guide developers to better Laravel usage. We will go through Composer packages, directory structures, and the Laravel docs to compose these topics. So let’s dive in.

Models

Laravel is a framework that gives the developer big responsibility. It gives you the ability to freely choose the location of your models. Laravel doesn’t care if you want to place them in the root directory, divide them into subdirectories, or just place them anywhere in the framework. The freedom that we have is huge, and sometimes new developers don’t know how to handle that. (Or if you’re an experienced developer, you may not know what the best place to store the files is.)

Models

So here, I present what I have found useful in how to handle models, and the solution is simple: store them in a folder called Models.

To keep things even better, you can also create subdirectories inside the Models folder, as long as it makes sense to do so.

Models don’t last forever: repositories to the rescue

This topic is totally apart from Laravel’s framework base, which means that we are going to talk about a package called l5-repository. This package is used with the Laravel framework to make it possible to use the repository pattern.

It queries the data source for the data, maps the data from the data source to a business entity, and persists changes in the business entity to the data source. A repository separates the business logic from the interactions with the underlying data source or Web service.

As our application grows, it is normal to have a lot of files, a lot of classes, and many assets to handle. It is no different with our models. In the MVC pattern, we use models to store the business logic.

Business rules inside a model

There is nothing to fear when dealing with small applications, but if you have an application that is a little bit bigger, you are going to start having many methods inside a single file. Don’t believe me? Let’s have a look at a real application:

Too many methods

What’s the problem with that? It seems perfect, right? The first problem here is the coupled access to the data in the database. This is tightly tied to the model’s methods. The second problem is that if we need to reuse the code in another method, let’s say only the where clause, it would be impossible.

Besides the persistence layer, we have coupled some business logic into our models, as the figure above shows us. We have at least 8 methods, and by their names, we can see that there are rules behind them.

Introducing services

My point of view in doing all of this is: ok, you have the MVC pattern and can build your application really well, but there are a few gaps. The first is project organization (should I always add the business rule inside a model? What if I have the same rule but in a different kind? How would you use polymorphism?). The second is the size of the project. With three main folders (model, view, controller), it will get too many files really quickly. The last is modularity: how would you use modules?

regular MVC

For those reasons, we could start using the service layer. The service layer is where all the business rules live.

The basic approach is to build the services, and the service is going to use the models. The controllers will use the service. This must be a single direction, which means that services don’t use controllers. Otherwise, there is no point in having a layer specific to it.

MVC and service layer

The good point of using a service layer is the flexibility that it gives you. It is possible to concentrate the business rules inside this layer and consume them.

Imagine two different controllers: one needs to return JSON to the client, and the other XML. In regular MVC, you could have two different methods inside your model, call each controller the methods needed, and everything just works. But one of the problems is testability and the S.O.L.I.D. violation.