Skip to content

Commit f05b338

Browse files
committed
fix & examples
1 parent 8d6788b commit f05b338

File tree

5 files changed

+108
-15
lines changed

5 files changed

+108
-15
lines changed

examples/print_balances.php

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
<?php
2+
3+
include '../vendor/autoload.php';
4+
5+
$blockDir = getenv('HOME') . '/Library/Application Support/Bitcoin/blocks';
6+
7+
$reader = new \AndKom\PhpBitcoinBlockchain\BlockFileReader();
8+
9+
// txid:index => balance
10+
$outputs = [];
11+
12+
// txid:index => address
13+
$addresses = [];
14+
15+
foreach ($reader->read($blockDir . '/blk00000.dat') as $block) {
16+
17+
foreach ($block->transactions as $tx) {
18+
foreach ($tx->inputs as $in) {
19+
if ($in->isCoinbase()) continue;
20+
21+
$prev = $in->prevTxHash . ':' . $in->prevTxOutIndex;
22+
$outputs[$prev] = 0;
23+
}
24+
25+
$txid = $tx->getHash();
26+
27+
foreach ($tx->outputs as $index => $out) {
28+
try {
29+
$address = $out->scriptPubKey->getOutputAddress();
30+
} catch (\Exception $e) {
31+
$address = 'unknown script: ' . $out->scriptPubKey;
32+
}
33+
34+
$output = "$txid:$index";
35+
36+
if (!isset($outputs[$output])) {
37+
$outputs[$output] = 0;
38+
}
39+
40+
$outputs[$output] += $out->value;
41+
$addresses[$output] = $address;
42+
}
43+
}
44+
}
45+
46+
$balances = [];
47+
48+
foreach ($outputs as $out => $value) {
49+
// @todo address may not exists because blocks are unordered
50+
$address = $addresses[$out];
51+
52+
if (!isset($balances[$address])) {
53+
$balances[$address] = 0;
54+
}
55+
56+
$balances[$address] += $value;
57+
}
58+
59+
arsort($balances);
60+
61+
foreach ($balances as $address => $balance) {
62+
echo $address . ' => ' . bcdiv($balance, 1e8, 8) . " BTC\n";
63+
}

examples/print_blocks.php

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
<?php
2+
3+
include '../vendor/autoload.php';
4+
5+
$blockDir = getenv('HOME') . '/Library/Application Support/Bitcoin/blocks';
6+
7+
$reader = new \AndKom\PhpBitcoinBlockchain\BlockFileReader();
8+
9+
foreach ($reader->read($blockDir . '/blk00000.dat') as $block) {
10+
11+
echo str_repeat('=', 71) . "\n";
12+
echo "Block: " . $block->header->getHash() . "\n";
13+
echo "Date: " . date('r', $block->header->time) . "\n";
14+
15+
foreach ($block->transactions as $tx) {
16+
echo "\nTX: " . $tx->getHash() . "\n";
17+
18+
foreach ($tx->inputs as $in) {
19+
if ($in->isCoinbase()) {
20+
echo "IN: Coinbase\n";
21+
} else {
22+
echo "IN: " . $in->prevTxHash . ':' . $in->prevTxOutIndex . "\n";
23+
}
24+
}
25+
26+
foreach ($tx->outputs as $out) {
27+
try {
28+
$address = $out->scriptPubKey->getOutputAddress();
29+
} catch (\Exception $e) {
30+
$address = 'Unable to decode output address.';
31+
}
32+
33+
echo "OUT: " . bcdiv($out->value, 1e8, 8) . " BTC => " . $address . "\n";
34+
}
35+
}
36+
}

src/Input.php

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,4 +64,12 @@ public function serialize(Writer $stream): self
6464
$stream->writeInt32($this->sequenceNo);
6565
return $this;
6666
}
67+
68+
/**
69+
* @return bool
70+
*/
71+
public function isCoinbase(): bool
72+
{
73+
return $this->prevTxHash == '0000000000000000000000000000000000000000000000000000000000000000';
74+
}
6775
}

src/Transaction.php

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -142,18 +142,4 @@ public function getHash(bool $segWit = false): string
142142
$hash = bin2hex($hash);
143143
return $hash;
144144
}
145-
146-
/**
147-
* @return bool
148-
*/
149-
public function isCoinbase(): bool
150-
{
151-
foreach ($this->inputs as $input) {
152-
if ($input->prevTxHash == '0000000000000000000000000000000000000000000000000000000000000000') {
153-
return true;
154-
}
155-
}
156-
157-
return false;
158-
}
159145
}

tests/BlockTest.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,14 +43,14 @@ public function testParse()
4343
$this->assertEquals($block->transactions[0]->getHash(), '4a5e1e4baab89f3a32518a88c31bc87f618f76673e2cc77ab2127b7afdeda33b');
4444
$this->assertEquals($block->transactions[0]->version, 1);
4545
$this->assertEquals($block->transactions[0]->inCount, 1);
46+
$this->assertEquals($block->transactions[0]->inputs[0]->isCoinbase(), true);
4647
$this->assertEquals($block->transactions[0]->inputs[0]->prevTxHash, '0000000000000000000000000000000000000000000000000000000000000000');
4748
$this->assertEquals($block->transactions[0]->inputs[0]->prevTxOutIndex, -1);
4849
$this->assertEquals($block->transactions[0]->inputs[0]->sequenceNo, -1);
4950
$this->assertEquals($block->transactions[0]->inputs[0]->scriptSig->getData(), hex2bin('04ffff001d0104455468652054696d65732030332f4a616e2f32303039204368616e63656c6c6f72206f6e206272696e6b206f66207365636f6e64206261696c6f757420666f722062616e6b73'));
5051
$this->assertEquals($block->transactions[0]->outputs[0]->value, 5000000000);
5152
$this->assertEquals($block->transactions[0]->outputs[0]->scriptPubKey->getData(), hex2bin('4104678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5fac'));
5253
$this->assertEquals($block->transactions[0]->lockTime, 0);
53-
$this->assertTrue($block->transactions[0]->isCoinbase());
5454

5555
$stream = new Writer();
5656
$block->serialize($stream);

0 commit comments

Comments
 (0)