bitauth / chaingraph

A multi-node blockchain indexer and GraphQL API
https://chaingraph.cash/
MIT License
52 stars 15 forks source link

Query failing with "negative substring length not allowed" #55

Open A60AB5450353F40E opened 1 year ago

A60AB5450353F40E commented 1 year ago

If limit: 1 then it fails, if some greater number then it executes OK. In this example even limit: 2 executes OK.

# Matches all spends from AnyHedge v0.11 contract template
# https://gitlab.com/GeneralProtocols/anyhedge/contracts/-/blob/development/contracts/v0.11/bytecode.asm
query {
  input(
    limit: 1
    offset: 0
    where: {
      transaction: {
        block_inclusions: {
          block: {
            height: { _gte: 780000, _lt: 780100 }
            accepted_by: { node: { name: { _eq: "bchn-mainnet" } } }
          }
        }
      }
      _or: [
        { unlocking_bytecode_pattern: { _eq: "40104010514d" } }
        { unlocking_bytecode_pattern: { _eq: "4141004d" } }
      ]
      redeem_bytecode_pattern: {
        _regex: "04040[2-4]0[2-4]0[2-8]0[2-8]21(17|19|23)(17|19|23)(00|51)21215c79009c637b695c7a7cad5b7a7cad6d6d6d6d6d51675c7a519dc3519d5f7a5f795779bb5d7a5d79577abb5c79587f77547f75817600a0695c79587f77547f75818c9d5c7a547f75815b799f695b795c7f77817600a0695979a35879a45c7a547f7581765c7aa2695b7aa2785a7a8b5b7aa5919b690276587a537a96a47c577a527994a4c4529d00cc7b9d00cd557a8851cc9d51cd547a8777777768"
      }
    }
  ) {
    transaction {
      block_inclusions {
        block {
          height
          timestamp
        }
      }
      inputs {
        outpoint_transaction_hash
        outpoint_index
        outpoint {
          value_satoshis
          transaction {
            block_inclusions {
              block {
                height
                timestamp
              }
            }
          }
        }
      }
    }
  }
}
bitjson commented 1 year ago

Thanks for opening an issue! On the demo instance, that returns:

{
  "errors": [
    {
      "extensions": {
        "code": "data-exception",
        "path": "$"
      },
      "message": "negative substring length not allowed"
    }
  ]
}

That's an error coming back from Postgres. To figure it out, we'd need to run the query in the Hasura console and use the analyze button to get the actual Postgres query being run, then figure out where the error is actually happening.

I'd guess it's because you're filtering by redeem_bytecode_pattern, which is itself a computed property. So if the other conditions take your limit 1 query down to 0, it's running that function on nothing, and somewhere inside there it "works" until a substring function is called with a negative integer.

I'd guess redeem_bytecode_pattern just needs to return early before doing the invalid operation. I can't prioritize figuring this out myself, but I'd be happy to take a PR!

A60AB5450353F40E commented 1 year ago

Thing is, other conditions don't limit it to 0. For example if you change to limit: 2 then it returns a proper result. If you change the block height range to something that hasn't been mined yet, then you get a proper empty array as result, with both limit: 1 and limit: 2.

A60AB5450353F40E commented 1 year ago

Also, this one which selects only 1 block trips with the same error. Change _gte and _lt heights +1 and it returns empty array proper. Commenting out the redeem_bytecode_pattern makes it return empty array, so I suspect some bug there.

# Matches all spends from AnyHedge v0.11 contract template
# https://gitlab.com/GeneralProtocols/anyhedge/contracts/-/blob/development/contracts/v0.11/bytecode.asm
query {
  input(
    #limit: 10
    #offset: 0
    where: {
      transaction: {
        block_inclusions: {
          block: {
            height: { _gte: 781888, _lt: 781889 }
            accepted_by: { node: { name: { _eq: "bchn-mainnet" } } }
          }
        }
      }
      _or: [
        { unlocking_bytecode_pattern: { _eq: "40104010514d" } }
        { unlocking_bytecode_pattern: { _eq: "4141004d" } }
      ]
      redeem_bytecode_pattern: {
        _regex: "04040[2-4]0[2-4]0[2-8]0[2-8]21(17|19|23)(17|19|23)(00|51)21215c79009c637b695c7a7cad5b7a7cad6d6d6d6d6d51675c7a519dc3519d5f7a5f795779bb5d7a5d79577abb5c79587f77547f75817600a0695c79587f77547f75818c9d5c7a547f75815b799f695b795c7f77817600a0695979a35879a45c7a547f7581765c7aa2695b7aa2785a7a8b5b7aa5919b690276587a537a96a47c577a527994a4c4529d00cc7b9d00cd557a8851cc9d51cd547a8777777768"
      }
    }
  ) {
    transaction {
      block_inclusions {
        block {
          height
          timestamp
        }
      }
      inputs {
        outpoint_transaction_hash
        outpoint_index
        outpoint {
          value_satoshis
          locking_bytecode
          locking_bytecode_pattern
          transaction {
            block_inclusions {
              block {
                height
                timestamp
              }
            }
          }
        }
        unlocking_bytecode
        unlocking_bytecode_pattern
        redeem_bytecode_pattern
      }
    }
  }
}
A60AB5450353F40E commented 1 year ago

Replacing regex with like fails on some blocks, too:

Query

# Matches all spends from AnyHedge v0.11 contract template
# https://gitlab.com/GeneralProtocols/anyhedge/contracts/-/blob/development/contracts/v0.11/bytecode.asm
query {
  input(
    #limit: 0
    #offset: 0
    where: {
      transaction: {
        block_inclusions: {
          block: {
            height: { _gte: 785576, _lt: 785577 }
            accepted_by: { node: { name: { _like: "%mainnet" } } }
          }
        }
      }
      _or: [
        { unlocking_bytecode_pattern: { _eq: "40104010514d" } }
        { unlocking_bytecode_pattern: { _eq: "4141004d" } }
      ]
      redeem_bytecode_pattern: {
        #_regex: "04040[2-4]0[2-4]0[2-8]0[2-8]21(17|19|23)(17|19|23)(00|51)21215c79009c637b695c7a7cad5b7a7cad6d6d6d6d6d51675c7a519dc3519d5f7a5f795779bb5d7a5d79577abb5c79587f77547f75817600a0695c79587f77547f75818c9d5c7a547f75815b799f695b795c7f77817600a0695979a35879a45c7a547f7581765c7aa2695b7aa2785a7a8b5b7aa5919b690276587a537a96a47c577a527994a4c4529d00cc7b9d00cd557a8851cc9d51cd547a8777777768"
        _like: "%21215c79009c637b695c7a7cad5b7a7cad6d6d6d6d6d51675c7a519dc3519d5f7a5f795779bb5d7a5d79577abb5c79587f77547f75817600a0695c79587f77547f75818c9d5c7a547f75815b799f695b795c7f77817600a0695979a35879a45c7a547f7581765c7aa2695b7aa2785a7a8b5b7aa5919b690276587a537a96a47c577a527994a4c4529d00cc7b9d00cd557a8851cc9d51cd547a8777777768"
      }
    }
  ) {
    transaction {
      block_inclusions {
        block {
          height
          timestamp
        }
      }
      inputs {
        outpoint_transaction_hash
        outpoint_index
        outpoint {
          value_satoshis
          locking_bytecode
          locking_bytecode_pattern
          transaction {
            block_inclusions {
              block {
                height
                timestamp
              }
            }
          }
        }
        unlocking_bytecode
        unlocking_bytecode_pattern
        redeem_bytecode_pattern
      }
    }
  }
}

Result

{
  "errors": [
    {
      "extensions": {
        "code": "data-exception",
        "path": "$"
      },
      "message": "negative substring length not allowed"
    }
  ]
}