Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

debug: test failure #145

Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
e4f2532
feat: replace zmq with http calls
DhananjayPurohit Dec 12, 2023
57114ba
fix: tests, remove txsigningtool
DhananjayPurohit Dec 13, 2023
f1fcbd6
Merge branch 'develop' into feat/replace-zmq-with-http
DhananjayPurohit Dec 14, 2023
954a4f8
Merge branch 'feat/replace-zmq-with-http' of https://github.com/comme…
DhananjayPurohit Dec 15, 2023
2cef9fe
fix: upgrade golang version in dockerfile.tests
DhananjayPurohit Dec 15, 2023
376dfff
fix: test config
DhananjayPurohit Dec 15, 2023
7b1c41d
chore: remove unnecessary multi-sig attestation test
DhananjayPurohit Dec 18, 2023
87b22ef
fix: logical error with tx preimages
DhananjayPurohit Dec 21, 2023
3e8c3f8
fix: handle unconfirmed state service
DhananjayPurohit Dec 22, 2023
e0f2a24
fix: upgrade btcsuite to 0.24.0
DhananjayPurohit Jan 9, 2024
70ac453
Merge branch 'develop' into feat/replace-zmq-with-http
DhananjayPurohit Jan 10, 2024
f591f0d
fix: fieldval conversion from int
DhananjayPurohit Jan 10, 2024
69403bb
Merge branch 'feat/replace-zmq-with-http' of https://github.com/comme…
DhananjayPurohit Jan 10, 2024
b11f3f3
fix: change multi-sig to single-sig
DhananjayPurohit Dec 19, 2023
da2de73
fix: tx signing issues with segwit
DhananjayPurohit Jan 22, 2024
a64e2a9
fix: remove scripts from config
DhananjayPurohit Jan 23, 2024
15f1a1b
fix: sighash calculation and signing
DhananjayPurohit Jan 29, 2024
006f563
fix: os import
DhananjayPurohit Jan 29, 2024
5e974b7
fix: http signer for segwit
DhananjayPurohit Jan 30, 2024
fa65f45
chore: fix signer url, comment test for signer
DhananjayPurohit Jan 30, 2024
b3a752e
fix: os import error
DhananjayPurohit Jan 30, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
413 changes: 127 additions & 286 deletions attestation/attestclient.go

Large diffs are not rendered by default.

161 changes: 49 additions & 112 deletions attestation/attestclient_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,21 +5,19 @@
package attestation

import (
"encoding/hex"
"errors"
"math"
"testing"

"mainstay/clients"
confpkg "mainstay/config"
"mainstay/crypto"
"mainstay/models"
testpkg "mainstay/test"

"github.com/btcsuite/btcd/btcjson"
"github.com/btcsuite/btcd/btcutil"
"github.com/btcsuite/btcd/chaincfg/chainhash"
"github.com/btcsuite/btcd/wire"
"github.com/btcsuite/btcutil"
"github.com/stretchr/testify/assert"
)

Expand Down Expand Up @@ -70,31 +68,24 @@ func verifyFirstUnspent(t *testing.T, client *AttestClient) btcjson.ListUnspentR
}

// verify key derivation and return address
func verifyKeysAndAddr(t *testing.T, client *AttestClient, hash chainhash.Hash) (btcutil.Address, string) {
func verifyKeysAndAddr(t *testing.T, client *AttestClient, hash chainhash.Hash) (*btcutil.AddressWitnessPubKeyHash) {
// test getting next attestation key
key, errKey := client.GetNextAttestationKey(hash)
assert.Equal(t, nil, errKey)

// test getting next attestation address
addr, script, nextAddrErr := client.GetNextAttestationAddr(key, hash)
addr, nextAddrErr := client.GetNextAttestationAddr(key, hash)
assert.Equal(t, nil, nextAddrErr)

// test GetKeyAndScriptFromHash returns the same results
keyTest := client.GetKeyFromHash(hash)
scriptTest, scriptErr := client.GetScriptFromHash(hash)
assert.Equal(t, nil, scriptErr)
assert.Equal(t, *key, keyTest)
assert.Equal(t, script, scriptTest)

// test importing address
importErr := client.ImportAttestationAddr(addr)
assert.Equal(t, nil, importErr)

return addr, script
return addr
}

// verify transaction pre image generation
func verifyTransactionPreImages(t *testing.T, client *AttestClient, tx *wire.MsgTx, script string, hash chainhash.Hash, i int) {
func verifyTransactionPreImages(t *testing.T, client *AttestClient, tx *wire.MsgTx, hash chainhash.Hash, i int) {

// getTransactionPreImages with empty transaction
_, emptyPreImageErr := client.getTransactionPreImages(hash, &(wire.MsgTx{}))
Expand All @@ -106,16 +97,9 @@ func verifyTransactionPreImages(t *testing.T, client *AttestClient, tx *wire.Msg
assert.Equal(t, 1-1*int(math.Min(0, float64((i%(topupLevel+1)-1)))), len(txPreImages))
assert.Equal(t, 1-1*int(math.Min(0, float64((i%(topupLevel+1)-1)))), len(txPreImages[0].TxIn))

// get tweaked script and topup script serialisation
scriptSer, _ := hex.DecodeString(script)
topupScriptSer, _ := hex.DecodeString(client.scriptTopup)

// test signature script set correctly
assert.Equal(t, scriptSer, txPreImages[0].TxIn[0].SignatureScript)
if i == topupLevel+1 {
assert.Equal(t, []byte(nil), txPreImages[0].TxIn[1].SignatureScript)
assert.Equal(t, []byte(nil), txPreImages[1].TxIn[0].SignatureScript)
assert.Equal(t, topupScriptSer, txPreImages[1].TxIn[1].SignatureScript)
}
}

Expand Down Expand Up @@ -205,7 +189,7 @@ func TestAttestClient_Signer(t *testing.T) {
oceanCommitmentHash := oceanCommitment.GetCommitmentHash()

// get addr
addr, script := verifyKeysAndAddr(t, client, oceanCommitmentHash)
addr := verifyKeysAndAddr(t, client, oceanCommitmentHash)

var unspentList []btcjson.ListUnspentResult
unspentList = append(unspentList, unspent)
Expand All @@ -225,14 +209,14 @@ func TestAttestClient_Signer(t *testing.T) {
assert.Equal(t, false, (unspentAmount-(float64(tx.TxOut[0].Value)/Coin)) <= 0)

// verify transaction pre-image generation
verifyTransactionPreImages(t, client, tx, script, oceanCommitmentHash, i)
verifyTransactionPreImages(t, client, tx, oceanCommitmentHash, i)

// check fee value and bump
assert.Equal(t, client.Fees.minFee+(i-1)*client.Fees.feeIncrement, client.Fees.GetFee())
client.Fees.BumpFee()

// test signing and sending attestation
signedTx, signErr := client.signAttestation(tx, [][]crypto.Sig{}, lastHash)
signedTx, signErr := client.signAttestation(tx, []wire.TxWitness{}, lastHash)
assert.Equal(t, nil, signErr)
txid, sendErr := client.sendAttestation(signedTx)
assert.Equal(t, nil, sendErr)
Expand Down Expand Up @@ -284,21 +268,13 @@ func TestAttestClient_SignerAndNoSigner(t *testing.T) {

// test that when attempting to generate a new address with
// an empty hash, the intial address/script are returned
addrNoHash, scriptNoHash, nextAddrErr := client.GetNextAttestationAddr(nil, lastHash)
_, nextAddrErr := client.GetNextAttestationAddr(nil, lastHash)
assert.Equal(t, nil, nextAddrErr)
assert.Equal(t, testpkg.Address, addrNoHash.String())
assert.Equal(t, testpkg.Script, scriptNoHash)
assert.Equal(t, client.script0, scriptNoHash)
assert.Equal(t, unspent.Address, addrNoHash.String())
addrNoHash, scriptNoHash, nextAddrErr = clientSigner.GetNextAttestationAddr(nil, lastHash)
_, nextAddrErr = clientSigner.GetNextAttestationAddr(nil, lastHash)
assert.Equal(t, nil, nextAddrErr)
assert.Equal(t, testpkg.Address, addrNoHash.String())
assert.Equal(t, testpkg.Script, scriptNoHash)
assert.Equal(t, clientSigner.script0, scriptNoHash)
assert.Equal(t, unspent.Address, addrNoHash.String())

// test invalid tx signing
_, _, errSign := clientSigner.SignTransaction(chainhash.Hash{}, wire.MsgTx{})
_, errSign := clientSigner.SignTransaction(chainhash.Hash{}, wire.MsgTx{})
assert.Equal(t, errSign, errors.New(ErrorInputMissingForTx))

client.Fees.ResetFee(true) // reset fee to minimum
Expand All @@ -315,16 +291,9 @@ func TestAttestClient_SignerAndNoSigner(t *testing.T) {
assert.Equal(t, true, key == nil)

// test getting next attestation address
addr, script, nextAddrErr := client.GetNextAttestationAddr(key, oceanCommitmentHash)
addr, nextAddrErr := client.GetNextAttestationAddr(key, oceanCommitmentHash)
assert.Equal(t, nil, nextAddrErr)

// test GetKeyAndScriptFromHash returns the same results
// skip testing this - not applicable in no signer case
//keyTest := clientSigner.GetKeyFromHash(oceanCommitmentHash)
scriptTest, scriptErr := client.GetScriptFromHash(oceanCommitmentHash)
assert.Equal(t, nil, scriptErr)
assert.Equal(t, script, scriptTest)

// test importing address
importErr := client.ImportAttestationAddr(addr, false)
assert.Equal(t, nil, importErr)
Expand All @@ -347,67 +316,43 @@ func TestAttestClient_SignerAndNoSigner(t *testing.T) {
assert.Equal(t, false, (unspentAmount-(float64(tx.TxOut[0].Value)/Coin)) <= 0)

// verify transaction pre-image generation
verifyTransactionPreImages(t, client, tx, script, oceanCommitmentHash, i)
verifyTransactionPreImages(t, client, tx, oceanCommitmentHash, i)

// check fee value and bump
assert.Equal(t, client.Fees.minFee+(i-1)*client.Fees.feeIncrement, client.Fees.GetFee())
client.Fees.BumpFee()

// test signing and sending attestation
signedTx, signErr := client.signAttestation(tx, [][]crypto.Sig{}, lastHash)
assert.Equal(t, errors.New(ErrorSigsMissingForTx), signErr)
signedTx, signErr := client.signAttestation(tx, []wire.TxWitness{}, lastHash)
assert.Equal(t, nil, signErr)

txid, sendErr := client.sendAttestation(signedTx)
assert.Equal(t, true, sendErr != nil)

// client can't sign - we need to sign using clientSigner
signedTxSigner, signedScriptSigner, signErrSigner := clientSigner.SignTransaction(lastHash, *tx)
signedTxSigner, signErrSigner := clientSigner.SignTransaction(lastHash, *tx)
assert.Equal(t, nil, signErrSigner)
assert.Equal(t, true, len(signedTxSigner.TxIn[0].SignatureScript) > 0)
// extract sig
sigs, sigScript := crypto.ParseScriptSig(signedTxSigner.TxIn[0].SignatureScript)
assert.Equal(t, signedScriptSigner, hex.EncodeToString(sigScript))
assert.Equal(t, 1, len(sigs))
assert.Equal(t, false, len(signedTxSigner.TxIn[0].SignatureScript) > 0)
assert.Equal(t, true, len(signedTxSigner.TxIn[0].Witness) > 0)

sig := signedTxSigner.TxIn[0].Witness
// test signing and sending attestation again
signedTx, signErr = client.signAttestation(tx, [][]crypto.Sig{[]crypto.Sig{sigs[0]}}, lastHash)
signedTx, signErr = client.signAttestation(tx, []wire.TxWitness{}, lastHash)
// exceptional top-up case - need to include additional unspent + signatures
if i == topupLevel+1 {
// test error for not enough sigs
assert.Equal(t, errors.New(ErrorSigsMissingForTx), signErr)
sigsTopup, sigScriptTopup := crypto.ParseScriptSig(signedTxSigner.TxIn[1].SignatureScript)
assert.Equal(t, client.scriptTopup, hex.EncodeToString(sigScriptTopup))
assert.Equal(t, 1, len(sigsTopup))

// test error for not enough sigs
signedTx, signErr = client.signAttestation(tx,
[][]crypto.Sig{[]crypto.Sig{sigs[0]}, []crypto.Sig{}}, lastHash)
assert.Equal(t, errors.New(ErrorSigsMissingForVin), signErr)

signedTx, signErr = client.signAttestation(tx,
[][]crypto.Sig{[]crypto.Sig{sigs[0]}}, lastHash)
assert.Equal(t, errors.New(ErrorSigsMissingForTx), signErr)

signedTx, signErr = client.signAttestation(tx,
[][]crypto.Sig{}, lastHash)
assert.Equal(t, errors.New(ErrorSigsMissingForTx), signErr)

// actually sign attestation transaction
signedTx, signErr = client.signAttestation(tx,
[][]crypto.Sig{[]crypto.Sig{sigs[0]}, []crypto.Sig{sigsTopup[0]}}, lastHash)
assert.Equal(t, nil, signErr)
assert.Equal(t, true, len(signedTx.TxIn[1].SignatureScript) > 0)
sigTopup := signedTxSigner.TxIn[1].Witness
assert.Equal(t, true, len(sigTopup) > 0)

// adding more signatures than required has the same result
signedTx, signErr = client.signAttestation(tx,
[][]crypto.Sig{[]crypto.Sig{sigs[0], sigs[0]}, []crypto.Sig{sigsTopup[0], sigs[0], sigs[0]}}, lastHash)
// sign attestation transaction
signedTx, signErr = client.signAttestation(tx, []wire.TxWitness{sig, sigTopup}, lastHash)
assert.Equal(t, nil, signErr)
assert.Equal(t, true, len(signedTx.TxIn[1].SignatureScript) > 0)

assert.Equal(t, false, len(signedTx.TxIn[1].SignatureScript) > 0)
assert.Equal(t, true, len(signedTx.TxIn[1].Witness) > 0)
} else {
assert.Equal(t, nil, signErr)
}
assert.Equal(t, true, len(signedTx.TxIn[0].SignatureScript) > 0)
assert.Equal(t, false, len(signedTx.TxIn[0].SignatureScript) > 0)
assert.Equal(t, true, len(signedTx.TxIn[0].Witness) > 0)

txid, sendErr = client.sendAttestation(signedTx)
assert.Equal(t, nil, sendErr)
Expand Down Expand Up @@ -468,7 +413,7 @@ func TestAttestClient_FeeBumping(t *testing.T) {
oceanCommitmentHash := oceanCommitment.GetCommitmentHash()

// get address
addr, script := verifyKeysAndAddr(t, client, oceanCommitmentHash)
addr := verifyKeysAndAddr(t, client, oceanCommitmentHash)

// test creating attestation transaction
tx, attestationErr := client.createAttestation(addr, []btcjson.ListUnspentResult{unspent})
Expand All @@ -482,7 +427,7 @@ func TestAttestClient_FeeBumping(t *testing.T) {
currentFee := client.Fees.GetFee()

// test signing and sending attestation
signedTx, signErr := client.signAttestation(tx, [][]crypto.Sig{}, lastHash)
signedTx, signErr := client.signAttestation(tx, []wire.TxWitness{}, lastHash)
assert.Equal(t, nil, signErr)
txid, sendErr := client.sendAttestation(signedTx)
assert.Equal(t, nil, sendErr)
Expand Down Expand Up @@ -510,7 +455,7 @@ func TestAttestClient_FeeBumping(t *testing.T) {
assert.Equal(t, nil, attestationErr2)

// verify transaction pre-image generation
verifyTransactionPreImages(t, client, tx2, script, oceanCommitmentHash, i)
verifyTransactionPreImages(t, client, tx2, oceanCommitmentHash, i)

// test attestation transaction fee bumping
if i == topupLevel+1 {
Expand All @@ -536,15 +481,13 @@ func TestAttestClient_FeeBumping(t *testing.T) {

newFee := client.Fees.GetFee()
newValue := tx2.TxOut[0].Value
newTxFee := calcSignedTxFee(newFee, tx2.SerializeSize(),
len(client.script0)/2, client.numOfSigs, len(tx2.TxIn))
currentTxFee := calcSignedTxFee(currentFee, tx.SerializeSize(),
len(client.script0)/2, client.numOfSigs, len(tx.TxIn))
newTxFee := calcSignedTxFee(newFee)
currentTxFee := calcSignedTxFee(currentFee)
assert.Equal(t, newTxFee-currentTxFee, currentValue+topupValue-newValue)
assert.Equal(t, client.Fees.minFee+client.Fees.feeIncrement, newFee)

// test signing and sending attestation again
signedTx, signErr = client.signAttestation(tx2, [][]crypto.Sig{}, lastHash)
signedTx, signErr = client.signAttestation(tx2, []wire.TxWitness{}, lastHash)
assert.Equal(t, nil, signErr)
txid, sendErr = client.sendAttestation(signedTx)
assert.Equal(t, nil, sendErr)
Expand Down Expand Up @@ -578,27 +521,21 @@ func TestAttestClient_FeeBumping(t *testing.T) {

// Test fee calculation for an unsigned transaction
func TestAttestClient_feeCalculation(t *testing.T) {
unsignedTxSize := 83
feePerByte := 10

scriptSize := len(testpkg.Script) / 2
_, numOfSigs := crypto.ParseRedeemScript(testpkg.Script)
assert.Equal(t, 229, calcSignedTxSize(unsignedTxSize, scriptSize, numOfSigs, 1))
assert.Equal(t, int64(2290), calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize, numOfSigs, 1))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize, numOfSigs, 1))/calcSignedTxSize(unsignedTxSize, scriptSize, numOfSigs, 1))

assert.Equal(t, 375, calcSignedTxSize(unsignedTxSize, scriptSize, numOfSigs, 2))
assert.Equal(t, int64(3750), calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize, numOfSigs, 2))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize, numOfSigs, 2))/calcSignedTxSize(unsignedTxSize, scriptSize, numOfSigs, 2))

script2 := "52210325bf82856a8fdcc7a2c08a933343d2c6332c4c252974d6b09b6232ea4080462621028ed149d77203c79d7524048689a80cc98f27e3427f2edaec52eae1f630978e08210254a548b59741ba35bfb085744373a8e10b1cf96e71f53356d7d97f807258d38c53ae"
scriptSize2 := len(script2) / 2
_, numOfSigs2 := crypto.ParseRedeemScript(script2)
assert.Equal(t, 339, calcSignedTxSize(unsignedTxSize, scriptSize2, numOfSigs2, 1))
assert.Equal(t, int64(3390), calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize2, numOfSigs2, 1))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize2, numOfSigs2, 1))/calcSignedTxSize(unsignedTxSize, scriptSize2, numOfSigs2, 1))

assert.Equal(t, 851, calcSignedTxSize(unsignedTxSize, scriptSize2, numOfSigs2, 3))
assert.Equal(t, int64(8510), calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize2, numOfSigs2, 3))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte, unsignedTxSize, scriptSize2, numOfSigs2, 3))/calcSignedTxSize(unsignedTxSize, scriptSize2, numOfSigs2, 3))
assert.Equal(t, 110, signedTxSize)
assert.Equal(t, int64(1100), calcSignedTxFee(feePerByte))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte))/signedTxSize)

assert.Equal(t, 110, signedTxSize)
assert.Equal(t, int64(1100), calcSignedTxFee(feePerByte))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte))/signedTxSize)

assert.Equal(t, 110, signedTxSize)
assert.Equal(t, int64(1100), calcSignedTxFee(feePerByte))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte))/signedTxSize)

assert.Equal(t, 110, signedTxSize)
assert.Equal(t, int64(1100), calcSignedTxFee(feePerByte))
assert.Equal(t, 10, int(calcSignedTxFee(feePerByte))/signedTxSize)
}
Loading
Loading