Subgraph to track yearn vaults metrics on Mainnet.
- Copy
.envrc.example
to.envrc
. - Set
ACCESS_TOKEN
to your The Graph access token. - Set
GRAPH_PATH
to<github-username>/<subgraph-name>
. - Export
.envrc
variables.
yarn
– install dependenciesyarn codegen
– generate codeyarn create
– allocate subgraph name in Graph Nodeyarn deploy
- deploy supgraph to Graph Nodeyarn publish-graph
– run all steps in one command
See package.json
for local deployment.
The Vault
entity is the most relevant one on this subgraph, since it holds most of the data related to the scope of the Vault, like vault balance (how much of the base token the vault has), strategy balance (how much of that base token is invested in the strategy), aggregated data for deposits, withdrawals, earnings, links to other related entities such as the Controller and Strategy, and many more.
type Vault @entity {
id: ID!
"Amount of underlying token that a full share of <yToken> represents"
pricePerFullShare: BigDecimal!
pricePerFullShareRaw: BigInt!
totalSupply: BigDecimal!
totalSupplyRaw: BigInt!
"Balance of the Vault contract of underlying Token + balance of the Strategy contract of underlying Token"
vaultBalance: BigDecimal!
"Balance of underlying Token specifically held in the strategy"
strategyBalance: BigDecimal!
"How much the vault allows to be borrowed"
available: BigDecimal!
"Balance of the Vault contract of underlying Token + balance of the Strategy contract of underlying Token"
vaultBalanceRaw: BigInt!
"Balance of underlying Token specifically held in the strategy"
strategyBalanceRaw: BigInt!
"How much the vault allows to be borrowed"
availableRaw: BigInt!
"Token accepted as deposit on the Vault"
underlyingToken: Token!
"yToken minted as shares by the Vault"
shareToken: Token!
currentController: Controller!
currentStrategy: Strategy!
"Transaction metadata for the last update"
transaction: Transaction!
"totalDeposited - totalWithdrawn. Considers all deposits of underlying made by external accounts"
netDeposits: BigDecimal!
totalDeposited: BigDecimal!
totalWithdrawn: BigDecimal!
"totalSharesMinted - totalSharesBurned"
totalActiveShares: BigDecimal!
totalSharesMinted: BigDecimal!
totalSharesBurned: BigDecimal!
netDepositsRaw: BigInt!
totalDepositedRaw: BigInt!
totalWithdrawnRaw: BigInt!
totalActiveSharesRaw: BigInt!
totalSharesMintedRaw: BigInt!
totalSharesBurnedRaw: BigInt!
totalEarnings: BigDecimal!
totalEarningsRaw: BigInt!
totalHarvestCalls: BigInt!
transfers: [Transfer!]! @derivedFrom(field: "vault")
deposits: [Deposit!]! @derivedFrom(field: "vault")
withdrawals: [Withdrawal!]! @derivedFrom(field: "vault")
harvests: [Harvest!]! @derivedFrom(field: "vault")
balances: [AccountVaultBalance!]! @derivedFrom(field: "vault")
strategies: [Strategy!]! @derivedFrom(field: "vault")
controllers: [Controller!]! @derivedFrom(field: "vault")
}
The Acount
entity represents an ethereum address that interacted with the protocol (at least 1 Vault). This entity is only really there to centralize all the data for a specific user, such as all the user balances (one for each vault, more on that later), all the deposits, withdrawals and transfer that the account is related to.
type Account @entity {
"Ethereum address of the user"
id: ID!
vaultBalances: [AccountVaultBalance!]! @derivedFrom(field: "account")
"Deposits that are related to this account"
deposits: [Deposit!]! @derivedFrom(field: "account")
"Withdrawals that are related to this account"
withdrawals: [Deposit!]! @derivedFrom(field: "account")
"Transfers that are sent to this account"
receivedTransfers: [Transfer!]! @derivedFrom(field: "to")
"Transfers that are sent from this account"
sentTransfers: [Transfer!]! @derivedFrom(field: "from")
}
This entity represent the balance (or position) of an Account within a specific Vault (hence the name). It has a lot of aggregated values that are tracked by following the minting/burning of shares of the yToken, which allow for tracking of the underlying token movement as well as the share token movements (such as deposits, withdrawals and transfers), and aggregation of those values to know the total amount of each of the possible fields. We also provide some variables that depict internal "balances" of those aggregated values, like the netDeposits
field, which represents the balance of ingess and egress transfers ((deposits + transfersIN) - (withdrawals + transfersOUT)).
This entity does not have a real-time balance of the underlying token (with earnings included) like the Vault
entity has, given that it's only able to be updated when ERC20 share token Transfer events occur for the specified account, and cannot be updated when earnings are calculated (Harvest), thus making it impossible to have a real-time earnings value pre-calculated. It is possible to calculate it with the values provided when you query this entity, given that it has the linked Vault
entity which has the real-time pricePerFullShare
value, and the AccountVaultBalance
does keep track of the real-time shareBalance
, and with those values you can calculate the updated underlying token balance for this specific Account
.
type AccountVaultBalance @entity {
id: ID!
vault: Vault!
account: Account!
"Token used on deposits/withdrawals"
underlyingToken: Token!
"Token received as shares"
shareToken: Token!
"Net deposits of a given Account within a given Vault. Transfers between accounts are taken into consideration for this metric"
netDeposits: BigDecimal!
"Total tokens deposited by this Account in Vault"
totalDeposited: BigDecimal!
"Total tokens withdrawn by this Account in Vault"
totalWithdrawn: BigDecimal!
"Total tokens sent to another account by this Account in Vault"
totalSent: BigDecimal!
"Total tokens received from another account by this Account in Vault"
totalReceived: BigDecimal!
"Shares are the token minted by the Vault"
shareBalance: BigDecimal!
totalSharesMinted: BigDecimal!
totalSharesBurned: BigDecimal!
totalSharesSent: BigDecimal!
totalSharesReceived: BigDecimal!
"Net deposits of a given Account within a given Vault. Transfers between accounts are taken into consideration for this metric"
netDepositsRaw: BigInt!
"Total tokens deposited by this Account in Vault"
totalDepositedRaw: BigInt!
"Total tokens withdrawn by this Account in Vault"
totalWithdrawnRaw: BigInt!
"Total tokens sent to another account by this Account in Vault"
totalSentRaw: BigInt!
"Total tokens received from another account by this Account in Vault"
totalReceivedRaw: BigInt!
"Shares are the token minted by the Vault"
shareBalanceRaw: BigInt!
totalSharesMintedRaw: BigInt!
totalSharesBurnedRaw: BigInt!
totalSharesSentRaw: BigInt!
totalSharesReceivedRaw: BigInt!
}
This entity holds information regarding ERC20 tokens present in the subgraph.
type Token @entity {
id: ID!
address: Bytes!
decimals: Int!
name: String!
symbol: String!
}
These entities hold the specific raw data that was processed to update the other entities to their latest state when an ERC20 Transfer from the yVault triggered (depending on the type of transfer it creates one of the 3 entities). They also track the metadata for the block that triggered it (block number, transaction hash and timestamp) and are linked to the corresponding entities that they modified. (Vault, AccountVaultBalance, etc).
This entity, much like the Transfer
, Deposit
and Withdraw
entity, tracks data that was used to update the state of other entities as well as metadata for the block that triggered it, whenever a harvest call is made to the strategy of a yVault.
This entity also aggregates some data, and calculate earnings gained for the yVault when it was called, which are then aggregated to the total it holds as well as the strategy total. It also track balance changes before and after the harvest() call, and pricePerFullShare
changes too.
type Harvest @entity {
id: ID!
vault: Vault!
strategy: Strategy!
caller: Bytes!
pricePerFullShareBefore: BigDecimal!
pricePerFullShareAfter: BigDecimal!
pricePerFullShareBeforeRaw: BigInt!
pricePerFullShareAfterRaw: BigInt!
vaultBalanceBefore: BigDecimal!
vaultBalanceAfter: BigDecimal!
strategyBalanceBefore: BigDecimal!
strategyBalanceAfter: BigDecimal!
vaultBalanceBeforeRaw: BigInt!
vaultBalanceAfterRaw: BigInt!
strategyBalanceBeforeRaw: BigInt!
strategyBalanceAfterRaw: BigInt!
earnings: BigDecimal!
earningsRaw: BigInt!
transaction: Transaction!
}
These two entities hold barely any information for each of the smart contracts that they represent (Strategy and Controller), but allow us to keep tabs of all the historical controllers and strategies that a yVault might have overtime by deriving a list of all that have a link to the yVault.
The Strategy
entity also keeps track of all the Harvest
entities it has created, as well as the earnings made for the Vault when it was active.
type Strategy @entity {
"Ethereum address"
id: ID!
vault: Vault!
totalEarnings: BigDecimal!
totalEarningsRaw: BigInt!
harvests: [Harvest!]! @derivedFrom(field: "strategy")
activeOnVaults: [Vault!] @derivedFrom(field: "currentStrategy")
}
type Controller @entity {
"Ethereum address"
id: ID!
vault: Vault!
activeOnVaults: [Vault!] @derivedFrom(field: "currentController")
}
This entity tracks metadata for specific transactions, as well as some derived data for all the deposits, withdrawals, transfers, harvests performed on it, as well as tracking a list of all the vaults that were last updated on that transaction.
type Transaction @entity {
"ID = Transaction Hash"
id: ID!
timestamp: BigInt!
blockNumber: BigInt!
"Duplicated field to allow for byte search with transactionHash_contains"
transactionHash: Bytes!
deposits: [Deposit!]! @derivedFrom(field: "transaction")
withdrawals: [Withdrawal!]! @derivedFrom(field: "transaction")
transfers: [Transfer!]! @derivedFrom(field: "transaction")
harvests: [Harvest!]! @derivedFrom(field: "transaction")
"List of Vaults that last updated on this transaction"
vaultsUpdated: [Vault!]! @derivedFrom(field: "transaction")
}