Enhancement Request: Method to retrieve list of mature transactions (w/details)

A question came up on Reddit, " This is confusing, care to explain? (PoS minting)," that reminded me of a feature request that I’ve meant to discuss with the community.

Basically, the confusion exists due to a misconception between the what a user perceives “stake” to mean, and how the client (or the daemon) uses the term “stake”. From talking to other users (and from my own experiences, initially), the expectation is that somewhere in the client you would be able to see how many of your coins are mature and actively being used to solve for a block. Even though proof-of-stake is a fundamentally important part of the protocol (arguably the most important part), there’s no way for a user to gain insight into what’s happening behind the scenes when ‘CPUMinter’ is active.

Proposal
I’d like to propose the addition of a new method that can be called from the command line, or from the Peercoin-Qt client, that would output a list of the current input transactions that the CPUMinter process would look to after a block was solved. The (tentatively titled) method, listminting, in a hypothetical scenario, would report back to the user the following information, for each transaction:

[font=courier]$ ./ppcoind listminting
[
{
“account” : “A really old input transaction from an address kept offline until two minutes ago”,
“address” : “PLLxYKXkBxp2baP7Fn2sxcr1fCUjDxsHX6”,
“input_txid” : “e74b4543b44bfcfd431481dc641e25dcc9f3f63895293796757fdf9c1fcaa2e6”,
“amount” : 10000.001,
“status” : “mature”,
“age-in-days” : 568.21,
“coindayweight” : 900000.09,
“time” : 1394480691,
“proof-of-stake-difficulty” : 10.68816069,
“target” : 10987012,
“search-interval-in-sec” : 1,
“attempts” : 274
},
{
“account” : “A large input transaction that is over 90 days old”,
“address” : “PYK7Fn2sxcr1fCUjDxsHXXkBxp2baP6LLx”,
“input_txid” : “31481dc641e25dcc9f3f63895293796757fdf9c1fcaa2e6e74b4543b44bfcfd4”,
“time” : 1394780691,
“amount” : 10000.001,
“status” : “mature”,
“age-in-days” : 91.00,
“coindayweight” : 900000.09,
“proof-of-stake-difficulty” : 10.68816069,
“target” : 10987012,
“search-interval-in-sec” : 1,
“attempts” : 5270400
},
{
“account” : “Consulting Work”,
“address” : “PxsHLxYKX12baUjDP7Fn2sxcr1fCkBxX6L”,
“input_txid” : “c95293796757fdf91fcaa2e6e74b4543b44bfcfd431481dc641e25dcc9f3f638”,
“time” : 1396980691,
“amount” : 134.51289,
“status” : “mature”,
“age-in-days” : 37.901,
“coindayweight” : 5098.17304389,
“proof-of-stake-difficulty” : 10.68816069,
“target” : 10987012,
“search-interval-in-sec” : 1,
“attempts” : 682646
},
{
“account” : “An input transaction that has not yet matured”,
“address” : “Pp2baUjDxsHX6LLxYKXP7Fn2sxcr1fCkBx”,
“input_txid” : “481dc641e25dcc9f3f63895293796757fdf9c1fcaa2e6e74b4543b44bfcfd431”,
“time” : 1398480691,
“amount” : 8.001,
“status” : “immature”,
“age-in-days” : 7.21,
“coindayweight” : 57.68721,
“proof-of-stake-difficulty” : 10.68816069,
“target” : 10987012,
“search-interval-in-sec” : 1,
“attempts” : 0
},
][/font]

I’m not positive that it’s something that you could calculate (I assume it is, but need to re-read the code), but if we could include a “maxHashValue” report, it could be possible to then do a probability calculation to see how likely it is that a given transaction will come up with a hash that passes the test, [font=courier](target * coinDayWeight) / maxHashValue[/font].

Also, I’m still thinking about arguments that could be passed to the method. Presumably, you’d want a couple of related methods that covered all of the important ways to segment the data and to keep the scope of each more concise (I don’t know if you’d want all of these to be separate, but I wanted to cover the different ways of pulling back data):

[font=courier]./ppcoind listmintingbyaccount [count=10] [from=0] [minconf=1]
./ppcoind listmintingbyaddress [count=10] [from=0] [minconf=1]
./ppcoind listmintingbytransaction [count=10] [from=0] [minconf=1]
./ppcoind listmintingbyage [count=10] [from=0] [minconf=1]
./ppcoind listmintingbyweight [count=10] [from=0] [minconf=1]
./ppcoind listmintingbyattempts [count=10] [from=0] [minconf=1][/font]

Did I miss anything? Are there other values that would be useful to report on?

Edit: Added method variations section

I like this idea.

Since this does not involve changes to the network, any one could try to code this in their own wallet as a test, especially on testnet.

I wonder what type of conversation would spill on to the forums:

Hey! My transaction had 274 attempts and minted. Some one else goes! Yeah, but I’m up to 2506 attempts and I still haven’t minted.

…also doing so, eats cpu cycles, and takes up extra bytes of space. This does fatten the work ppcoind must do, even if it is just counters. :slight_smile:

I still like it though.

[b]Add one more field:

"mint-priority: " where you can give a value. This way you could set your largest transaction as the highest priority, and it would be user-selectable.[/b]

I think this is a really good idea and it shouldn’t be too difficult to implement since all this information is already available using a collection of other methods.

I suggest you have a try the service from http://stakexplorer.com, which provides online coin-days calculation for each transaction in/out for each address in real time. For example, the present PoS block 105880 mined by address: PR484eBkWLTwCU1T1kwxAe2UAMEkQUS9mA , so you can get this address’s coin-days list for each tx at http://stakexplorer.com:2750/address/PR484eBkWLTwCU1T1kwxAe2UAMEkQUS9mA . You can just replace with your address in the above link to have a check of your mature/unmature transactions, and decide when/how to do PoS minting. It also provides the destroyed coin days history.

Hi there !
As a follow up of the minting tab on the qt client, I started implementing the listminting rpc command.
So far i got this from my wallet on testnet :

$ ./src/ppcoind listminting
[
    {
        "account" : "",
        "address" : "myxGci8Dd2a3tkzrRPnEW1AyS9Gud1yKU3",
        "input-txid" : "3ce5ef8d04ed2bcadab893746c76eb5bdde3e1a61ab87c04f15604d8d9956a63",
        "time" : "1402520565",
        "amount" : "4990000",
        "status" : "immature",
        "age-in-day" : "0",
        "coin-day-weight" : "0",
        "proof-of-stake-difficulty" : 5.12229169,
        "minting-probability-10min" : 0.00000000,
        "minting-probability-24h" : 0.00000000,
        "minting-probability-30d" : 0.00000000,
        "minting-probability-90d" : 0.00000000,
        "target" : "todo",
        "search-interval-in-sec" : "todo",
        "attempts" : "todo"
    },
    {
        "account" : "main",
        "address" : "mj5bQKkZ1YDnjXvuBD2dr6JLSqWr4GVTC3",
        "input-txid" : "e8bdd9ba9b3eb04329d79bd849d066a66a7ab47a704caf2397b3e4e3dcce2f5c",
        "time" : "1401658074",
        "amount" : "10000000",
        "status" : "mature",
        "age-in-day" : "9",
        "coin-day-weight" : "80",
        "proof-of-stake-difficulty" : 5.12229169,
        "minting-probability-10min" : 0.00000218,
        "minting-probability-24h" : 0.00031413,
        "minting-probability-30d" : 0.00938114,
        "minting-probability-90d" : 0.02788024,
        "target" : "todo",
        "search-interval-in-sec" : "todo",
        "attempts" : "todo"
    },
    {
        "account" : "",
        "address" : "mfrprKncR9brCfP3E3Z6tBUSmM41gySthj",
        "input-txid" : "f75cff68bdede7f9ddef427403349f2cd933550eff414eb71265ea8de5dafd19",
        "time" : "1402331968",
        "amount" : "24980000",
        "status" : "mature",
        "age-in-day" : "2",
        "coin-day-weight" : "24",
        "proof-of-stake-difficulty" : 5.12229169,
        "minting-probability-10min" : 0.00000065,
        "minting-probability-24h" : 0.00009425,
        "minting-probability-30d" : 0.00282363,
        "minting-probability-90d" : 0.00844700,
        "target" : "todo",
        "search-interval-in-sec" : "todo",
        "attempts" : "todo"
    }
]

I added the probability fields (minting-probability-*) since I had those values available with no extra processing.
We should also consider that the “account” field will be mostly empty since output are send on generated addresses.

Can anyone help me with the “target”, “attempts” and “search-interval-in-sec” fields ? I have no idea what is it and how retreive their value !

Next, i’ll get those sorting functions running :wink:

Can anyone answer daeMOn on this? We have an interested and active developer here, which is the bread and butter of the community. Don’t miss this opportunity to lend a hand.

A transaction old enough to mint tries to find a block every second.
So if the transaction is old enough, ‘search-interval-in-sec’ is 1; and if the transaction is too young or if it is not minting because the wallet is locked, ‘search-interval-in-sec’ is 0.

Then, if ‘attempts’ is the number of times a transaction tried to find a block, it is also the number of seconds it has been minting.

If ‘target’ is the target related to the POS difficulty:

target = max_target / difficulty; (where max_target is 2^224)

But if ‘target’ is the target that will be used for a transaction trying to find a block:

target = coin_day_weight * max_target / difficulty;

You can find this formula in the ‘CheckStakeKernelHash’ function in ‘src/kernel.cpp’.

Thanx for the precisions glv.

So, i’m good with attemps and search-interval. But i can’t manage to find something good for target.

I’m getting huge numbers with no much meaning with the formulas (like 271140100183367869781917544476611578910685721522009637826832704200507392.00000000) with a PoS difficulty at 24.83279233.

Is it an expected result, a testnet only effect or i’m doing anything wrong ?

Yes, given the current difficulty, the target is a big number.

When minting, every second you hash some values (sha256) and if the resulting hash is smaller than the target, you can make a valid block and broadcast it to the network.
The hash is a 256bit value (max 115792089237316195423570985008687907853269984665640564039457584007913129639935), and the target related to the POS difficulty is a 224bit value (max 26959946667150639794667015087019630673637144422540572481103610249215).

I don’t know if displaying the target will be useful for someone though. The POS difficulty is already displayed and it gives an easier to read indication on the state of the network.
However instead of the target, maybe we could display the difficulty for each stake (POS difficulty divided by coin-day weight).
Something like this for a 100 coin-days stake:

...
"proof-of-stake-difficulty" : 5.12229169,
"stake-difficulty" : 0.05122292,
...