@indigo-labs/indigo-sdk
Version:
Indigo SDK for interacting with Indigo endpoints via lucid-evolution
49 lines (41 loc) • 2.33 kB
text/typescript
import { Constr, Data } from "@lucid-evolution/lucid";
import { InterestOracleDatum } from "../types/indigo/interest-oracle";
import { oneYear } from "../helpers/time-helpers";
const unitaryInterestPrecision = 1_000_000_000_000_000_000n;
const decimalUnit = 1_000_000n;
export class InterestOracleContract {
static decodeInterestOracleDatum(datum: string): InterestOracleDatum {
const oracleDatum = Data.from(datum) as any;
if (oracleDatum.index != 0 || oracleDatum.fields.length !== 3 || oracleDatum.fields[1].index !== 0)
throw 'Invalid Interest Oracle Datum provided.'
return {
unitaryInterest: oracleDatum.fields[0],
interestRate: oracleDatum.fields[1].fields[0],
lastUpdated: oracleDatum.fields[2],
}
}
static encodeInterestOracleDatum(datum: InterestOracleDatum): string {
return Data.to(
new Constr(0, [
datum.unitaryInterest,
new Constr(0, [datum.interestRate]),
datum.lastUpdated,
])
)
}
static calculateUnitaryInterestSinceOracleLastUpdated(now: bigint, oracleDatum: InterestOracleDatum): bigint {
return InterestOracleContract.calculateUnitaryInterest(now - oracleDatum.lastUpdated, oracleDatum.interestRate);
}
static calculateUnitaryInterest(timePeriod: bigint, interestRate: bigint): bigint {
return ((timePeriod * interestRate * unitaryInterestPrecision) / oneYear) / decimalUnit;
}
static calculateAccruedInterest(now: bigint, unitaryInterestSnapshot: bigint, mintedAmount: bigint, interestLastSettled: bigint, interestOracleDatum: InterestOracleDatum): bigint {
if (interestOracleDatum.unitaryInterest >= unitaryInterestSnapshot) {
const interestFromPreviousRates = ((interestOracleDatum.unitaryInterest - unitaryInterestSnapshot) * mintedAmount) / unitaryInterestPrecision;
const lastRateInterest = (((now - interestOracleDatum.lastUpdated) * interestOracleDatum.interestRate * mintedAmount) / oneYear) / decimalUnit;
return interestFromPreviousRates + lastRateInterest;
} else {
return (((now - interestLastSettled) * interestOracleDatum.interestRate * mintedAmount) / oneYear) / decimalUnit;
}
}
}