Principal Token

The Principal Token is the main contract of Spectra. It is EIP 5095, and 2612 compliant.

Users deposit the IBT (or underlying token of the IBT) and receive the Principal Token (PT) and the Yield Token (YT) in return. For example, user deposits aDAI (or DAI) and receives the PT and YT of the aDAI position with a certain expiry.

The user can also withdraw and redeem after and before expiry. For more information, see the Tokenising Yield guide.

Code for PrincipalToken.sol can be found on GitHub.

Methods

deposit

function deposit(
    uint256 assets,
    address receiver
) public returns (uint256 shares)

Deposits the amount of the underlying assets (e.g. DAI or USDC etc) and mints an amount of shares (i.e. Principal Tokens) and Yield Tokens for the receiver.

msg.sender must approve the relevant allowance of the underlying asset before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

assets

uint256

The amount of the underlying assets to deposit.

See also asset()

receiver

address

The address that will receive the minted PT and YT. Note: This can be different from msg.sender if depositing on behalf of another address.

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

deposit

function deposit(
        uint256 assets,
        address ptReceiver,
        address ytReceiver
) external returns (uint256 shares);

Deposits amount of assets in the PT vault specifying the PT receiver (ptReceiver) and the YT receiver (ytReceiver).

msg.sender must approve the relevant allowance of the underlying asset before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

assets

uint256

The amount of the underlying assets to deposit.

See also asset()

ptReceiver

address

The address that will receive the minted PT Note: This can be different from msg.sender if depositing on behalf of another address.

ytReceiver

address

The address that will receive the minted YT Note: This can be different from msg.sender if depositing on behalf of another address.

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

deposit

function deposit(
    uint256 assets,
    address ptReceiver,
    address ytReceiver,
    uint256 minShares
) external returns (uint256 shares);

Deposits amount of assets with a lower bound on shares received (minShares).

msg.sender must approve the relevant allowance of the underlying asset before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

assets

uint256

The amount of the underlying assets to deposit.

See also asset()

ptReceiver

address

The address that will receive the minted PT Note: This can be different from msg.sender if depositing on behalf of another address.

ytReceiver

address

The address that will receive the minted YT Note: This can be different from msg.sender if depositing on behalf of another address.

minShares

uint256

The minimum amount of shares the caller expect to receive from the posit

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

depositIBT

function depositIBT(
    uint256 ibts,
    address receiver
) public returns (uint256 shares)

Deposits the ibts of the Interest Bearing Token (e.g. aDAI or aUSDC etc) and mints an amount of shares (i.e. Principal Tokens) and Yield Tokens for the receiver.

msg.sender must approve the relevant allowance of the IBT before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

ibts

uint256

The amount of the PrincipalToken's IBT assets to deposit.

See also getIBT()

receiver

address

The address that will receive the minted PT and YT. Note: This can be different from msg.sender if depositing on behalf of another address.

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

depositIBT

function depositIBT(
        uint256 ibts,
        address ptReceiver,
        address ytReceiver
) external returns (uint256 shares);

Deposits the ibts of the Interest Bearing Token (e.g. aDAI or aUSDC etc) and mints an amount of shares (i.e. Principal Tokens) for the ptReceiver and Yield Tokens for the ytReceiver.

msg.sender must approve the relevant allowance of the IBT before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

ibts

uint256

The amount of the PrincipalToken's IBT assets to deposit.

See also getIBT()

ptReceiver

address

The address that will receive the minted PT Note: This can be different from msg.sender if depositing on behalf of another address.

ytReceiver

address

The address that will receive the minted YT Note: This can be different from msg.sender if depositing on behalf of another address.

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

depositIBT

function depositIBT(
        uint256 ibts,
        address ptReceiver,
        address ytReceiver,
        uint256 minShares
) external returns (uint256 shares);

Deposits the ibts of the Interest Bearing Token (e.g. aDAI or aUSDC etc) and mints an amount of shares (i.e. Principal Tokens) for the ptReceiver and Yield Tokens for the ytReceiver.

msg.sender must approve the relevant allowance of the IBT before calling this method.

deposit must be called before the expiry of the Principal Token.

Input ParameterTypeDescription

ibts

uint256

The amount of the PrincipalToken's IBT assets to deposit.

See also getIBT()

ptReceiver

address

The address that will receive the minted PT Note: This can be different from msg.sender if depositing on behalf of another address.

ytReceiver

address

The address that will receive the minted YT Note: This can be different from msg.sender if depositing on behalf of another address.

minShares

uint256

The minimum amount of shares the caller expect to receive from the posit

Return ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) and Yield Tokens that were minted for the receiver.

redeem

function redeem(
    uint256 shares,
    address receiver,
    address owner
) returns (uint256 assets)

Redeems (by burning tokens) the amount of shares (i.e. Principal Tokens) from owner, redeeming an amount of assets of the underlying asset.

The first caller to Redeem after expiry will make an implicit call to StoreRatesAtExpiry()to store the rates after expiry. This is done only once for all.

Input ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) that the user wants to redeem/burn.

receiver

address

The address that will receive the redeemed assets.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be redeemed. This must be the same as msg.sender.

Return ParameterTypeDescription

assets

uint256

The amount of underlying assets that are redeemed.

Conforms to ERC-5095 standards.

redeem

function redeem(
        uint256 shares,
        address receiver,
        address owner,
        uint256 minAssets
) external returns (uint256 assets);

Redeems (by burning tokens) the amount of shares (i.e. Principal Tokens) from owner, redeeming an amount of assets of the underlying asset, while also specifying the minimum asset (minAssets) amount that the caller expects the receiver to receive.

I.e. converts PT to the underlying asset, using the number of PT to burn, after expiry.

The first caller to Redeem after expiry will make an implicit call to StoreRatesAtExpiry()to store the rates after expiry. This is done only once for all.

Input ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) that the user wants to redeem/burn.

receiver

address

The address that will receive the redeemed assets.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be redeemed. This must be the same as msg.sender.

minAssets

uint256

The minimum asset amount that the caller expects the receiver to receive.

Return ParameterTypeDescription

assets

uint256

The amount of underlying assets that are redeemed.

redeemForIBT

function redeemForIBT(
    uint256 shares,
    address receiver,
    address owner
) returns (uint256 ibts)

Redeems (by burning tokens) the amount of shares (i.e. Principal Tokens) from owner, redeeming an amount of ibts of the IBT.

The first caller to Redeem after expiry will make an implicit call to StoreRatesAtExpiry()to store the rates after expiry. This is done only once for all.

Input ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) that the user wants to redeem/burn.

receiver

address

The address that will receive the redeemed tokens.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be redeemed. This must be the same as msg.sender.

Return ParameterTypeDescription

ibts

uint256

The amount of IBTs that are redeemed.

redeemForIBT

function redeemForIBT(
        uint256 shares,
        address receiver,
        address owner,
        uint256 minIbts
) external returns (uint256 ibts);

Redeems (by burning tokens) the amount of shares (i.e. Principal Tokens) from owner, redeeming an amount of ibts of the IBT, while also specifying the minimum asset (minIbts) amount that the caller expects the receiver to receive.

The first caller to Redeem after expiry will make an implicit call to StoreRatesAtExpiry()to store the rates after expiry. This is done only once for all.

Input ParameterTypeDescription

shares

uint256

The amount of shares (i.e. Principal Tokens) that the user wants to redeem/burn.

receiver

address

The address that will receive the redeemed tokens.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be redeemed. This must be the same as msg.sender.

minIbts

uint256

The minimum asset amount that the caller expects the receiver to receive.

Return ParameterTypeDescription

ibts

uint256

The amount of IBTs that are redeemed.

withdraw

function withdraw(
    uint256 assets,
    address receiver,
    address owner
) returns (uint256 shares)

Withdraws the amount of underlying assets of a position of owner, withdrawing those assets to receiver. This is done by burning shares (i.e. Principal Tokens) and remaining Yield Tokens of owner.

Input ParameterTypeDescription

assets

uint256

The amount of assets that the user wants to withdraw.

receiver

address

The address that will receive the redeemed assets.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be withdrawn/burned. This must be the same as msg.sender.

Return ParameterTypeDescription

shares

uint256

The amount of the owner shares (i.e. Principal Tokens) that were burned from the withdrawal.

Conforms to ERC-5095 standards.

withdraw

function withdraw(
        uint256 assets,
        address receiver,
        address owner,
        uint256 maxShares
) external returns (uint256 shares)

Withdraws the amount of underlying assets of a position of owner, withdrawing those assets to receiver. This is done by burning shares (i.e. Principal Tokens) and remaining Yield Tokens of owner, while specifying the maximum amount (maxShares) of shares to withdraw.

I.e. converts PT and YT to the underlying asset, using the number of underlying assets to withdraw, before expiry.

Input ParameterTypeDescription

assets

uint256

The amount of assets that the user wants to withdraw.

receiver

address

The address that will receive the redeemed assets.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be withdrawn/burned. This must be the same as msg.sender.

maxShares

uint256

The maximum amount of shares allowed to be burnt

Return ParameterTypeDescription

shares

uint256

The amount of the owner shares (i.e. Principal Tokens) that were burned from the withdrawal.

withdrawIBT

function withdrawIBT(
    uint256 ibts,
    address receiver,
    address owner
) returns (uint256 shares)

Withdraws the amount of IBTs of a position of owner, withdrawing those ibts to receiver. This is done by burning shares (i.e. Principal Tokens) and remaining Yield Tokens of owner.

Input ParameterTypeDescription

ibts

uint256

The amount of IBTs that the user wants to withdraw.

receiver

address

The address that will receive the withdrawn tokens.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be withdrawn/burned. This must be the same as msg.sender.

Return ParameterTypeDescription

shares

uint256

The amount of the owner shares (i.e. Principal Tokens) that were burned from the withdrawal.

withdrawIBT

function withdrawIBT(
        uint256 ibts,
        address receiver,
        address owner,
        uint256 maxShares
) external returns (uint256 shares)

Withdraws the amount of IBTs of a position of owner, withdrawing those ibts to receiver. This is done by burning shares (i.e. Principal Tokens) and remaining Yield Tokens of owner, while specifying the maximum amount (maxShares) of shares to withdraw.

Input ParameterTypeDescription

ibts

uint256

The amount of IBTs that the user wants to withdraw.

receiver

address

The address that will receive the withdrawn tokens.

owner

address

The address of the owner of the shares (i.e. Principal Tokens) that are to be withdrawn/burned. This must be the same as msg.sender.

maxShares

uint256

The maximum amount of shares allowed to be burnt

Return ParameterTypeDescription

shares

uint256

The amount of the owner shares (i.e. Principal Tokens) that were burned from the withdrawal.

claimYield

function claimYield(address _receiver) public returns (uint256)

Claims the yield of msg.sender based on their current balance of YT. Send the yield as underlying tokens.

Input ParameterTypeDescription

_receiver

address

The address that will receive the yield.

Return ParameterTypeDescription

yieldInAsset

uint256

The amount of yield claimed in the underlying asset.

claimYieldInIBT

function claimYieldInIBT(address _receiver) public returns (uint256)

Claims the yield of msg.sender based on their current balance of YT. Send the yield as IBT tokens.

Input ParameterTypeDescription

_receiver

address

The address that will receive the yield.

Return ParameterTypeDescription

yieldInIBT

uint256

The amount of yield claimed (in IBT).

updateYield

function updateYield(address _user) external returns (uint256 updatedUserYieldInRay)

Updates _user yield with the latest yield in IBT generated since the previous update.

This method should not be used by users. This method is called implicitely before each action to deposit, redeem, withdraw and sending receiving YT tokens.

Input ParameterTypeDescription

_user

address

The address of the user to compute the yield

Return ParameterTypeDescription

updatedUserYieldInRay

uint256

The unclaimed yield (amount of IBT tokens) of the _user in Ray decimals. The user can get this yield by calling claimYield() .

flashLoan

function flashLoan(
        IERC3156FlashBorrower _receiver,
        address _token,
        uint256 _amount,
        bytes calldata _data
    ) external override returns (bool)

The flashLoan method is used to swap PT for YT tokens by borrowing the IBT of the PT contract to swap PT for YTs.

The transaction reverts if the trade is not profitable and the borrower is unable to repay the loan.

Input ParameterTypeDescription

_receiver

IERC3156FlashBorrower

The receiver of the tokens in the loan, and the receiver of the callback.

_token

address

The loan currency.

_amount

uint256

The amount of tokens lent.

_data

bytes calldata

Arbitrary data structure, intended to contain user-defined parameters.

Return ParameterTypeDescription

bool

If successful, flashLoan return true.

Conforms to EIP-3156 standards.

StoreRatesAtExpiry

Store the rates at the time of expiry.

This can only be called after expiry/maturity of the position.

function storeRatesAtExpiry() external

View Methods

previewDeposit

function previewDeposit(uint256 assets) public view returns (uint256)

Calculates the amount of shares (i.e. Principal Tokens) and Yield Tokens that would be minted for depositing amount of assets.Only available if position is not expired/reached maturity.

maxDeposit

function maxDeposit(address) public view returns (uint256)

This function returns the maximum amount of underlying assets that can be deposited in a single deposit call by the receiver.

previewDepositIBT

function previewDepositIBT(uint256 ibts) public view returns (uint256)

Calculates the amount of shares (i.e. Principal Tokens) and Yield Tokens that would be minted for depositing amount of ibts.Only available if position is not expired/reached maturity.

previewWithdraw

function previewWithdraw(uint256 assets) public view returns (uint256)

Calculates the amount of shares (i.e. Principal Tokens) that would be burned for withdrawing an amount of assets.

Conforms to ERC-5095 standards.

previewWithdrawIBT

function previewWithdrawInIBT(uint256 ibts) public view returns (uint256)

Calculates the amount of shares (i.e. Principal Tokens) that would be burned for withdrawing an amount of ibts.

maxWithdraw

function maxWithdraw(address owner) public returns (uint256)

Calculates the maximum amount of underlying assets that can withdrawn by the owner.

Conforms to ERC-5095 standards.

maxWithdrawIBT

function maxWithdraw(address owner) public returns (uint256)

Calculates the maximum amount of IBTs that can withdrawn by the owner.

previewRedeem

function previewRedeem(uint256 shares) public view returns (uint256)

Calculates the amount of assets that would be redeemed for an amount of shares (i.e. Principal Tokens).

Conforms to ERC-5095 standards.

previewRedeemForIBT

function previewRedeemForIBT(uint256 shares) public view returns (uint256)

Calculates the amount of IBTs that would be redeemed for an amount of shares (i.e. Principal Tokens).

maxRedeem

function maxRedeem(address owner) public view returns (uint256)

Calculations the maximum amount of shares (i.e. Principal Tokens) that the owner can currently redeem/burn.

Conforms to ERC-5095 standards.

convertToPrincipal

function convertToPrincipal(uint256 underlyingAmount) public view returns (uint256 principalAmount)

Calculates the amount of principal tokens that are equivalent to the amount of underlyingAmount.

Conforms to EIP-5095 standard.

convertToUnderlying

function convertToUnderlying(uint256 principalAmount) public view returns (uint256)

Same as convertToAssets().

Conforms to ERC-5095 standard.

underlying

function underlying() public view virtual override returns (address)

Returns the address of the underlying ERC20 or ERC777 asset.

E.g. if the IBT is aDAI, then the asset is DAI. If the IBT is cUSDC, then the asset is USDC.

Conforms to ERC-5095 standard.

totalAssets

function totalAssets() public view virtual override returns (uint256)

Returns the total balance of the underlying assets in the Principal Token. Useful for TVL calculations.

decimals

function decimals() public view returns (uint8)

Returns the decimals of the IBT.

maturity

function maturity() public view returns (uint256)

Returns the expiry/maturity of the position in unix timestamp, at or after which the Principal Tokens can be redeemed for their underlying asset.

Conforms to ERC-5095 standard.

getDuration

function getDuration() public view returns (uint256)

Returns the total duration of the principal token period in seconds.

getIBT

function getIBT() public view returns (address)

Returns the address of the IBT (Interest Bearing Token).

E.g. if the underlying asset is DAI, the IBT could be aDAI (for Aave deposited DAI) or cDAI (for Compound deposited DAI), etc.

getYT

function getYT() public view returns (address)

Returns the address of the YT (Yield Token).

getIBTRate

function getIBTRate() public view returns (uint256)

Returns the ibtRate.

getPTRate

function getPTRate() public view returns (uint256)

Returns the ptRate.

getIBTUnit

function getIBTUnit() public view returns (uint256)

Returns the number used for one unit (10^decimals) of the IBT.

getAssetUnit

function getAssetUnit() public view returns (uint256)

Returns the number used for one unit (10^decimals) of the asset.

getIBTRateAtExpiry

function getIBTRateAtExpiry() public view returns (uint256)

Returns the IBT rate at expiry. Only valid after maturity.

getPTRateAtExpiry

function getPTRateAtExpiry() public view returns (uint256)

Returns the PT rate at expiry. Only valid after maturity.

getCurrentYieldOfUserInIBT

function getCurrentYieldOfUserInIBT(address _user) public view returns (uint256 _yieldOfUserInIBT)

Returns the yield of _user in IBT tokens.

Internal Methods

_computeYield

function _computeYield(
    address _user,
    uint256 _oldIBTRate,
    uint256 _ibtRate,
    uint256 _oldPTRate,
    uint256 _ptRate
) internal view returns (uint256)

Computes the yield generated by a user given old and new rates. For more information, see the Yield Calculations page.

Last updated