signature verification failed; please verify account number and chain-id: unauthorized

1.4k Views Asked by At

You don't want to know how many hours I've spent trying to figure this one out.

I'm trying to send a broadcast to the Cosmos Blockchain, via the Terra Pisco/Rebel1 Api.

LUNA2: https://pisco-lcd.terra.dev/swagger/#/

LUNC: https://rebel1.grouptwo.org/swagger/#/

When I run the simulation Api, the transaction works perfectly. However when I run a transaction just via the standard api, it fails with a "signature verification failed" error. This issue is related to the signature being passed to Cosmos not containing the correct Chain-Id or Sequence Number. However I've confirmed that the base64 has it. And all the payloads being sent are correct (Protobuf & Rest JSON), according to the Cosmos SDK support team.

I have generated an issue in the cosmos-sdk repo below (it contains all the details, models, dtos, protos, I pass cosmos): https://github.com/cosmos/cosmos-sdk/issues/14789

  1. I've verified the Protobuf data according to terra-money's terra.js library https://github.com/terra-money/terra.js. And the data looks correct.

  2. I've also confirmed that the signature contains the correct Chain-Id & Sequence number.

This issue is related to the C# SDK that I'm currently building. It allows users to broadcast Tx data to Terra (Cosmos). Here's the link, if you want to generate a PR:

https://github.com/TerraMystics/terra-sharp

1

There are 1 best solutions below

0
Daniel Harapko On

Based on the description of your issue, it seems that the problem is related to incorrect data preparation for transaction signing. Here are a few steps to ensure that all necessary data is correctly passed for signing:

  1. Preliminary Check: Ensure that when you sign the transaction, you are passing the same amount of bytes as when using other working methods. This will help to eliminate possible errors in data preparation.
  2. Passing All Necessary Data: Make sure that SignerData contains all the required fields(not all required):

    SignerData{
        ChainID:       networkId,
        AccountNumber: accountNumber,
        Sequence:      sequence,
        PubKey:        pubKey,
        Address:       sdk.AccAddress(pubKey.Address()).String(),
        Address:       addressBech32,
    }

  1. Besides SignerData, it's also important to pass SignatureV2 with the correct SignMode and Sequence. Example:

    sigData := signing.SingleSignatureData{
        SignMode:  signMode,
        Signature: nil,
    }
    sig := signing.SignatureV2{
        PubKey:   pubKey,
        Data:     &sigData,
        Sequence: sequence,
    }
    sigs := []signing.SignatureV2{sig}
    txBuilder.SetSignatures(sigs...)

  1. Signing Data: Consider the signing process in the Sign method at github.com/cosmos/cosmos-sdk/client/tx. This will give you an insight into the requirements for the data to be signed and its preparation. https://github.com/cosmos/cosmos-sdk/blob/7628592c6a1fbefdff0afa71e89f08b147a02977/client/tx/tx.go#L251-L361

Note that in the mentioned method, some data is also prepared before signing, which you can see. The actual signing is done at the end of the method using keybase.Sign, where keybase is the keyring.