Skip to content

Commit

Permalink
UtilizationConstraint updates (compound-finance#264)
Browse files Browse the repository at this point in the history
* update UtilizationConstraint; additional utilization scenarios

* clean up

* add failing scenario

* update currentUtilizationFactor definition

* remove BigInt -> Number conversions

* delete early return
  • Loading branch information
scott-silver authored Mar 30, 2022
1 parent 7b4bd0b commit 41adda7
Show file tree
Hide file tree
Showing 2 changed files with 56 additions and 16 deletions.
50 changes: 48 additions & 2 deletions scenario/ConstraintScenario.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { scenario } from './context/CometContext';
import { expect } from 'chai';
import { expectApproximately } from './utils';
import { defactor, expect } from '../test/helpers';

scenario(
'Comet#constraint > collateral CometBalanceConstraint + BalanceConstraint both satisfied',
Expand Down Expand Up @@ -48,7 +48,7 @@ scenario(
scenario(
'Comet#constraint > negative comet base balance (borrow position)',
{
upgrade: true,
upgrade: true,
tokenBalances: {
albert: { $base: 100 }, // in units of asset, not wei
},
Expand All @@ -65,4 +65,50 @@ scenario(
expect(await baseAsset.balanceOf(albert.address)).to.be.equal(100n * scale);
expectApproximately(await albert.getCometBaseBalance(), -100n * scale, 1n);
}
);

scenario(
'UtilizationConstraint > sets utilization to 25%',
{ utilization: 0.25 },
async ({ comet }) => {
expect(defactor(await comet.getUtilization())).to.approximately(0.25, 0.000001);
}
);

scenario(
'UtilizationConstraint > sets utilization to 50%',
{ utilization: 0.50 },
async ({ comet }) => {
expect(defactor(await comet.getUtilization())).to.approximately(0.5, 0.000001);
}
);

scenario(
'UtilizationConstraint > sets utilization to 75%',
{ utilization: 0.75 },
async ({ comet }) => {
expect(defactor(await comet.getUtilization())).to.approximately(0.75, 0.000001);
}
);

scenario(
'UtilizationConstraint > sets utilization to 100%',
{ utilization: 1 },
async ({ comet }) => {
expect(defactor(await comet.getUtilization())).to.approximately(1, 0.000001);
}
);

// XXX enable scenario; fails on test nets currently
scenario.skip(
'UtilizationConstraint > works in combination with other constraints',
{
cometBalances: {
albert: { $base: -100 },
},
utilization: 1
},
async ({ comet }) => {
expect(defactor(await comet.getUtilization())).to.approximately(1, 0.000001);
}
);
22 changes: 8 additions & 14 deletions scenario/constraints/UtilizationConstraint.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
import { Constraint, Scenario, Solution, World } from '../../plugins/scenario';
import { Constraint, World } from '../../plugins/scenario';
import { CometContext } from '../context/CometContext';
import { deployComet } from '../../src/deploy';
import { optionalNumber } from '../utils';
import { defactor, exp, factor, factorScale, ZERO } from '../../test/helpers';
import { defactor, factor, factorScale } from '../../test/helpers';
import { expect } from 'chai';
import { Requirements } from './Requirements';

Expand Down Expand Up @@ -34,10 +33,6 @@ function getUtilizationConfig(requirements: object): UtilizationConfig | null {
};
}

function floor(n: number): bigint {
return BigInt(Math.floor(n));
}

/*
some math notes:
Expand Down Expand Up @@ -80,14 +75,12 @@ export class UtilizationConstraint<T extends CometContext, R extends Requirement
}

let expectedSupplyBase = totalSupplyBase + toSupplyBase;
let currentUtilization = totalBorrowBase / expectedSupplyBase;
let currentUtilizationFactor = (totalBorrowBase * factorScale) / expectedSupplyBase;

if (currentUtilization < utilizationFactor) {
toBorrowBase =
toBorrowBase + floor(utilization * Number(expectedSupplyBase)) - totalBorrowBase;
if (currentUtilizationFactor < utilizationFactor) {
toBorrowBase = toBorrowBase + (utilizationFactor * expectedSupplyBase / factorScale) - totalBorrowBase;
} else {
toSupplyBase =
toSupplyBase + floor(Number(totalBorrowBase) / utilization) - expectedSupplyBase;
toSupplyBase = toSupplyBase + (totalBorrowBase * factorScale / utilizationFactor) - expectedSupplyBase;
}

// It's really hard to target a utilization if we don't have _any_ base token supply, since
Expand Down Expand Up @@ -142,6 +135,7 @@ export class UtilizationConstraint<T extends CometContext, R extends Requirement
await context.sourceTokens(world, collateralNeeded, collateralToken, borrowActor);
await collateralToken.approve(borrowActor, comet);
await comet.connect(borrowActor.signer).supply(collateralToken.address, collateralNeeded);

await comet.connect(borrowActor.signer).withdraw(baseToken.address, toBorrowBase);
}

Expand All @@ -155,7 +149,7 @@ export class UtilizationConstraint<T extends CometContext, R extends Requirement

if (utilization) {
let comet = await context.getComet();
expect(defactor(await comet.getUtilization())).to.approximately(0.5, 0.000001);
expect(defactor(await comet.getUtilization())).to.approximately(utilization, 0.000001);
}
}
}

0 comments on commit 41adda7

Please sign in to comment.