diff --git a/src/supernode/baseclientproxy.cpp b/src/supernode/baseclientproxy.cpp index 0a43d54b3..c8ef5226d 100644 --- a/src/supernode/baseclientproxy.cpp +++ b/src/supernode/baseclientproxy.cpp @@ -47,6 +47,7 @@ void supernode::BaseClientProxy::Init() m_DAPIServer->ADD_DAPI_HANDLER(GetSeed, rpc_command::GET_SEED, BaseClientProxy); m_DAPIServer->ADD_DAPI_HANDLER(RestoreAccount, rpc_command::RESTORE_ACCOUNT, BaseClientProxy); m_DAPIServer->ADD_DAPI_HANDLER(Transfer, rpc_command::TRANSFER, BaseClientProxy); + m_DAPIServer->ADD_DAPI_HANDLER(GetTransferFee, rpc_command::GET_TRANSFER_FEE, BaseClientProxy); } bool supernode::BaseClientProxy::GetWalletBalance(const supernode::rpc_command::GET_WALLET_BALANCE::request &in, supernode::rpc_command::GET_WALLET_BALANCE::response &out) @@ -174,6 +175,84 @@ bool supernode::BaseClientProxy::RestoreAccount(const supernode::rpc_command::RE return true; } +bool supernode::BaseClientProxy::GetTransferFee(const supernode::rpc_command::GET_TRANSFER_FEE::request &in, supernode::rpc_command::GET_TRANSFER_FEE::response &out) +{ + std::unique_ptr wal = initWallet(base64_decode(in.Account), in.Password); + if (!wal) + { + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + + if (wal->restricted()) + { + // er.code = WALLET_RPC_ERROR_CODE_DENIED; + // er.message = "Command unavailable in restricted mode."; + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + + std::vector dsts; + std::vector extra; + + std::string payment_id = ""; + + uint64_t amount; + std::istringstream iss(in.Amount); + iss >> amount; + + // validate the transfer requested and populate dsts & extra + if (!validate_transfer(in.Account, in.Password, in.Address, amount, payment_id, dsts, extra)) + { + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + + try + { + uint64_t mixin = 4; + uint64_t unlock_time = 0; + uint64_t priority = 0; + std::vector ptx_vector = + wal->create_transactions_2(dsts, mixin, unlock_time, priority, extra, false); + + // reject proposed transactions if there are more than one. see on_transfer_split below. + if (ptx_vector.size() != 1) + { + // er.code = WALLET_RPC_ERROR_CODE_GENERIC_TRANSFER_ERROR; + // er.message = "Transaction would be too large. try /transfer_split."; + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + + out.Fee = ptx_vector.back().fee; + } + catch (const tools::error::daemon_busy& e) + { + // er.code = WALLET_RPC_ERROR_CODE_DAEMON_IS_BUSY; + // er.message = e.what(); + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + catch (const std::exception& e) + { + // er.code = WALLET_RPC_ERROR_CODE_GENERIC_TRANSFER_ERROR; + // er.message = e.what(); + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + catch (...) + { + // er.code = WALLET_RPC_ERROR_CODE_UNKNOWN_ERROR; + // er.message = "WALLET_RPC_ERROR_CODE_UNKNOWN_ERROR"; + out.Result = ERROR_OPEN_WALLET_FAILED; + return false; + } + + out.Result = STATUS_OK; + return true; +} + bool supernode::BaseClientProxy::Transfer(const supernode::rpc_command::TRANSFER::request &in, supernode::rpc_command::TRANSFER::response &out) { std::unique_ptr wal = initWallet(base64_decode(in.Account), in.Password); diff --git a/src/supernode/baseclientproxy.h b/src/supernode/baseclientproxy.h index 23082cf2d..482763948 100644 --- a/src/supernode/baseclientproxy.h +++ b/src/supernode/baseclientproxy.h @@ -53,6 +53,7 @@ class BaseClientProxy : public BaseRTAProcessor bool GetSeed(const rpc_command::GET_SEED::request &in, rpc_command::GET_SEED::response &out); bool RestoreAccount(const rpc_command::RESTORE_ACCOUNT::request &in, rpc_command::RESTORE_ACCOUNT::response &out); + bool GetTransferFee(const rpc_command::GET_TRANSFER_FEE::request &in, rpc_command::GET_TRANSFER_FEE::response &out); bool Transfer(const rpc_command::TRANSFER::request &in, rpc_command::TRANSFER::response &out); private: diff --git a/src/supernode/supernode_rpc_command.cpp b/src/supernode/supernode_rpc_command.cpp index dbe603795..36b60fcef 100644 --- a/src/supernode/supernode_rpc_command.cpp +++ b/src/supernode/supernode_rpc_command.cpp @@ -64,6 +64,7 @@ DCALL(CreateAccount) DCALL(GetSeed) DCALL(RestoreAccount) DCALL(Transfer) +DCALL(GetTransferFee) DCALL(WalletRejectPay) DCALL(WalletProxyRejectPay) DCALL(AuthWalletRejectPay) diff --git a/src/supernode/supernode_rpc_command.h b/src/supernode/supernode_rpc_command.h index 0e2162027..08e5498ae 100644 --- a/src/supernode/supernode_rpc_command.h +++ b/src/supernode/supernode_rpc_command.h @@ -62,6 +62,7 @@ namespace supernode { extern const string GetSeed; extern const string RestoreAccount; extern const string Transfer; + extern const string GetTransferFee; extern const string WalletRejectPay; extern const string WalletProxyRejectPay; @@ -484,6 +485,32 @@ namespace supernode { }; }; + + struct GET_TRANSFER_FEE { + struct request { + std::string Account; + std::string Password; + std::string Address; + std::string Amount; + + BEGIN_KV_SERIALIZE_MAP() + KV_SERIALIZE(Account) + KV_SERIALIZE(Password) + KV_SERIALIZE(Address) + KV_SERIALIZE(Amount) + END_KV_SERIALIZE_MAP() + }; + struct response { + int64_t Result; + uint64_t Fee; + + BEGIN_KV_SERIALIZE_MAP() + KV_SERIALIZE(Result) + KV_SERIALIZE(Fee) + END_KV_SERIALIZE_MAP() + }; + }; + void ConvertFromTR(RTA_TransactionRecordRequest& dst, const RTA_TransactionRecord& src); void ConvertToTR(RTA_TransactionRecord& dst, const RTA_TransactionRecordRequest& src, const FSN_ServantBase* servant); @@ -589,10 +616,6 @@ namespace supernode { vector List; }; }; - - - - } }