#!/usr/bin/env python3
#
# mmgen = Multi-Mode GENerator, command-line Bitcoin cold storage solution
# Copyright (C)2013-2021 The MMGen Project <mmgen@tuta.io>
#
# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU General Public License as published by the Free Software
# Foundation, either version 3 of the License, or (at your option) any later
# version.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
# details.
#
# You should have received a copy of the GNU General Public License along with
# this program.  If not, see <http://www.gnu.org/licenses/>.

"""
mmnode-blocks-info: Display information about a block or range of blocks
"""

from mmgen.common import *
from mmgen.node_tools.BlocksInfo import BlocksInfo,JSONBlocksInfo

opts_data = {
	'sets': [
		('hashes',     True,   'fields',     'block,hash'),
		('hashes',     True,   'stats',      'none'),
		('json_raw',   True,   'json',       True),
		('raw_miner_info',True,'miner_info', True),
	],
	'text': {
		'desc':    'Display information about a block or range of blocks',
		'usage':   '[opts] blocknum [blocknum ...] | blocknum-blocknum[+step] | [blocknum|-nBlocks]+nBlocks[+step]',
		'usage2': [
			'[opts] blocknum [blocknum ...]',
			'[opts] blocknum-blocknum[+step]',
			'[opts] [blocknum|-nBlocks]+nBlocks[+step]',
		],
		'options': """
-h, --help            Print this help message
--, --longhelp        Print help message for long options (common options)
-H, --hashes          Display only block numbers and hashes
-j, --json            Produce JSON output
-J, --json-raw        Produce JSON output with unformatted values
-m, --miner-info      Display miner info in coinbase transaction
-M, --raw-miner-info  Display miner info in uninterpreted form
-n, --no-header       Don’t print the column header
-o, --fields=         Display the specified fields (comma-separated list).
                      See AVAILABLE FIELDS below.  Prefix the list with '+'
                      to add the fields to the defaults, or '-' to remove
                      them.  The special values 'all' and 'none' select all
                      available fields or none, respectively.
-s, --stats=          Display the specified stats (comma-separated list).
                      See AVAILABLE STATS below.  The prefixes and special
                      values available to the --fields option are recognized.
""",
	'notes': """
If no block number is specified, the current chain tip is assumed.

The special value 'cur' can be used to designate the chain tip wherever a
block number is expected.

If the requested range ends at the current chain tip, an estimate of the next
difficulty adjustment is also displayed. The estimate is based on the average
Block Discovery Interval from the beginning of the current 2016-block period.

All fee fields except for 'totalfee' are in satoshis per virtual byte.

AVAILABLE FIELDS: {f}

AVAILABLE STATS: {s}

EXAMPLES:

    Display info for current block:
    $ {p}

    Display info for the Genesis Block:
    $ {p} 0

    Display info for the last 20 blocks:
    $ {p} +20

    Display specified fields for blocks 165-190
    $ {p} -o block,date,size,inputs,nTx 165-190

    Display info for 10 blocks beginning at block 600000:
    $ {p} 600000+10

    Display info for every 5th block of 50-block range beginning at 1000
    blocks from chain tip:
    $ {p} -- -1000+50+5

    Display info for block 152817, adding miner field:
    $ {p} -o +miner 152817

    Display specified fields for listed blocks:
    $ {p} -o block,date,hash 245798 170 624044

    Display every difficulty adjustment from Genesis Block to chain tip:
    $ {p} -o +difficulty 0-cur+2016

    Display roughly a block a day over the last two weeks.  Note that
    multiplication is allowed in the nBlocks spec:
    $ {p} +144*14+144

    Display only range stats for the last ten blocks:
    $ {p} -o none -s range +10

    Display data for the last ten blocks, skipping 'size' and 'subsidy'
    fields and stats:
    $ {p} -o -size,subsidy -s none +10

    Display all fields and stats for the last ten blocks:
    $ {p} -o all -s all +10

This program requires a txindex-enabled daemon for correct operation.
""".format(
		f = fmt_list(BlocksInfo.fields,fmt='bare'),
		s = fmt_list(BlocksInfo.all_stats,fmt='bare'),
		p = g.prog_name )
	}
}

cmd_args = opts.init(opts_data)

async def main():

	from mmgen.protocol import init_proto_from_opts
	from mmgen.rpc import rpc_init

	proto = init_proto_from_opts()

	cls = JSONBlocksInfo if opt.json else BlocksInfo

	m = cls( cmd_args, opt, await rpc_init(proto) )

	if m.fnames and not opt.no_header:
		m.print_header()

	await m.process_blocks()

	if m.last:
		for i,sname in enumerate(m.stats):
			m.process_stats_pre(i)
			await m.process_stats(sname)

	m.finalize_output()

run_session(main())
