Skip to content

Commit

Permalink
Merge pull request #59 from domob1812/rawtx-nameupdate
Browse files Browse the repository at this point in the history
Implement name_update in createrawtransaction.
  • Loading branch information
phelixbtc committed May 15, 2014
2 parents 84974c0 + f18e37f commit 426a6d8
Show file tree
Hide file tree
Showing 3 changed files with 85 additions and 3 deletions.
19 changes: 16 additions & 3 deletions src/bitcoinrpc.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2846,17 +2846,23 @@ Value listunspent(const Array& params, bool fHelp)

Value createrawtransaction(const Array& params, bool fHelp)
{
if (fHelp || params.size() != 2)
if (fHelp || (params.size() != 2 && params.size() != 3))
throw runtime_error(
"createrawtransaction [{\"txid\":txid,\"vout\":n},...] {address:amount,...}\n"
"optional third argument:\n"
" {\"op\":\"name_update\", \"name\":name, \"value\":value, \"address\":address}\n\n"
"Create a transaction spending given inputs\n"
"(array of objects containing transaction id and output number),\n"
"sending to given address(es).\n"
"Returns hex-encoded raw transaction.\n"
"Optionally, a name_update operation can be performed.\n\n"
"Returns hex-encoded raw transaction.\n\n"
"Note that the transaction's inputs are not signed, and\n"
"it is not stored in the wallet or transmitted to the network.");

RPCTypeCheck(params, boost::assign::list_of(array_type)(obj_type));
if (params.size() == 2)
RPCTypeCheck(params, boost::assign::list_of(array_type)(obj_type));
else
RPCTypeCheck(params, boost::assign::list_of(array_type)(obj_type)(obj_type));

Array inputs = params[0].get_array();
Object sendTo = params[1].get_obj();
Expand Down Expand Up @@ -2899,6 +2905,12 @@ Value createrawtransaction(const Array& params, bool fHelp)
rawTx.vout.push_back(out);
}

if (params.size() == 3)
{
Object nameOp = params[2].get_obj();
AddRawTxNameOperation(rawTx, nameOp);
}

CDataStream ss(SER_NETWORK, VERSION);
ss << rawTx;
return HexStr(ss.begin(), ss.end());
Expand Down Expand Up @@ -3939,6 +3951,7 @@ void RPCConvertValues(const std::string &strMethod, json_spirit::Array &params)
if (strMethod == "getrawtransaction" && n > 1) ConvertTo<boost::int64_t>(params[1]);
if (strMethod == "createrawtransaction" && n > 0) ConvertTo<Array>(params[0]);
if (strMethod == "createrawtransaction" && n > 1) ConvertTo<Object>(params[1]);
if (strMethod == "createrawtransaction" && n > 2) ConvertTo<Object>(params[2]);
if (strMethod == "signrawtransaction" && n > 1) ConvertTo<Array>(params[1], true);
if (strMethod == "signrawtransaction" && n > 2) ConvertTo<Array>(params[2], true);
if (strMethod == "listsinceblock" && n > 1) ConvertTo<boost::int64_t>(params[1]);
Expand Down
64 changes: 64 additions & 0 deletions src/namecoin.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1255,6 +1255,70 @@ Value name_new(const Array& params, bool fHelp)
return res;
}

/* Implement name operations for createrawtransaction. */
void
AddRawTxNameOperation (CTransaction& tx, const Object& obj)
{
Value val = find_value (obj, "op");
if (val.type () != str_type)
throw JSONRPCError (RPC_INVALID_PARAMETER, "Missing op key.");
const std::string op = val.get_str ();

if (op != "name_update")
throw std::runtime_error ("Only name_update is implemented"
" for raw transactions at the moment.");

val = find_value (obj, "name");
if (val.type () != str_type)
throw JSONRPCError (RPC_INVALID_PARAMETER, "Missing name key.");
const std::string name = val.get_str ();
const std::vector<unsigned char> vchName = vchFromString (name);

val = find_value (obj, "value");
if (val.type () != str_type)
throw JSONRPCError (RPC_INVALID_PARAMETER, "Missing value key.");
const std::string value = val.get_str ();

val = find_value (obj, "address");
if (val.type () != str_type)
throw JSONRPCError (RPC_INVALID_PARAMETER, "Missing address key.");
const std::string address = val.get_str ();
if (!IsValidBitcoinAddress (address))
{
std::ostringstream msg;
msg << "Invalid Namecoin address: " << address;
throw JSONRPCError (RPC_INVALID_ADDRESS_OR_KEY, msg.str ());
}

/* Find the transaction input to add. */

CRITICAL_BLOCK(cs_main)
{
CNameDB dbName("r");
CTransaction prevTx;
if (!GetTxOfName (dbName, vchName, prevTx))
throw std::runtime_error ("could not find a coin with this name");
const uint256 prevTxHash = prevTx.GetHash();
const int nTxOut = IndexOfNameOutput (prevTx);

CTxIn in(COutPoint(prevTxHash, nTxOut));
tx.vin.push_back (in);
}

/* Construct the transaction output. */

CScript scriptPubKeyOrig;
scriptPubKeyOrig.SetBitcoinAddress (address);

CScript scriptPubKey;
scriptPubKey << OP_NAME_UPDATE << vchName << vchFromString (value)
<< OP_2DROP << OP_DROP;
scriptPubKey += scriptPubKeyOrig;

CTxOut out(MIN_AMOUNT, scriptPubKey);
tx.vout.push_back (out);
}

void UnspendInputs(CWalletTx& wtx)
{
set<CWalletTx*> setCoins;
Expand Down
5 changes: 5 additions & 0 deletions src/namecoin.h
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
#ifndef NAMECOIN_H
#define NAMECOIN_H

#include "json/json_spirit.h"

class CNameDB : public CDB
{
protected:
Expand Down Expand Up @@ -92,4 +94,7 @@ std::string SendMoneyWithInputTx(CScript scriptPubKey, int64 nValue, int64 nNetF
bool CreateTransactionWithInputTx(const std::vector<std::pair<CScript, int64> >& vecSend, CWalletTx& wtxIn, int nTxOut, CWalletTx& wtxNew, CReserveKey& reservekey, int64& nFeeRet);
int64 GetNetworkFee(int nHeight);

/* Handle the name operation part of the RPC call createrawtransaction. */
void AddRawTxNameOperation(CTransaction& tx, const json_spirit::Object& obj);

#endif // NAMECOIN_H

0 comments on commit 426a6d8

Please sign in to comment.