Completed
Push — master ( 34a4c4...267ea0 )
by thomas
76:18 queued 73:19
created

OutputScriptFactory::witnessKeyHash()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 8
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 6

Importance

Changes 0
Metric Value
cc 2
eloc 4
nc 2
nop 1
dl 0
loc 8
ccs 0
cts 4
cp 0
crap 6
rs 9.4285
c 0
b 0
f 0
1
<?php
2
3
namespace BitWasp\Bitcoin\Script\Factory;
4
5
use BitWasp\Bitcoin\Address\AddressInterface;
6
use BitWasp\Bitcoin\Address\ScriptHashAddress;
7
use BitWasp\Bitcoin\Crypto\EcAdapter\Key\PublicKeyInterface;
8
use BitWasp\Bitcoin\Script\Opcodes;
9
use BitWasp\Bitcoin\Script\ScriptFactory;
10
use BitWasp\Bitcoin\Script\ScriptInterface;
11
use BitWasp\Buffertools\BufferInterface;
12
use BitWasp\Buffertools\Buffertools;
13
14
class OutputScriptFactory
15
{
16
    /**
17
     * @param AddressInterface $address
18
     * @return ScriptInterface
19
     */
20 96
    public function payToAddress(AddressInterface $address)
21
    {
22 64
        return $address instanceof ScriptHashAddress
23 40
            ? ScriptFactory::sequence([Opcodes::OP_HASH160, $address->getHash(), Opcodes::OP_EQUAL])
24 96
            : ScriptFactory::sequence([Opcodes::OP_DUP, Opcodes::OP_HASH160, $address->getHash(), Opcodes::OP_EQUALVERIFY, Opcodes::OP_CHECKSIG]);
25
    }
26
27
    /**
28
     * Create a Pay to pubkey output
29
     *
30
     * @param PublicKeyInterface  $publicKey
31
     * @return ScriptInterface
32
     */
33 30
    public function payToPubKey(PublicKeyInterface $publicKey)
34
    {
35 30
        return ScriptFactory::sequence([$publicKey->getBuffer(), Opcodes::OP_CHECKSIG]);
36
    }
37
38
    /**
39
     * Create a P2PKH output script
40
     *
41
     * @param BufferInterface $pubKeyHash
42
     * @return ScriptInterface
43
     */
44 54
    public function payToPubKeyHash(BufferInterface $pubKeyHash)
45
    {
46 54
        if ($pubKeyHash->getSize() !== 20) {
47
            throw new \RuntimeException('Public key hash must be exactly 20 bytes');
48
        }
49
50 54
        return ScriptFactory::sequence([Opcodes::OP_DUP, Opcodes::OP_HASH160, $pubKeyHash, Opcodes::OP_EQUALVERIFY, Opcodes::OP_CHECKSIG]);
51
    }
52
53
    /**
54
    /**
55
     * Create a P2SH output script
56
     *
57
     * @param BufferInterface $scriptHash
58
     * @return ScriptInterface
59
     */
60 84
    public function payToScriptHash(BufferInterface $scriptHash)
61
    {
62 84
        if ($scriptHash->getSize() !== 20) {
63
            throw new \RuntimeException('P2SH scriptHash must be exactly 20 bytes');
64
        }
65
66 84
        return ScriptFactory::sequence([Opcodes::OP_HASH160, $scriptHash, Opcodes::OP_EQUAL]);
67
    }
68
69
    /**
70
     * @param int $m
71
     * @param PublicKeyInterface[] $keys
72
     * @param bool|true $sort
73
     * @return ScriptInterface
74
     */
75 72
    public function multisig($m, array $keys = [], $sort = true)
76
    {
77 72
        $n = count($keys);
78 72
        if ($m < 0) {
79
            throw new \LogicException('Number of signatures cannot be less than zero');
80
        }
81
82 72
        if ($m > $n) {
83
            throw new \LogicException('Required number of sigs exceeds number of public keys');
84
        }
85
86 72
        if ($n > 20) {
87
            throw new \LogicException('Number of public keys is greater than 16');
88
        }
89
90 72
        if ($sort) {
91 36
            $keys = Buffertools::sort($keys);
92 12
        }
93
94 72
        $new = ScriptFactory::create();
95 72
        $new->int($m);
96 72
        foreach ($keys as $key) {
97 72
            if (!$key instanceof PublicKeyInterface) {
98
                throw new \LogicException('Values in $keys[] must be a PublicKey');
99
            }
100
101 72
            $new->push($key->getBuffer());
102 24
        }
103
104 72
        return $new->int($n)->op('OP_CHECKMULTISIG')->getScript();
105
    }
106
107
    /**
108
     * @param BufferInterface $keyHash
109
     * @return ScriptInterface
110
     */
111
    public function witnessKeyHash(BufferInterface $keyHash)
112
    {
113
        if ($keyHash->getSize() !== 20) {
114
            throw new \RuntimeException('witness key-hash should be 20 bytes');
115
        }
116
117
        return ScriptFactory::sequence([Opcodes::OP_0, $keyHash]);
118
    }
119
120
    /**
121
     * @param BufferInterface $scriptHash
122
     * @return ScriptInterface
123
     */
124
    public function witnessScriptHash(BufferInterface $scriptHash)
125
    {
126
        if ($scriptHash->getSize() !== 32) {
127
            throw new \RuntimeException('witness script-hash should be 32 bytes');
128
        }
129
130
        return ScriptFactory::sequence([Opcodes::OP_0, $scriptHash]);
131
    }
132
}
133