Introduction
Here is a short guide about how to show test coverage of a Flutter app in Visual Studio Code. With code coverage, you can identify parts of your app that aren’t tested yet. However, it doesn’t tell you if your tests are good or your app is free of bugs!
We are going to use Visual Studio Code and two free extensions from the Visual Studio Marketplace:


If you are unfamiliar with the concept of unit testing and how to write tests for a Flutter app please check my other article where I explain the basics of testing.

The test subject
I created a simple class called login_service.dart
. It allows logging in, logging out, and checking the current state (logged in or not). It’s very basic and has flaws (like hard-coded user name and password) but will be enough to demonstrate how coverage works.
class LoginService {
final String _expectedPassword = "abc123!?=";
final String _expectedUser = "superUser";
bool _isLoggedIn = false;
void login(String? user, String? password) {
if (_isLoggedIn) throw Exception("Please log out first");
if (user != _expectedUser) throw Exception("Wrong user name");
if (password != _expectedPassword) throw Exception("Wrong password");
_isLoggedIn = true;
}
void logout() {
_isLoggedIn = false;
}
bool isLoggedIn() {
return _isLoggedIn;
}
}
The unit tests
Furthermore, we have some unit tests to cover all possible statements of the LoginService
. You can see it in the file below.
import 'package:flutter_test/flutter_test.dart';
import 'package:flutter_test_coverage/login_service.dart';
void main() {
test("Verify failed login with wrong user", () {
var _sut = LoginService();
expect(() => _sut.login("user", "abc123!?="), throwsException);
expect(_sut.isLoggedIn(), isFalse);
});
test("Verify failed login with wrong password", () {
var _sut = LoginService();
expect(() => _sut.login("superUser", "password"), throwsException);
expect(_sut.isLoggedIn(), isFalse);
});
test("Verify logout before login", () {
var _sut = LoginService();
_sut.login("superUser", "abc123!?=");
expect(_sut.isLoggedIn(), isTrue);
expect(() => _sut.login("superUser", "abc123!?="), throwsException);
expect(_sut.isLoggedIn(), isTrue);
});
test("Verify successful login", () {
var _sut = LoginService();
_sut.login("superUser", "abc123!?=");
expect(_sut.isLoggedIn(), isTrue);
});
test("Verify logout works", () {
var _sut = LoginService();
expect(_sut.isLoggedIn(), isFalse);
_sut.login("superUser", "abc123!?=");
expect(_sut.isLoggedIn(), isTrue);
_sut.logout();
expect(_sut.isLoggedIn(), isFalse);
_sut.logout();
expect(_sut.isLoggedIn(), isFalse);
});
}
Collect coverage information
Flutter has a built-in command to collect coverage information while executing all tests. So you just need to open a shell of your choice, navigate to the project root folder, and execute the following command flutter test --coverage
.
This will execute all tests in your project and create a file lcov.info
which contains the coverage information. The extensions you installed earlier rely on the file to visualize the information.
Become A Testing Expert!

Become a proficient Flutter app tester with my detailed guide. This ebook covers everything from unit tests over widget tests up to dependency mocking.
Show covered lines in the editor
After the coverage information has been collected open a file that has been tested (in this example the login_service.dart
file). You should see something like this.

A green line means that there is a test executing this code line while a red line means that there is no test executing this code line. This class has a coverage of 100% as all unmarked lines (like field declarations) are not measured by the Flutter tool.
❗
Warning
Be aware that the colors don’t indicate if a test passes or not. They just tell you if there is any test for a line.
If you can’t see any colorings check the status bar and enable the coverage gutters.


Show coverage information per file
In bigger projects, you’d like to have an overview of those files that have sufficient test coverage and those that don’t. To solve this problem you can use the Flutter Coverage extension. It shows the coverage percentage of every dart file in your project. Go to your Test Explorer in VS Code and open the Flutter Coverage drawer. You should see something like this.

The coverage of the login_service.dart
class is 100% as we have concluded before. Especially if your project gets bigger and bigger, this view will be quite handy to identify insufficiently tested classes.
Credits
If you like the extensions, the developers appreciate a rating or any feedback.
Source code
You can find the source code on GitHub.
Conclusion
In this article, you saw how to show test coverage of a Flutter app in Visual Studio Code. All it takes are two extensions and the built-in Flutter tools. With code coverage, you can better identify what parts of your app need more testing.
Related articels

