00001 #include <otsdaq-utilities/ECLWriter/ECLConnection.h>
00002 #include <iomanip>
00003 #include <openssl/md5.h>
00004 #include <sstream>
00005 #include <cstring>
00006 #include <fstream>
00007 #include "otsdaq-core/MessageFacility/MessageFacility.h"
00008 #include "otsdaq-core/Macros/CoutMacros.h"
00009
00010 ECLConnection::ECLConnection(std::string user,
00011 std::string pwd,
00012 std::string url)
00013 {
00014 _user = user;
00015 _pwd = pwd;
00016 _url = url;
00017
00018 srand(time(NULL));
00019
00020 }
00021
00022 size_t ECLConnection::WriteMemoryCallback(char *data, size_t size,
00023 size_t nmemb, std::string* buffer)
00024 {
00025 size_t realsize = 0;
00026
00027 if (buffer != NULL) {
00028 buffer->append(data, size*nmemb);
00029 realsize = size * nmemb;
00030 }
00031
00032 return realsize;
00033 }
00034
00035 bool ECLConnection::Get(std::string s, std::string& response)
00036 {
00037 response = "NULL";
00038
00039 char errorBuffer[CURL_ERROR_SIZE];
00040 std::string buffer;
00041 CURL *curl_handle;
00042
00043 curl_global_init(CURL_GLOBAL_ALL);
00044
00045
00046 curl_handle = curl_easy_init();
00047
00048 curl_easy_setopt(curl_handle, CURLOPT_ERRORBUFFER, errorBuffer);
00049
00050 std::string fullURL = _url + s;
00051
00052
00053 curl_easy_setopt(curl_handle, CURLOPT_URL, fullURL.c_str());
00054 curl_easy_setopt(curl_handle, CURLOPT_FOLLOWLOCATION, 1);
00055
00056
00057 curl_easy_setopt(curl_handle, CURLOPT_WRITEFUNCTION, ECLConnection::WriteMemoryCallback);
00058
00059
00060 curl_easy_setopt(curl_handle, CURLOPT_WRITEDATA, &buffer);
00061
00062
00063
00064 curl_easy_setopt(curl_handle, CURLOPT_USERAGENT, "libcurl-agent/1.0");
00065
00066
00067 CURLcode result = curl_easy_perform(curl_handle);
00068
00069
00070 curl_easy_cleanup(curl_handle);
00071
00072 if (result == CURLE_OK)
00073 response = buffer;
00074 else {
00075 std::cerr << "Error: [" << result << "] - " << errorBuffer << std::endl;
00076 return false;
00077 }
00078
00079 curl_global_cleanup();
00080
00081 return true;
00082 }
00083
00084 bool ECLConnection::Search(std::string s)
00085 {
00086 return false;
00087 }
00088
00089 std::string ECLConnection::MakeSaltString()
00090 {
00091 std::string rndString = "";
00092
00093 std::string chars("abcdefghijklmnopqrstuvwxyz"
00094
00095 "1234567890");
00096 for (int i = 0; i < 10; ++i) {
00097 rndString += chars[rand() % chars.size()];
00098 }
00099
00100 return rndString;
00101 }
00102
00103
00104 bool ECLConnection::Post(ECLEntry_t& e)
00105 {
00106 std::string safe_url;
00107 if (!Get("/secureURL", safe_url)) return false;
00108
00109 std::string rndString = MakeSaltString();
00110
00111 std::string myURL = "/E/xml_post?";
00112 std::string mySalt = "salt=" + rndString;
00113 std::string fullURL = _url + myURL + mySalt;
00114
00115 std::string myData = mySalt + ":" + _pwd + ":";
00116
00117
00118 std::ostringstream oss;
00119 entry(oss, e);
00120 std::string eclString = oss.str();
00121 __COUT__ << "ECL XML is: " << eclString << std::endl;
00122
00123 eclString = eclString.substr(eclString.find_first_of(">") + 2);
00124
00125 while (eclString.find('\n') != std::string::npos)
00126 {
00127 eclString = eclString.erase(eclString.find('\n'), 1);
00128 }
00129 while (eclString.find('\r') != std::string::npos)
00130 {
00131 eclString = eclString.erase(eclString.find('\r'), 1);
00132 }
00133 while (eclString.find(" <") != std::string::npos)
00134 {
00135 eclString = eclString.erase(eclString.find(" <"), 1);
00136 }
00137 boost::trim(eclString);
00138 myData += eclString;
00139 __COUT__ << "ECL Hash string is: " << myData << std::endl;
00140 unsigned char resultMD5[MD5_DIGEST_LENGTH];
00141 MD5((unsigned char*)myData.c_str(), myData.size(), resultMD5);
00142
00143 std::string xSig;
00144 char buf[3];
00145 for (auto i = 0; i < MD5_DIGEST_LENGTH; i++) {
00146 sprintf(buf, "%02x", resultMD5[i]);
00147 xSig.append(buf);
00148 }
00149 __COUT__ << "ECL MD5 Signature is: " << xSig << std::endl;
00150
00151 CURL *curl_handle;
00152 char errorBuffer[CURL_ERROR_SIZE];
00153
00154 curl_global_init(CURL_GLOBAL_ALL);
00155
00156
00157
00158 curl_handle = curl_easy_init();
00159
00160 curl_easy_setopt(curl_handle, CURLOPT_ERRORBUFFER, errorBuffer);
00161
00162
00163
00164 struct curl_slist* headers = NULL;
00165 std::string buff = "X-User: " + _user;
00166 headers = curl_slist_append(headers, buff.c_str());
00167 headers = curl_slist_append(headers, "Content-type: text/xml");
00168 headers = curl_slist_append(headers, "X-Signature-Method: md5");
00169 buff = "X-Signature: " + xSig;
00170 headers = curl_slist_append(headers, buff.c_str());
00171
00172 const char* estr = eclString.c_str();
00173
00174 __COUT__ << "ECL Setting message headers" << std::endl;
00175 curl_easy_setopt(curl_handle, CURLOPT_POSTFIELDS, estr);
00176 curl_easy_setopt(curl_handle, CURLOPT_HTTPHEADER, headers);
00177 curl_easy_setopt(curl_handle, CURLOPT_URL, fullURL.c_str());
00178
00179
00180
00181
00182 __COUT__ << "ECL Posting message" << std::endl;
00183 CURLcode result = curl_easy_perform(curl_handle);
00184
00185 if (result != CURLE_OK) {
00186 std::cerr << "Error: [" << result << "] - " << errorBuffer << std::endl;
00187 return false;
00188 }
00189
00190 __COUT__ << "ECL Cleanup" << std::endl;
00191
00192 curl_easy_cleanup(curl_handle);
00193 curl_slist_free_all(headers);
00194
00195 curl_global_cleanup();
00196
00197 return true;
00198
00199 }
00200
00201
00202 Attachment_t ECLConnection::MakeAttachmentImage(std::string const& imageFileName) {
00203 Attachment_t attachment;
00204 std::string fileNameShort = imageFileName;
00205 if (fileNameShort.rfind('/') != std::string::npos) {
00206 fileNameShort = fileNameShort.substr(imageFileName.rfind('/'));
00207 }
00208 std::ifstream fin(imageFileName, std::ios::in | std::ios::binary);
00209 fin.seekg(0, std::ios::end);
00210 std::streamsize size = fin.tellg();
00211 fin.seekg(0, std::ios::beg);
00212 std::vector<char> buffer(size);
00213 if (!fin.read(buffer.data(), size))
00214 {
00215 __COUT__ << "ECLConnection: Error reading file: " << imageFileName << std::endl;
00216 attachment = Attachment_t("Image=none", fileNameShort);
00217 }
00218 else {
00219 attachment = Attachment_t(::xml_schema::base64_binary(&buffer[0], size), "image", fileNameShort);
00220 }
00221 return attachment;
00222 }
00223
00224
00225 Attachment_t ECLConnection::MakeAttachmentFile(std::string const& fileName) {
00226 Attachment_t attachment;
00227 std::string fileNameShort = fileName;
00228 if (fileNameShort.rfind('/') != std::string::npos) {
00229 fileNameShort = fileNameShort.substr(fileName.rfind('/'));
00230 }
00231 std::ifstream fin(fileName, std::ios::in | std::ios::binary);
00232 fin.seekg(0, std::ios::end);
00233 std::streamsize size = fin.tellg();
00234 fin.seekg(0, std::ios::beg);
00235
00236 std::vector<char> buffer(size);
00237 if (!fin.read(buffer.data(), size))
00238 {
00239 __COUT__ << "ECLConnection: Error reading file: " << fileName;
00240 attachment = Attachment_t("File=none", fileNameShort);
00241 }
00242 else {
00243 attachment = Attachment_t(::xml_schema::base64_binary(&buffer[0], size), "file", fileNameShort);
00244 }
00245 return attachment;
00246 }