blob: ccdcce85590b4df7b284183c1db2e2007f49df7f [file] [log] [blame]
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +02001#include "dbus_environment.hpp"
Krzysztof Grobelnyd2238192020-12-02 09:27:28 +00002#include "helpers.hpp"
Wludzik, Jozefe2362792020-10-27 17:23:55 +01003#include "mocks/json_storage_mock.hpp"
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +02004#include "mocks/metric_mock.hpp"
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +02005#include "mocks/report_manager_mock.hpp"
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +02006#include "params/report_params.hpp"
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +02007#include "report.hpp"
8#include "report_manager.hpp"
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +02009#include "utils/conv_container.hpp"
Krzysztof Grobelnye8fc5752021-02-05 14:30:45 +000010#include "utils/tstring.hpp"
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +020011
12#include <sdbusplus/exception.hpp>
13
14using namespace testing;
15using namespace std::literals::string_literals;
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020016using namespace std::chrono_literals;
Krzysztof Grobelnye8fc5752021-02-05 14:30:45 +000017namespace tstring = utils::tstring;
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +020018
19class TestReport : public Test
20{
21 public:
Wludzik, Jozefe2362792020-10-27 17:23:55 +010022 ReportParams defaultParams;
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +020023
24 std::unique_ptr<ReportManagerMock> reportManagerMock =
Wludzik, Jozefe2362792020-10-27 17:23:55 +010025 std::make_unique<NiceMock<ReportManagerMock>>();
26 testing::NiceMock<StorageMock> storageMock;
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000027 std::vector<std::shared_ptr<MetricMock>> metricMocks;
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020028 std::unique_ptr<Report> sut;
29
Wludzik, Jozefe2362792020-10-27 17:23:55 +010030 MockFunction<void()> checkPoint;
31
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000032 void initMetricMocks(
33 const std::vector<LabeledMetricParameters>& metricParameters)
Wludzik, Jozefe2362792020-10-27 17:23:55 +010034 {
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000035 for (auto i = metricMocks.size(); i < metricParameters.size(); ++i)
Wludzik, Jozefe2362792020-10-27 17:23:55 +010036 {
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000037 metricMocks.emplace_back(std::make_shared<NiceMock<MetricMock>>());
38 }
39 metricMocks.resize(metricParameters.size());
Krzysztof Grobelnyd2238192020-12-02 09:27:28 +000040
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000041 std::vector<MetricValue> readings{{MetricValue{"a", "b", 17.1, 114},
42 MetricValue{"aa", "bb", 42.0, 74}}};
43 readings.resize(metricParameters.size());
Krzysztof Grobelnyd2238192020-12-02 09:27:28 +000044
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000045 for (size_t i = 0; i < metricParameters.size(); ++i)
46 {
47 ON_CALL(*metricMocks[i], getReadings())
Krzysztof Grobelny80697712021-03-04 09:49:27 +000048 .WillByDefault(Return(std::vector({readings[i]})));
Krzysztof Grobelnyd2238192020-12-02 09:27:28 +000049 ON_CALL(*metricMocks[i], dumpConfiguration())
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000050 .WillByDefault(Return(metricParameters[i]));
Wludzik, Jozefe2362792020-10-27 17:23:55 +010051 }
52 }
53
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020054 void SetUp() override
55 {
56 sut = makeReport(ReportParams());
57 }
58
Wludzik, Jozefe2362792020-10-27 17:23:55 +010059 static interfaces::JsonStorage::FilePath to_file_path(std::string name)
60 {
61 return interfaces::JsonStorage::FilePath(
62 std::to_string(std::hash<std::string>{}(name)));
63 }
64
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020065 std::unique_ptr<Report> makeReport(const ReportParams& params)
66 {
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000067 initMetricMocks(params.metricParameters());
68
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020069 return std::make_unique<Report>(
70 DbusEnvironment::getIoc(), DbusEnvironment::getObjServer(),
71 params.reportName(), params.reportingType(),
Wludzik, Jozefe2362792020-10-27 17:23:55 +010072 params.emitReadingUpdate(), params.logToMetricReportCollection(),
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +000073 params.interval(), *reportManagerMock, storageMock,
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020074 utils::convContainer<std::shared_ptr<interfaces::Metric>>(
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +020075 metricMocks),
76 params.enabled());
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +020077 }
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +020078
79 template <class T>
80 static T getProperty(const std::string& path, const std::string& property)
81 {
Szymon Dompkee28aa532021-10-27 12:33:12 +020082 return DbusEnvironment::getProperty<T>(path, Report::reportIfaceName,
83 property);
84 }
85
86 template <class T>
87 static boost::system::error_code setProperty(const std::string& path,
88 const std::string& property,
89 const T& newValue)
90 {
91 return DbusEnvironment::setProperty<T>(path, Report::reportIfaceName,
92 property, newValue);
Krzysztof Grobelnyf32f6fe2020-10-30 13:51:58 +010093 }
94
95 boost::system::error_code call(const std::string& path,
96 const std::string& interface,
97 const std::string& method)
98 {
99 std::promise<boost::system::error_code> methodPromise;
100 DbusEnvironment::getBus()->async_method_call(
101 [&methodPromise](boost::system::error_code ec) {
102 methodPromise.set_value(ec);
103 },
104 DbusEnvironment::serviceName(), path, interface, method);
105 return DbusEnvironment::waitForFuture(methodPromise.get_future());
106 }
107
108 boost::system::error_code update(const std::string& path)
109 {
110 return call(path, Report::reportIfaceName, "Update");
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200111 }
112
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200113 boost::system::error_code deleteReport(const std::string& path)
114 {
Krzysztof Grobelnyf32f6fe2020-10-30 13:51:58 +0100115 return call(path, Report::deleteIfaceName, "Delete");
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200116 }
117};
118
119TEST_F(TestReport, verifyIfPropertiesHaveValidValue)
120{
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200121 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Enabled"),
122 Eq(defaultParams.enabled()));
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200123 EXPECT_THAT(getProperty<uint64_t>(sut->getPath(), "Interval"),
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100124 Eq(defaultParams.interval().count()));
125 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Persistency"), Eq(true));
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200126 EXPECT_THAT(getProperty<bool>(sut->getPath(), "EmitsReadingsUpdate"),
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100127 Eq(defaultParams.emitReadingUpdate()));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200128 EXPECT_THAT(
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200129 getProperty<bool>(sut->getPath(), "LogToMetricReportsCollection"),
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100130 Eq(defaultParams.logToMetricReportCollection()));
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000131 EXPECT_THAT(getProperty<ReadingParameters>(
132 sut->getPath(), "ReadingParametersFutureVersion"),
133 Eq(toReadingParameters(defaultParams.metricParameters())));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200134}
135
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200136TEST_F(TestReport, readingsAreInitialyEmpty)
137{
138 EXPECT_THAT(getProperty<Readings>(sut->getPath(), "Readings"),
139 Eq(Readings{}));
140}
141
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200142TEST_F(TestReport, setEnabledWithNewValue)
143{
144 bool newValue = !defaultParams.enabled();
145 EXPECT_THAT(setProperty(sut->getPath(), "Enabled", newValue).value(),
146 Eq(boost::system::errc::success));
147 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Enabled"), Eq(newValue));
148}
149
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200150TEST_F(TestReport, setIntervalWithValidValue)
151{
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100152 uint64_t newValue = defaultParams.interval().count() + 1;
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200153 EXPECT_THAT(setProperty(sut->getPath(), "Interval", newValue).value(),
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200154 Eq(boost::system::errc::success));
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200155 EXPECT_THAT(getProperty<uint64_t>(sut->getPath(), "Interval"),
156 Eq(newValue));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200157}
158
159TEST_F(TestReport, settingIntervalWithInvalidValueDoesNotChangeProperty)
160{
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100161 uint64_t newValue = defaultParams.interval().count() - 1;
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200162 EXPECT_THAT(setProperty(sut->getPath(), "Interval", newValue).value(),
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200163 Eq(boost::system::errc::success));
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200164 EXPECT_THAT(getProperty<uint64_t>(sut->getPath(), "Interval"),
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100165 Eq(defaultParams.interval().count()));
166}
167
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200168TEST_F(TestReport, settingEmitsReadingsUpdateHaveNoEffect)
169{
170 EXPECT_THAT(setProperty(sut->getPath(), "EmitsReadingsUpdate",
171 !defaultParams.emitReadingUpdate())
172 .value(),
173 Eq(boost::system::errc::read_only_file_system));
174 EXPECT_THAT(getProperty<bool>(sut->getPath(), "EmitsReadingsUpdate"),
175 Eq(defaultParams.emitReadingUpdate()));
176}
177
178TEST_F(TestReport, settingLogToMetricReportCollectionHaveNoEffect)
179{
180 EXPECT_THAT(setProperty(sut->getPath(), "LogToMetricReportsCollection",
181 !defaultParams.logToMetricReportCollection())
182 .value(),
183 Eq(boost::system::errc::read_only_file_system));
184 EXPECT_THAT(
185 getProperty<bool>(sut->getPath(), "LogToMetricReportsCollection"),
186 Eq(defaultParams.logToMetricReportCollection()));
187}
188
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100189TEST_F(TestReport, settingPersistencyToFalseRemovesReportFromStorage)
190{
191 EXPECT_CALL(storageMock, remove(to_file_path(sut->getName())));
192
193 bool persistency = false;
194 EXPECT_THAT(setProperty(sut->getPath(), "Persistency", persistency).value(),
195 Eq(boost::system::errc::success));
196 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Persistency"),
197 Eq(persistency));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200198}
199
200TEST_F(TestReport, deleteReport)
201{
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200202 EXPECT_CALL(*reportManagerMock, removeReport(sut.get()));
203 auto ec = deleteReport(sut->getPath());
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200204 EXPECT_THAT(ec, Eq(boost::system::errc::success));
205}
206
207TEST_F(TestReport, deletingNonExistingReportReturnInvalidRequestDescriptor)
208{
209 auto ec = deleteReport(Report::reportDir + "NonExisting"s);
210 EXPECT_THAT(ec.value(), Eq(EBADR));
211}
212
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100213TEST_F(TestReport, deleteReportExpectThatFileIsRemoveFromStorage)
214{
215 EXPECT_CALL(storageMock, remove(to_file_path(sut->getName())));
216 auto ec = deleteReport(sut->getPath());
217 EXPECT_THAT(ec, Eq(boost::system::errc::success));
218}
219
220class TestReportStore :
221 public TestReport,
222 public WithParamInterface<std::pair<std::string, nlohmann::json>>
223{
224 public:
225 void SetUp() override
226 {}
227
228 nlohmann::json storedConfiguration;
229};
230
231INSTANTIATE_TEST_SUITE_P(
232 _, TestReportStore,
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200233 Values(std::make_pair("Enabled"s, nlohmann::json(ReportParams().enabled())),
234 std::make_pair("Version"s, nlohmann::json(4)),
Krzysztof Grobelnye8fc5752021-02-05 14:30:45 +0000235 std::make_pair("Name"s, nlohmann::json(ReportParams().reportName())),
236 std::make_pair("ReportingType",
237 nlohmann::json(ReportParams().reportingType())),
238 std::make_pair("EmitsReadingsUpdate",
239 nlohmann::json(ReportParams().emitReadingUpdate())),
240 std::make_pair(
241 "LogToMetricReportsCollection",
242 nlohmann::json(ReportParams().logToMetricReportCollection())),
243 std::make_pair("Interval",
244 nlohmann::json(ReportParams().interval().count())),
245 std::make_pair(
246 "ReadingParameters",
247 nlohmann::json(
248 {{{tstring::SensorPath::str(),
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000249 {{{tstring::Service::str(), "Service"},
250 {tstring::Path::str(),
251 "/xyz/openbmc_project/sensors/power/p1"}}}},
Krzysztof Grobelnye8fc5752021-02-05 14:30:45 +0000252 {tstring::OperationType::str(), OperationType::single},
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000253 {tstring::Id::str(), "MetricId1"},
254 {tstring::MetricMetadata::str(), "Metadata1"},
255 {tstring::CollectionTimeScope::str(),
256 CollectionTimeScope::point},
257 {tstring::CollectionDuration::str(), 0}},
Krzysztof Grobelnye8fc5752021-02-05 14:30:45 +0000258 {{tstring::SensorPath::str(),
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000259 {{{tstring::Service::str(), "Service"},
260 {tstring::Path::str(),
261 "/xyz/openbmc_project/sensors/power/p2"}}}},
262 {tstring::OperationType::str(), OperationType::single},
263 {tstring::Id::str(), "MetricId2"},
264 {tstring::MetricMetadata::str(), "Metadata2"},
265 {tstring::CollectionTimeScope::str(),
266 CollectionTimeScope::point},
267 {tstring::CollectionDuration::str(), 0}}}))));
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100268
269TEST_P(TestReportStore, settingPersistencyToTrueStoresReport)
270{
271 sut = makeReport(ReportParams());
272
273 {
274 InSequence seq;
275 EXPECT_CALL(storageMock, remove(to_file_path(sut->getName())));
276 EXPECT_CALL(checkPoint, Call());
277 EXPECT_CALL(storageMock, store(to_file_path(sut->getName()), _))
278 .WillOnce(SaveArg<1>(&storedConfiguration));
279 }
280
281 setProperty(sut->getPath(), "Persistency", false);
282 checkPoint.Call();
283 setProperty(sut->getPath(), "Persistency", true);
284
285 const auto& [key, value] = GetParam();
286
287 ASSERT_THAT(storedConfiguration.at(key), Eq(value));
288}
289
290TEST_P(TestReportStore, reportIsSavedToStorageAfterCreated)
291{
292 EXPECT_CALL(storageMock,
293 store(to_file_path(ReportParams().reportName()), _))
294 .WillOnce(SaveArg<1>(&storedConfiguration));
295
296 sut = makeReport(ReportParams());
297
298 const auto& [key, value] = GetParam();
299
300 ASSERT_THAT(storedConfiguration.at(key), Eq(value));
301}
302
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200303class TestReportValidNames :
304 public TestReport,
305 public WithParamInterface<ReportParams>
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200306{
307 public:
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200308 void SetUp() override
309 {}
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200310};
311
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200312INSTANTIATE_TEST_SUITE_P(
313 ValidNames, TestReportValidNames,
314 Values(ReportParams().reportName("Valid_1"),
315 ReportParams().reportName("Valid_1/Valid_2"),
316 ReportParams().reportName("Valid_1/Valid_2/Valid_3")));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200317
318TEST_P(TestReportValidNames, reportCtorDoesNotThrowOnValidName)
319{
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200320 EXPECT_NO_THROW(makeReport(GetParam()));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200321}
322
323class TestReportInvalidNames :
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200324 public TestReport,
325 public WithParamInterface<ReportParams>
326{
327 public:
328 void SetUp() override
329 {}
330};
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200331
332INSTANTIATE_TEST_SUITE_P(InvalidNames, TestReportInvalidNames,
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200333 Values(ReportParams().reportName("/"),
334 ReportParams().reportName("/Invalid"),
335 ReportParams().reportName("Invalid/"),
336 ReportParams().reportName("Invalid/Invalid/"),
337 ReportParams().reportName("Invalid?")));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200338
339TEST_P(TestReportInvalidNames, reportCtorThrowOnInvalidName)
340{
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200341 EXPECT_THROW(makeReport(GetParam()), sdbusplus::exception::SdBusError);
342}
343
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100344TEST_F(TestReportInvalidNames, reportCtorThrowOnInvalidNameAndNoStoreIsCalled)
345{
346 EXPECT_CALL(storageMock, store).Times(0);
347 EXPECT_THROW(makeReport(ReportParams().reportName("/Invalid")),
348 sdbusplus::exception::SdBusError);
349}
350
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200351class TestReportAllReportTypes :
352 public TestReport,
353 public WithParamInterface<ReportParams>
354{
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200355 public:
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200356 void SetUp() override
357 {
358 sut = makeReport(GetParam());
359 }
360};
361
362INSTANTIATE_TEST_SUITE_P(_, TestReportAllReportTypes,
363 Values(ReportParams().reportingType("OnRequest"),
364 ReportParams().reportingType("OnChange"),
365 ReportParams().reportingType("Periodic")));
366
367TEST_P(TestReportAllReportTypes, returnPropertValueOfReportType)
368{
369 EXPECT_THAT(getProperty<std::string>(sut->getPath(), "ReportingType"),
370 Eq(GetParam().reportingType()));
371}
372
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200373TEST_P(TestReportAllReportTypes, updateReadingsCallEnabledPropertyOff)
374{
375 const uint64_t expectedTime = std::time(0);
376
377 setProperty(sut->getPath(), "Enabled", false);
378 sut->updateReadings();
379 const auto [timestamp, readings] =
380 getProperty<Readings>(sut->getPath(), "Readings");
381
382 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Enabled"), Eq(false));
383 EXPECT_THAT(timestamp, Lt(expectedTime));
384}
385
386TEST_P(TestReportAllReportTypes, updateReadingsCallEnabledPropertyOn)
Wludzik, Jozefd960e1f2021-01-08 09:25:59 +0100387{
388 const uint64_t expectedTime = std::time(0);
389
390 sut->updateReadings();
Wludzik, Jozefd960e1f2021-01-08 09:25:59 +0100391 const auto [timestamp, readings] =
392 getProperty<Readings>(sut->getPath(), "Readings");
393
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200394 EXPECT_THAT(getProperty<bool>(sut->getPath(), "Enabled"), Eq(true));
Wludzik, Jozefd960e1f2021-01-08 09:25:59 +0100395 EXPECT_THAT(timestamp, Ge(expectedTime));
396}
397
Krzysztof Grobelnyf32f6fe2020-10-30 13:51:58 +0100398class TestReportOnRequestType : public TestReport
399{
400 void SetUp() override
401 {
402 sut = makeReport(ReportParams().reportingType("OnRequest"));
403 }
404};
405
406TEST_F(TestReportOnRequestType, updatesReadingTimestamp)
407{
408 const uint64_t expectedTime = std::time(0);
409
410 ASSERT_THAT(update(sut->getPath()), Eq(boost::system::errc::success));
411
412 const auto [timestamp, readings] =
413 getProperty<Readings>(sut->getPath(), "Readings");
414
415 EXPECT_THAT(timestamp, Ge(expectedTime));
416}
417
418TEST_F(TestReportOnRequestType, updatesReadingWhenUpdateIsCalled)
419{
420 ASSERT_THAT(update(sut->getPath()), Eq(boost::system::errc::success));
421
422 const auto [timestamp, readings] =
423 getProperty<Readings>(sut->getPath(), "Readings");
424
425 EXPECT_THAT(readings,
426 ElementsAre(std::make_tuple("a"s, "b"s, 17.1, 114u),
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000427 std::make_tuple("aa"s, "bb"s, 42.0, 74u)));
Krzysztof Grobelnyf32f6fe2020-10-30 13:51:58 +0100428}
429
430class TestReportNonOnRequestType :
431 public TestReport,
432 public WithParamInterface<ReportParams>
433{
434 void SetUp() override
435 {
436 sut = makeReport(GetParam());
437 }
438};
439
440INSTANTIATE_TEST_SUITE_P(_, TestReportNonOnRequestType,
441 Values(ReportParams().reportingType("Periodic"),
442 ReportParams().reportingType("OnChange")));
443
444TEST_P(TestReportNonOnRequestType, readingsAreNotUpdateOnUpdateCall)
445{
446 ASSERT_THAT(update(sut->getPath()), Eq(boost::system::errc::success));
447
448 EXPECT_THAT(getProperty<Readings>(sut->getPath(), "Readings"),
449 Eq(Readings{}));
450}
451
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200452class TestReportNonPeriodicReport :
453 public TestReport,
454 public WithParamInterface<ReportParams>
455{
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200456 public:
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200457 void SetUp() override
458 {
459 sut = makeReport(GetParam());
460 }
461};
462
463INSTANTIATE_TEST_SUITE_P(_, TestReportNonPeriodicReport,
464 Values(ReportParams().reportingType("OnRequest"),
465 ReportParams().reportingType("OnChange")));
466
467TEST_P(TestReportNonPeriodicReport, readingsAreNotUpdatedAfterIntervalExpires)
468{
469 DbusEnvironment::sleepFor(ReportManager::minInterval + 1ms);
470
471 EXPECT_THAT(getProperty<Readings>(sut->getPath(), "Readings"),
472 Eq(Readings{}));
473}
474
475class TestReportPeriodicReport : public TestReport
476{
477 void SetUp() override
478 {
479 sut = makeReport(ReportParams().reportingType("Periodic"));
Krzysztof Grobelnyc8e3a642020-10-23 12:29:16 +0200480 }
481};
482
483TEST_F(TestReportPeriodicReport, readingTimestampIsUpdatedAfterIntervalExpires)
484{
485 const uint64_t expectedTime = std::time(0);
486 DbusEnvironment::sleepFor(ReportManager::minInterval + 1ms);
487
488 const auto [timestamp, readings] =
489 getProperty<Readings>(sut->getPath(), "Readings");
490
491 EXPECT_THAT(timestamp, Ge(expectedTime));
492}
493
494TEST_F(TestReportPeriodicReport, readingsAreUpdatedAfterIntervalExpires)
495{
496 DbusEnvironment::sleepFor(ReportManager::minInterval + 1ms);
497
498 const auto [timestamp, readings] =
499 getProperty<Readings>(sut->getPath(), "Readings");
500
501 EXPECT_THAT(readings,
502 ElementsAre(std::make_tuple("a"s, "b"s, 17.1, 114u),
Krzysztof Grobelnydcc4e192021-03-08 09:09:34 +0000503 std::make_tuple("aa"s, "bb"s, 42.0, 74u)));
Wludzik, Jozef2f9f9b82020-10-13 09:07:45 +0200504}
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100505
506class TestReportInitialization : public TestReport
507{
508 public:
509 void SetUp() override
510 {}
511
512 void monitorProc(sdbusplus::message::message& msg)
513 {
514 std::string iface;
515 std::vector<std::pair<std::string, std::variant<Readings>>>
516 changed_properties;
517 std::vector<std::string> invalidated_properties;
518
519 msg.read(iface, changed_properties, invalidated_properties);
520
521 if (iface == Report::reportIfaceName)
522 {
523 for (const auto& [name, value] : changed_properties)
524 {
525 if (name == "Readings")
526 {
527 readingsUpdated.Call();
528 }
529 }
530 }
531 }
532
533 void makeMonitor()
534 {
Patrick Williams3a62ee12021-12-03 10:13:25 -0600535 monitor = std::make_unique<sdbusplus::bus::match_t>(
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100536 *DbusEnvironment::getBus(),
537 sdbusplus::bus::match::rules::propertiesChanged(
538 sut->getPath(), Report::reportIfaceName),
539 [this](auto& msg) { monitorProc(msg); });
540 }
541
Patrick Williams3a62ee12021-12-03 10:13:25 -0600542 std::unique_ptr<sdbusplus::bus::match_t> monitor;
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100543 MockFunction<void()> readingsUpdated;
544};
545
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200546TEST_F(TestReportInitialization,
547 metricsAreInitializedWhenEnabledReportConstructed)
Krzysztof Grobelny6ccfcbf2020-11-04 09:31:36 +0100548{
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200549 initMetricMocks(defaultParams.metricParameters());
Krzysztof Grobelny6ccfcbf2020-11-04 09:31:36 +0100550 for (auto& metric : metricMocks)
551 {
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200552 EXPECT_CALL(*metric, initialize()).Times(1);
Krzysztof Grobelny6ccfcbf2020-11-04 09:31:36 +0100553 }
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200554 sut = makeReport(defaultParams.enabled(true));
555}
Krzysztof Grobelny6ccfcbf2020-11-04 09:31:36 +0100556
Lukasz Kazmierczak7e098e92021-09-16 15:59:56 +0200557TEST_F(TestReportInitialization,
558 metricsAreNotInitializedWhenDisabledReportConstructed)
559{
560 initMetricMocks(defaultParams.metricParameters());
561 for (auto& metric : metricMocks)
562 {
563 EXPECT_CALL(*metric, initialize()).Times(0);
564 }
565 sut = makeReport(defaultParams.enabled(false));
Krzysztof Grobelny6ccfcbf2020-11-04 09:31:36 +0100566}
567
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200568TEST_F(TestReportInitialization,
569 emitReadingsUpdateIsTrueReadingsPropertiesChangedSingalEmits)
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100570{
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200571 EXPECT_CALL(readingsUpdated, Call())
572 .WillOnce(
573 InvokeWithoutArgs(DbusEnvironment::setPromise("readingsUpdated")));
574
575 const auto elapsed = DbusEnvironment::measureTime([this] {
576 sut = makeReport(
577 defaultParams.reportingType("Periodic").emitReadingUpdate(true));
578 makeMonitor();
579 EXPECT_TRUE(DbusEnvironment::waitForFuture("readingsUpdated"));
580 });
581
582 EXPECT_THAT(elapsed, AllOf(Ge(defaultParams.interval()),
583 Lt(defaultParams.interval() * 2)));
584}
585
586TEST_F(TestReportInitialization,
587 emitReadingsUpdateIsFalseReadingsPropertiesChangesSigalDoesNotEmits)
588{
589 EXPECT_CALL(readingsUpdated, Call()).Times(0);
590
591 sut = makeReport(
592 defaultParams.reportingType("Periodic").emitReadingUpdate(false));
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100593 makeMonitor();
Wludzik, Jozefb1ff1f62020-10-23 13:20:52 +0200594 DbusEnvironment::sleepFor(defaultParams.interval() * 2);
Wludzik, Jozefe2362792020-10-27 17:23:55 +0100595}