Google Cloud C++ Client  2.1.0
C++ Client Library for Google Cloud Platform
polling_policy.h
Go to the documentation of this file.
1 // Copyright 2020 Google LLC
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of 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,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #ifndef GOOGLE_CLOUD_CPP_GOOGLE_CLOUD_POLLING_POLICY_H
16 #define GOOGLE_CLOUD_CPP_GOOGLE_CLOUD_POLLING_POLICY_H
17 
18 #include "google/cloud/internal/backoff_policy.h"
19 #include "google/cloud/internal/retry_policy.h"
20 #include "google/cloud/status.h"
21 #include "google/cloud/version.h"
22 #include <chrono>
23 #include <memory>
24 
25 namespace google {
26 namespace cloud {
28 
29 /**
30  * Control the Cloud C++ client library behavior with respect to polling on
31  * long running operations.
32  *
33  * Some operations in Cloud services return a `google.longrunning.Operation`
34  * object. As their name implies, these objects represent requests that may take
35  * a long time to complete, in some cases operations may take tens of seconds
36  * or even 30 minutes to complete.
37  *
38  * The Cloud C++ client libraries models these long running operations
39  * as a `google::cloud::future<StatusOr<T>>`, where `T` represents the final
40  * result of the operation. In the background, the library polls the service
41  * until the operation completes (or fails) and then satisfies the future.
42  *
43  * This class defines the interface for policies that control the behavior of
44  * this polling loop.
45  *
46  * @see https://aip.dev/151 for more information on long running operations.
47  */
49  public:
50  virtual ~PollingPolicy() = default;
51 
52  /**
53  * Return a copy of the current policy.
54  *
55  * This function is called at the beginning of the polling loop. Policies that
56  * are based on relative time should restart their timers when this function
57  * is called.
58  */
59  virtual std::unique_ptr<PollingPolicy> clone() const = 0;
60 
61  /**
62  * A callback to indicate that a polling attempt failed.
63  *
64  * This is called when a polling request fails. Note that this callback is not
65  * invoked when the polling request succeeds with "operation not done".
66  *
67  * @return true if the failure should be treated as transient and the polling
68  * loop should continue.
69  */
70  virtual bool OnFailure(Status const& status) = 0;
71 
72  /**
73  * How long should the polling loop wait before trying again.
74  */
75  virtual std::chrono::milliseconds WaitPeriod() = 0;
76 };
77 
78 /**
79  * Construct a polling policy from existing Retry and Backoff policies.
80  *
81  * A polling policy can be built by composing a retry and backoff policy. For
82  * example, to create a polling policy that "retries N times, waiting a fixed
83  * period between retries" you could compose the "try N times" retry policy with
84  * the "wait a fixed period between retries" backoff policy.
85  *
86  * This class makes it easier to create such composed polling policies.
87  *
88  * @tparam Retry the retry policy used to limit the number of errors or the
89  * total duration of the polling loop.
90  * @tparam Backoff the backoff policy used to control how often the
91  * library polls.
92  */
93 template <typename Retry, typename Backoff>
95  public:
96  GenericPollingPolicy(Retry retry_policy, Backoff backoff_policy)
97  : retry_prototype_(std::move(retry_policy)),
98  backoff_prototype_(std::move(backoff_policy)),
99  retry_clone_(maybe_deref(retry_prototype_).clone()),
100  backoff_clone_(maybe_deref(backoff_prototype_).clone()) {}
101 
102  //@{
103  std::unique_ptr<PollingPolicy> clone() const override {
104  return std::unique_ptr<PollingPolicy>(
105  new GenericPollingPolicy<Retry, Backoff>(retry_prototype_,
106  backoff_prototype_));
107  }
108 
109  bool OnFailure(Status const& status) override {
110  return retry_clone_->OnFailure(status);
111  }
112 
113  std::chrono::milliseconds WaitPeriod() override {
114  return backoff_clone_->OnCompletion();
115  }
116  //@}
117 
118  private:
119  template <typename T>
120  T& maybe_deref(T& v) {
121  return v;
122  }
123  template <typename T>
124  T& maybe_deref(std::shared_ptr<T>& v) {
125  return *v;
126  }
127 
128  Retry retry_prototype_;
129  Backoff backoff_prototype_;
130 
131  std::unique_ptr<internal::RetryPolicy> retry_clone_;
132  std::unique_ptr<internal::BackoffPolicy> backoff_clone_;
133 };
134 
136 } // namespace cloud
137 } // namespace google
138 
139 #endif // GOOGLE_CLOUD_CPP_GOOGLE_CLOUD_POLLING_POLICY_H