blob: d3a847e0b8601f54dc3c2197dbe698f90d9fd7f2 [file] [log] [blame]
Alex Deymoc705cc82014-02-19 11:15:00 -08001// Copyright (c) 2014 The Chromium OS Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Alex Deymo7b948f02014-03-10 17:01:10 -07005#include <algorithm>
6#include <string>
Alex Deymo94c06162014-03-21 20:34:46 -07007#include <utility>
Alex Deymo7b948f02014-03-10 17:01:10 -07008#include <vector>
9
10#include <base/bind.h>
Alex Deymoc705cc82014-02-19 11:15:00 -080011#include <base/memory/scoped_ptr.h>
Alex Deymoc705cc82014-02-19 11:15:00 -080012#include <gtest/gtest.h>
13#include <gmock/gmock.h>
Alex Deymoc705cc82014-02-19 11:15:00 -080014
Alex Deymo41a75a72014-04-15 15:36:22 -070015#include "update_engine/fake_clock.h"
Alex Deymoc705cc82014-02-19 11:15:00 -080016#include "update_engine/policy_manager/default_policy.h"
Gilad Arnold308c1012014-03-12 15:37:06 -070017#include "update_engine/policy_manager/fake_state.h"
Alex Deymoc705cc82014-02-19 11:15:00 -080018#include "update_engine/policy_manager/mock_policy.h"
19#include "update_engine/policy_manager/pmtest_utils.h"
20#include "update_engine/policy_manager/policy_manager.h"
Alex Deymo7b948f02014-03-10 17:01:10 -070021#include "update_engine/test_utils.h"
Alex Deymoc705cc82014-02-19 11:15:00 -080022
Alex Deymo7b948f02014-03-10 17:01:10 -070023using base::Bind;
24using base::Callback;
Alex Deymo41a75a72014-04-15 15:36:22 -070025using chromeos_update_engine::FakeClock;
Alex Deymo7b948f02014-03-10 17:01:10 -070026using std::pair;
Alex Deymoc705cc82014-02-19 11:15:00 -080027using std::string;
Alex Deymo7b948f02014-03-10 17:01:10 -070028using std::vector;
Alex Deymoc705cc82014-02-19 11:15:00 -080029using testing::Return;
30using testing::StrictMock;
Gilad Arnold5ef9c482014-03-03 13:51:02 -080031using testing::_;
32
Alex Deymoc705cc82014-02-19 11:15:00 -080033namespace chromeos_policy_manager {
34
35class PmPolicyManagerTest : public ::testing::Test {
Alex Deymo41a75a72014-04-15 15:36:22 -070036 public:
37 PmPolicyManagerTest() : pmut_(&fake_clock_) {}
38
Alex Deymoc705cc82014-02-19 11:15:00 -080039 protected:
40 virtual void SetUp() {
Alex Deymo42c30c32014-04-24 18:41:18 -070041 fake_state_ = new FakeState();
Alex Deymo94c06162014-03-21 20:34:46 -070042 EXPECT_TRUE(pmut_.Init(fake_state_));
Alex Deymoc705cc82014-02-19 11:15:00 -080043 }
44
Alex Deymo94c06162014-03-21 20:34:46 -070045 FakeState* fake_state_;
Alex Deymo41a75a72014-04-15 15:36:22 -070046 FakeClock fake_clock_;
Gilad Arnold5ef9c482014-03-03 13:51:02 -080047 PolicyManager pmut_;
Alex Deymoc705cc82014-02-19 11:15:00 -080048};
49
50// The FailingPolicy implements a single method and make it always fail. This
51// class extends the DefaultPolicy class to allow extensions of the Policy
52// class without extending nor changing this test.
53class FailingPolicy : public DefaultPolicy {
Alex Deymo2de23f52014-02-26 14:30:13 -080054 virtual EvalStatus UpdateCheckAllowed(EvaluationContext* ec, State* state,
Alex Deymoc705cc82014-02-19 11:15:00 -080055 string* error,
56 bool* result) const {
57 *error = "FailingPolicy failed.";
Alex Deymoe636c3c2014-03-11 19:02:08 -070058 return EvalStatus::kFailed;
Alex Deymoc705cc82014-02-19 11:15:00 -080059 }
60};
61
Alex Deymo7b948f02014-03-10 17:01:10 -070062// The LazyPolicy always returns EvalStatus::kAskMeAgainLater.
Alex Deymoc705cc82014-02-19 11:15:00 -080063class LazyPolicy : public DefaultPolicy {
Alex Deymo2de23f52014-02-26 14:30:13 -080064 virtual EvalStatus UpdateCheckAllowed(EvaluationContext* ec, State* state,
Alex Deymoc705cc82014-02-19 11:15:00 -080065 string* error,
66 bool* result) const {
Alex Deymoe636c3c2014-03-11 19:02:08 -070067 return EvalStatus::kAskMeAgainLater;
Alex Deymoc705cc82014-02-19 11:15:00 -080068 }
69};
70
Alex Deymo7b948f02014-03-10 17:01:10 -070071// AccumulateCallsCallback() adds to the passed |acc| accumulator vector pairs
72// of EvalStatus and T instances. This allows to create a callback that keeps
73// track of when it is called and the arguments passed to it, to be used with
74// the PolicyManager::AsyncPolicyRequest().
75template<typename T>
76static void AccumulateCallsCallback(vector<pair<EvalStatus, T>>* acc,
77 EvalStatus status, const T& result) {
78 acc->push_back(std::make_pair(status, result));
79}
80
Alex Deymoc705cc82014-02-19 11:15:00 -080081TEST_F(PmPolicyManagerTest, PolicyRequestCall) {
82 bool result;
83 EvalStatus status = pmut_.PolicyRequest(&Policy::UpdateCheckAllowed, &result);
Alex Deymoe636c3c2014-03-11 19:02:08 -070084 EXPECT_EQ(status, EvalStatus::kSucceeded);
Alex Deymoc705cc82014-02-19 11:15:00 -080085}
86
87TEST_F(PmPolicyManagerTest, PolicyRequestCallsPolicy) {
88 StrictMock<MockPolicy>* policy = new StrictMock<MockPolicy>();
89 pmut_.policy_.reset(policy);
90 bool result;
91
92 // Tests that the method is called on the policy_ instance.
Alex Deymo2de23f52014-02-26 14:30:13 -080093 EXPECT_CALL(*policy, UpdateCheckAllowed(_, _, _, _))
Alex Deymoe636c3c2014-03-11 19:02:08 -070094 .WillOnce(Return(EvalStatus::kSucceeded));
Alex Deymoc705cc82014-02-19 11:15:00 -080095 EvalStatus status = pmut_.PolicyRequest(&Policy::UpdateCheckAllowed, &result);
Alex Deymoe636c3c2014-03-11 19:02:08 -070096 EXPECT_EQ(status, EvalStatus::kSucceeded);
Alex Deymoc705cc82014-02-19 11:15:00 -080097}
98
99TEST_F(PmPolicyManagerTest, PolicyRequestCallsDefaultOnError) {
100 pmut_.policy_.reset(new FailingPolicy());
101
102 // Tests that the DefaultPolicy instance is called when the method fails,
103 // which will set this as true.
104 bool result = false;
105 EvalStatus status = pmut_.PolicyRequest(&Policy::UpdateCheckAllowed, &result);
Alex Deymoe636c3c2014-03-11 19:02:08 -0700106 EXPECT_EQ(status, EvalStatus::kSucceeded);
Alex Deymoc705cc82014-02-19 11:15:00 -0800107 EXPECT_TRUE(result);
108}
109
110TEST_F(PmPolicyManagerTest, PolicyRequestDoesntBlock) {
111 pmut_.policy_.reset(new LazyPolicy());
112 bool result;
113
114 EvalStatus status = pmut_.PolicyRequest(&Policy::UpdateCheckAllowed, &result);
Alex Deymoe636c3c2014-03-11 19:02:08 -0700115 EXPECT_EQ(status, EvalStatus::kAskMeAgainLater);
Alex Deymoc705cc82014-02-19 11:15:00 -0800116}
117
Alex Deymo7b948f02014-03-10 17:01:10 -0700118TEST_F(PmPolicyManagerTest, AsyncPolicyRequestDelaysEvaluation) {
119 // To avoid differences in code execution order between an AsyncPolicyRequest
120 // call on a policy that returns AskMeAgainLater the first time and one that
121 // succeeds the first time, we ensure that the passed callback is called from
122 // the main loop in both cases even when we could evaluate it right now.
123 pmut_.policy_.reset(new FailingPolicy());
124
125 vector<pair<EvalStatus, bool>> calls;
126 Callback<void(EvalStatus, const bool& result)> callback =
127 Bind(AccumulateCallsCallback<bool>, &calls);
128
129 pmut_.AsyncPolicyRequest(callback, &Policy::UpdateCheckAllowed);
130 // The callback should wait until we run the main loop for it to be executed.
131 EXPECT_EQ(0, calls.size());
132 chromeos_update_engine::RunGMainLoopMaxIterations(100);
133 EXPECT_EQ(1, calls.size());
134}
135
Alex Deymoc705cc82014-02-19 11:15:00 -0800136} // namespace chromeos_policy_manager