CernVM-FS  2.13.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
swissknife_lease_curl.cc
Go to the documentation of this file.
1 
6 
7 #include "crypto/hash.h"
8 #include "gateway_util.h"
9 #include "json_document.h"
10 #include "ssl.h"
11 #include "util/logging.h"
12 #include "util/pointer.h"
13 #include "util/posix.h"
14 #include "util/string.h"
15 
16 namespace {
17 
18 CURL *PrepareCurl(const std::string &method) {
19  const char *user_agent_string = "cvmfs/" CVMFS_VERSION;
20 
21  CURL *h_curl = curl_easy_init();
22 
23  if (h_curl) {
24  curl_easy_setopt(h_curl, CURLOPT_NOPROGRESS, 1L);
25  curl_easy_setopt(h_curl, CURLOPT_USERAGENT, user_agent_string);
26  curl_easy_setopt(h_curl, CURLOPT_MAXREDIRS, 50L);
27  curl_easy_setopt(h_curl, CURLOPT_CUSTOMREQUEST, method.c_str());
28  }
29 
30  return h_curl;
31 }
32 
33 size_t RecvCB(void *buffer, size_t size, size_t nmemb, void *userp) {
34  CurlBuffer *my_buffer = static_cast<CurlBuffer *>(userp);
35 
36  if (size * nmemb < 1) {
37  return 0;
38  }
39 
40  my_buffer->data = my_buffer->data
41  + std::string(static_cast<char *>(buffer), nmemb);
42 
43  return nmemb;
44 }
45 
46 } // namespace
47 
48 bool MakeAcquireRequest(const std::string &key_id, const std::string &secret,
49  const std::string &repo_path,
50  const std::string &repo_service_url,
51  CurlBuffer *buffer) {
52  CURLcode ret = static_cast<CURLcode>(0);
53 
54  CURL *h_curl = PrepareCurl("POST");
55  if (!h_curl) {
56  return false;
57  }
58 
59  const std::string payload = "{\"path\" : \"" + repo_path
60  + "\", \"api_version\" : \""
62  + ", \"hostname\" : \"" + GetHostname() + "\"}";
63 
65  shash::HmacString(secret, payload, &hmac);
66 
69  cs.ApplySslCertificatePath(h_curl);
70 
71  const std::string header_str = std::string("Authorization: ") + key_id + " "
72  + Base64(hmac.ToString(false));
73  struct curl_slist *auth_header = NULL;
74  auth_header = curl_slist_append(auth_header, header_str.c_str());
75  curl_easy_setopt(h_curl, CURLOPT_HTTPHEADER, auth_header);
76 
77  // Make request to acquire lease from repo services
78  curl_easy_setopt(h_curl, CURLOPT_URL, (repo_service_url + "/leases").c_str());
79  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDSIZE_LARGE,
80  static_cast<curl_off_t>(payload.length()));
81  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDS, payload.c_str());
82  curl_easy_setopt(h_curl, CURLOPT_WRITEFUNCTION, RecvCB);
83  curl_easy_setopt(h_curl, CURLOPT_WRITEDATA, buffer);
84 
85  ret = curl_easy_perform(h_curl);
86  if (ret) {
88  "Make lease acquire request failed: %d. Reply: %s", ret,
89  buffer->data.c_str());
90  }
91 
92  curl_easy_cleanup(h_curl);
93  h_curl = NULL;
94 
95  return !ret;
96 }
97 
98 bool MakeEndRequest(const std::string &method, const std::string &key_id,
99  const std::string &secret, const std::string &session_token,
100  const std::string &repo_service_url,
101  const std::string &request_payload, CurlBuffer *reply) {
102  CURLcode ret = static_cast<CURLcode>(0);
103 
104  CURL *h_curl = PrepareCurl(method);
105  if (!h_curl) {
106  return false;
107  }
108 
109  shash::Any hmac(shash::kSha1);
110  shash::HmacString(secret, session_token, &hmac);
111 
114  cs.ApplySslCertificatePath(h_curl);
115 
116  const std::string header_str = std::string("Authorization: ") + key_id + " "
117  + Base64(hmac.ToString(false));
118  struct curl_slist *auth_header = NULL;
119  auth_header = curl_slist_append(auth_header, header_str.c_str());
120  curl_easy_setopt(h_curl, CURLOPT_HTTPHEADER, auth_header);
121 
122  curl_easy_setopt(h_curl, CURLOPT_URL,
123  (repo_service_url + "/leases/" + session_token).c_str());
124  if (request_payload != "") {
125  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDSIZE_LARGE,
126  static_cast<curl_off_t>(request_payload.length()));
127  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDS, request_payload.c_str());
128  } else {
129  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDSIZE_LARGE,
130  static_cast<curl_off_t>(0));
131  curl_easy_setopt(h_curl, CURLOPT_POSTFIELDS, NULL);
132  }
133  curl_easy_setopt(h_curl, CURLOPT_WRITEFUNCTION, RecvCB);
134  curl_easy_setopt(h_curl, CURLOPT_WRITEDATA, reply);
135 
136  ret = curl_easy_perform(h_curl);
137  if (ret) {
139  "Lease end request - curl_easy_perform failed: %d", ret);
140  }
141 
143  const JSON *reply_status = JsonDocument::SearchInObject(
144  reply_json->root(), "status", JSON_STRING);
145  const bool ok = (reply_status != NULL
146  && std::string(reply_status->string_value) == "ok");
147  if (!ok) {
149  "Lease end request - error reply: %s", reply->data.c_str());
150  }
151 
152  curl_easy_cleanup(h_curl);
153  h_curl = NULL;
154 
155  return ok && !ret;
156 }
int APIVersion()
Definition: gateway_util.cc:26
bool MakeEndRequest(const std::string &method, const std::string &key_id, const std::string &secret, const std::string &session_token, const std::string &repo_service_url, const std::string &request_payload, CurlBuffer *reply)
static JSON * SearchInObject(const JSON *json_object, const std::string &name, const json_type type)
std::string ToString(const bool with_suffix=false) const
Definition: hash.h:241
static CURL * PrepareCurl(const std::string &method)
std::string GetHostname()
Definition: posix.cc:762
static JsonDocument * Create(const std::string &text)
bool ApplySslCertificatePath(CURL *handle) const
Definition: ssl.cc:61
void UseSystemCertificatePath()
Definition: ssl.cc:71
size_t RecvCB(void *buffer, size_t size, size_t nmemb, void *userp)
std::string data
string StringifyInt(const int64_t value)
Definition: string.cc:77
string Base64(const string &data)
Definition: string.cc:537
static void MakeAcquireRequest(const gateway::GatewayKey &key, const std::string &repo_path, const std::string &repo_service_url, int llvl, CurlBuffer *buffer)
void HmacString(const std::string &key, const std::string &content, Any *any_digest)
Definition: hash.h:515
struct json_value JSON
Definition: helper_allow.cc:11
static void size_t size
Definition: smalloc.h:54
const JSON * root() const
Definition: json_document.h:25
CVMFS_EXPORT void LogCvmfs(const LogSource source, const int mask, const char *format,...)
Definition: logging.cc:545