@drift-labs/sdk 2.52.0-beta.10 → 2.52.0-beta.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/VERSION CHANGED
@@ -1 +1 @@
1
- 2.52.0-beta.10
1
+ 2.52.0-beta.12
package/lib/math/amm.js CHANGED
@@ -456,12 +456,11 @@ function calculateSpreadReserves(amm, oraclePriceData, now) {
456
456
  }
457
457
  const quoteAssetReserveDelta = amm.quoteAssetReserve.div(numericConstants_1.BID_ASK_SPREAD_PRECISION.div(spreadFraction));
458
458
  let quoteAssetReserve;
459
- if ((spread >= 0 && (0, types_1.isVariant)(direction, 'long')) ||
460
- (spread <= 0 && (0, types_1.isVariant)(direction, 'short'))) {
461
- quoteAssetReserve = amm.quoteAssetReserve.add(quoteAssetReserveDelta);
459
+ if (quoteAssetReserveDelta.gte(numericConstants_1.ZERO)) {
460
+ quoteAssetReserve = amm.quoteAssetReserve.add(quoteAssetReserveDelta.abs());
462
461
  }
463
462
  else {
464
- quoteAssetReserve = amm.quoteAssetReserve.sub(quoteAssetReserveDelta);
463
+ quoteAssetReserve = amm.quoteAssetReserve.sub(quoteAssetReserveDelta.abs());
465
464
  }
466
465
  const baseAssetReserve = amm.sqrtK.mul(amm.sqrtK).div(quoteAssetReserve);
467
466
  return {
@@ -471,12 +470,18 @@ function calculateSpreadReserves(amm, oraclePriceData, now) {
471
470
  }
472
471
  const reservePrice = calculatePrice(amm.baseAssetReserve, amm.quoteAssetReserve, amm.pegMultiplier);
473
472
  // always allow 10 bps of price offset, up to a fifth of the market's max_spread
474
- const maxOffset = Math.max(amm.maxSpread / 5, numericConstants_1.PERCENTAGE_PRECISION.toNumber() / 1000);
475
- const liquidityFraction = calculateInventoryLiquidityRatio(amm.baseAssetAmountWithAmm, amm.baseAssetReserve, amm.minBaseAssetReserve, amm.maxBaseAssetReserve);
476
- const referencePriceOffset = calculateReferencePriceOffset(reservePrice, amm.last24HAvgFundingRate, liquidityFraction, amm.historicalOracleData.lastOraclePriceTwap5Min, amm.lastMarkPriceTwap5Min, amm.historicalOracleData.lastOraclePriceTwap, amm.lastMarkPriceTwap, maxOffset);
473
+ let maxOffset = 0;
474
+ let referencePriceOffset = numericConstants_1.ZERO;
475
+ if (amm.curveUpdateIntensity > 100) {
476
+ maxOffset = Math.max(amm.maxSpread / 5, (numericConstants_1.PERCENTAGE_PRECISION.toNumber() / 10000) *
477
+ (amm.curveUpdateIntensity - 100));
478
+ const liquidityFraction = calculateInventoryLiquidityRatio(amm.baseAssetAmountWithAmm, amm.baseAssetReserve, amm.minBaseAssetReserve, amm.maxBaseAssetReserve);
479
+ const liquidityFractionSigned = liquidityFraction.mul((0, __1.sigNum)(amm.baseAssetAmountWithAmm.add(amm.baseAssetAmountWithUnsettledLp)));
480
+ referencePriceOffset = calculateReferencePriceOffset(reservePrice, amm.last24HAvgFundingRate, liquidityFractionSigned, amm.historicalOracleData.lastOraclePriceTwap5Min, amm.lastMarkPriceTwap5Min, amm.historicalOracleData.lastOraclePriceTwap, amm.lastMarkPriceTwap, maxOffset);
481
+ }
477
482
  const [longSpread, shortSpread] = calculateSpread(amm, oraclePriceData, now, reservePrice);
478
483
  const askReserves = calculateSpreadReserve(longSpread + referencePriceOffset.toNumber(), types_1.PositionDirection.LONG, amm);
479
- const bidReserves = calculateSpreadReserve(shortSpread + referencePriceOffset.toNumber(), types_1.PositionDirection.SHORT, amm);
484
+ const bidReserves = calculateSpreadReserve(-shortSpread + referencePriceOffset.toNumber(), types_1.PositionDirection.SHORT, amm);
480
485
  return [bidReserves, askReserves];
481
486
  }
482
487
  exports.calculateSpreadReserves = calculateSpreadReserves;
@@ -25,16 +25,16 @@ class PriorityFeeSubscriber {
25
25
  }
26
26
  }
27
27
  get avgPriorityFee() {
28
- return this.lastAvgStrategyResult;
28
+ return Math.floor(this.lastAvgStrategyResult);
29
29
  }
30
30
  get maxPriorityFee() {
31
- return this.lastMaxStrategyResult;
31
+ return Math.floor(this.lastMaxStrategyResult);
32
32
  }
33
33
  get customPriorityFee() {
34
34
  if (!this.customStrategy) {
35
35
  console.error('Custom strategy not set');
36
36
  }
37
- return this.lastCustomStrategyResult;
37
+ return Math.floor(this.lastCustomStrategyResult);
38
38
  }
39
39
  async subscribe() {
40
40
  if (this.intervalId) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@drift-labs/sdk",
3
- "version": "2.52.0-beta.10",
3
+ "version": "2.52.0-beta.12",
4
4
  "main": "lib/index.js",
5
5
  "types": "lib/index.d.ts",
6
6
  "author": "crispheaney",
package/src/math/amm.ts CHANGED
@@ -863,13 +863,14 @@ export function calculateSpreadReserves(
863
863
  );
864
864
 
865
865
  let quoteAssetReserve;
866
- if (
867
- (spread >= 0 && isVariant(direction, 'long')) ||
868
- (spread <= 0 && isVariant(direction, 'short'))
869
- ) {
870
- quoteAssetReserve = amm.quoteAssetReserve.add(quoteAssetReserveDelta);
866
+ if (quoteAssetReserveDelta.gte(ZERO)) {
867
+ quoteAssetReserve = amm.quoteAssetReserve.add(
868
+ quoteAssetReserveDelta.abs()
869
+ );
871
870
  } else {
872
- quoteAssetReserve = amm.quoteAssetReserve.sub(quoteAssetReserveDelta);
871
+ quoteAssetReserve = amm.quoteAssetReserve.sub(
872
+ quoteAssetReserveDelta.abs()
873
+ );
873
874
  }
874
875
 
875
876
  const baseAssetReserve = amm.sqrtK.mul(amm.sqrtK).div(quoteAssetReserve);
@@ -886,26 +887,35 @@ export function calculateSpreadReserves(
886
887
  );
887
888
 
888
889
  // always allow 10 bps of price offset, up to a fifth of the market's max_spread
889
- const maxOffset = Math.max(
890
- amm.maxSpread / 5,
891
- PERCENTAGE_PRECISION.toNumber() / 1000
892
- );
893
- const liquidityFraction = calculateInventoryLiquidityRatio(
894
- amm.baseAssetAmountWithAmm,
895
- amm.baseAssetReserve,
896
- amm.minBaseAssetReserve,
897
- amm.maxBaseAssetReserve
898
- );
899
- const referencePriceOffset = calculateReferencePriceOffset(
900
- reservePrice,
901
- amm.last24HAvgFundingRate,
902
- liquidityFraction,
903
- amm.historicalOracleData.lastOraclePriceTwap5Min,
904
- amm.lastMarkPriceTwap5Min,
905
- amm.historicalOracleData.lastOraclePriceTwap,
906
- amm.lastMarkPriceTwap,
907
- maxOffset
908
- );
890
+ let maxOffset = 0;
891
+ let referencePriceOffset = ZERO;
892
+ if (amm.curveUpdateIntensity > 100) {
893
+ maxOffset = Math.max(
894
+ amm.maxSpread / 5,
895
+ (PERCENTAGE_PRECISION.toNumber() / 10000) *
896
+ (amm.curveUpdateIntensity - 100)
897
+ );
898
+
899
+ const liquidityFraction = calculateInventoryLiquidityRatio(
900
+ amm.baseAssetAmountWithAmm,
901
+ amm.baseAssetReserve,
902
+ amm.minBaseAssetReserve,
903
+ amm.maxBaseAssetReserve
904
+ );
905
+ const liquidityFractionSigned = liquidityFraction.mul(
906
+ sigNum(amm.baseAssetAmountWithAmm.add(amm.baseAssetAmountWithUnsettledLp))
907
+ );
908
+ referencePriceOffset = calculateReferencePriceOffset(
909
+ reservePrice,
910
+ amm.last24HAvgFundingRate,
911
+ liquidityFractionSigned,
912
+ amm.historicalOracleData.lastOraclePriceTwap5Min,
913
+ amm.lastMarkPriceTwap5Min,
914
+ amm.historicalOracleData.lastOraclePriceTwap,
915
+ amm.lastMarkPriceTwap,
916
+ maxOffset
917
+ );
918
+ }
909
919
 
910
920
  const [longSpread, shortSpread] = calculateSpread(
911
921
  amm,
@@ -920,7 +930,7 @@ export function calculateSpreadReserves(
920
930
  amm
921
931
  );
922
932
  const bidReserves = calculateSpreadReserve(
923
- shortSpread + referencePriceOffset.toNumber(),
933
+ -shortSpread + referencePriceOffset.toNumber(),
924
934
  PositionDirection.SHORT,
925
935
  amm
926
936
  );
@@ -46,18 +46,18 @@ export class PriorityFeeSubscriber {
46
46
  }
47
47
 
48
48
  public get avgPriorityFee(): number {
49
- return this.lastAvgStrategyResult;
49
+ return Math.floor(this.lastAvgStrategyResult);
50
50
  }
51
51
 
52
52
  public get maxPriorityFee(): number {
53
- return this.lastMaxStrategyResult;
53
+ return Math.floor(this.lastMaxStrategyResult);
54
54
  }
55
55
 
56
56
  public get customPriorityFee(): number {
57
57
  if (!this.customStrategy) {
58
58
  console.error('Custom strategy not set');
59
59
  }
60
- return this.lastCustomStrategyResult;
60
+ return Math.floor(this.lastCustomStrategyResult);
61
61
  }
62
62
 
63
63
  public async subscribe(): Promise<void> {
package/tests/amm/test.ts CHANGED
@@ -8,6 +8,7 @@ import {
8
8
  calculateSpread,
9
9
  calculateSpreadBN,
10
10
  ZERO,
11
+ sigNum,
11
12
  ONE,
12
13
  calculateLiveOracleStd,
13
14
  calculateLiveOracleTwap,
@@ -465,7 +466,7 @@ describe('AMM Tests', () => {
465
466
 
466
467
  mockAmm.baseAssetAmountWithAmm = new BN(0);
467
468
  mockAmm.pegMultiplier = new BN(13.553 * PEG_PRECISION.toNumber());
468
- mockAmm.ammJitIntensity = 100;
469
+ mockAmm.ammJitIntensity = 200;
469
470
  mockAmm.curveUpdateIntensity = 200;
470
471
  mockAmm.baseSpread = 2500;
471
472
  mockAmm.maxSpread = 25000;
@@ -521,13 +522,13 @@ describe('AMM Tests', () => {
521
522
  console.log('amm.baseAssetReserve:', mockAmm.baseAssetReserve.toString());
522
523
  assert(mockAmm.baseAssetReserve.eq(new BN('1000000000')));
523
524
  const reserves2 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
524
- console.log(reserves2[1].baseAssetReserve.toString());
525
- console.log(reserves2[1].quoteAssetReserve.toString());
525
+ console.log(reserves2[0].baseAssetReserve.toString());
526
+ console.log(reserves2[0].quoteAssetReserve.toString());
526
527
 
527
- assert(reserves2[0].baseAssetReserve.eq(new BN('1006711408')));
528
- assert(reserves2[0].quoteAssetReserve.eq(new BN('993333334')));
529
- assert(reserves2[1].baseAssetReserve.eq(new BN('993377484')));
530
- assert(reserves2[1].quoteAssetReserve.eq(new BN('1006666666')));
528
+ assert(reserves2[0].baseAssetReserve.eq(new BN('1005050504')));
529
+ assert(reserves2[0].quoteAssetReserve.eq(new BN('994974875')));
530
+ assert(reserves2[1].baseAssetReserve.eq(new BN('992537314')));
531
+ assert(reserves2[1].quoteAssetReserve.eq(new BN('1007518796')));
531
532
 
532
533
  // create imbalance for reference price offset
533
534
  mockAmm.baseAssetReserve = new BN(1000000000 * 1.1);
@@ -536,11 +537,12 @@ describe('AMM Tests', () => {
536
537
  mockAmm.baseAssetReserve.mul(mockAmm.quoteAssetReserve)
537
538
  );
538
539
 
539
- mockAmm.baseAssetAmountWithAmm = new BN(-1000000000 * 0.1);
540
+ mockAmm.baseAssetAmountWithAmm = new BN(1000000000 * 0.1);
540
541
 
541
542
  const maxOffset = Math.max(
542
543
  mockAmm.maxSpread / 5,
543
- PERCENTAGE_PRECISION.toNumber() / 1000
544
+ (PERCENTAGE_PRECISION.toNumber() / 10000) *
545
+ (mockAmm.curveUpdateIntensity - 100)
544
546
  );
545
547
  const liquidityFraction = calculateInventoryLiquidityRatio(
546
548
  mockAmm.baseAssetAmountWithAmm,
@@ -550,11 +552,17 @@ describe('AMM Tests', () => {
550
552
  );
551
553
  console.log('liquidityFraction:', liquidityFraction.toString());
552
554
  assert(liquidityFraction.eq(new BN(1000000))); // full
553
-
555
+ const liquidityFractionSigned = liquidityFraction.mul(
556
+ sigNum(
557
+ mockAmm.baseAssetAmountWithAmm.add(
558
+ mockAmm.baseAssetAmountWithUnsettledLp
559
+ )
560
+ )
561
+ );
554
562
  const referencePriceOffset = calculateReferencePriceOffset(
555
563
  reservePrice,
556
564
  mockAmm.last24HAvgFundingRate,
557
- liquidityFraction,
565
+ liquidityFractionSigned,
558
566
  mockAmm.historicalOracleData.lastOraclePriceTwap5Min,
559
567
  mockAmm.lastMarkPriceTwap5Min,
560
568
  mockAmm.historicalOracleData.lastOraclePriceTwap,
@@ -562,17 +570,304 @@ describe('AMM Tests', () => {
562
570
  maxOffset
563
571
  );
564
572
  console.log('referencePriceOffset:', referencePriceOffset.toString());
565
- assert(referencePriceOffset.eq(new BN(5000)));
573
+ assert(referencePriceOffset.eq(new BN(10000)));
566
574
  assert(referencePriceOffset.eq(new BN(maxOffset)));
567
575
 
576
+ // mockAmm.curveUpdateIntensity = 100;
577
+ const reserves3 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
578
+ console.log(reserves3[0].baseAssetReserve.toString());
579
+ console.log(reserves3[0].quoteAssetReserve.toString());
580
+
581
+ assert(reserves3[0].baseAssetReserve.eq(new BN('1094581278')));
582
+ assert(reserves3[0].quoteAssetReserve.eq(new BN('913591359')));
583
+ assert(reserves3[1].baseAssetReserve.eq(new BN('989999998')));
584
+ assert(reserves3[1].quoteAssetReserve.eq(new BN('1010101010')));
585
+
586
+ const p1 = calculatePrice(
587
+ reserves3[0].baseAssetReserve,
588
+ reserves3[0].quoteAssetReserve,
589
+ mockAmm.pegMultiplier
590
+ );
591
+
592
+ const p2 = calculatePrice(
593
+ reserves3[1].baseAssetReserve,
594
+ reserves3[1].quoteAssetReserve,
595
+ mockAmm.pegMultiplier
596
+ );
597
+ console.log(p1.toString(), p2.toString());
598
+
599
+ assert(p1.eq(new BN(11312000)));
600
+ assert(p2.eq(new BN(13828180)));
601
+
602
+ mockAmm.curveUpdateIntensity = 110;
603
+ const reserves4 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
604
+ console.log(reserves4[1].baseAssetReserve.toString());
605
+ console.log(reserves4[1].quoteAssetReserve.toString());
606
+
607
+ assert(reserves4[0].baseAssetReserve.eq(new BN('1097323599')));
608
+ assert(reserves4[0].quoteAssetReserve.eq(new BN('911308203')));
609
+ assert(reserves4[1].baseAssetReserve.eq(new BN('989999998')));
610
+ assert(reserves4[1].quoteAssetReserve.eq(new BN('1010101010')));
611
+
612
+ const p1RF = calculatePrice(
613
+ reserves4[0].baseAssetReserve,
614
+ reserves4[0].quoteAssetReserve,
615
+ mockAmm.pegMultiplier
616
+ );
617
+
618
+ const p2RF = calculatePrice(
619
+ reserves4[1].baseAssetReserve,
620
+ reserves4[1].quoteAssetReserve,
621
+ mockAmm.pegMultiplier
622
+ );
623
+ console.log(p1RF.toString(), p2RF.toString());
624
+
625
+ assert(p1RF.eq(new BN(11255531)));
626
+ assert(p2RF.eq(new BN(13828180)));
627
+ // no ref price offset at 100
628
+ mockAmm.curveUpdateIntensity = 100;
629
+ const reserves5 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
630
+ console.log(reserves5[0].baseAssetReserve.toString());
631
+ console.log(reserves5[0].quoteAssetReserve.toString());
632
+
633
+ assert(reserves5[0].baseAssetReserve.eq(new BN('1100068201')));
634
+ assert(reserves5[0].quoteAssetReserve.eq(new BN('909034546')));
635
+ assert(reserves5[1].baseAssetReserve.eq(new BN('989999998')));
636
+ assert(reserves5[1].quoteAssetReserve.eq(new BN('1010101010')));
637
+
638
+ const p1RFNone = calculatePrice(
639
+ reserves5[0].baseAssetReserve,
640
+ reserves5[0].quoteAssetReserve,
641
+ mockAmm.pegMultiplier
642
+ );
643
+
644
+ const p2RFNone = calculatePrice(
645
+ reserves5[1].baseAssetReserve,
646
+ reserves5[1].quoteAssetReserve,
647
+ mockAmm.pegMultiplier
648
+ );
649
+ console.log(p1RFNone.toString(), p2RFNone.toString());
650
+
651
+ assert(p1RFNone.eq(new BN(11199437)));
652
+ assert(p2RFNone.eq(new BN(13828180)));
653
+ assert(p1RF.sub(p1RFNone).eq(new BN(56094)));
654
+ assert(p2RF.sub(p2RFNone).eq(new BN(0))); // todo?
655
+ });
656
+ it('Spread Reserves (with negative offset)', () => {
657
+ const myMockPerpMarkets = _.cloneDeep(mockPerpMarkets);
658
+ const mockMarket1 = myMockPerpMarkets[0];
659
+ const mockAmm = mockMarket1.amm;
660
+ const now = new BN(new Date().getTime() / 1000); //todo
661
+
662
+ const oraclePriceData = {
663
+ price: new BN(13.553 * PRICE_PRECISION.toNumber()),
664
+ slot: new BN(68 + 1),
665
+ confidence: new BN(1),
666
+ hasSufficientNumberOfDataPoints: true,
667
+ };
668
+
669
+ const reserves = calculateSpreadReserves(mockAmm, oraclePriceData, now);
670
+ assert(reserves[0].baseAssetReserve.eq(new BN('1000000000')));
671
+ assert(reserves[0].quoteAssetReserve.eq(new BN('12000000000')));
672
+ assert(reserves[1].baseAssetReserve.eq(new BN('1000000000')));
673
+ assert(reserves[1].quoteAssetReserve.eq(new BN('12000000000')));
674
+
675
+ mockAmm.baseAssetReserve = new BN(1000000000);
676
+ mockAmm.quoteAssetReserve = new BN(1000000000);
677
+ mockAmm.sqrtK = new BN(1000000000);
678
+
679
+ mockAmm.baseAssetAmountWithAmm = new BN(0);
680
+ mockAmm.pegMultiplier = new BN(13.553 * PEG_PRECISION.toNumber());
681
+ mockAmm.ammJitIntensity = 200;
682
+ mockAmm.curveUpdateIntensity = 200;
683
+ mockAmm.baseSpread = 2500;
684
+ mockAmm.maxSpread = 25000;
685
+
686
+ mockAmm.last24HAvgFundingRate = new BN(-7590328523);
687
+
688
+ mockAmm.lastMarkPriceTwap = new BN(
689
+ (oraclePriceData.price.toNumber() / 1e6 + 0.01) * 1e6
690
+ );
691
+ mockAmm.historicalOracleData.lastOraclePriceTwap = new BN(
692
+ (oraclePriceData.price.toNumber() / 1e6 - 0.015) * 1e6
693
+ );
694
+
695
+ mockAmm.historicalOracleData.lastOraclePriceTwap5Min = new BN(
696
+ (oraclePriceData.price.toNumber() / 1e6 + 0.005) * 1e6
697
+ );
698
+ mockAmm.lastMarkPriceTwap5Min = new BN(
699
+ (oraclePriceData.price.toNumber() / 1e6 - 0.005) * 1e6
700
+ );
701
+
702
+ console.log('starting rr:');
703
+ let reservePrice = undefined;
704
+ if (!reservePrice) {
705
+ reservePrice = calculatePrice(
706
+ mockAmm.baseAssetReserve,
707
+ mockAmm.quoteAssetReserve,
708
+ mockAmm.pegMultiplier
709
+ );
710
+ }
711
+
712
+ const targetPrice = oraclePriceData?.price || reservePrice;
713
+ const confInterval = oraclePriceData.confidence || ZERO;
714
+ const targetMarkSpreadPct = reservePrice
715
+ .sub(targetPrice)
716
+ .mul(BID_ASK_SPREAD_PRECISION)
717
+ .div(reservePrice);
718
+
719
+ const confIntervalPct = confInterval
720
+ .mul(BID_ASK_SPREAD_PRECISION)
721
+ .div(reservePrice);
722
+
723
+ // now = now || new BN(new Date().getTime() / 1000); //todo
724
+ const liveOracleStd = calculateLiveOracleStd(mockAmm, oraclePriceData, now);
725
+ console.log('reservePrice:', reservePrice.toString());
726
+ console.log('targetMarkSpreadPct:', targetMarkSpreadPct.toString());
727
+ console.log('confIntervalPct:', confIntervalPct.toString());
728
+
729
+ console.log('liveOracleStd:', liveOracleStd.toString());
730
+
731
+ const tt = calculateSpread(mockAmm, oraclePriceData, now);
732
+ console.log(tt);
733
+
734
+ console.log('amm.baseAssetReserve:', mockAmm.baseAssetReserve.toString());
735
+ assert(mockAmm.baseAssetReserve.eq(new BN('1000000000')));
736
+ const reserves2 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
737
+ console.log(reserves2[1].baseAssetReserve.toString());
738
+ console.log(reserves2[1].quoteAssetReserve.toString());
739
+
740
+ assert(reserves2[0].baseAssetReserve.eq(new BN('1006289308')));
741
+ assert(reserves2[0].quoteAssetReserve.eq(new BN('993750000')));
742
+ assert(reserves2[1].baseAssetReserve.eq(new BN('993788819')));
743
+ assert(reserves2[1].quoteAssetReserve.eq(new BN('1006250000')));
744
+
745
+ // create imbalance for reference price offset
746
+ mockAmm.baseAssetReserve = new BN(1000000000 / 1.1);
747
+ mockAmm.quoteAssetReserve = new BN(1000000000 * 1.1);
748
+ mockAmm.sqrtK = squareRootBN(
749
+ mockAmm.baseAssetReserve.mul(mockAmm.quoteAssetReserve)
750
+ );
751
+
752
+ mockAmm.baseAssetAmountWithAmm = new BN(-1000000000 * 0.1);
753
+
754
+ const maxOffset = Math.max(
755
+ mockAmm.maxSpread / 5,
756
+ (PERCENTAGE_PRECISION.toNumber() / 10000) *
757
+ (mockAmm.curveUpdateIntensity - 100)
758
+ );
759
+ const liquidityFraction = calculateInventoryLiquidityRatio(
760
+ mockAmm.baseAssetAmountWithAmm,
761
+ mockAmm.baseAssetReserve,
762
+ mockAmm.minBaseAssetReserve,
763
+ mockAmm.maxBaseAssetReserve
764
+ );
765
+ console.log('liquidityFraction:', liquidityFraction.toString());
766
+ assert(liquidityFraction.eq(new BN(1000000))); // full
767
+ const liquidityFractionSigned = liquidityFraction.mul(
768
+ sigNum(
769
+ mockAmm.baseAssetAmountWithAmm.add(
770
+ mockAmm.baseAssetAmountWithUnsettledLp
771
+ )
772
+ )
773
+ );
774
+ const referencePriceOffset = calculateReferencePriceOffset(
775
+ reservePrice,
776
+ mockAmm.last24HAvgFundingRate,
777
+ liquidityFractionSigned,
778
+ mockAmm.historicalOracleData.lastOraclePriceTwap5Min,
779
+ mockAmm.lastMarkPriceTwap5Min,
780
+ mockAmm.historicalOracleData.lastOraclePriceTwap,
781
+ mockAmm.lastMarkPriceTwap,
782
+ maxOffset
783
+ );
784
+ console.log('referencePriceOffset:', referencePriceOffset.toString());
785
+ assert(referencePriceOffset.eq(new BN(-10000))); // neg
786
+
787
+ // assert(referencePriceOffset.eq(new BN(maxOffset)));
788
+
789
+ // mockAmm.curveUpdateIntensity = 100;
568
790
  const reserves3 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
569
- console.log(reserves3[1].baseAssetReserve.toString());
570
- console.log(reserves3[1].quoteAssetReserve.toString());
791
+ console.log(reserves3[0].baseAssetReserve.toString());
792
+ console.log(reserves3[0].quoteAssetReserve.toString());
793
+
794
+ assert(reserves3[0].baseAssetReserve.eq(new BN('1010101008')));
795
+ assert(reserves3[0].quoteAssetReserve.eq(new BN('990000000')));
796
+ assert(reserves3[1].baseAssetReserve.eq(new BN('913613747')));
797
+ assert(reserves3[1].quoteAssetReserve.eq(new BN('1094554456')));
798
+
799
+ const p1 = calculatePrice(
800
+ reserves3[0].baseAssetReserve,
801
+ reserves3[0].quoteAssetReserve,
802
+ mockAmm.pegMultiplier
803
+ );
804
+
805
+ const p2 = calculatePrice(
806
+ reserves3[1].baseAssetReserve,
807
+ reserves3[1].quoteAssetReserve,
808
+ mockAmm.pegMultiplier
809
+ );
810
+ console.log(p1.toString(), p2.toString());
811
+
812
+ assert(p1.eq(new BN(13283295)));
813
+ assert(p2.eq(new BN(16237164)));
814
+
815
+ mockAmm.curveUpdateIntensity = 110;
816
+ const reserves4 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
817
+ console.log(reserves4[1].baseAssetReserve.toString());
818
+ console.log(reserves4[1].quoteAssetReserve.toString());
819
+
820
+ assert(reserves4[0].baseAssetReserve.eq(new BN('999999998')));
821
+ assert(reserves4[0].quoteAssetReserve.eq(new BN('1000000000')));
822
+ assert(reserves4[1].baseAssetReserve.eq(new BN('911313622')));
823
+ assert(reserves4[1].quoteAssetReserve.eq(new BN('1097317074')));
824
+
825
+ const p1RF = calculatePrice(
826
+ reserves4[0].baseAssetReserve,
827
+ reserves4[0].quoteAssetReserve,
828
+ mockAmm.pegMultiplier
829
+ );
830
+
831
+ const p2RF = calculatePrice(
832
+ reserves4[1].baseAssetReserve,
833
+ reserves4[1].quoteAssetReserve,
834
+ mockAmm.pegMultiplier
835
+ );
836
+ console.log(p1RF.toString(), p2RF.toString());
837
+
838
+ assert(p1RF.eq(new BN(13553000)));
839
+ assert(p2RF.eq(new BN(16319231)));
840
+
841
+ // no ref price offset at 100
842
+ mockAmm.curveUpdateIntensity = 100;
843
+ const reserves5 = calculateSpreadReserves(mockAmm, oraclePriceData, now);
844
+ console.log(reserves5[0].baseAssetReserve.toString());
845
+ console.log(reserves5[0].quoteAssetReserve.toString());
846
+
847
+ assert(reserves5[0].baseAssetReserve.eq(new BN('999999998')));
848
+ assert(reserves5[0].quoteAssetReserve.eq(new BN('1000000000')));
849
+ assert(reserves5[1].baseAssetReserve.eq(new BN('909034547')));
850
+ assert(reserves5[1].quoteAssetReserve.eq(new BN('1100068200')));
851
+
852
+ const p1RFNone = calculatePrice(
853
+ reserves5[0].baseAssetReserve,
854
+ reserves5[0].quoteAssetReserve,
855
+ mockAmm.pegMultiplier
856
+ );
857
+
858
+ const p2RFNone = calculatePrice(
859
+ reserves5[1].baseAssetReserve,
860
+ reserves5[1].quoteAssetReserve,
861
+ mockAmm.pegMultiplier
862
+ );
863
+ console.log(p1RFNone.toString(), p2RFNone.toString());
571
864
 
572
- assert(reserves3[0].baseAssetReserve.eq(new BN('1164705879')));
573
- assert(reserves3[0].quoteAssetReserve.eq(new BN('858585859')));
574
- assert(reserves3[1].baseAssetReserve.eq(new BN('1042105261')));
575
- assert(reserves3[1].quoteAssetReserve.eq(new BN('959595959')));
865
+ const rr = p2RF.sub(p2RFNone).mul(PERCENTAGE_PRECISION).div(p2RF);
866
+ console.log(rr.toNumber());
867
+ assert(p1RFNone.eq(new BN(13553000)));
868
+ assert(p2RFNone.eq(new BN(16401163)));
869
+ assert(p1RF.sub(p1RFNone).eq(new BN(0))); // todo?
870
+ assert(rr.eq(new BN(-5020)));
576
871
  });
577
872
 
578
873
  it('live update functions', () => {