Skip to content

Commit a998bf6

Browse files
Make the build_coverage script more flexible (#37415)
* Make the build_coverage script more flexible * Restyled by prettier-markdown --------- Co-authored-by: Restyled.io <commits@restyled.io>
1 parent 9db6390 commit a998bf6

File tree

2 files changed

+161
-66
lines changed

2 files changed

+161
-66
lines changed

docs/guides/BUILDING.md

+62-15
Original file line numberDiff line numberDiff line change
@@ -589,30 +589,77 @@ SDK source code has been executed. It also provides information on how often the
589589
Matter SDK executes segments of the code and produces a copy of the source file,
590590
annotated with execution frequencies.
591591
592-
Run the following command to initiate the script:
592+
### How to Run
593+
594+
```
595+
./scripts/build_coverage.sh [OPTIONS]
596+
```
597+
598+
By default, the script
599+
600+
Builds the Matter SDK with coverage instrumentation (unless you specify a custom
601+
--output_root). Runs the unit tests to generate coverage data. Produces an HTML
602+
coverage report located at:
603+
604+
```
605+
out/coverage/coverage/html/index.html
606+
```
607+
608+
You can extend the coverage scope and test types with the following options:
609+
610+
Option Description -c, --code=<scope> Specify the scope to collect coverage
611+
data. - core (default): Coverage from the core Matter SDK stack - clusters:
612+
Coverage from cluster implementations - all: Coverage from the entire Matter SDK
613+
614+
--yaml Also run YAML-based tests, in addition to unit tests.
615+
616+
--python Also run Python-based tests, in addition to unit tests.
617+
618+
-o, --output_root=DIR If specified, skip the build phase and only run coverage
619+
on the provided build output directory. This directory must have been built with
620+
use_coverage=true and have had tests run already.
621+
622+
--target=<testname> When running unit tests, specifies a particular test target
623+
to run (e.g., TestEmberAttributeBuffer.run).
624+
625+
-h, --help Print script usage and exit.
626+
627+
### Examples
628+
629+
Run coverage with the default scope (core) and only unit tests:
593630
594631
```
595632
./scripts/build_coverage.sh
596633
```
597634
598-
By default, the code coverage script is performed at the unit testing level.
599-
Unit tests are created by developers, thus giving them the best overview of what
600-
tests to include in unit testing. You can extend the coverage test by scope and
601-
ways of execution with the following parameters:
635+
Run coverage including YAML tests (plus the always-enabled unit tests):
636+
637+
```
638+
./scripts/build_coverage.sh --yaml
639+
```
640+
641+
Run coverage including Python tests (plus the always-enabled unit tests):
602642
603643
```
604-
-c, --code Specify which scope to collect coverage data.
605-
'core': collect coverage data from core stack in Matter SDK. --default
606-
'clusters': collect coverage data from clusters implementation in Matter SDK.
607-
'all': collect coverage data from Matter SDK.
608-
-t, --tests Specify which tools to run the coverage check.
609-
'unit': Run unit test to drive the coverage check. --default
610-
'yaml': Run yaml test to drive the coverage check.
611-
'all': Run unit & yaml test to drive the coverage check.
644+
./scripts/build_coverage.sh --python
612645
```
613646
614-
Also, see the up-to-date unit testing coverage report of the Matter SDK
615-
(collected daily) at:
647+
Run coverage including both YAML and Python tests:
648+
649+
```
650+
./scripts/build_coverage.sh --yaml --python
651+
```
652+
653+
Change coverage scope to all (core + clusters) and run YAML tests:
654+
655+
```
656+
./scripts/build_coverage.sh --code=all --yaml
657+
```
658+
659+
### Viewing Coverage Results
660+
661+
After the script completes, open the following file in your web browser to view
662+
the HTML coverage report:
616663
[matter coverage](https://matter-build-automation.ue.r.appspot.com).
617664
618665
## Maintaining Matter

scripts/build_coverage.sh

+99-51
Original file line numberDiff line numberDiff line change
@@ -46,37 +46,45 @@ CHIP_ROOT=$(_normpath "$(dirname "$0")/..")
4646
OUTPUT_ROOT="$CHIP_ROOT/out/coverage"
4747
COVERAGE_ROOT="$OUTPUT_ROOT/coverage"
4848
SUPPORTED_CODE=(core clusters all)
49-
SUPPORTED_TESTS=(unit yaml all)
5049
CODE="core"
51-
TESTS="unit"
50+
5251
skip_gn=false
5352
TEST_TARGET=check
5453

55-
help() {
54+
# By default, do not run YAML or Python tests
55+
ENABLE_YAML=false
56+
ENABLE_PYTHON=false
5657

57-
echo "Usage: $file_name [--output_root=<output_root>] [--code=<core|clusters|all>] [--tests=<unit|yaml|all>]"
58+
help() {
59+
echo "Usage: $file_name [--output_root=<output_root>] [--code=<core|clusters|all>] [Test options"
60+
echo
61+
echo "Misc:"
62+
echo " -h, --help Print this help, then exit."
63+
echo
64+
echo "Build/Output options:"
65+
echo " -o, --output_root=DIR Set the build output directory."
66+
echo " When set manually, script only runs lcov on the provided build output."
67+
echo " This directory must be built with 'use_coverage=true' and 'ninja check' must have run."
68+
echo
69+
echo " -c, --code=TYPE Specify which scope to collect coverage data. One of:"
70+
echo " core - (default) coverage from core stack in Matter SDK."
71+
echo " clusters - coverage from cluster implementations in Matter SDK."
72+
echo " all - coverage from entire Matter SDK."
5873
echo
59-
echo "Misc:
60-
-h, --help Print this help, then exit."
74+
echo "Test options:"
75+
echo " --yaml In addition to unit tests, run YAML-based tests."
76+
echo " --python In addition to unit tests, run Python-based tests."
77+
echo " Both can be combined if needed."
78+
echo
79+
echo " --target=TARGET Specific test target to run for unit tests (e.g. 'TestEmberAttributeBuffer.run')."
6180
echo
62-
echo "Options:
63-
-o, --output_root Set the build output directory. When set manually, performs only lcov stage
64-
on provided build output. Assumes output_root has been built with 'use_coverage=true'
65-
and that 'ninja check' was run.
66-
-c, --code Specify which scope to collect coverage data.
67-
'core': collect coverage data from core stack in Matter SDK. --default
68-
'clusters': collect coverage data from clusters implementation in Matter SDK.
69-
'all': collect coverage data from Matter SDK.
70-
-t, --tests Specify which tools to run the coverage check.
71-
'unit': Run unit test to drive the coverage check. --default
72-
'yaml': Run yaml test to drive the coverage check.
73-
'all': Run unit & yaml test to drive the coverage check.
74-
--target Specific test target to run (e.g. TestEmberAttributeBuffer.run)
75-
"
7681
}
7782

7883
file_name=${0##*/}
7984

85+
# ------------------------------------------------------------------------------
86+
# Parse arguments
87+
# ------------------------------------------------------------------------------
8088
for i in "$@"; do
8189
case $i in
8290
-h | --help)
@@ -87,19 +95,24 @@ for i in "$@"; do
8795
CODE="${i#*=}"
8896
shift
8997
;;
90-
-t=* | --tests=*)
91-
TESTS="${i#*=}"
92-
shift
93-
;;
9498
--target=*)
9599
TEST_TARGET="${i#*=}"
100+
shift
96101
;;
97102
-o=* | --output_root=*)
98103
OUTPUT_ROOT="${i#*=}"
99104
COVERAGE_ROOT="$OUTPUT_ROOT/coverage"
100105
skip_gn=true
101106
shift
102107
;;
108+
--yaml)
109+
ENABLE_YAML=true
110+
shift
111+
;;
112+
--python)
113+
ENABLE_PYTHON=true
114+
shift
115+
;;
103116
*)
104117
echo "Unknown Option \"$1\""
105118
echo
@@ -109,49 +122,63 @@ for i in "$@"; do
109122
esac
110123
done
111124

125+
# Validate code argument
112126
if [[ ! " ${SUPPORTED_CODE[@]} " =~ " ${CODE} " ]]; then
113127
echo "ERROR: Code $CODE not supported"
114128
exit 1
115129
fi
116130

117-
if [[ ! " ${SUPPORTED_TESTS[@]} " =~ " ${TESTS} " ]]; then
118-
echo "ERROR: Tests $TESTS not supported"
119-
exit 1
120-
fi
121-
131+
# ------------------------------------------------------------------------------
132+
# Build & Test
133+
# ------------------------------------------------------------------------------
122134
if [ "$skip_gn" == false ]; then
123-
# Ensure we have a compilation environment
135+
# Ensure environment is set
124136
source "$CHIP_ROOT/scripts/activate.sh"
125137

126-
# Generates ninja files
138+
# Generate ninja files
127139
EXTRA_GN_ARGS=""
128-
if [[ "$TESTS" == "yaml" || "$TESTS" == "all" ]]; then
140+
141+
# We only need 'chip_build_all_clusters_app' if we run YAML tests
142+
if [ "$ENABLE_YAML" == true ]; then
129143
EXTRA_GN_ARGS="$EXTRA_GN_ARGS chip_build_all_clusters_app=true"
130144
else
145+
# Otherwise skip building tools
131146
EXTRA_GN_ARGS="$EXTRA_GN_ARGS chip_build_tools=false"
132147
fi
133-
gn --root="$CHIP_ROOT" gen "$OUTPUT_ROOT" --args="use_coverage=true$EXTRA_GN_ARGS"
134148

135-
# Run unit tests
136-
if [[ "$TESTS" == "unit" || "$TESTS" == "all" ]]; then
137-
ninja -C "$OUTPUT_ROOT" "$TEST_TARGET"
138-
fi
149+
gn --root="$CHIP_ROOT" gen "$OUTPUT_ROOT" --args="use_coverage=true $EXTRA_GN_ARGS"
150+
151+
#
152+
# 1) Always run unit tests
153+
#
154+
ninja -C "$OUTPUT_ROOT" "$TEST_TARGET"
139155

140-
# Run yaml tests
141-
if [[ "$TESTS" == "yaml" || "$TESTS" == "all" ]]; then
156+
#
157+
# 2) Run YAML tests if requested
158+
#
159+
if [ "$ENABLE_YAML" == true ]; then
142160
ninja -C "$OUTPUT_ROOT"
143161

144162
scripts/run_in_build_env.sh \
145163
"./scripts/tests/run_test_suite.py \
146-
--chip-tool ""$OUTPUT_ROOT/chip-tool \
164+
--chip-tool \"$OUTPUT_ROOT/chip-tool\" \
147165
run \
148166
--iterations 1 \
149167
--test-timeout-seconds 120 \
150-
--all-clusters-app ""$OUTPUT_ROOT/chip-all-clusters-app
151-
"
168+
--all-clusters-app \"$OUTPUT_ROOT/chip-all-clusters-app\""
169+
fi
170+
171+
#
172+
# 3) Run Python tests if requested
173+
#
174+
if [ "$ENABLE_PYTHON" == true ]; then
175+
echo "Running Python tests ..."
176+
# TODO: run python tests.
152177
fi
153178

154-
# Remove misc support components from coverage statistics
179+
# ----------------------------------------------------------------------------
180+
# Remove objects we do NOT want included in coverage
181+
# ----------------------------------------------------------------------------
155182
rm -rf "$OUTPUT_ROOT/obj/src/app/app-platform"
156183
rm -rf "$OUTPUT_ROOT/obj/src/app/common"
157184
rm -rf "$OUTPUT_ROOT/obj/src/app/util/mock"
@@ -162,24 +189,45 @@ if [ "$skip_gn" == false ]; then
162189
rm -rf "$OUTPUT_ROOT/obj/src/platform"
163190
rm -rf "$OUTPUT_ROOT/obj/src/tools"
164191

165-
# Remove unit test itself from coverage statistics
192+
# Remove unit test objects from coverage
166193
find "$OUTPUT_ROOT/obj/src/" -depth -name 'tests' -exec rm -rf {} \;
167194

195+
# Restrict coverage to 'core' or 'clusters' if specified
168196
if [ "$CODE" == "core" ]; then
169197
rm -rf "$OUTPUT_ROOT/obj/src/app/clusters"
170198
elif [ "$CODE" == "clusters" ]; then
171199
mv "$OUTPUT_ROOT/obj/src/app/clusters" "$OUTPUT_ROOT/obj/clusters"
172200
rm -rf "$OUTPUT_ROOT/obj/src"
173-
mkdir "$OUTPUT_ROOT/obj/src"
201+
mkdir -p "$OUTPUT_ROOT/obj/src"
174202
mv "$OUTPUT_ROOT/obj/clusters" "$OUTPUT_ROOT/obj/src/clusters"
175203
fi
176204
fi
177205

206+
# ------------------------------------------------------------------------------
207+
# Coverage Generation
208+
# ------------------------------------------------------------------------------
178209
mkdir -p "$COVERAGE_ROOT"
179-
lcov --initial --capture --ignore-errors inconsistent --directory "$OUTPUT_ROOT/obj/src" --exclude="$PWD"/zzz_generated/* --exclude="$PWD"/third_party/* --exclude=/usr/include/* --output-file "$COVERAGE_ROOT/lcov_base.info"
180-
lcov --capture --ignore-errors inconsistent --directory "$OUTPUT_ROOT/obj/src" --exclude="$PWD"/zzz_generated/* --exclude="$PWD"/third_party/* --exclude=/usr/include/* --output-file "$COVERAGE_ROOT/lcov_test.info"
181-
lcov --ignore-errors inconsistent --add-tracefile "$COVERAGE_ROOT/lcov_base.info" --add-tracefile "$COVERAGE_ROOT/lcov_test.info" --output-file "$COVERAGE_ROOT/lcov_final.info"
182-
genhtml "$COVERAGE_ROOT/lcov_final.info" --output-directory "$COVERAGE_ROOT/html" --title "SHA:$(git rev-parse HEAD)" --header-title "Matter SDK Coverage Report"
183210

184-
# Copy webapp's YAML file to the coverage output directory
185-
cp "$CHIP_ROOT/integrations/appengine/webapp_config.yaml" "$COVERAGE_ROOT/webapp_config.yaml"
211+
lcov --initial --capture --directory "$OUTPUT_ROOT/obj/src" \
212+
--exclude="$PWD"/zzz_generated/* \
213+
--exclude="$PWD"/third_party/* \
214+
--exclude=/usr/include/* \
215+
--output-file "$COVERAGE_ROOT/lcov_base.info"
216+
217+
lcov --capture --directory "$OUTPUT_ROOT/obj/src" \
218+
--exclude="$PWD"/zzz_generated/* \
219+
--exclude="$PWD"/third_party/* \
220+
--exclude=/usr/include/* \
221+
--output-file "$COVERAGE_ROOT/lcov_test.info"
222+
223+
lcov --add-tracefile "$COVERAGE_ROOT/lcov_base.info" \
224+
--add-tracefile "$COVERAGE_ROOT/lcov_test.info" \
225+
--output-file "$COVERAGE_ROOT/lcov_final.info"
226+
227+
genhtml "$COVERAGE_ROOT/lcov_final.info" \
228+
--output-directory "$COVERAGE_ROOT/html" \
229+
--title "SHA:$(git rev-parse HEAD)" \
230+
--header-title "Matter SDK Coverage Report"
231+
232+
cp "$CHIP_ROOT/integrations/appengine/webapp_config.yaml" \
233+
"$COVERAGE_ROOT/webapp_config.yaml"

0 commit comments

Comments
 (0)