Skip to content

Commit

Permalink
chore: more staked token tests
Browse files Browse the repository at this point in the history
  • Loading branch information
naddison36 committed Aug 20, 2021
1 parent 010dae8 commit 08e9758
Showing 1 changed file with 89 additions and 17 deletions.
106 changes: 89 additions & 17 deletions test/governance/staked-token.spec.ts
Expand Up @@ -48,7 +48,7 @@ describe("Staked Token", () => {
deployTime = await getTimestamp()
nexus = await new MockNexus__factory(sa.default.signer).deploy(sa.governor.address, DEAD_ADDRESS, DEAD_ADDRESS)
await nexus.setRecollateraliser(sa.mockRecollateraliser.address)
rewardToken = await new MockERC20__factory(sa.default.signer).deploy("Reward", "RWD", 18, sa.default.address, 10000000)
rewardToken = await new MockERC20__factory(sa.default.signer).deploy("Reward", "RWD", 18, sa.default.address, startingMintAmount)

const signatureVerifier = await new SignatureVerifier__factory(sa.default.signer).deploy()
const gamifiedManager = await new GamifiedManager__factory(sa.default.signer).deploy()
Expand Down Expand Up @@ -924,6 +924,7 @@ describe("Staked Token", () => {
await rewardToken.connect(sa.default.signer).approve(stakedToken.address, simpleToExactAmount(10000))
await stakedToken["stake(uint256,address)"](stakedAmount, sa.default.address)
stakedTimestamp = await getTimestamp()
await increaseTime(ONE_WEEK.mul(2))
})
context("should fail when", () => {
it("nothing staked", async () => {
Expand All @@ -948,8 +949,7 @@ describe("Staked Token", () => {
expect(stakerDataAfter.cooldownTimestamp, "cooldown timestamp after").to.eq(startCooldownTimestamp)
expect(stakerDataAfter.cooldownPercentage, "cooldown percentage after").to.eq(cooldown100Percentage)
expect(stakerDataAfter.userBalances.raw, "staked raw balance after").to.eq(stakedAmount)
// TODO why is weightedTimestamp 1 second behind lastAction?
expect(stakerDataAfter.userBalances.weightedTimestamp, "weighted timestamp after").to.eq(startCooldownTimestamp.sub(1))
expect(stakerDataAfter.userBalances.weightedTimestamp, "weighted timestamp after").to.eq(stakedTimestamp)
expect(stakerDataAfter.userBalances.lastAction, "last action after").to.eq(startCooldownTimestamp)
expect(stakerDataAfter.userBalances.permMultiplier, "perm multiplier after").to.eq(0)
expect(stakerDataAfter.userBalances.seasonMultiplier, "season multiplier after").to.eq(0)
Expand All @@ -972,9 +972,7 @@ describe("Staked Token", () => {
expect(stakerDataAfter1stooldown.cooldownTimestamp, "cooldown timestamp after 1st").to.eq(cooldown1stTimestamp)
expect(stakerDataAfter1stooldown.cooldownPercentage, "cooldown percentage after 1st").to.eq(firstCooldown)
expect(stakerDataAfter1stooldown.userBalances.raw, "staked raw balance after 1st").to.eq(stakedAmount)
expect(stakerDataAfter1stooldown.userBalances.weightedTimestamp, "weighted timestamp after 1st").to.eq(
cooldown1stTimestamp.sub(1),
)
expect(stakerDataAfter1stooldown.userBalances.weightedTimestamp, "weighted timestamp after 1st").to.eq(stakedTimestamp)
expect(stakerDataAfter1stooldown.userBalances.lastAction, "last action after 1st").to.eq(cooldown1stTimestamp)
expect(stakerDataAfter1stooldown.userBalances.permMultiplier, "perm multiplier after 1st").to.eq(0)
expect(stakerDataAfter1stooldown.userBalances.seasonMultiplier, "season multiplier after 1st").to.eq(0)
Expand Down Expand Up @@ -1340,7 +1338,9 @@ describe("Staked Token", () => {
// fee = staked withdraw * 0.1
// fee = withdraw with fee / 1.1 * 0.1 = withdraw with fee / 11
const redemptionFee = stakedAmount.div(11)

const tx2 = await stakedToken.withdraw(stakedAmount, sa.default.address, true, true)

await expect(tx2).to.emit(stakedToken, "Withdraw").withArgs(sa.default.address, sa.default.address, stakedAmount)

const afterData = await snapshotUserStakingData(sa.default.address)
Expand All @@ -1350,9 +1350,6 @@ describe("Staked Token", () => {
expect(afterData.cooldownPercentage, "staked cooldown percentage").to.eq(0)
expect(afterData.userBalances.cooldownMultiplier, "cooldown multiplier after").to.eq(0)
expect(afterData.userBalances.raw, "staked raw balance after").to.eq(0)
// expect(afterData.rewardsBalance, "staker rewards after").to.eq(
// beforeData.rewardsBalance.add(stakedAmount).sub(redemptionFee),
// )
assertBNClose(afterData.rewardsBalance, beforeData.rewardsBalance.add(stakedAmount).sub(redemptionFee), 1)
})
it("not reset the cooldown timer unless all is all unstaked")
Expand Down Expand Up @@ -1395,8 +1392,8 @@ describe("Staked Token", () => {
console.log("data before")
console.log(beforeData.cooldownPercentage.toString(), beforeData.userBalances.raw.toString())
console.log(afterData.cooldownPercentage.toString(), afterData.userBalances.raw.toString())
// expect(afterData.stakedBalance, "staker staked after").to.eq(remainingBalance)
// expect(afterData.votes, "staker votes after").to.eq(remainingBalance)
// TODO expect(afterData.stakedBalance, "staker staked after").to.eq(remainingBalance)
// TODO expect(afterData.votes, "staker votes after").to.eq(remainingBalance)
expect(afterData.cooldownTimestamp, "cooldown timestamp after").to.eq(beforeData.cooldownTimestamp)
// 1400 / 2000 * 100 = 70
// (1400 - 300 - 30) / (2000 - 300 - 30) * 1e18 = 64.0718563e16
Expand Down Expand Up @@ -1427,9 +1424,6 @@ describe("Staked Token", () => {
expect(afterData.cooldownPercentage, "staked cooldown percentage").to.eq(0)
expect(afterData.userBalances.cooldownMultiplier, "cooldown multiplier after").to.eq(0)
expect(afterData.userBalances.raw, "staked raw balance after").to.eq(stakedAmount.sub(cooldownAmount))
// expect(afterData.rewardsBalance, "staker rewards after").to.eq(
// beforeData.rewardsBalance.add(cooldownAmount).sub(redemptionFee),
// )
assertBNClose(afterData.rewardsBalance, beforeData.rewardsBalance.add(cooldownAmount).sub(redemptionFee), 1)
})
it("not reset the cooldown timer unless all is all unstaked")
Expand All @@ -1449,7 +1443,9 @@ describe("Staked Token", () => {
it("should withdraw all incl fee and get 75% of rewards", async () => {
const tx = await stakedToken.withdraw(stakedAmount, sa.default.address, true, false)
await expect(tx).to.emit(stakedToken, "Withdraw").withArgs(sa.default.address, sa.default.address, stakedAmount)
await expect(tx).to.emit(rewardToken, "Transfer").withArgs(stakedToken.address, sa.default.address, stakedAmount.mul(3).div(4))
await expect(tx)
.to.emit(rewardToken, "Transfer")
.withArgs(stakedToken.address, sa.default.address, stakedAmount.mul(3).div(4))

const afterData = await snapshotUserStakingData(sa.default.address)
expect(afterData.stakedBalance, "staker stkRWD after").to.eq(0)
Expand All @@ -1462,7 +1458,9 @@ describe("Staked Token", () => {
it("should withdraw all excl. fee and get 75% of rewards", async () => {
const tx = await stakedToken.withdraw(stakedAmount, sa.default.address, false, false)
await expect(tx).to.emit(stakedToken, "Withdraw").withArgs(sa.default.address, sa.default.address, stakedAmount)
await expect(tx).to.emit(rewardToken, "Transfer").withArgs(stakedToken.address, sa.default.address, stakedAmount.mul(3).div(4))
await expect(tx)
.to.emit(rewardToken, "Transfer")
.withArgs(stakedToken.address, sa.default.address, stakedAmount.mul(3).div(4))

const afterData = await snapshotUserStakingData(sa.default.address)
expect(afterData.stakedBalance, "staker stkRWD after").to.eq(0)
Expand All @@ -1476,7 +1474,9 @@ describe("Staked Token", () => {
const withdrawAmount = stakedAmount.div(10)
const tx = await stakedToken.withdraw(withdrawAmount, sa.default.address, true, false)
await expect(tx).to.emit(stakedToken, "Withdraw").withArgs(sa.default.address, sa.default.address, withdrawAmount)
await expect(tx).to.emit(rewardToken, "Transfer").withArgs(stakedToken.address, sa.default.address, withdrawAmount.mul(3).div(4))
await expect(tx)
.to.emit(rewardToken, "Transfer")
.withArgs(stakedToken.address, sa.default.address, withdrawAmount.mul(3).div(4))

const afterData = await snapshotUserStakingData(sa.default.address)
expect(afterData.stakedBalance, "staker stkRWD after").to.eq(stakedAmount.sub(withdrawAmount))
Expand All @@ -1487,6 +1487,30 @@ describe("Staked Token", () => {
expect(afterData.userBalances.raw, "staked raw balance after").to.eq(stakedAmount.sub(withdrawAmount))
})
})
context.only("calc redemption fee", () => {
let currentTime: BN
before(async () => {
stakedToken = await redeployStakedToken()
currentTime = await getTimestamp()
})
const runs = [
{ stakedSeconds: BN.from(0), expected: 100, desc: "immediate" },
{ stakedSeconds: ONE_DAY, expected: 100, desc: "1 day" },
{ stakedSeconds: ONE_WEEK, expected: 100, desc: "1 week" },
{ stakedSeconds: ONE_WEEK.mul(2), expected: 100, desc: "2 weeks" },
{ stakedSeconds: ONE_WEEK.mul(21).div(10), expected: 94.52286093, desc: "2.1 weeks" },
{ stakedSeconds: ONE_WEEK.mul(10), expected: 29.77225575, desc: "10 weeks" },
{ stakedSeconds: ONE_WEEK.mul(12), expected: 25, desc: "12 weeks" },
{ stakedSeconds: ONE_WEEK.mul(47), expected: 0.26455763, desc: "47 weeks" },
{ stakedSeconds: ONE_WEEK.mul(48), expected: 0, desc: "48 weeks" },
{ stakedSeconds: ONE_WEEK.mul(50), expected: 0, desc: "50 weeks" },
]
runs.forEach((run) => {
it(run.desc, async () => {
expect(await stakedToken.calcRedemptionFeeRate(currentTime.sub(run.stakedSeconds))).to.eq(simpleToExactAmount(run.expected, 15))
})
})
})
})
context("backward compatibility", () => {
const stakedAmount = simpleToExactAmount(2000)
Expand Down Expand Up @@ -1572,7 +1596,55 @@ describe("Staked Token", () => {
expect(afterData.votes, "staker votes after").to.eq(stakedAmount)

expect(await stakedToken.totalSupply(), "total staked after").to.eq(stakedAmount)
})
it("first exit", async () => {
await stakedToken.createLock(stakedAmount, ONE_WEEK.mul(20))
const stakeTimestamp = await getTimestamp()
await increaseTime(ONE_WEEK.mul(18))

const tx = await stakedToken.exit()

await expect(tx).to.emit(stakedToken, "Cooldown").withArgs(sa.default.address, cooldown100Percentage)

const startCooldownTimestamp = await getTimestamp()
const stakerDataAfter = await snapshotUserStakingData(sa.default.address)
expect(stakerDataAfter.cooldownTimestamp, "cooldown timestamp after").to.eq(startCooldownTimestamp)
expect(stakerDataAfter.cooldownPercentage, "cooldown percentage after").to.eq(cooldown100Percentage)
expect(stakerDataAfter.userBalances.raw, "staked raw balance after").to.eq(stakedAmount)
expect(stakerDataAfter.userBalances.weightedTimestamp, "weighted timestamp after").to.eq(stakeTimestamp)
expect(stakerDataAfter.userBalances.lastAction, "last action after").to.eq(startCooldownTimestamp)
expect(stakerDataAfter.userBalances.permMultiplier, "perm multiplier after").to.eq(0)
expect(stakerDataAfter.userBalances.seasonMultiplier, "season multiplier after").to.eq(0)
expect(stakerDataAfter.userBalances.timeMultiplier, "time multiplier after").to.eq(20)
expect(stakerDataAfter.userBalances.cooldownMultiplier, "cooldown multiplier after").to.eq(100)
expect(stakerDataAfter.stakedBalance, "staked balance after").to.eq(0)
expect(stakerDataAfter.votes, "votes after").to.eq(0)
})
it("second exit", async () => {
await stakedToken.createLock(stakedAmount, ONE_WEEK.mul(20))
await increaseTime(ONE_DAY.mul(1))
await stakedToken.exit()
await increaseTime(ONE_DAY.mul(8))

const tx = await stakedToken.exit()

const redemptionFee = stakedAmount.div(11).add(1)
await expect(tx).to.emit(stakedToken, "Withdraw").withArgs(sa.default.address, sa.default.address, stakedAmount)
await expect(tx)
.to.emit(rewardToken, "Transfer")
.withArgs(stakedToken.address, sa.default.address, stakedAmount.sub(redemptionFee))

const withdrawTimestamp = await getTimestamp()
const afterData = await snapshotUserStakingData(sa.default.address)
expect(afterData.stakedBalance, "staker stkRWD after").to.eq(0)
expect(afterData.votes, "staker votes after").to.eq(0)
expect(afterData.cooldownTimestamp, "staked cooldown start").to.eq(0)
expect(afterData.cooldownPercentage, "staked cooldown percentage").to.eq(0)
expect(afterData.userBalances.cooldownMultiplier, "cooldown multiplier after").to.eq(0)
expect(afterData.userBalances.raw, "staked raw balance after").to.eq(0)
// TODO expect(afterData.userBalances.weightedTimestamp, "weighted timestamp after").to.eq(withdrawTimestamp)
expect(afterData.userBalances.lastAction, "last action after").to.eq(withdrawTimestamp)
// TODO expect(afterData.rewardsBalance, "staker rewards after").to.eq(startingMintAmount.sub(redemptionFee))
})
})
context("interacting from a smart contract", () => {
Expand Down

0 comments on commit 08e9758

Please sign in to comment.