xref: /aosp_15_r20/external/pigweed/pw_unit_test/unit_test_service.cc (revision 61c4878ac05f98d0ceed94b57d316916de578985)
1 // Copyright 2020 The Pigweed Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
5 // the License at
6 //
7 //     https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
13 // the License.
14 
15 #include "pw_unit_test/unit_test_service.h"
16 
17 #include "pw_containers/vector.h"
18 #include "pw_log/log.h"
19 #include "pw_protobuf/decoder.h"
20 #include "pw_unit_test/framework.h"
21 
22 namespace pw::unit_test {
23 
Run(ConstByteSpan request,RawServerWriter & writer)24 void UnitTestService::Run(ConstByteSpan request, RawServerWriter& writer) {
25   writer_ = std::move(writer);
26   verbose_ = false;
27 
28   // List of test suite names to run. The string views in this vector point to
29   // data in the raw protobuf request message, so it is only valid for the
30   // duration of this function.
31   pw::Vector<std::string_view, 16> suites_to_run;
32 
33   protobuf::Decoder decoder(request);
34 
35   Status status;
36   while ((status = decoder.Next()).ok()) {
37     switch (static_cast<pwpb::TestRunRequest::Fields>(decoder.FieldNumber())) {
38       case pwpb::TestRunRequest::Fields::kReportPassedExpectations:
39         decoder.ReadBool(&verbose_)
40             .IgnoreError();  // TODO: b/242598609 - Handle Status properly
41         break;
42 
43       case pwpb::TestRunRequest::Fields::kTestSuite: {
44         std::string_view suite_name;
45         if (!decoder.ReadString(&suite_name).ok()) {
46           break;
47         }
48 
49         if (!suites_to_run.full()) {
50           suites_to_run.push_back(suite_name);
51         } else {
52           PW_LOG_ERROR("Maximum of %u test suite filters supported",
53                        static_cast<unsigned>(suites_to_run.max_size()));
54           writer_.Finish(Status::InvalidArgument())
55               .IgnoreError();  // TODO: b/242598609 - Handle Status properly
56           return;
57         }
58 
59         break;
60       }
61     }
62   }
63 
64   if (status != Status::OutOfRange()) {
65     writer_.Finish(status)
66         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
67     return;
68   }
69 
70   PW_LOG_INFO("Starting unit test run");
71   handler_.ExecuteTests(suites_to_run);
72   PW_LOG_INFO("Unit test run complete");
73 
74   writer_.Finish().IgnoreError();  // TODO: b/242598609 - Handle Status properly
75 }
76 
WriteTestRunStart()77 void UnitTestService::WriteTestRunStart() {
78   // Write out the key for the start field (even though the message is empty).
79   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
80     event.GetTestRunStartEncoder();
81   });
82 }
83 
WriteTestRunEnd(const RunTestsSummary & summary)84 void UnitTestService::WriteTestRunEnd(const RunTestsSummary& summary) {
85   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
86     pwpb::TestRunEnd::StreamEncoder test_run_end = event.GetTestRunEndEncoder();
87     test_run_end.WritePassed(summary.passed_tests)
88         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
89     test_run_end.WriteFailed(summary.failed_tests)
90         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
91     test_run_end.WriteSkipped(summary.skipped_tests)
92         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
93     test_run_end.WriteDisabled(summary.disabled_tests)
94         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
95   });
96 }
97 
WriteTestCaseStart(const TestCase & test_case)98 void UnitTestService::WriteTestCaseStart(const TestCase& test_case) {
99   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
100     pwpb::TestCaseDescriptor::StreamEncoder descriptor =
101         event.GetTestCaseStartEncoder();
102     descriptor.WriteSuiteName(test_case.suite_name)
103         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
104     descriptor.WriteTestName(test_case.test_name)
105         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
106     descriptor.WriteFileName(test_case.file_name)
107         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
108   });
109 }
110 
WriteTestCaseEnd(TestResult result)111 void UnitTestService::WriteTestCaseEnd(TestResult result) {
112   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
113     event.WriteTestCaseEnd(static_cast<pwpb::TestCaseResult>(result))
114         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
115   });
116 }
117 
WriteTestCaseDisabled(const TestCase & test_case)118 void UnitTestService::WriteTestCaseDisabled(const TestCase& test_case) {
119   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
120     pwpb::TestCaseDescriptor::StreamEncoder descriptor =
121         event.GetTestCaseDisabledEncoder();
122     descriptor.WriteSuiteName(test_case.suite_name)
123         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
124     descriptor.WriteTestName(test_case.test_name)
125         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
126     descriptor.WriteFileName(test_case.file_name)
127         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
128   });
129 }
130 
WriteTestCaseExpectation(const TestExpectation & expectation)131 void UnitTestService::WriteTestCaseExpectation(
132     const TestExpectation& expectation) {
133   if (!verbose_ && expectation.success) {
134     return;
135   }
136 
137   WriteEvent([&](pwpb::Event::StreamEncoder& event) {
138     pwpb::TestCaseExpectation::StreamEncoder test_case_expectation =
139         event.GetTestCaseExpectationEncoder();
140     test_case_expectation.WriteExpression(expectation.expression)
141         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
142     test_case_expectation
143         .WriteEvaluatedExpression(expectation.evaluated_expression)
144         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
145     test_case_expectation.WriteLineNumber(expectation.line_number)
146         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
147     test_case_expectation.WriteSuccess(expectation.success)
148         .IgnoreError();  // TODO: b/242598609 - Handle Status properly
149   });
150 }
151 
152 }  // namespace pw::unit_test
153