Testingmania #1: Unit Testing Laravel Models

Some might consider Laravel model testing to be a gruesome task, especially when there’s plenty of them in the codebase, and most of them are covered by other unit or feature tests. However, to get to that sweet 100% (or so) coverage, these tests need to be carried out. Plus, you can be much more specific when testing them in isolation.

The model we’re testing goes like this, stripped of comments and similar relationships and attributes since we need to show only one of each thing we’re testing.

Testing that the model has the expected columns

The first assertion that we want to do is to check if the model has all the important columns in the database. This will ensure that whatever happens, the models’ schema will be accounted for.

Testing that the model has the expected attributes

The Photo model has a selected attribute, and we can't know for sure that it will always be there unless we write a test for it. The attribute simply returns false at the time of writing, which is the only thing we need to test.

Testing the relationships on the model

When testing model relationships there are generally two things I want to test. The first one is the relationship type or the class of the object being returned, and the second is checking whether the object returned is the correct one. This has proven to me to work well on many occasions, it’s neither too strict nor too relaxed.

Testing the methods on the model

Notice the Photo has a categories method. It simply returns an array of strings, so we make a simple assertion for that.

The next stop is the tags method. What it does is basically strips the empty tags off of every category relationship of the model. Since we're unit testing, we don't need to know why, we just need to know that it works. So:

The total method calculates the total number of litter present in a Photo by summing the totals of each category. It should filter out the litter for brands and for that reason we include an item for it. However, we test that it does not get added to the total number of items:

The code used for illustration is taken from the OpenLitterMap project. They’re doing a great job creating the world’s most advanced open database on litter, brands & plastic pollution. The project is open-sourced and would love your contributions, both as users and developers.

Originally published at https://genijaho.dev on June 10, 2021.

Full-stack web developer with a passion for software architecture and cloud computing.

Full-stack web developer with a passion for software architecture and cloud computing.