Tech
Untamo Hirvonen, QA Competence Lead at Wolt
May 26, 2023
How to develop quality products
🙋♀️This blog post is a summary of our QA Competence Lead Untamo’s talk. If you’d rather watch the full video, jump to the end of this blog post to view it!
At Wolt we believe everyone is a tester and everyone should think like a user.
The role of our Quality Assistance (QA) team is to ensure that the software we build provides our customers with exactly what they need. This is the second blog post in our QA blog series, following the earlier blog about Quality Assistance that showcased what our QA mindset looks like at Wolt and how we define, set goals, and define quality together. In this blog post, we’ll dive deeper into what makes a high-quality product and how we think about developing quality products at Wolt.
Firstly, what actually is ‘quality’?
Quality can be hard to define and evaluate as it depends on each user’s subjective view. At Wolt, we aim to define the expectations for quality for all of our teams and groups based on their ownership area and scope.
There are plenty of attributes of quality, including for example:
✅ Reliable: the product should be reliable across environments (both development and production)
✅ Maintainable: the product should be easy to extend with new features and refactor existing code
✅ Efficient: the product should be using the computing resources efficiently and performing well under load
✅ Testable: the product should be divided into separate modules and units that are easy to test in isolation.
✅ Secure: the product should be secure and user data and privacy should be kept with utmost care
To start assessing the quality of a product, testing plays a key role. There are two ways of testing when it comes to software development:
Functional testing is all about the user's perspective — who’s the customer, how will they use the product, how easy it is to use, and how well it solves the problem or need the customer has.
Non-functional testing is more technical — it focuses on things like system architecture and how the product is built, maintained, and how performant and secure it is. It also includes accessibility and usability — your product should work for all the different customers and the ways in which they use the product.
Once a product is tested we must verify and validate how and why we’ve built it to ensure we’re on the right track and are constantly learning and innovating our products.
To verify we need to ask: are we building the product right? This is done by comparing what the plans were to build initially to the final result. In this phase, we aim to identify and fix all implementation-related challenges.
To validate we need to ask: are we building the right product? This is where it gets interesting as you need to define who we’re building the product for and how easy to use or accessible is the product. In validation, you need to step into your user’s shoes to truly understand how the product works to make sure that your test is right.
Often in product development, it can be easy to verify what you’re building but forget to validate if you’re truly building the right things for your customers. At Wolt we put effort into making sure we don’t just verify but also validate what we’re building, by ensuring our teams are close to our customers and the problems that users are facing. That’s why our product teams are small, cross-functional, autonomous, and focused around specific user groups or needs, to be able to solve the right things. This way we can make sure we build quality products for them, and that’s where the importance of a quality mindset comes in.
Why quality is everyone’s responsibility
Traditionally, companies often have a tester or a team of testers that spend their time testing the code and spotting bugs. But if one person or a separate team does all the testing that can create blockers:
No ownership: the team doesn't own the product end-to-end so quality is owned by the tester who might not know it either.
Bottlenecks: as a product grows the scope for testing does too which slows down the process
Errors: people make mistakes and if you rely on just one person, that increases the pressure and incidence
Missing the user POV (Point of View): when the team building something isn’t part of testing, they easily miss the usability element that is key to everything we do
When everyone’s involved in testing we can improve:
Team ownership: teams own the quality of the product from idea to production
Fewer errors: people still make mistakes but more eyes on things helps a lot
Scalability: everyone testing stops one person from being the bottleneck
Understanding the product: by testing the product the team gets to grips with the user’s POV
How to build a quality mindset
You don’t need a background in computer science to know how to test. At Wolt we’re all testers. As quality means different things to different people, we believe in creating a mindset that allows all of us to own quality, whether you’re a software engineer or a product designer.
So how is a quality mindset built? First and foremost you need to think like your user and solve problems from their perspective. Get to grips with and understand your products, know how to use them, and know the features of your products inside and out. Putting yourself in your customer’s shoes will help you solve their problem and add value to them.
Finally, work together to solve problems. Getting into the mindset where quality is king means taking ownership beyond the obvious. Knowledge-sharing, collaboration with teams outside of your own, and even solving problems that might not be in your day-to-day role can help to collaborate more effectively.
At Wolt, our 60+ product teams share knowledge in various ways to keep in touch and align with each other. On the wider Product team level, we actively keep in touch about each new feature release, hold product all-hands meetings where teams share what they’ve worked on, and communicate very closely with other product teams in the day-to-day. Amongst our engineers, we host biweekly engineering competence meetups with knowledge-sharing around different technologies while we also host testing parties where we test the product together. More on those parties in a bit!
Here are some foundational thoughts on how we think a quality mindset differs from simply writing lines of code:
To ensure our teams can build on this quality mindset, our QA engineers focus on quality assistance, rather than traditional quality assurance. A few ways in which we do this in practice are:
Planning tests together, so everyone’s on the same page about the objectives and approach we’re taking when developing new features. This involves mapping out potential risks beforehand so they can be mitigated from the start and development can be done with the least amount of effort. Think of preventing instead of detecting or reacting.
Coaching and doing pair development so teams can take ownership of their testing. We coach teams to ensure they’re always keeping the user perspective in mind when developing something new. Pair development sessions often include talking through what was developed and how. This helps to take you back to the user’s perspective. Sessions always have two main goals: ensure the feature or product is of high quality and teach team members more about testing.
Testing parties are where everyone tests a particular part of the product together before releasing it to the customers. It’s a fun, relaxed environment which creates great conversations about the product and facilitates knowledge-sharing and learning, before shipping it. And of course, we’ve always got some donuts at the testing parties! 🍩
Continuous testing helps to ensure high quality
Continuous testing is a great way to ensure you think about building quality products throughout the software development cycle — from discovery to deploying, releasing, and learning how the release performed in actual usage. Every phase should have testing inbuilt so you’re always testing and innovating to improve the feature.
Ensuring continuous testing helps to create, build, and deploy code and new features efficiently and learn from everything we launch. To enable us to go fast we aim to create test automation to cover most of the regression once the new features have been tested during development. It’s important however to keep in mind that you can’t and shouldn’t automate all testing. For example, we don’t automate testing for our Wolt App UX because usability testing for the app still requires real user testing to have a human touch. So in this case focusing on low-level testing (unit, component, and integration) instead provides the biggest return on investment and enables us to go forward fast.
Figure borrowed from Janet Gregory’s blog: Testing From a Holistic Point of View
In a nutshell — the why, how, and when of testing
To start with the why — we write tests to have confidence that what we’ve built works. And, we often use automated tests to be more efficient and drive higher quality as there’s less room for error. Testing big and small elements of the product allows us to test the whole flow for the user which is essential in building quality.
When thinking about how to build tests, it’s best to start by splitting the functionality into meaningful units (a unit is a small piece of code). Then define the test data, perform the action, and assert the result. Repeat.
Finally, when to build tests? As elaborated with continuous testing, it’s best to do testing throughout the development process in different forms. We aim to write automated tests along the way to ensure the quality is high at the end. Testing only at the end can be very costly and hasn’t allowed your product to evolve during the development process.
Takeaways
Quality is a shared responsibility — there shouldn’t be a single person or team that makes sure you’re building quality products, but it’s everyone’s responsibility
Everyone is a tester, the team should take ownership of the work
Think like your user and make sure you deeply understand the product you’re building to build high-quality products, not just lines of code
Make sure you incorporate continuous testing throughout your development cycle — it can be very costly to only do testing at the end
Hungry for more details on the topic? Watch Untamo’s full talk below 👇