Skip to content
This repository was archived by the owner on Oct 15, 2024. It is now read-only.

feat: migrate to b-sdk 0.26.0 #1107

Merged
merged 6 commits into from
Sep 19, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion lib/debug-helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ export const vaultV3Address = sepoliaNetworkConfig.contracts.balancer.vaultV3 as

export const poolId = '0x68e3266c9c8bbd44ad9dca5afbfe629022aee9fe000200000000000000000512' as const // Balancer Weighted wjAura and WETH

export const sepoliaRouter = '0x1c58cc548a23956469c7C528Bb3a846c842dfaF9'
export const sepoliaRouter = '0xB12FcB422aAe6720f882E22C340964a7723f2387'

/*
Used to pretty print objects when debugging
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,13 @@ import { aWjAuraWethPoolElementMock } from '@/test/msw/builders/gqlPoolElement.b
import { UnbalancedAddLiquidityHandler } from './UnbalancedAddLiquidity.handler'
import { selectAddLiquidityHandler } from './selectAddLiquidityHandler'
import { HumanTokenAmountWithAddress } from '@/lib/modules/tokens/token.types'
import { Pool } from '../../../PoolProvider'

function selectUnbalancedHandler() {
return selectAddLiquidityHandler(aWjAuraWethPoolElementMock()) as UnbalancedAddLiquidityHandler
}

describe('When adding unbalanced liquidity for a weighted pool', () => {
describe('When adding unbalanced liquidity for a weighted V2 pool', () => {
test('calculates price impact', async () => {
const handler = selectUnbalancedHandler()

Expand Down Expand Up @@ -72,3 +73,45 @@ describe('When adding unbalanced liquidity for a weighted pool', () => {
expect(result.data).toBeDefined()
})
})

// TODO: unskip this test when sepolia V3 pools are available in production api
describe.skip('When adding unbalanced liquidity for a V3 pool', async () => {
// Sepolia
const balAddress = '0xb19382073c7a0addbb56ac6af1808fa49e377b75'
// const poolId = '0xec1b5ca86c83c7a85392063399e7d2170d502e00' // Sepolia B-50BAL-50WETH
// const v3Pool = await getPoolMock(poolId, GqlChain.Sepolia)
const v3Pool = {} as unknown as Pool

const handler = selectAddLiquidityHandler(v3Pool) as UnbalancedAddLiquidityHandler

const humanAmountsIn: HumanTokenAmountWithAddress[] = [
{ humanAmount: '0.1', tokenAddress: balAddress },
]

it('calculates price impact', async () => {
const priceImpact = await handler.getPriceImpact(humanAmountsIn)
expect(priceImpact).toBeGreaterThan(0.002)
})

it('queries bptOut', async () => {
const result = await handler.simulate(humanAmountsIn)

expect(result.bptOut.amount).toBeGreaterThan(100000000000000n)
})

it('builds Tx Config', async () => {
// Store query response in handler instance
const queryOutput = await handler.simulate(humanAmountsIn)

const result = await handler.buildCallData({
humanAmountsIn,
account: defaultTestUserAccount,
slippagePercent: '0.2',
queryOutput,
})

const sepoliaRouter = '0xB12FcB422aAe6720f882E22C340964a7723f2387'
expect(result.to).toBe(sepoliaRouter)
expect(result.data).toBeDefined()
})
})
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import networkConfig from '@/lib/config/networks/mainnet'
import { balAddress, wETHAddress } from '@/lib/debug-helpers'
import { balAddress, sepoliaRouter, wETHAddress } from '@/lib/debug-helpers'
import {
aBalWethPoolElementMock,
aPhantomStablePoolMock,
Expand All @@ -11,6 +11,8 @@ import { selectRemoveLiquidityHandler } from './selectRemoveLiquidityHandler'
import { ProportionalRemoveLiquidityHandler } from './ProportionalRemoveLiquidity.handler'
import { emptyAddress } from '@/lib/modules/web3/contracts/wagmi-helpers'
import { connectWithDefaultUser } from '@/test/utils/wagmi/wagmi-connections'
// import { GqlChain } from '@/lib/shared/services/api/generated/graphql'
// import { getPoolMock } from '../../../__mocks__/getPoolMock'

const poolMock = aBalWethPoolElementMock() // 80BAL-20WETH

Expand All @@ -30,7 +32,7 @@ const defaultBuildInput = { account: defaultTestUserAccount, slippagePercent: '0

await connectWithDefaultUser()

describe('When proportionally removing liquidity for a weighted pool', async () => {
describe('When proportionally removing liquidity for a weighted v2 pool', async () => {
test('returns ZERO price impact', async () => {
const handler = selectProportionalHandler(poolMock)

Expand Down Expand Up @@ -67,7 +69,7 @@ describe('When proportionally removing liquidity for a weighted pool', async ()
})
})

describe('When removing liquidity from a stable pool', () => {
describe('When removing liquidity from a V2 stable pool', () => {
test('queries remove liquidity', async () => {
const pool = aPhantomStablePoolMock() // wstETH-rETH-sfrxETH

Expand All @@ -79,3 +81,54 @@ describe('When removing liquidity from a stable pool', () => {
expect(result.account).toBe(defaultTestUserAccount)
})
})

// TODO: unskip this test when sepolia V3 pools are available in production api
describe.skip('When proportionally removing liquidity for a weighted v3 pool', async () => {
// Sepolia
const balAddress = '0xb19382073c7a0addbb56ac6af1808fa49e377b75'
const wethAddress = '0x7b79995e5f793a07bc00c21412e50ecae098e7f9'
// const poolId = '0xec1b5ca86c83c7a85392063399e7d2170d502e00' // Sepolia B-50BAL-50WETH
// const v3Pool = await getPoolMock(poolId, GqlChain.Sepolia)

const v3Pool = {} as unknown as Pool

const defaultQueryInput: QueryRemoveLiquidityInput = {
humanBptIn: '0.01',
tokenOut: emptyAddress, // We don't use in this scenario it but it is required to simplify TS interfaces
}

test('returns ZERO price impact', async () => {
const handler = selectProportionalHandler(v3Pool)

const priceImpact = await handler.getPriceImpact()

expect(priceImpact).toBe(0)
})
test('queries amounts out', async () => {
const handler = selectProportionalHandler(v3Pool)

const result = await handler.simulate(defaultQueryInput)

const [wEthTokenAmountOut, balTokenAmountOut] = result.amountsOut

expect(balTokenAmountOut.token.address).toBe(balAddress)
expect(balTokenAmountOut.amount).toBeGreaterThan(200000000000000n)

expect(wEthTokenAmountOut.token.address).toBe(wethAddress)
expect(wEthTokenAmountOut.amount).toBeGreaterThan(100000000000000n)
})

test('builds Tx Config', async () => {
const handler = selectProportionalHandler(v3Pool)

const queryOutput = await handler.simulate(defaultQueryInput)

const result = await handler.buildCallData({
...defaultBuildInput,
queryOutput,
})

expect(result.to).toBe(sepoliaRouter)
expect(result.data).toBeDefined()
})
})
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
import networkConfig from '@/lib/config/networks/mainnet'
import { balAddress, wETHAddress } from '@/lib/debug-helpers'
import { balAddress, sepoliaRouter, wETHAddress } from '@/lib/debug-helpers'
import { aBalWethPoolElementMock } from '@/test/msw/builders/gqlPoolElement.builders'
import { defaultTestUserAccount } from '@/test/anvil/anvil-setup'
import { Pool } from '../../../PoolProvider'
import { QueryRemoveLiquidityInput, RemoveLiquidityType } from '../remove-liquidity.types'
import { SingleTokenRemoveLiquidityHandler } from './SingleTokenRemoveLiquidity.handler'
import { selectRemoveLiquidityHandler } from './selectRemoveLiquidityHandler'

const poolMock = aBalWethPoolElementMock() // 80BAL-20WETH
// import { getPoolMock } from '../../../__mocks__/getPoolMock'
// import { GqlChain } from '@/lib/shared/services/api/generated/graphql'

function selectSingleTokenHandler(pool: Pool): SingleTokenRemoveLiquidityHandler {
return selectRemoveLiquidityHandler(
Expand All @@ -23,9 +23,11 @@ const defaultQueryInput: QueryRemoveLiquidityInput = {

const defaultBuildInput = { account: defaultTestUserAccount, slippagePercent: '0.2' }

describe('When removing unbalanced liquidity for a weighted pool', () => {
describe('When removing unbalanced liquidity for a weighted V2 pool', () => {
const v2poolMock = aBalWethPoolElementMock() // 80BAL-20WETH

test('queries amounts out', async () => {
const handler = selectSingleTokenHandler(poolMock)
const handler = selectSingleTokenHandler(v2poolMock)

const result = await handler.simulate(defaultQueryInput)

Expand All @@ -39,7 +41,7 @@ describe('When removing unbalanced liquidity for a weighted pool', () => {
})

test('builds Tx Config', async () => {
const handler = selectSingleTokenHandler(poolMock)
const handler = selectSingleTokenHandler(v2poolMock)

const inputs: QueryRemoveLiquidityInput = {
humanBptIn: '1',
Expand All @@ -54,3 +56,43 @@ describe('When removing unbalanced liquidity for a weighted pool', () => {
expect(result.data).toBeDefined()
})
})

// TODO: unskip this test when sepolia V3 pools are available in production api
describe.skip('When removing unbalanced liquidity for a weighted V3 pool', async () => {
// Sepolia
const balAddress = '0xb19382073c7a0addbb56ac6af1808fa49e377b75'
const wethAddress = '0x7b79995e5f793a07bc00c21412e50ecae098e7f9'
// const poolId = '0xec1b5ca86c83c7a85392063399e7d2170d502e00' // Sepolia B-50BAL-50WETH
// const v3Pool = await getPoolMock(poolId, GqlChain.Sepolia)
const v3Pool = {} as unknown as Pool

const defaultQueryInput: QueryRemoveLiquidityInput = {
humanBptIn: '0.001',
tokenOut: balAddress,
}

test('queries amounts out', async () => {
const handler = selectSingleTokenHandler(v3Pool)

const result = await handler.simulate(defaultQueryInput)

const [wEthTokenAmountOut, balTokenAmountOut] = result.amountsOut

expect(wEthTokenAmountOut.token.address).toBe(wethAddress)
expect(wEthTokenAmountOut.amount).toBe(0n)

expect(balTokenAmountOut.token.address).toBe(balAddress)
expect(balTokenAmountOut.amount).toBeGreaterThan(50000000000000000n)
})

test('builds Tx Config', async () => {
const handler = selectSingleTokenHandler(v3Pool)

const queryOutput = await handler.simulate(defaultQueryInput)

const result = await handler.buildCallData({ ...defaultBuildInput, queryOutput })

expect(result.to).toBe(sepoliaRouter)
expect(result.data).toBeDefined()
})
})
2 changes: 1 addition & 1 deletion lib/modules/pool/pool.helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ import { PoolIssue } from './alerts/pool-issues/PoolIssue.type'
import { getUserTotalBalanceInt } from './user-balance.helpers'
import { dateToUnixTimestamp } from '@/lib/shared/utils/time'
import { balancerV2VaultAbi } from '../web3/contracts/abi/generated'
import { balancerV3VaultAbi } from '../web3/contracts/abi/balancerV3Abi'
import { balancerV3VaultAbi } from '../web3/contracts/abi/balancerV3VaultAbi'

/**
* METHODS
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@ function testPoolEnrichWithOnChainData(pool: Pool) {
return result
}

// TODO: un-skip when pool 0x7cf221fa36584f59a4f7fd7b946b8571c78e3692 is available in production api
// TODO: un-skip when pool 0xec1b5ca86c83c7a85392063399e7d2170d502e00 is available in production api
test.skip('enriches V3 pool with on-chain data', async () => {
const poolId = '0x7cf221fa36584f59a4f7fd7b946b8571c78e3692' // V3 Balancer 50 BAL 50 WETH (sepolia experimental)
const poolId = '0xec1b5ca86c83c7a85392063399e7d2170d502e00' // V3 Balancer 50 BAL 50 WETH (sepolia)
const pool = await getPoolMock(poolId, GqlChain.Sepolia, defaultTestUserAccount)

// delete values to ensure that onchain data is used
Expand Down Expand Up @@ -45,12 +45,10 @@ test('enriches V2 pool with on-chain data', async () => {
expect(Number(result.current.pool.dynamicData.totalShares)).toBeGreaterThan(0)
})

// TODO: un-skip when pool 0x232a18645c4e33dd64e6925e03da0f0dd77ad003 is available in production api
test.skip('enriches V1 Cow AMM pool with on-chain data', async () => {
// const poolId = '0x232a18645c4e33dd64e6925e03da0f0dd77ad003' // V1 test Cow AMM pool
const sepoliaPoolId = '0xd1bdc51decb61ee0c98e47fe17217c58be525180' // V1 test Cow AMM pool
test('enriches V1 Cow AMM pool with on-chain data', async () => {
const cowPoolId = '0xf706c50513446d709f08d3e5126cd74fb6bfda19'

const pool = await getPoolMock(sepoliaPoolId, GqlChain.Sepolia)
const pool = await getPoolMock(cowPoolId, GqlChain.Mainnet)

// delete values to ensure that onchain data is used
pool.dynamicData.totalLiquidity = '0'
Expand Down
4 changes: 2 additions & 2 deletions lib/modules/pool/queries/usePoolEnrichWithOnChainData.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { cloneDeep } from 'lodash'
import { Address, formatUnits } from 'viem'
import { useReadContracts } from 'wagmi'
import { useTokens } from '../../tokens/TokensProvider'
import { balancerV3VaultAbi } from '../../web3/contracts/abi/balancerV3Abi'
import { balancerV3ExtensionVaultAbi } from '../../web3/contracts/abi/balancerV3ExtensionVaultAbi'
import { weightedPoolV3Abi } from '../../web3/contracts/abi/weightedPoolV3Abi'
import { Pool } from '../PoolProvider'
import { BPT_DECIMALS } from '../pool.constants'
Expand Down Expand Up @@ -53,7 +53,7 @@ function useV3PoolOnchainData(pool: Pool) {
contracts: [
{
chainId,
abi: balancerV3VaultAbi,
abi: balancerV3ExtensionVaultAbi,
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We will probably use the vault explorer abi instead of this extension abi but this works for the sake of testing.

address: vaultAddress,
functionName: 'getPoolTokenInfo',
args: [pool.address as Address],
Expand Down
Loading
Loading