Skip to content

Token Rate Limit System

The token rate limit system is used to control the frequency and quantity of token transactions. This tutorial will explain how to implement a secure and reliable rate limit system.

Features

  • Rate limit management
  • Frequency control
  • Quantity restriction
  • Permission management
  • Emergency handling

Contract Implementation

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

import "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import "@openzeppelin/contracts/access/Ownable.sol";
import "@openzeppelin/contracts/security/ReentrancyGuard.sol";
import "@openzeppelin/contracts/security/Pausable.sol";
import "@openzeppelin/contracts/utils/math/SafeMath.sol";

/**
 * @title TokenRateLimit
 * @dev Token rate limit contract implementation
 */
contract TokenRateLimit is Ownable, ReentrancyGuard, Pausable {
    using SafeMath for uint256;

    // Rate limit information
    struct RateLimitInfo {
        uint256 interval;       // Time interval
        uint256 maxAmount;      // Maximum amount
        uint256 maxTimes;       // Maximum times
        bool isActive;          // Whether active
    }

    // User information
    struct UserInfo {
        uint256 lastTime;       // Last time
        uint256 totalAmount;    // Total amount
        uint256 totalTimes;     // Total times
        bool isProcessing;      // Whether processing
    }

    // Configuration information
    struct RateLimitConfig {
        uint256 defaultInterval; // Default interval
        uint256 defaultAmount;   // Default amount
        uint256 defaultTimes;    // Default times
        bool requiresApproval;   // Whether approval required
        bool isActive;           // Whether active
    }

    // State variables
    mapping(address => mapping(address => RateLimitInfo)) public rateLimits;  // Rate limits
    mapping(address => mapping(address => UserInfo)) public userInfos;        // User information
    mapping(address => bool) public operators;                                // Operators
    mapping(address => bool) public exemptAddresses;                         // Exempt addresses
    RateLimitConfig public config;                                           // Configuration

    // Events
    event RateLimitUpdated(address indexed token, address indexed account, uint256 interval, uint256 maxAmount, uint256 maxTimes);
    event TransactionLimited(address indexed token, address indexed from, address indexed to, uint256 amount);
    event OperatorUpdated(address indexed operator, bool status);
    event ExemptAddressUpdated(address indexed account, bool status);
    event ConfigUpdated(uint256 defaultInterval, uint256 defaultAmount, uint256 defaultTimes);

    /**
     * @dev Constructor
     */
    constructor(
        uint256 _defaultInterval,
        uint256 _defaultAmount,
        uint256 _defaultTimes
    ) {
        config = RateLimitConfig({
            defaultInterval: _defaultInterval,
            defaultAmount: _defaultAmount,
            defaultTimes: _defaultTimes,
            requiresApproval: true,
            isActive: true
        });
    }

    /**
     * @dev Set rate limit
     */
    function setRateLimit(
        address _token,
        address _account,
        uint256 _interval,
        uint256 _maxAmount,
        uint256 _maxTimes
    ) external onlyOperator whenNotPaused {
        require(_token != address(0), "Invalid token");
        require(_account != address(0), "Invalid account");
        require(_interval > 0, "Invalid interval");
        require(_maxAmount > 0, "Invalid amount");
        require(_maxTimes > 0, "Invalid times");

        rateLimits[_token][_account] = RateLimitInfo({
            interval: _interval,
            maxAmount: _maxAmount,
            maxTimes: _maxTimes,
            isActive: true
        });

        emit RateLimitUpdated(_token, _account, _interval, _maxAmount, _maxTimes);
    }

    /**
     * @dev Check rate limit
     */
    function checkRateLimit(
        address _token,
        address _from,
        address _to,
        uint256 _amount
    ) public view returns (bool) {
        if (!config.isActive) {
            return true;
        }

        if (exemptAddresses[_from] || exemptAddresses[_to]) {
            return true;
        }

        RateLimitInfo storage rateLimit = rateLimits[_token][_from];
        if (!rateLimit.isActive) {
            rateLimit = RateLimitInfo({
                interval: config.defaultInterval,
                maxAmount: config.defaultAmount,
                maxTimes: config.defaultTimes,
                isActive: true
            });
        }

        UserInfo storage userInfo = userInfos[_token][_from];
        
        // Check time interval
        if (block.timestamp < userInfo.lastTime.add(rateLimit.interval)) {
            return false;
        }

        // Check amount limit
        if (userInfo.totalAmount.add(_amount) > rateLimit.maxAmount) {
            return false;
        }

        // Check times limit
        if (userInfo.totalTimes.add(1) > rateLimit.maxTimes) {
            return false;
        }

        return true;
    }

    /**
     * @dev Update user information
     */
    function updateUserInfo(
        address _token,
        address _from,
        uint256 _amount
    ) external onlyOperator whenNotPaused {
        require(_token != address(0), "Invalid token");
        require(_from != address(0), "Invalid from");
        require(_amount > 0, "Invalid amount");

        UserInfo storage userInfo = userInfos[_token][_from];
        RateLimitInfo storage rateLimit = rateLimits[_token][_from];

        // Check if reset needed
        if (block.timestamp >= userInfo.lastTime.add(rateLimit.interval)) {
            userInfo.totalAmount = 0;
            userInfo.totalTimes = 0;
        }

        userInfo.lastTime = block.timestamp;
        userInfo.totalAmount = userInfo.totalAmount.add(_amount);
        userInfo.totalTimes = userInfo.totalTimes.add(1);
    }

    /**
     * @dev Batch set rate limit
     */
    function batchSetRateLimit(
        address _token,
        address[] calldata _accounts,
        uint256[] calldata _intervals,
        uint256[] calldata _maxAmounts,
        uint256[] calldata _maxTimes
    ) external onlyOperator whenNotPaused {
        require(
            _accounts.length == _intervals.length &&
            _accounts.length == _maxAmounts.length &&
            _accounts.length == _maxTimes.length,
            "Length mismatch"
        );

        for (uint256 i = 0; i < _accounts.length; i++) {
            require(_accounts[i] != address(0), "Invalid account");
            require(_intervals[i] > 0, "Invalid interval");
            require(_maxAmounts[i] > 0, "Invalid amount");
            require(_maxTimes[i] > 0, "Invalid times");

            rateLimits[_token][_accounts[i]] = RateLimitInfo({
                interval: _intervals[i],
                maxAmount: _maxAmounts[i],
                maxTimes: _maxTimes[i],
                isActive: true
            });

            emit RateLimitUpdated(_token, _accounts[i], _intervals[i], _maxAmounts[i], _maxTimes[i]);
        }
    }

    /**
     * @dev Get rate limit information
     */
    function getRateLimitInfo(
        address _token,
        address _account
    ) external view returns (
        uint256 interval,
        uint256 maxAmount,
        uint256 maxTimes,
        bool isActive
    ) {
        RateLimitInfo storage rateLimit = rateLimits[_token][_account];
        return (
            rateLimit.interval,
            rateLimit.maxAmount,
            rateLimit.maxTimes,
            rateLimit.isActive
        );
    }

    /**
     * @dev Get user information
     */
    function getUserInfo(
        address _token,
        address _account
    ) external view returns (
        uint256 lastTime,
        uint256 totalAmount,
        uint256 totalTimes,
        bool isProcessing
    ) {
        UserInfo storage userInfo = userInfos[_token][_account];
        return (
            userInfo.lastTime,
            userInfo.totalAmount,
            userInfo.totalTimes,
            userInfo.isProcessing
        );
    }

    /**
     * @dev Set operator
     */
    function setOperator(
        address _operator,
        bool _status
    ) external onlyOwner {
        require(_operator != address(0), "Invalid operator");
        operators[_operator] = _status;
        emit OperatorUpdated(_operator, _status);
    }

    /**
     * @dev Set exempt address
     */
    function setExemptAddress(
        address _account,
        bool _status
    ) external onlyOwner {
        require(_account != address(0), "Invalid account");
        exemptAddresses[_account] = _status;
        emit ExemptAddressUpdated(_account, _status);
    }

    /**
     * @dev Update configuration
     */
    function updateConfig(
        uint256 _defaultInterval,
        uint256 _defaultAmount,
        uint256 _defaultTimes,
        bool _requiresApproval
    ) external onlyOwner {
        require(_defaultInterval > 0, "Invalid interval");
        require(_defaultAmount > 0, "Invalid amount");
        require(_defaultTimes > 0, "Invalid times");
        
        config.defaultInterval = _defaultInterval;
        config.defaultAmount = _defaultAmount;
        config.defaultTimes = _defaultTimes;
        config.requiresApproval = _requiresApproval;
        
        emit ConfigUpdated(_defaultInterval, _defaultAmount, _defaultTimes);
    }

    /**
     * @dev Pause contract
     */
    function pause() external onlyOwner {
        _pause();
    }

    /**
     * @dev Unpause contract
     */
    function unpause() external onlyOwner {
        _unpause();
    }

    /**
     * @dev Reset user information
     */
    function resetUserInfo(
        address _token,
        address _account
    ) external onlyOperator whenNotPaused {
        require(_token != address(0), "Invalid token");
        require(_account != address(0), "Invalid account");
        
        delete userInfos[_token][_account];
    }

    /**
     * @dev Operator modifier
     */
    modifier onlyOperator() {
        require(operators[msg.sender] || msg.sender == owner(), "Not operator");
        _;
    }
}

Key Concepts

Rate Limit Management

Rate limit features include:

  • Rate limit setting
  • Rate limit verification
  • Rate limit adjustment
  • Rate limit recording

Frequency Control

Frequency features include:

  • Time interval
  • Times limit
  • Quantity limit
  • Status reset

Permission Management

Permission features include:

  • Operator management
  • Permission verification
  • Configuration control
  • Status management

Security Considerations

  1. Rate limit security

    • Frequency verification
    • Quantity verification
    • Status check
    • Exception handling
  2. Permission security

    • Operator verification
    • Permission check
    • Configuration control
    • Status protection
  3. System security

    • Permission control
    • Pause mechanism
    • Reentrancy protection
    • Status synchronization
  4. Upgrade security

    • Configuration update
    • Rate limit adjustment
    • Status migration
    • Emergency handling

Best Practices

  1. Rate limit management

    • Frequency control
    • Quantity control
    • Status tracking
    • Exception handling
  2. Permission management

    • Operator allocation
    • Permission verification
    • Configuration control
    • Status management
  3. Risk management

    • Rate limit monitoring
    • Exception detection
    • Risk warning
    • Emergency handling
  4. System maintenance

    • Parameter optimization
    • Performance monitoring
    • Security audit
    • Upgrade plan

Extended Features

  1. Multi-token rate limit
  2. Dynamic rate limit
  3. Hierarchical rate limit
  4. Intelligent rate limit
  5. Rate limit incentive

Application Scenarios

  1. Transaction rate limit

    • Frequency limit
    • Quantity limit
    • Transaction control
    • Risk prevention
  2. Security protection

    • Attack prevention
    • Risk control
    • Exception prevention
    • Security protection
  3. Ecological governance

    • Behavior control
    • Risk management
    • Ecological protection
    • Market stability

Summary

The token rate limit system is an important security component in the DeFi ecosystem. Through this tutorial, you can:

  • Implement rate limit functionality
  • Optimize transaction control
  • Strengthen security protection
  • Provide risk control

Common Questions and Answers (FAQ)

1. Basic Concepts

Q: What is token rate limit? A: Token rate limit is a traffic control mechanism, with the main features including:

  • Transaction frequency limit
  • Quantity limit
  • Time window control
  • Dynamic adjustment
  • Emergency handling

Q: What types of rate limit systems are there? A: The main types include:

  • Fixed window rate limit
  • Sliding window rate limit
  • Token bucket rate limit
  • Leaky bucket rate limit
  • Adaptive rate limit

Q: How to design rate limit strategies? A: Design points:

solidity
function checkRateLimit(
    address user,
    uint256 amount
) public view returns (bool) {
    // 1. Get time window
    uint256 window = block.timestamp / WINDOW_SIZE;
    
    // 2. Get user current window usage
    uint256 currentUsage = usage[user][window];
    
    // 3. Check if it exceeds the limit
    return currentUsage + amount <= RATE_LIMIT;
}

Q: How to manage rate limit rules? A: Management strategies:

  • Rule configuration
  • Dynamic adjustment
  • Whitelist management
  • Emergency control
  • Data statistics

Q: What are the risks of rate limit systems? A: The main risks include:

  • Time attack
  • Multi-account bypass
  • Calculation error
  • Denial of service
  • Rule failure

Q: How to protect rate limit security? A: Security measures include:

  • Account association detection
  • Multi-layer rate limit
  • Exception monitoring
  • Emergency pause
  • Audit verification

Q: How to optimize rate limit mechanisms? A: Optimization strategies:

  • Cache optimization
  • Storage optimization
  • Gas optimization
  • Calculation optimization
  • Status compression

Q: How to improve system efficiency? A: Improvement solutions:

  • Batch processing
  • Pre-calculation
  • Intelligent scheduling
  • Automatic adjustment
  • Data cleaning

5. Implementation Details

Q: How to implement token bucket rate limit? A: Implementation mechanism:

solidity
function consumeTokens(
    address user,
    uint256 amount
) internal returns (bool) {
    // 1. Update token bucket
    updateTokens(user);
    
    // 2. Check token quantity
    if (tokens[user] < amount) {
        return false;
    }
    
    // 3. Consume tokens
    tokens[user] -= amount;
    return true;
}

Q: How to handle emergencies? A: Handling mechanism:

  • Global pause
  • Limit adjustment
  • Rule reset
  • Status recovery
  • Log recording

6. Best Practices

Q: Rate limit system development suggestions? A: Development suggestions:

  • Complete testing
  • Performance testing
  • Stress testing
  • Documentation improvement
  • Monitoring and warning

Q: How to improve system reliability? A: Improvement solutions:

  • Fault detection
  • Automatic recovery
  • Status verification
  • Backup mechanism
  • Degradation handling

7. Error Handling

Q: Common errors and solutions? A: Error types:

  • "Rate limit exceeded": Wait for recovery
  • "Invalid amount": Check quantity
  • "System paused": System maintenance
  • "Invalid window": Time synchronization
  • "Not authorized": Permission check

Q: How to handle exceptions? A: Handling mechanism:

  • Error retry
  • Degraded service
  • Notification mechanism
  • Manual intervention
  • Compensation mechanism

8. Upgrade Maintenance

Q: How to upgrade rate limit systems? A: Upgrade strategies:

  • Rule migration
  • Data backup
  • Smooth transition
  • Version control
  • Rollback mechanism

Q: How to monitor system status? A: Monitoring solutions:

  • Usage statistics
  • Exception detection
  • Performance monitoring
  • Resource usage
  • Rule effectiveness

9. Integration with Other Systems

Q: How to integrate with transaction systems? A: Integration solutions:

  • Pre-check
  • Transaction filtering
  • Status synchronization
  • Data sharing
  • Exception handling

Q: How to implement distributed rate limit? A: Implementation strategies:

  • Node synchronization
  • Data consistency
  • Load balancing
  • Fault transfer
  • Status recovery

Released under the MIT License by Vogeb.