Robinhood MainnetChain ID: 4663
Contract detail

ChainGreetsGN

ChainGreetsGN is a verified Robinhood Chain smart contract at 0xac392810…76ffb6db with 528 indexed transactions.

Address type
Smart contract
Transactions
528
First indexed block
#879568
Latest indexed block
#92699305
ERC-20 transfers
3
Emitted events
525
Verification
Verified
Compiler
v0.8.34+commit.80d5c536
Verification match
partial
Creation transaction
0x49e1e5aa…d611b922
Created at block
#879568
Language
solidity
EVM version
cancun
License
mit
Compiler optimization
Enabled · 200 runs
Related activity

Transactions

Verified contract

Contract source code

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.28;

contract ChainGreetsGN {
    address public owner;
    address payable public constant COLLECTOR = payable(0xcA96369a4D186887c88867d3bA9239DD679f1547);

    // 0.00000123 ETH = 1,230,000,000,000 wei (~0.002$)
    uint256 public feeWei = 1230000000000;

    bool public paused;
    bool private locked;

    mapping(address => uint256) public lastGnDay;

    event GN(
        address indexed sender,
        uint256 indexed dayIndex,
        uint256 timestamp,
        uint256 feePaid
    );
    event Paused(address indexed by);
    event Unpaused(address indexed by);
    event FeeUpdated(uint256 oldFeeWei, uint256 newFeeWei);
    event OwnershipTransferred(address indexed oldOwner, address indexed newOwner);
    event RescueETH(address indexed to, uint256 amount);

    error NotOwner();
    error ContractPaused();
    error IncorrectFee(uint256 expected, uint256 received);
    error AlreadyGreetedToday(address sender, uint256 dayIndex);
    error InvalidOwner();
    error ReentrancyBlocked();
    error EthTransferFailed();
    error DirectPaymentsDisabled();
    error InvalidRecipient();
    error InvalidAmount();

    modifier onlyOwner() {
        if (msg.sender != owner) revert NotOwner();
        _;
    }
    modifier whenNotPaused() {
        if (paused) revert ContractPaused();
        _;
    }
    modifier nonReentrant() {
        if (locked) revert ReentrancyBlocked();
        locked = true;
        _;
        locked = false;
    }

    constructor() {
        owner = msg.sender;
    }

    function currentDay() public view returns (uint256) {
        return block.timestamp / 86400;
    }

    function canGn(address user) public view returns (bool) {
        return lastGnDay[user] < currentDay();
    }

    function secondsUntilNextReset() public view returns (uint256) {
        return 86400 - (block.timestamp % 86400);
    }

    function gn() external payable whenNotPaused nonReentrant {
        uint256 dayIndex = currentDay();
        if (lastGnDay[msg.sender] >= dayIndex) {
            revert AlreadyGreetedToday(msg.sender, dayIndex);
        }
        if (msg.value != feeWei) {
            revert IncorrectFee(feeWei, msg.value);
        }
        lastGnDay[msg.sender] = dayIndex;

        (bool sent, ) = COLLECTOR.call{value: msg.value}("");
        if (!sent) revert EthTransferFailed();

        emit GN(msg.sender, dayIndex, block.timestamp, msg.value);
    }

    function pause() external onlyOwner {
        paused = true;
        emit Paused(msg.sender);
    }

    function unpause() external onlyOwner {
        paused = false;
        emit Unpaused(msg.sender);
    }

    function setFeeWei(uint256 newFeeWei) external onlyOwner {
        uint256 oldFeeWei = feeWei;
        feeWei = newFeeWei;
        emit FeeUpdated(oldFeeWei, newFeeWei);
    }

    function transferOwnership(address newOwner) external onlyOwner {
        if (newOwner == address(0)) revert InvalidOwner();
        address oldOwner = owner;
        owner = newOwner;
        emit OwnershipTransferred(oldOwner, newOwner);
    }

    function rescueETH(address payable to, uint256 amount) external onlyOwner nonReentrant {
        if (to == address(0)) revert InvalidRecipient();
        if (amount == 0) revert InvalidAmount();
        (bool sent, ) = to.call{value: amount}("");
        if (!sent) revert EthTransferFailed();
        emit RescueETH(to, amount);
    }

    receive() external payable {
        revert DirectPaymentsDisabled();
    }
}