English 中文(简体)
How to set a timer in solidity?
原标题:

I am launching a game that should close after exactly 3 days/72 hours of initializing & deploying the contract.

My current thoughts are:

  1. declare a variable, timestamp.
  2. in the constructor, set the variable timestamp to block.timestamp
  3. add 3 days worth of time [in milliseconds i presume] to the timestamp variable
  4. do a require(block.timestamp < timestamp) in the game logic [users call a write function, so I can do it in there], so users cannot write the function if block.timestamp is past timestamp + 3 days

Is this is a feasible solution? Is there a better solution? Is there a more gas efficient solution?

Thanks in advance

问题回答

I just wrote this:

  // SPDX-License-Identifier: MIT

    pragma solidity 0.8.0;
    contract MyContract{
        uint start;
        uint end;
        modifier timeIsOver{
            require(block.timestamp<=end,"Time is up");
            _;
        }
         // Firstly, call this 
        function startTimer() public{
            start=block.timestamp;
        }
        // Secondly, call this 
        // timestamp of the current block in seconds since the epoch
        // period is in seconds
        function endTimer(uint period) public {
            end=period+start;
        }

        function timeLeft() public view returns(uint){
            return end-block.timestamp;
        }

        function callThisWhenTimeIsUp() external timeIsOver{
            // write the logic here
        }

    }

Or you could use oracle to set up timer. Oracle is external serice that you use in ethereum. an example: https://blog.chain.link/blockchain-voting-using-a-chainlink-alarm-clock-oracle/

// File: contracts/MyToken.sol

pragma solidity 0.8.16;


contract ICO {
    //Administration Details
    address public admin;
    address payable public ICOWallet;

    //Token
    IERC20 public token;

    //ICO Details
    uint public tokenPrice = 0.000000001 ether;
    uint public hardCap = 8 ether;
    uint public raisedAmount;
    uint public minInvestment = 0.005 ether;
    uint public maxInvestment = 1 ether;
    uint public icoStartTime;
    uint public icoEndTime;

    //Investor
    mapping(address => uint) public investedAmountOf;

    //ICO State
    enum State {
        BEFORE,
        RUNNING,
        END,
        HALTED
    }
    State public ICOState;

    //Events
    event Invest(
        address indexed from,
        address indexed to,
        uint value,
        uint tokens
    );
    event TokenBurn(address to, uint amount, uint time);

    //Initialize Variables
    constructor(address payable _icoWallet, address _token) {
        admin = msg.sender;
        ICOWallet = _icoWallet;
        token = IERC20(_token);
    }

    //Access Control
    modifier onlyAdmin() {
        require(msg.sender == admin, "Admin Only function");
        _;
    }

    //Receive Ether Directly
    receive() external payable {
        invest();
    }

    fallback() external payable {
        invest();
    }

    /* Functions */

    //Get ICO State
    function getICOState() external view returns (string memory) {
        if (ICOState == State.BEFORE) {
            return "Not Started";
        } else if (ICOState == State.RUNNING) {
            return "Running";
        } else if (ICOState == State.END) {
            return "End";
        } else {
            return "Halted";
        }
    }

    /* Admin Functions */

    //Start, Halt and End ICO
    function startICO() external onlyAdmin {
        require(ICOState == State.BEFORE, "ICO isn t in before state");

        icoStartTime = block.timestamp;
        icoEndTime = icoStartTime + (2 weeks);
        ICOState = State.RUNNING;
    }

    function haltICO() external onlyAdmin {
        require(ICOState == State.RUNNING, "ICO isn t running yet");
        ICOState = State.HALTED;
    }

    function resumeICO() external onlyAdmin {
        require(ICOState == State.HALTED, "ICO State isn t halted yet");
        ICOState = State.RUNNING;
    }

    //Change ICO Wallet
    function changeICOWallet(address payable _newICOWallet) external onlyAdmin {
        ICOWallet = _newICOWallet;
    }

    //Change Admin
    function changeAdmin(address _newAdmin) external onlyAdmin {
        admin = _newAdmin;
    }

    /* User Function */
    
    //Invest
    function invest() public payable returns (bool) {
        require(ICOState == State.RUNNING, "ICO isn t running");
        require(
            msg.value >= minInvestment && msg.value <= maxInvestment,
            "Check Min and Max Investment"
        );
        require(
            investedAmountOf[msg.sender] + msg.value <= maxInvestment,
            "Investor reached maximum Investment Amount"
        );

        require(
            raisedAmount + msg.value <= hardCap,
            "Send within hardcap range"
        );
        require(
            block.timestamp <= icoEndTime,
            "ICO already Reached Maximum time limit"
        );

        raisedAmount += msg.value;
        investedAmountOf[msg.sender] += msg.value;

        (bool transferSuccess, ) = ICOWallet.call{value: msg.value}("");
        require(transferSuccess, "Failed to Invest");

        uint tokens = (msg.value / tokenPrice) * 1e18;
        bool saleSuccess = token.transfer(msg.sender, tokens);
        require(saleSuccess, "Failed to Invest");

        emit Invest(address(this), msg.sender, msg.value, tokens);
        return true;
    }

    //Burn Tokens
    function burn() external returns (bool) {
        require(ICOState == State.END, "ICO isn t over yet");

        uint remainingTokens = token.balanceOf(address(this));
        bool success = token.transfer(address(0), remainingTokens);
        require(success, "Failed to burn remaining tokens");

        emit TokenBurn(address(0), remainingTokens, block.timestamp);
        return true;
    }

    //End ICO After reaching Hardcap or ICO Timelimit
    function endIco() public {
        require(ICOState == State.RUNNING, "ICO Should be in Running State");
        require(
            block.timestamp > icoEndTime || raisedAmount >= hardCap,
            "ICO Hardcap or timelimit not reached"
        );
        ICOState = State.END;
    }

    //Check ICO Contract Token Balance
    function getICOTokenBalance() external view returns (uint) {
        return token.balanceOf(address(this));
    }

    //Check ICO Contract Investor Token Balance
    function investorBalanceOf(address _investor) external view returns (uint) {
        return token.balanceOf(_investor);
    }
}

I just posted an ICO Contract with a 2 week timer as an example of using and changing states w/ a timer. Hope this helps!





相关问题
unable to get data from blockchain using thirdweb

I am building a simple crowdfunding app using React and thirdweb , I was able to successfully create a Campaign mean data is pushed successfully , I have read docs everything works fine , but when i ...

How named accounts works in NEAR

It appears that named accounts in NEAR are being managed by the near and register smart contracts. However, this raises the question of whether NEAR natively supports named accounts. it s unclear if ...

ETH sendSignedTransaction

I Try to use @ethereumjs/tx to sign Transaction. I want to send ETH from one address to second address. .... const legacy = require( @ethereumjs/tx/dist/legacyTransaction ); const utils = require( ...

How to set a timer in solidity?

I am launching a game that should close after exactly 3 days/72 hours of initializing & deploying the contract. My current thoughts are: declare a variable, timestamp. in the constructor, set the ...

"code": -32000, "message": "execution reverted"

Hello I am trying to deploy a contract using remix.ethereum.org after linked the metamask account using mumbai network. I receive this error while making the transaction for the contract Gas ...

How to get all accounts from near protocol blockchain?

I am currently working on a program within the Near Protocol to generate user-specific Near token ownership statistics. However, I m not sure how to obtain a list of all user accounts. Is there an ...

热门标签