Testing fundamentals

Over the past few months, I've been learning how testing works in programming. The main reason for this was to improve myself as a developer. And because it was so useful, I thought why not make a post about it. So, here it is.

The basics

When working on a new application, or maintaining old ones you always discover bugs. In the case of an older application, most of the bugs are already in production. Most of these bugs come from a simple change you might have made on the code. This change might have nothing to do with the bug, but after all that's how code works. To prevent bugs from entering your code you can add tests to your project. With tests you can automatically check if the code still does what it's intended to do. Adding tests also helps any new dev understand how the code works. But where to start.

As a backend developer, the best way to start is by writing unit tests. You create a unit test to check a small piece of code (mostly functions) for errors. When creating a unit test, you first execute the function to then check if the results of that function are as expected. So when you later change the function, you still now that it returns the right result.

Now, unit tests are nice, but sometimes you might have whole actions. Those actions use the functions and returns a combined result of those functions. So for example, I have a CreateUserAction.php file in which I first check if the provided data is correct and what I need. Then I create the user. After that, I check the email if it matches the administrator mail, if so assign the user a admin role if not assign it the basic role. And when all that is done, return the user. There are some important things that has to work as intended, otherwise someone may get the wrong role. Or an exception is thrown. Therefore we write a Feature Test. In these tests you can:

  • Check if the result is as expected
  • Make sure that, when given wrong data, it doesn't proceed.
  • Test if none of the users get a wrong role with specific data. As you already can see, it's so useful to write tests.

But what if you have a frontend application, that talks to an api. In this application you have forms, navigation, tables maybe even more interactive elements that can be broken. There even is a way to test that, it's named E2E testing. With E2E testing you can write the flow a user has to follow, the framework then walks through this flow to make sure everything works as intended. So for example, when you have an authentication flow, you want to make sure a user get's the right error when providing wrong credentials. And if given the right ones, you want to see if the user gets redirected to the dashboard. In each test you can write these expectations as expect. The framework then knows it has to check the page for this expectation. How nice is that.

Digging deeper

There is so much more than just testing existing code. The most interesting thing is, Test Driven Development. It's a technique you can use to write test before writing your code. With this technique you always make sure that the code you write will return the expected result. But it doesn't work always, in some cases you don't need a test. Maybe because you are sure something works, or maybe just because it's not necessary. In that case you can just skip the Test part and go straight into coding the solution.

There is another interesting thing, Behaviour driven development (BDD). With BDD you kinda write user stories in a programmatically way. This gives a project manager or team member who is not a programmer the power to explain a specific workflow (like logging in or creating a post) and then test it. This solution is perfect for bigger companies starting new projects. Mostly because it's really time consuming to write these tests.

Useful packages

When getting into testing, I found some really useful packages that might help you get started.

  • PestPHP a testing frameworks that adds a simpeler syntax to phpunit and some really nice functions.
  • Playwright a cross platform e2e testing framework with lots of nice helper functions and examples.
  • Pest plugin GWT a small package that gets you started with BDD

Conclusion

Testing is a fundamental part of programming. If you take your time to write well thought tests, you improve the quality of the project and reduce bugs. Especially in the future you might find out why tests are as useful as everyone says they are. But as I said, writing tests takes time, and time is not always your friend. That's why it might be useful to just take the time in the first place. This can be done by writing the test before writing the implementation.

It all comes down to how much you think it's needed to write tests. If you don't think it's useful, then don't do it. Because if that's the case, you may wright useless tests that won't be updated when necessary. So, to conclude. First think about how useful a test might be, if it's useful then write it. Find ways that work for you and push it in when you might not have the time. Others may not see why its necessarily but in the end it is useful.