Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Fix] Osmosis - Continuously creating position on amm-LP strategy #318

Open
wants to merge 7 commits into
base: development
Choose a base branch
from
Open
Changes from 1 commit
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
Prev Previous commit
Next Next commit
add new priceToTick calculation
mlguys committed Apr 27, 2024
commit ed45375755053179932fa17191abdd81d3d22368
9 changes: 6 additions & 3 deletions src/chains/osmosis/osmosis.ts
Original file line number Diff line number Diff line change
@@ -50,7 +50,7 @@ import { Pool as CLPool } from 'osmo-query/dist/codegen/osmosis/concentrated-liq
import { TradeInfo } from './osmosis.controllers';
import { HttpException, TRADE_FAILED_ERROR_CODE, TRADE_FAILED_ERROR_MESSAGE, GAS_LIMIT_EXCEEDED_ERROR_MESSAGE, GAS_LIMIT_EXCEEDED_ERROR_CODE, AMOUNT_LESS_THAN_MIN_AMOUNT_ERROR_MESSAGE, AMOUNT_LESS_THAN_MIN_AMOUNT_ERROR_CODE } from '../../services/error-handler';
import { extendPool, filterPoolsSwap, filterPoolsLP, filterPoolsSwapAndLP } from './osmosis.lp.utils';
import { fetchFees, findTickForPrice, tickToPrice } from './osmosis.utils';
import { fetchFees, findTickForPrice, tickToPrice, calculatePriceToTick } from './osmosis.utils';
import { getImperatorPriceHash } from './osmosis.prices';
import { GasPrice, calculateFee, setupIbcExtension, SigningStargateClient, AminoTypes } from '@cosmjs/stargate';
import { CosmWasmClient } from "@cosmjs/cosmwasm-stargate";
@@ -1361,8 +1361,11 @@ export class Osmosis extends CosmosBase implements Cosmosish{
}

// FIXME: The calculation of lowerTick and upperTick is not correct for the case where price is less than 1
const lowerTick = findTickForPrice(req.lowerPrice!, pool.exponentAtPriceOne, pool.tickSpacing, true) // pool.currentTick,
const upperTick = findTickForPrice(req.upperPrice!, pool.exponentAtPriceOne, pool.tickSpacing, false)
const lowerTick = calculatePriceToTick(req.lowerPrice!, pool.exponentAtPriceOne, pool.tickSpacing, true) // pool.currentTick,
const upperTick = calculatePriceToTick(req.upperPrice!, pool.exponentAtPriceOne, pool.tickSpacing, false)

console.log('lowerTick', lowerTick)
console.log('upperTick', upperTick)

var tokenMinAmount0_final = tokenMinAmount0.toString()
var tokenMinAmount1_final = tokenMinAmount1.toString()
55 changes: 55 additions & 0 deletions src/chains/osmosis/osmosis.utils.ts
Original file line number Diff line number Diff line change
@@ -93,3 +93,58 @@ export function findTickForPrice(desiredPriceString: string, exponentAtPriceOne:
return returnTick.toString()
}


export function calculatePriceToTick(desiredPriceString: string, exponentAtPriceOne: number, tickSpacing: number, is_lowerBound: boolean): string {
console.log(`Inputs: desiredPriceString=${desiredPriceString}, exponentAtPriceOne=${exponentAtPriceOne}, tickSpacing=${tickSpacing}, is_lowerBound=${is_lowerBound}`);

const desiredPrice = new BigNumber(desiredPriceString)
const exponent = new BigNumber(exponentAtPriceOne);
const geometricExponentIncrementDistanceInTicks = new BigNumber(9).multipliedBy(new BigNumber(10).exponentiatedBy(exponent.multipliedBy(-1)))

console.log(`Initial calculations: desiredPrice=${desiredPrice}, exponent=${exponent}, geometricExponentIncrementDistanceInTicks=${geometricExponentIncrementDistanceInTicks}`);

let currentPrice = new BigNumber(1);
let ticksPassed = new BigNumber(0);
let exponentAtCurrentTick = exponent;
let currentAdditiveIncrementInTicks = new BigNumber(10).exponentiatedBy(exponent)

if (desiredPrice.gt(new BigNumber(1))) {
while (currentPrice.lt(desiredPrice)) {
currentAdditiveIncrementInTicks = new BigNumber(10).exponentiatedBy(exponentAtCurrentTick);
const maxPriceForCurrentAdditiveIncrementInTicks = geometricExponentIncrementDistanceInTicks.multipliedBy(currentAdditiveIncrementInTicks);
currentPrice = currentPrice.plus(maxPriceForCurrentAdditiveIncrementInTicks);
exponentAtCurrentTick = exponentAtCurrentTick.plus(1);
ticksPassed = ticksPassed.plus(geometricExponentIncrementDistanceInTicks);

console.log(`Loop (desiredPrice > 1): currentPrice=${currentPrice}, exponentAtCurrentTick=${exponentAtCurrentTick}, ticksPassed=${ticksPassed}`);
}
} else {
exponentAtCurrentTick = exponent.minus(1);
while (currentPrice.gt(desiredPrice)) {
currentAdditiveIncrementInTicks = new BigNumber(10).exponentiatedBy(exponentAtCurrentTick);
const maxPriceForCurrentAdditiveIncrementInTicks = geometricExponentIncrementDistanceInTicks.multipliedBy(currentAdditiveIncrementInTicks);
currentPrice = currentPrice.minus(maxPriceForCurrentAdditiveIncrementInTicks);
exponentAtCurrentTick = exponentAtCurrentTick.minus(1);
ticksPassed = ticksPassed.minus(geometricExponentIncrementDistanceInTicks);

console.log(`Loop (desiredPrice <= 1): currentPrice=${currentPrice}, exponentAtCurrentTick=${exponentAtCurrentTick}, ticksPassed=${ticksPassed}`);
}
}

const ticksToBeFulfilledByExponentAtCurrentTick = desiredPrice.minus(currentPrice).dividedBy(currentAdditiveIncrementInTicks);
console.log(`Ticks to be fulfilled by current exponent: ${ticksToBeFulfilledByExponentAtCurrentTick}`);

const tickIndex = ticksPassed.plus(ticksToBeFulfilledByExponentAtCurrentTick);
console.log(`Tick index: ${tickIndex}`);

let returnTick = new BigNumber(0);
if (is_lowerBound){
returnTick = tickIndex.dividedBy(tickSpacing).integerValue(BigNumber.ROUND_DOWN).multipliedBy(tickSpacing)
}
else{
returnTick = tickIndex.dividedBy(tickSpacing).integerValue(BigNumber.ROUND_CEIL).multipliedBy(tickSpacing)
}

console.log(`Final calculations: tickIndex=${tickIndex}, returnTick=${BigInt(returnTick.toNumber()).toString()}`);
return BigInt(returnTick.toNumber()).toString();
}