cURL based HTTP/HTTPS RPC client for Hive

This commit is contained in:
serkixenos 2021-10-20 14:31:03 +02:00
parent 9b3c84c2bd
commit de9ee9fc76
4 changed files with 87 additions and 19 deletions

View file

@ -43,7 +43,7 @@ endif()
unset(ENABLE_PEERPLAYS_ASSET_DEPOSITS) unset(ENABLE_PEERPLAYS_ASSET_DEPOSITS)
unset(ENABLE_PEERPLAYS_ASSET_DEPOSITS CACHE) unset(ENABLE_PEERPLAYS_ASSET_DEPOSITS CACHE)
target_link_libraries( peerplays_sidechain PRIVATE graphene_plugin zmq ) target_link_libraries( peerplays_sidechain PRIVATE curl graphene_plugin zmq )
target_include_directories( peerplays_sidechain target_include_directories( peerplays_sidechain
PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/include" ) PUBLIC "${CMAKE_CURRENT_SOURCE_DIR}/include" )

View file

@ -1,13 +1,16 @@
#include <graphene/peerplays_sidechain/common/rpc_client.hpp> #include <graphene/peerplays_sidechain/common/rpc_client.hpp>
#include <sstream> #include <sstream>
#include <string>
#include <boost/property_tree/json_parser.hpp> #include <boost/property_tree/json_parser.hpp>
#include <boost/property_tree/ptree.hpp> #include <boost/property_tree/ptree.hpp>
#include <curl/curl.h>
#include <fc/crypto/base64.hpp> #include <fc/crypto/base64.hpp>
#include <fc/log/logger.hpp> #include <fc/log/logger.hpp>
#include <fc/network/ip.hpp> //#include <fc/network/ip.hpp>
namespace graphene { namespace peerplays_sidechain { namespace graphene { namespace peerplays_sidechain {
@ -99,19 +102,78 @@ std::string rpc_client::send_post_request(std::string method, std::string params
return ""; return "";
} }
fc::http::reply rpc_client::send_post_request(std::string body, bool show_log) { //fc::http::reply rpc_client::send_post_request(std::string body, bool show_log) {
fc::http::connection conn; // fc::http::connection conn;
conn.connect_to(fc::ip::endpoint(fc::ip::address(ip), port)); // conn.connect_to(fc::ip::endpoint(fc::ip::address(ip), port));
//
// std::string url = "http://" + ip + ":" + std::to_string(port);
//
// //if (wallet.length() > 0) {
// // url = url + "/wallet/" + wallet;
// //}
//
// fc::http::reply reply = conn.request("POST", url, body, fc::http::headers{authorization});
//
// if (show_log) {
// ilog("### Request URL: ${url}", ("url", url));
// ilog("### Request: ${body}", ("body", body));
// std::stringstream ss(std::string(reply.body.begin(), reply.body.end()));
// ilog("### Response: ${ss}", ("ss", ss.str()));
// }
//
// return reply;
//}
std::string url = "http://" + ip + ":" + std::to_string(port); static size_t write_callback(char *ptr, size_t size, size_t nmemb, rpc_reply *reply) {
size_t retval = 0;
if (reply != nullptr) {
reply->body.append(ptr, size * nmemb);
retval = size * nmemb;
}
return retval;
}
//if (wallet.length() > 0) { rpc_reply rpc_client::send_post_request(std::string body, bool show_log) {
// url = url + "/wallet/" + wallet;
//}
fc::http::reply reply = conn.request("POST", url, body, fc::http::headers{authorization}); struct curl_slist *headers = nullptr;
headers = curl_slist_append(headers, "Accept: application/json");
headers = curl_slist_append(headers, "Content-Type: application/json");
headers = curl_slist_append(headers, "charset: utf-8");
CURL *curl = curl_easy_init();
if (ip.find("https://", 0) != 0) {
curl_easy_setopt(curl, CURLOPT_URL, ip.c_str());
curl_easy_setopt(curl, CURLOPT_PORT, port);
} else {
std::string full_address = ip + ":" + std::to_string(port);
curl_easy_setopt(curl, CURLOPT_URL, full_address.c_str());
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, false);
curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, false);
}
if (!user.empty()) {
curl_easy_setopt(curl, CURLOPT_USERNAME, user.c_str());
curl_easy_setopt(curl, CURLOPT_PASSWORD, password.c_str());
}
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
curl_easy_setopt(curl, CURLOPT_POSTFIELDS, body.c_str());
//curl_easy_setopt(curl, CURLOPT_VERBOSE, true);
rpc_reply reply;
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, write_callback);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, &reply);
curl_easy_perform(curl);
curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &reply.status);
curl_easy_cleanup(curl);
curl_slist_free_all(headers);
if (show_log) { if (show_log) {
std::string url = ip + ":" + std::to_string(port);
ilog("### Request URL: ${url}", ("url", url)); ilog("### Request URL: ${url}", ("url", url));
ilog("### Request: ${body}", ("body", body)); ilog("### Request: ${body}", ("body", body));
std::stringstream ss(std::string(reply.body.begin(), reply.body.end())); std::stringstream ss(std::string(reply.body.begin(), reply.body.end()));

View file

@ -7,6 +7,11 @@
namespace graphene { namespace peerplays_sidechain { namespace graphene { namespace peerplays_sidechain {
struct rpc_reply {
uint16_t status;
std::string body;
};
class rpc_client { class rpc_client {
public: public:
rpc_client(std::string _ip, uint32_t _port, std::string _user, std::string _password, bool _debug_rpc_calls); rpc_client(std::string _ip, uint32_t _port, std::string _user, std::string _password, bool _debug_rpc_calls);
@ -27,7 +32,8 @@ protected:
fc::http::header authorization; fc::http::header authorization;
private: private:
fc::http::reply send_post_request(std::string body, bool show_log); //fc::http::reply send_post_request(std::string body, bool show_log);
rpc_reply send_post_request(std::string body, bool show_log);
}; };
}} // namespace graphene::peerplays_sidechain }} // namespace graphene::peerplays_sidechain

View file

@ -35,7 +35,7 @@ hive_node_rpc_client::hive_node_rpc_client(std::string _ip, uint32_t _port, std:
} }
std::string hive_node_rpc_client::account_history_api_get_transaction(std::string transaction_id) { std::string hive_node_rpc_client::account_history_api_get_transaction(std::string transaction_id) {
std::string params = "{ \"id\": \"" + transaction_id + "\" }"; std::string params = "{ \"id\": \"" + transaction_id + "\", \"include_reversible\": \"true\" }";
return send_post_request("account_history_api.get_transaction", params, debug_rpc_calls); return send_post_request("account_history_api.get_transaction", params, debug_rpc_calls);
} }
@ -145,13 +145,13 @@ sidechain_net_handler_hive::sidechain_net_handler_hive(peerplays_sidechain_plugi
} }
} }
fc::http::connection conn; //fc::http::connection conn;
try { //try {
conn.connect_to(fc::ip::endpoint(fc::ip::address(node_ip), node_rpc_port)); // conn.connect_to(fc::ip::endpoint(fc::ip::address(node_ip), node_rpc_port));
} catch (fc::exception &e) { //} catch (fc::exception &e) {
elog("No Hive node running at ${ip} or wrong rpc port: ${port}", ("ip", node_ip)("port", node_rpc_port)); // elog("No Hive node running at ${ip} or wrong rpc port: ${port}", ("ip", node_ip)("port", node_rpc_port));
FC_ASSERT(false); // FC_ASSERT(false);
} //}
node_rpc_client = new hive_node_rpc_client(node_ip, node_rpc_port, node_rpc_user, node_rpc_password, debug_rpc_calls); node_rpc_client = new hive_node_rpc_client(node_ip, node_rpc_port, node_rpc_user, node_rpc_password, debug_rpc_calls);