From ef1e4459e17a264f02d47e3cab30fd93098bc8d1 Mon Sep 17 00:00:00 2001 From: josibake Date: Mon, 2 Oct 2023 16:48:02 +0200 Subject: [PATCH] wallet,rpc: Add ParseOutputs function Move the options parsing logic for SFFO out of FundTransaction into this function. Copy the options parsing logic from AddOutputs (called in ConstructTransaction) into this function. This sets us up to use ParseRecipients in the next commit and remove SFFO logic from FundTransaction. --- src/wallet/rpc/spend.cpp | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/src/wallet/rpc/spend.cpp b/src/wallet/rpc/spend.cpp index f6ce11a53cd2c7..5637de0c2484de 100644 --- a/src/wallet/rpc/spend.cpp +++ b/src/wallet/rpc/spend.cpp @@ -77,6 +77,38 @@ std::set ParseSubtractFeeFromOutputs(const UniValue& subtract_fee_from_outp return set_sffo; } +std::vector ParseOutputs(const UniValue& outputs_in, const UniValue& options) +{ + if (outputs_in.isNull()) { + throw JSONRPCError(RPC_INVALID_PARAMETER, "Invalid parameter, output argument must be non-null"); + } + + const bool outputs_is_obj = outputs_in.isObject(); + UniValue outputs = outputs_is_obj ? outputs_in.get_obj() : outputs_in.get_array(); + + if (!outputs_is_obj) { + // Translate array of key-value pairs into dict + UniValue outputs_dict = UniValue(UniValue::VOBJ); + for (size_t i = 0; i < outputs.size(); ++i) { + const UniValue& output = outputs[i]; + if (!output.isObject()) { + throw JSONRPCError(RPC_INVALID_PARAMETER, "Invalid parameter, key-value pair not an object as expected"); + } + if (output.size() != 1) { + throw JSONRPCError(RPC_INVALID_PARAMETER, "Invalid parameter, key-value pair must contain exactly one key"); + } + outputs_dict.pushKVs(output); + } + outputs = std::move(outputs_dict); + } + std::set set_sffo; + if (options.exists("subtractFeeFromOutputs") || options.exists("subtract_fee_from_outputs") ) { + UniValue sffo = (options.exists("subtract_fee_from_outputs") ? options["subtract_fee_from_outputs"] : options["subtractFeeFromOutputs"]).get_array(); + set_sffo = ParseSubtractFeeFromOutputs(sffo, outputs.getKeys()); + } + return ParseRecipients(outputs, set_sffo); +} + static void InterpretFeeEstimationInstructions(const UniValue& conf_target, const UniValue& estimate_mode, const UniValue& fee_rate, UniValue& options) { if (options.exists("conf_target") || options.exists("estimate_mode")) {