pragma solidity ^0.5.16; import "./SafeMath.sol"; contract NikiTreasuryVester { using SafeMath for uint; address public niki; address public recipient; uint public vestingAmount; uint public vestingBegin; uint public vestingCliff; uint public vestingEnd; uint public lastUpdate; constructor( address niki_, address recipient_, uint vestingAmount_, uint vestingBegin_, uint vestingCliff_, uint vestingEnd_ ) public { require(vestingBegin_ >= block.timestamp, 'EliteTreasuryVester::constructor: vesting begin too early'); require(vestingCliff_ >= vestingBegin_, 'EliteTreasuryVester::constructor: cliff is too early'); require(vestingEnd_ > vestingCliff_, 'EliteTreasuryVester::constructor: end is too early'); niki = niki_; recipient = recipient_; vestingAmount = vestingAmount_; vestingBegin = vestingBegin_; vestingCliff = vestingCliff_; vestingEnd = vestingEnd_; lastUpdate = vestingBegin; } function setRecipient(address recipient_) public { require(msg.sender == recipient, 'EliteTreasuryVester::setRecipient: unauthorized'); recipient = recipient_; } function claim() public { require(block.timestamp >= vestingCliff, 'EliteTreasuryVester::claim: not time yet'); uint amount; if (block.timestamp >= vestingEnd) { amount = INiki(niki).balanceOf(address(this)); } else { amount = vestingAmount.mul(block.timestamp - lastUpdate).div(vestingEnd - vestingBegin); lastUpdate = block.timestamp; } INiki(niki).transfer(recipient, amount); } } interface INiki { function balanceOf(address account) external view returns (uint); function transfer(address dst, uint rawAmount) external returns (bool); }