edgecase
Author: StJohn Piano
Published: 2020-09-12
Datafeed Article 176
This article has been digitally signed by Edgecase Datafeed.
729 words - 338 lines - 9 pages





Parts


- Description
- Assets
- Notes
- Recipe
- Examples




Description


This recipe describes a method of looking up the unspent outputs associated with a Bitcoin address.

The unspent outputs can be used:
- to calculate the balance of the address.
- as inputs to a new Bitcoin transaction.

This version of the recipe relies on a feature of a particular block explorer that automates most of the previous version.

Previous version of this recipe:
Recipe for looking up the unspent outputs in a Bitcoin address






Assets


Asset: A tool that queries blockchain.info for the list of unspent outputs in an address and re-formats the result.
get_unspent_outputs_in_address.py






Notes


Bitcoin is stored in a Bitcoin address.

An address holds "unspent outputs", which have been created by previous Bitcoin transactions.

(The sum of the values in the unspent outputs) = (the amount of bitcoin that is held in the address).

Any unspent output used as an input in a transaction becomes "spent".






Recipe


Block explorers usually:
- allow a user to look up an address and see a list of all related transactions.
- look up a transaction and get information about its inputs and outputs.

These two features can be used to derive the list of unspent outputs in an address.

In the previous version of this recipe, this process was manual.

In this version, we rely on a feature of the block explorer blockchain.info. This block explorer tracks the unspent outputs stored in each address and makes them available for querying at this URL:

http://blockchain.info/unspent?active={ADDRESS}




1) Prerequisite: Python 2.7.x. The code in this recipe has been run successfully under Python 2.7.12.


2) Scroll to the Assets section of this recipe. Download
get_unspent_outputs_in_address.py.


3) Commands:

Guidance:
python get_unspent_outputs_in_address.py --help


Use:
python get_unspent_outputs_in_address.py --address {ADDRESS}


Example:

python get_unspent_outputs_in_address.py --address 12YCFdpsRDvEHNcj5rsmvJ5G2XXkW1icJP











Examples


This recipe was written during the previous project Creating and signing a standard Bitcoin transaction with two inputs and two outputs, so I was able to test it while some of the test addresses contained unspent outputs.


Look up the unspent outputs in address A1:
1BB66Gx4833uKx8Lo2k8Mt4TRk42WTr7cZ


Browse to:
blockchain.info/unspent?active=1BB66Gx4833uKx8Lo2k8Mt4TRk42WTr7cZ

Result:
No free outputs to spend



Look up the unspent outputs in address A2:
12YCFdpsRDvEHNcj5rsmvJ5G2XXkW1icJP


Browse to:
blockchain.info/unspent?active=12YCFdpsRDvEHNcj5rsmvJ5G2XXkW1icJP

Result:
{"notice":"","unspent_outputs":[{"tx_hash":"ea1b9db39c6fd5df377e381a896ddb47da4c3c23faf80fe2da9b13014c055f58","tx_hash_big_endian":"585f054c01139bdae20ff8fa233c4cda47db6d891a387e37dfd56f9cb39d1bea","tx_output_n":0,"script":"76a91410de69df99d4b834ee6f2bd1466edab556beb7d688ac","value":474300,"value_hex":"073cbc","confirmations":395,"tx_index":0}]}



This is the information we want, but to be useful it needs to be reformatted a bit.

This block explorer uses these terms:
- "tx_hash_big_endian" (txid)
- "tx_output_n" (previous_output_index)
- "value" (satoshi_value)


The tool get_unspent_outputs_in_address.py queries the URL for a specified address and re-formats the result to be more readable.


stjohn@judgement:work$ python get_unspent_outputs_in_address.py --help

usage: get_unspent_outputs_in_address.py [-h] -a ADDRESS A command-line tool that looks up the Unspent Transaction Outputs (UTXOs) in a particular Bitcoin address. It queries blockchain.info. It ignores unspent outputs that have less than 6 confirmations. optional arguments: -h, --help show this help message and exit -a ADDRESS, --address ADDRESS Address to look up



stjohn@judgement:work$ python get_unspent_outputs_in_address.py --address 1BB66Gx4833uKx8Lo2k8Mt4TRk42WTr7cZ

This address has 0 unspent outputs. Its balance is therefore 0 satoshi (0.00000000 bitcoin).


stjohn@judgement:work$ python get_unspent_outputs_in_address.py --address 12YCFdpsRDvEHNcj5rsmvJ5G2XXkW1icJP

address: 12YCFdpsRDvEHNcj5rsmvJ5G2XXkW1icJP
balance (satoshi): 474300
balance (bitcoin): 0.00474300
- unspent output 0:
-- txid: 585f054c01139bdae20ff8fa233c4cda47db6d891a387e37dfd56f9cb39d1bea
-- previous_output_index: 0
-- satoshi_value: 474300
-- bitcoin_value: 0.00474300





At this point in these examples, the previous project has ended. I've made a few tweaks in the code.


I'll test the tool on the final address from the previous project.


stjohn@judgement:work$ python get_unspent_outputs_in_address.py -a 1NBXXLc7443x5KFw7k5jbnHBwM1CNGw6ka

address: 1NBXXLc7443x5KFw7k5jbnHBwM1CNGw6ka
balance (satoshi): 6385539
balance (bitcoin): 0.06385539
- unspent output 0:
-- txid: 961be73009cba0e361f8dd41c82aeb584167134f63bec08d54f77aca5d284de2
-- previous_output_index: 10
-- satoshi_value: 210000
-- bitcoin_value: 0.00210000
- unspent output 1:
-- txid: cf0789ccbd8234cbfd522e11f4552363e2e928323b6f41ccf0f58a3a796f42e9
-- previous_output_index: 27
-- satoshi_value: 5307339
-- bitcoin_value: 0.05307339
- unspent output 2:
-- txid: aad6d03ab13203ee7bdfb7e747c5aaef5a60f23c46b87e744176ad7955bd8bb6
-- previous_output_index: 0
-- satoshi_value: 868200
-- bitcoin_value: 0.00868200





Let's test that the bitcoin values in the outputs all add up to the balance:

stjohn@judgement:work$ python

Python 2.7.12 (default, Jul 21 2020, 15:19:50)
[GCC 5.4.0 20160609] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> values = ['0.00210000', '0.05307339', '0.00868200']
>>> from decimal import Decimal
>>> values = [Decimal(v) for v in values]
>>> balance = Decimal('0.06385539')
>>> sum(values) == balance
True
>>> sum(values)
Decimal('0.06385539')



Yup, works.


On a block explorer, the balance is confirmed to be:
0.06385539 bitcoin



Good. That's the end of this project.