LimeChain / matchstick

🔥 Unit testing framework for Subgraph development on The Graph protocol. ⚙️
MIT License
207 stars 17 forks source link

@graphprotocol/graph-ts types are not assignable to matchstick-as types #380

Closed scherroman closed 1 year ago

scherroman commented 1 year ago

I'm trying to write some tests with assertions like addressEquals and bigIntEquals because the fieldEquals assertion seems unnecessarily verbose and repetitive. However, when using these assertions compilation fails with type errors like Address is not assignable to Address and BigInt is not assignable to BigInt:

ERROR TS2322: Type '~lib/@graphprotocol/graph-ts/common/numbers/Address' is not assignable to type '~lib/matchstick-as/node_modules/@graphprotocol/graph-ts/common/numbers/Address'.

                 Address.fromBytes(nftListedEvent.nftAddress),

ERROR TS2322: Type '~lib/@graphprotocol/graph-ts/common/numbers/BigInt' is not assignable to type '~lib/matchstick-as/node_modules/@graphprotocol/graph-ts/common/numbers/BigInt'.

             assert.bigIntEquals(nftListedEvent.nftId, listing.nft.id)

I would expect the types used in the latest version of the matchstick-as package to match the types used in the latest version of the @graphprotocol/graph-ts where I import Address and BigInt from, but it seems this is not the case currently. I'm using the latest versions of @graphprotocol/graph-cli@0.36.1, @graphprotocol/graph-ts@0.29.0, and matchstick-as@0.5.0. It does look like there's a 0.5.4 version of matchstick tagged on github, but that hasn't been published to npm.

Code for reference:

import { describe, test, assert, afterAll, clearStore } from 'matchstick-as'
import { Address, BigInt } from '@graphprotocol/graph-ts'
import { NftListedEvent } from '../generated/schema'
import {
    handleNftListed,
    getEventId
} from '../src/nifty'
import { createNftListedEvent } from './nifty-utils'

// No object literals or destructuring in AssemblyScript is rough >.<

class Nft {
    address: Address
    id: BigInt

    constructor(address: Address, id: BigInt) {
        this.address = address
        this.id = id
    }
}

class Listing {
    nft: Nft
    price: BigInt
    seller: Address

    constructor(nft: Nft, price: BigInt, seller: Address) {
        this.nft = nft
        this.price = price
        this.seller = seller
    }
}

let listing = new Listing(
    new Nft(
        Address.fromString('0x0000000000000000000000000000000000000001'),
        BigInt.fromI32(0)
    ),
    BigInt.fromI32(100),
    Address.fromString('0x0000000000000000000000000000000000000002')
)

describe('Events', () => {
    afterAll(() => {
        clearStore()
    })

    describe('NftListed', () => {
        test('stores an NftListedEvent entity', () => {
            let event = createNftListedEvent(
                listing.nft.address,
                listing.nft.id,
                listing.price,
                listing.seller
            )
            handleNftListed(event)

            let nftListedEvent = NftListedEvent.load(getEventId(event))

            if (nftListedEvent == null) {
                throw new Error('NftListedEvent not found')
            }

            assert.entityCount('NftListedEvent', 1)
            assert.addressEquals(
                Address.fromBytes(nftListedEvent.nftAddress),
                listing.nft.address
            )
            assert.bigIntEquals(nftListedEvent.nftId, listing.nft.id)
            assert.bigIntEquals(nftListedEvent.price, listing.price)
            assert.addressEquals(
                Address.fromBytes(nftListedEvent.seller),
                listing.seller
            )
        })
    })
})
dimitrovmaksim commented 1 year ago

Does the compilation fail, or is it IDE errors?

matchstick-as is a helper library and it has separate releases, it's latest version is 0.5.0.

scherroman commented 1 year ago

There are no errors in the IDE, just the AssemblyScript compilation fails when running graph test. I tried importing the types from matchstick-as' own installed version of @graphprotocol/graph-ts from its node_modules, but then types tied to the top level @graphprotocol/graph-ts still encounter type errors during compilation, like using the autogenerated createNftListedEvent function, and when using properties from entities loaded from the store like NftListedEvent.load(...) in assertions.

import {
    Address,
    BigInt
} from 'matchstick-as/node_modules/@graphprotocol/graph-ts'

...
💬 Compiling nifty...
ERROR TS2322: Type '~lib/matchstick-as/node_modules/@graphprotocol/graph-ts/common/numbers/Address' is not assignable to type '~lib/@graphprotocol/graph-ts/common/numbers/Address'.

                 listing.nft.address,
                 ~~~~~~~~~~~~~~~~~~~

ERROR TS2322: Type '~lib/@graphprotocol/graph-ts/common/collections/Bytes' is not assignable to type '~lib/matchstick-as/node_modules/@graphprotocol/graph-ts/common/collections/Bytes'.

                 Address.fromBytes(nftListedEvent.nftAddress),
                                   ~~~~~~~~~~~~~~~~~~~~~~~~~

It appears the only ways around this currently are to either 1. forget the other assertions and just use fieldEquals or 2. to install the specific version of @graphprotocol/graph-ts that the latest version of matchstick-as uses, which I found from digging in the node_modules for matchstick-as@0.5.0 is @graphprotocol/graph-ts@0.27.0. Tried and can confirm the tests work with option 2, but this is currently undocumented and seems backwards, as tests are usually written after installing the the graph-cli, initializing a new subgraph, and autogenerating code from your schema. Worried things might break elsewhere if I were to downgrade the @graphprotocol/graph-ts package after all that.

dimitrovmaksim commented 1 year ago

This is weird, is the repo public?

scherroman commented 1 year ago

It's pretty much wrapped up so I've gone ahead and published it here: https://github.com/scherroman/nifty

To build the subgraph, you'd run:

npm run build:subgraph:staging

And to run the subgraph tests, you'd run:

npm run test:subgraph:unit

You could also go down into the subgraph directory to run the commands directly:

cd subgraph

Note that I switched to using fieldEquals to get around the issue, so you won't see any errors when running the subgraph tests unless you copy and paste the code from the opening comment

dimitrovmaksim commented 1 year ago

I cloned the repo and did all the steps and it compiles and runs fine for me:

[10:09:50] maksimdimitrov:nifty git:(main*) $ npm run build:subgraph:staging

> build:subgraph:staging
> cd subgraph && npm run build:staging

> build:staging
> npm run codegen && graph build --network goerli

> codegen
> graph codegen

  Skip migration: Bump mapping apiVersion from 0.0.1 to 0.0.2
  Skip migration: Bump mapping apiVersion from 0.0.2 to 0.0.3
  Skip migration: Bump mapping apiVersion from 0.0.3 to 0.0.4
  Skip migration: Bump mapping apiVersion from 0.0.4 to 0.0.5
  Skip migration: Bump mapping apiVersion from 0.0.5 to 0.0.6
  Skip migration: Bump manifest specVersion from 0.0.1 to 0.0.2
  Skip migration: Bump manifest specVersion from 0.0.2 to 0.0.4
✔ Apply migrations
✔ Load subgraph from subgraph.yaml
  Load contract ABI from abis/Nifty.json
✔ Load contract ABIs
  Generate types for contract ABI: Nifty (abis/Nifty.json)
  Write types to generated/Nifty/Nifty.ts
✔ Generate types for contract ABIs
✔ Generate types for data source templates
✔ Load data source template ABIs
✔ Generate types for data source template ABIs
✔ Load GraphQL schema from schema.graphql
  Write types to generated/schema.ts
✔ Generate types for GraphQL schema

Types generated successfully

  Reading networks config
  Skip 'Nifty': No changes to network configuration
✔ Update sources network
  Skip migration: Bump mapping apiVersion from 0.0.1 to 0.0.2
  Skip migration: Bump mapping apiVersion from 0.0.2 to 0.0.3
  Skip migration: Bump mapping apiVersion from 0.0.3 to 0.0.4
  Skip migration: Bump mapping apiVersion from 0.0.4 to 0.0.5
  Skip migration: Bump mapping apiVersion from 0.0.5 to 0.0.6
  Skip migration: Bump manifest specVersion from 0.0.1 to 0.0.2
  Skip migration: Bump manifest specVersion from 0.0.2 to 0.0.4
✔ Apply migrations
✔ Load subgraph from subgraph.yaml
  Compile data source: Nifty => build/Nifty/Nifty.wasm
✔ Compile subgraph
  Copy schema file build/schema.graphql
  Write subgraph file build/Nifty/abis/Nifty.json
  Write subgraph manifest build/subgraph.yaml
✔ Write compiled subgraph to build/

Build completed: /Users/maksimdimitrov/Projects/nifty/subgraph/build/subgraph.yaml

[10:12:05] maksimdimitrov:nifty git:(main*) $ npm run test:subgraph:unit

> test:subgraph:unit
> cd subgraph && npm run test

> test
> graph test

Skipping download/install step because binary already exists at /Users/maksimdimitrov/Projects/nifty/subgraph/node_modules/binary-install-raw/bin/0.5.4

___  ___      _       _         _   _      _
|  \/  |     | |     | |       | | (_)    | |
| .  . | __ _| |_ ___| |__  ___| |_ _  ___| | __
| |\/| |/ _` | __/ __| '_ \/ __| __| |/ __| |/ /
| |  | | (_| | || (__| | | \__ \ |_| | (__|   <
\_|  |_/\__,_|\__\___|_| |_|___/\__|_|\___|_|\_\

Compiling...

💬 Compiling nifty...

Igniting tests 🔥

nifty
--------------------------------------------------
  Events:
    NftListed:
      √ stores an NftListedEvent entity - 0.433ms

All 1 tests passed! 😎

[Thu, 24 Nov 2022 10:12:20 +0200] Program executed in: 6.941s.

I think there was an issue like this before, I will have to ask the team what the work around was

scherroman commented 1 year ago

What the...I was thinking this might be an OS-related issue (I'm running macOS Monterey v12.6.1), but in any case I just retried the tests and it's now working. Despite not having changed any package versions...I wonder if it had anything to do with the version of the binary that gets installed under binary-install-raw/bin? Currently it has binary-install-raw/bin/0.5.4 installed. Though it shows it was installed/last modified on Nov 22nd before I opened this issue, so don't think it changed either.

Skipping download/install step because binary already exists at /Users/romanscher/Documents/code/crypto/ethereum/nifty/subgraph/node_modules/binary-install-raw/bin/0.5.4

___  ___      _       _         _   _      _
|  \/  |     | |     | |       | | (_)    | |
| .  . | __ _| |_ ___| |__  ___| |_ _  ___| | __
| |\/| |/ _` | __/ __| '_ \/ __| __| |/ __| |/ /
| |  | | (_| | || (__| | | \__ \ |_| | (__|   <
\_|  |_/\__,_|\__\___|_| |_|___/\__|_|\___|_|\_\

Compiling...

💬 Compiling nifty...

Igniting tests 🔥

nifty
--------------------------------------------------
  Events:
    NftListed:
      √ stores an NftListedEvent entity - 0.356ms

All 1 tests passed! 😎

[Fri, 25 Nov 2022 10:16:12 -0500] Program executed in: 5.785s.

It does look like as I was making some final touches to publish the repo on the 23rd however, there were for some reason a few changes to the subgraph/package-lock.json on commit https://github.com/scherroman/nifty/commit/fc7bb73 concerning the binaryen/long/assemblyscript modules under the matchstick-as module, which may be related:

Screen Shot 2022-11-25 at 10 48 09 AM Screen Shot 2022-11-25 at 10 50 19 AM
dimitrovmaksim commented 1 year ago

It will still probably be good to update the graph-ts version in matchstick-as and release an updated version.

rafinskipg commented 1 year ago

I'm having similar issues with ethereum.Values from thegraph and matchstick. It does not compile.

dimitrovmaksim commented 1 year ago

Can you try setting matchstick-as in your package.json as "matchstick-as": "https://github.com/LimeChain/matchstick-as#update-graph-ts" and see if it compiles

gershido commented 1 year ago

I had the problem with the ethereum.Values types mismatch. Downgrading @graphprotocol/graph-ts to 0.27.0 solved it for me

dimitrovmaksim commented 1 year ago

Released matchstick-as 0.5.1, please try it and see if it fixes the issue