Model Testing Strategies

Learn about model testing strategies in our Rails application.

Models tend to be inputs to (and outputs of) our business logic. In many cases, models are only bags of data, so they don’t require that much testing themselves. That said, there are three considerations related to model testing:

  • Tests for database constraints, like we wrote in Writing Tests for Database Constraints in the previous lessons of this course, naturally belong in the Active Record whose backing table has the constraint.
  • Although simple validations might not benefit from tests, complex validations and callbacks certainly do.
  • There should be an easy ability to produce reliable and realistic test instances of the model. We prefer Factory Bot over Rails’ fixtures.

Let’s go through each of these in a bit more detail.

Active record tests should test database constraints

We already saw an example of this in the previous lesson, but for completeness, the model is the best place to put tests of the database constraints because the model is backed by the database table.

When writing these tests, we make sure to use update_column so we can modify the database directly. We want our test to continue to function even if the model gets more validations or callbacks. We also make sure we assert as closely on the error as we can. We watch the test fail to see what error the database produces. Then, we craft a regular expression that matches as specifically as possible so that the test will only fail if the constraint is violated.

Tests for complex validations or callbacks

Although our before_validation callback is just a few lines of code, there’s value in testing it. At the very least, it prevents someone from removing it without thinking about it. Let’s write two tests, one for an empty string and one for a string with spaces in it.

Get hands-on with 1200+ tech skills courses.