Last Updated: 2019-04-30

The subgraph definition

it consists of a few files:

  1. subgraph.yaml: a YAML file containing the subgraph manifest
  1. schema.graphql: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL
  1. AssemblyScript Mappings: AssemblyScript code that translates from the event data to the entities defined in your schema (e.g. mapping.ts in this tutorial)

Before you go into detail about the contents of the manifest file, you need to install the Graph CLI which you will need to build and deploy a subgraph.

And a subgraph can be deployed on :

The Graph CLI is written in JavaScript, and you will need to install either yarn or npm to use it; it is assumed that you have yarn in what follows.

Once you have yarn, install the Graph CLI by running

Install with yarn:

yarn global add @graphprotocol/graph-cli

Install with npm:

npm install -g @graphprotocol/graph-cli

The following command creates a subgraph that indexes all events of an existing contract. It attempts to fetch the contract ABI from Etherscan and falls back to requesting a local file path. If any of the optional arguments are missing, it takes you through an interactive form.

graph init \

--product subgraph-studio

--from-contract <CONTRACT_ADDRESS> \

[--network <ETHEREUM_NETWORK>] \

[--abi <FILE>] \

<SUBGRAPH_SLUG> [<DIRECTORY>]

The <SUBGRAPH_SLUG> is the ID of your subgraph in Subgraph Studio, it can be found on your subgraph details page.

cd <SUBGRAPH_SLUG>

yarn codegen

Multiple files are created

The subgraph manifest subgraph.yaml defines the smart contracts your subgraph indexes, which events from these contracts to pay attention to, and how to map event data to entities that Graph Node stores and allows to query. The full specification for subgraph manifests can be found here.

subgraph.yaml

specVersion: 0.0.4
description: Gravatar for Ethereum
repository: https://github.com/graphprotocol/example-subgraphs
schema:
 file: ./schema.graphql
dataSources:
 - kind: ethereum/contract
   name: Gravity
   network: mainnet
   source:
     address: '0x2E645469f354BB4F5c8a05B3b30A929361cf77eC'
     abi: Gravity
     startBlock: 6175244
   mapping:
     kind: ethereum/events
     apiVersion: 0.0.6
     language: wasm/assemblyscript
     entities:
       - Gravatar
     abis:
       - name: Gravity
         file: ./abis/Gravity.json
     eventHandlers:
       - event: NewGravatar(uint256,address,string,string)
         handler: handleNewGravatar
       - event: UpdatedGravatar(uint256,address,string,string)
         handler: handleUpdatedGravatar
     callHandlers:
       - function: createGravatar(string,string)
         handler: handleCreateGravatar
     blockHandlers:
       - handler: handleBlock
       - handler: handleBlockWithCall
         filter:
           kind: call
     file: ./src/mapping.ts

Schema.graphql

type Gravatar @entity(immutable: true) {
 id: Bytes!
 owner: Bytes
 displayName: String
 imageUrl: String
 accepted: Boolean
}

The mappings transform the Ethereum data your mappings are sourcing into entities defined in your schema. Mappings are written in a subset of TypeScript called AssemblyScript which can be compiled to WASM (WebAssembly). AssemblyScript is stricter than normal TypeScript, yet provides a familiar syntax.

src/mapping.ts

import { NewGravatar, UpdatedGravatar } from '../generated/Gravity/Gravity'
import { Gravatar } from '../generated/schema'


export function handleNewGravatar(event: NewGravatar): void {
 let gravatar = new Gravatar(event.params.id)
 gravatar.owner = event.params.owner
 gravatar.displayName = event.params.displayName
 gravatar.imageUrl = event.params.imageUrl
 gravatar.save()
}


export function handleUpdatedGravatar(event: UpdatedGravatar): void {
 let id = event.params.id
 let gravatar = Gravatar.load(id)
 if (gravatar == null) {
   gravatar = new Gravatar(id)
 }
 gravatar.owner = event.params.owner
 gravatar.displayName = event.params.displayName
 gravatar.imageUrl = event.params.imageUrl
 gravatar.save()
}

You've made it this far - congrats! Publishing your subgraph means that an IPFS hash was generated when you deployed the subgraph within the CLI and is stored in the network's Ethereum smart contracts.