Testing a PHP/Laravel Application
Oliver Sarfas • June 6, 2019
programming laravelLove it or hate it, testing is a necessary evil. It proves that your application works as intended and hopefully covers off any "unwanted features" slipping in. With the recent rise in TDD, I'm going to dive into the different methods of testing, and how you can implement each one in your organisation.
There are various methods of testing, they will either be functional or non-functional. For this article, I'll only be looking at the functional tests. I'll be sure to do a follow-up article about the non-functional in the near future.
Functional tests can be broken down into many, many, different categories - depending on how granular you feel like being. However, for your sanity as a reader, I'll keep the list short and concise.
Unit Testing
The process in which the developer / programmer takes apart the core classes / objects within an application, and writes tests to ensure that the "Unit" works in isolation.
Break down your code into small chunks
The definition of a "Unit" is technically the smallest possible version of a resource. However this is often argued in teams. Just how granular do you go? Is a Class a Unit? A method? Do you have to write a test for every getter and setter? What about magic methods? The list goes on.
Integration / Feature Testing
One level up from Unit testing, Integration tests ensure that your "Units" can work together and achieve expected results.
2 Unit tests. No Integration tests 🤷♂️
An example of this would be, I have a request coming in that should store a record in the database. I'll need an Integration/Feature test for the process around that request. The flow of which would be;
Request comes in (randomly generated data)
Request is handled
Confirm validation checks
No session errors
Response code is as expected
Response body is as expected (JSON structure, or contains certain things)
Database now contains expected data
I'd also expect to see tests for intentionally bad requests to ensure that they are handled accordingly and the database is missing the data.
System Testing
You know the little pieces should work, and those pieces fit together. Now for the full puzzle.
Can you, as a user, navigate through each page without fault. Add data as expected? Functionally, does the site work as intended?
Your application works - kinda
This can be done in a number of ways with Laravel. You can test it yourself, as a developer on a local instance of the application using Homestead, or Valet. Equally, you could write Dusk tests which will run Chrome in a headless mode and run automated browser tests for you.
This is a good chance to give your application to other developers in your team as well, see if there's something that they can think of that potentially you've missed along the way.
Beta/Acceptance/User Testing
Hands off the project. Give it to a 3rd party, or completely isolated user group. Let them destroy it. You want them to find any and all bugs possible at this stage. After this, it's deploy / hand over - so there's no turning back!
Time to disappear and hope that everything works..!
The great thing about this type of testing is that Users are really really stupid at the best of times. But you need to cover this off.
User testing will involve things like;
Cross browser compatibility
Form Validation
Putting a name into a DOB field, because they can
Uploading a 2GB file, again because they can
General UX and UI feedback
Cross platform/device testing
The dreaded "does it work on iPad in both portrait and landscape mode"
Do you support IE? To what versions? Are your users aware of this? How is that handled?
What's this TDD I always hear about?
TDD is Test-Driven Development. The core idea is that the developers will write their Unit and Feature tests before any application / business logic is written.
TDD - the future
You then write the code to pass the test, and refactor once all tests are passing. The biggest takeaways from this is that you have a naturally tested environment and your application is, for the most part, more stable when making changes in the future.
Adding new features will be less prone to sneaky bugs due to unforeseen impact on other elements - as those existing elements have their tests to ensure that they're compatible with requirements.
It's a great methodology and I thoroughly recommend bringing it into your workflow if you can. It is a little slower to produce results for clients though - which doesn't always go down well. It does however deliver more stable, maintainable, and extensible solutions; so there's a great trade off if you can get it in.