Free 30-min Web3 Consultation
Book Consultation
Smart Contract Security Audits
View Audit Services
Custom DeFi Protocol Development
Explore DeFi
Full-Stack Web3 dApp Development
View App Services
Free 30-min Web3 Consultation
Book Consultation
Smart Contract Security Audits
View Audit Services
Custom DeFi Protocol Development
Explore DeFi
Full-Stack Web3 dApp Development
View App Services
Free 30-min Web3 Consultation
Book Consultation
Smart Contract Security Audits
View Audit Services
Custom DeFi Protocol Development
Explore DeFi
Full-Stack Web3 dApp Development
View App Services
Free 30-min Web3 Consultation
Book Consultation
Smart Contract Security Audits
View Audit Services
Custom DeFi Protocol Development
Explore DeFi
Full-Stack Web3 dApp Development
View App Services
LABS
Guides

Setting Up an On-Chain Proposal Lifecycle

This guide details the technical implementation of a complete on-chain governance process, from proposal submission to automated execution, using smart contracts.
Chainscore © 2026
introduction
IMPLEMENTATION GUIDE

Setting Up an On-Chain Proposal Lifecycle

A technical walkthrough for developers on structuring a complete governance proposal process, from drafting to execution, using smart contracts.

An on-chain governance lifecycle is the formal process for submitting, voting on, and executing changes to a decentralized protocol. Unlike informal signaling, this lifecycle is codified in smart contracts, ensuring proposals are binding and automatically enforceable. A typical lifecycle progresses through distinct phases: proposal submission, a voting period, a timelock delay for security, and finally execution. Setting this up requires defining clear rules for each stage within your governance contract, such as proposal thresholds, voting durations, and quorum requirements.

The first step is proposal creation. A user, often a token holder who meets a minimum stake requirement, submits a transaction that calls a function like propose() in the governance contract. This transaction includes the calldata for the target function to be executed if the proposal passes. For example, a proposal to change the feePercentage in a DEX contract would encode the call to setFeePercentage(uint256). The contract stores this proposal with a unique ID and initiates the voting delay, a period allowing voters to review the proposal before voting begins.

Voting Mechanism and Security

Once the voting delay ends, the voting period starts. Token holders cast votes weighted by their stake, using mechanisms like token-weighted voting or delegated voting (e.g., Compound's Governor Bravo). Critical parameters here are the voting period (e.g., 3 days), quorum (the minimum voting power required for validity), and the vote threshold (e.g., >50% for simple majority). After voting concludes, the proposal state is calculated: it can be Defeated, Succeeded, or Expired. A successful proposal then typically enters a timelock period.

The timelock is a mandatory waiting period between a proposal's approval and its execution. This is a critical security feature, implemented via a TimelockController contract (like OpenZeppelin's), which gives users time to react to a malicious proposal. During this period, the encoded calldata is queued in the timelock. After the delay elapses, any account can call the execute() function to trigger the actual on-chain changes. This multi-step process—propose, vote, timelock, execute—creates a robust and transparent framework for decentralized decision-making.

Implementing this requires integrating governance standards. The most common is OpenZeppelin's Governor contract, which provides modular components for the proposal lifecycle. A basic setup involves deploying a Governor contract, a TimelockController, and an ERC-20/Votes token. The Governor is configured with the token address as the voting weight source and the Timelock as the executor. Developers must carefully set parameters like votingDelay, votingPeriod, proposalThreshold, and quorum based on their protocol's needs and security model.

For developers, testing the full lifecycle is essential. Use a forked mainnet or a local testnet to simulate proposal submission, voting with different token allocations, and execution via the timelock. Tools like Hardhat or Foundry are ideal for this. Remember, the goal is to create a system that is not only functional but also resistant to governance attacks, such as proposal spam or voter apathy leading to low quorum. A well-structured lifecycle is foundational to a protocol's long-term resilience and community trust.

prerequisites
ON-CHAIN GOVERNANCE

Prerequisites and Required Knowledge

Before building an on-chain proposal lifecycle, you need a solid foundation in core Web3 technologies and governance concepts.

To effectively set up an on-chain proposal lifecycle, you must first understand the underlying blockchain infrastructure. This requires proficiency with a smart contract development environment like Hardhat or Foundry, and familiarity with a primary language such as Solidity or Vyper. You should be comfortable deploying contracts to a testnet (e.g., Sepolia, Goerli) using tools like MetaMask and understanding gas estimation. A working knowledge of Ethereum Request for Comments (ERC) standards is crucial, particularly ERC-20 for governance tokens and ERC-721/ERC-1155 if your DAO manages NFTs. Ensure your development environment is configured with Node.js, npm/yarn, and the necessary SDKs for your chosen blockchain.

The governance logic itself is encoded in smart contracts. You'll need to understand common patterns like a timelock controller, which delays execution of passed proposals to allow for a review period, and a governor contract, which manages the proposal state machine (Created, Active, Canceled, Defeated, Succeeded, Queued, Expired, Executed). Many projects use battle-tested implementations like OpenZeppelin's Governor contracts, which provide modular components for voting, vote counting, and proposal lifecycle management. You should be able to read and extend these contracts, customizing parameters such as the voting delay, voting period, proposal threshold, and quorum requirements to match your community's needs.

Interacting with these contracts requires a front-end or scripted interface. You should be able to use a Web3 library such as ethers.js or viem to connect to a wallet, fetch proposal data, and submit transactions. For example, creating a proposal involves encoding the target contract address, value, and calldata for the desired function call. Understanding EIP-712 for typed structured data signing is also important for gasless voting via signatures. Furthermore, you'll need to consider off-chain components like a Snapshot-style interface for signaling or a dedicated backend indexer to track proposal events and cache state for efficient UI updates, which may require knowledge of The Graph or similar indexing protocols.

key-concepts-text
CORE CONCEPTS

Setting Up an On-Chain Proposal Lifecycle

An on-chain proposal lifecycle is a structured, automated process for governance, executed entirely via smart contracts. This guide explains its core components and how to implement a basic framework.

An on-chain proposal lifecycle is a sequence of smart contract functions that govern a proposal from creation to execution. Unlike informal off-chain discussions, it provides a cryptographically verifiable and tamper-resistant record of governance actions. The typical stages are: proposal creation, a voting period, a timelock delay, and final execution. Each stage is enforced by contract logic, ensuring no single party can unilaterally alter the process. This structure is fundamental to Decentralized Autonomous Organizations (DAOs) and protocol upgrades.

The lifecycle begins with proposal creation. A user, often a token holder who meets a minimum stake threshold, submits a transaction that calls a propose function. This function stores the proposal's metadata—such as the target contract address, calldata for the action, and a description—on-chain. Platforms like OpenZeppelin Governor provide standard interfaces for this. The proposal is assigned a unique ID and enters a pending state, awaiting the start of the voting period, which is usually defined by a votingDelay parameter.

During the voting period, token holders cast their votes. Voting power is typically calculated from a snapshot of token balances at the start of the period, preventing manipulation. Voters can choose options like For, Against, or Abstain. The voting logic, including quorum and vote thresholds, is defined in the governance contract. For example, a proposal may require a quorum of 20% of total supply and a majority of For votes to pass. Once the voting period ends, the contract's state function updates to reflect the result.

If a proposal succeeds, it usually enters a timelock period before execution. This is a security-critical delay, implemented by contracts like OpenZeppelin's TimelockController. It allows users to review the passed action and provides a window to exit systems or prepare for changes. After the delay, any address can call the execute function, which relays the approved calldata to the target contract. This final step atomically performs the governance-mandated action, such as upgrading a contract or transferring treasury funds.

Setting up a basic lifecycle requires deploying several contracts. A common stack includes: a voting token (e.g., an ERC-20 or ERC-721), a governor contract (like OpenZeppelin Governor), and a timelock controller. You must configure parameters like votingDelay, votingPeriod, quorumPercentage, and timelock delay at deployment. Thorough testing on a testnet is essential to verify that proposals move correctly through all states and that execution respects the defined permissions and delays.

lifecycle-stages
ON-CHAIN GOVERNANCE

The Six Stages of a Proposal

A structured guide to the technical lifecycle of an on-chain governance proposal, from ideation to execution.

02

2. Specification & Drafting

This stage formalizes the proposal into executable code or parameters. For technical upgrades, this involves writing and auditing the specific smart contract changes, such as modifying a protocol's interest rate model or adding a new collateral type. The draft includes:

  • The exact calldata or function calls to be executed
  • A detailed technical specification
  • A link to the finalized forum discussion
  • For parameter changes, the precise new values (e.g., reserveFactor: 0.15)
03

3. On-Chain Submission

The proposal is submitted as a transaction to the governance contract (e.g., Compound's Governor Bravo, Aave's AaveGovernanceV2). This creates a unique proposal ID and starts the formal voting timeline. Critical submission parameters include:

  • Target addresses and calldata for execution
  • Voting delay period before voting starts
  • Voting period length (typically 3-7 days)
  • Proposal threshold (minimum governance token balance required to submit) A gas fee is paid, and the proposal becomes immutable on-chain.
05

5. Timelock & Security Review

After a successful vote, proposals enter a mandatory timelock period (e.g., 2 days for Uniswap, 1 day for Compound). This is a critical security feature that allows users to review the executed code and exit the system if they disagree. During this period:

  • The approved calldata is queued in the Timelock controller contract.
  • Developers and security researchers perform a final review.
  • The community has a final chance to react before state changes occur.
06

6. Execution

The final step where the proposal's calldata is executed on the target contracts. After the timelock expires, any address (usually a keeper bot or a multisig) can call the execute function on the governance contract. This triggers the state changes, such as:

  • Updating a treasury parameter
  • Deploying a new smart contract
  • Transferring funds from a community treasury Execution consumes gas and is irreversible. Failed execution (e.g., due to revert conditions) requires a new proposal.
contract-architecture
SMART CONTRACT ARCHITECTURE

Setting Up an On-Chain Proposal Lifecycle

A step-by-step guide to implementing a decentralized governance system using smart contracts, from proposal creation to execution.

An on-chain proposal lifecycle is the core mechanism for decentralized governance in DAOs and DeFi protocols. It allows token holders to propose, vote on, and execute changes to a protocol's parameters or code. This process is entirely managed by smart contracts, ensuring transparency and immutability. Key components include a proposal factory for creation, a voting module for tallying votes, and a timelock or executor contract for safe implementation. Popular frameworks like OpenZeppelin's Governor provide modular, audited building blocks for this architecture.

The lifecycle typically follows a defined state machine: Pending -> Active -> Succeeded/Defeated -> Queued -> Executed. A proposal starts in a Pending state after submission, often requiring a minimum proposal threshold. It then moves to Active for a fixed voting period, where votes are cast using tokens or NFTs. The voting strategy is critical; it can be based on token-weighted votes, quadratic voting, or conviction voting. After voting ends, the proposal state is determined by comparing for/against votes against a quorum and a required majority.

Implementing this requires careful contract design. Here's a basic structure using Solidity and OpenZeppelin Governor: import "@openzeppelin/contracts/governance/Governor.sol";. You extend the Governor contract and configure parameters like votingDelay, votingPeriod, and quorum. The propose function allows users to submit an array of target addresses, values, and calldata for the proposed actions. Security considerations are paramount; proposals should never allow arbitrary code execution and should utilize a timelock controller to introduce a mandatory delay between proposal success and execution, giving users time to exit if they disagree.

For execution, the execute function processes the successful proposal's calldata. Integration with a Treasury or AccessControl module is common to manage funds or upgrade contracts. Real-world examples include Compound's Governor Bravo and Uniswap's governance system. Testing is essential; use frameworks like Hardhat or Foundry to simulate proposal lifecycles, voter behavior, and edge cases. Always verify contract interactions and ensure the governance contract has the correct permissions to call other protocol contracts upon execution.

AUDIENCE GUIDE

Implementation Steps by Component

Core Contract Architecture

The on-chain system typically requires three main contracts:

  1. Governance Token (ERC-20Votes): Must implement snapshotting for vote delegation. Use OpenZeppelin's ERC20Votes.
  2. Governor Contract: Manages proposal state. Key functions are propose(), castVote(), queue(), and execute(). Inherit from Governor and GovernorCountingSimple.
  3. TimelockController: Holds treasury funds and executes queued transactions after a delay.

Implementation Example:

solidity
// SPDX-License-Identifier: MIT
import "@openzeppelin/contracts/governance/Governor.sol";
import "@openzeppelin/contracts/governance/extensions/GovernorSettings.sol";

contract MyGovernor is Governor, GovernorSettings {
    constructor(IVotes _token)
        Governor("MyGovernor")
        GovernorSettings(7200 /* 1 day */, 50400 /* 1 week */, 0)
    {}
    function quorum(uint256 blockNumber) public pure override returns (uint256) {
        return 1000e18; // 1000 token quorum
    }
    // ... voting logic and proposal logic
}
CONFIGURATION COMPARISON

Governance Parameter Trade-offs

Key governance parameters and their impact on security, participation, and efficiency.

ParameterHigh Security / Low RiskBalanced ApproachHigh Efficiency / Low Friction

Proposal Submission Threshold

1.0% of total supply

0.5% of total supply

< 0.1% of total supply

Voting Period Duration

7-14 days

3-5 days

1-2 days

Quorum Requirement

20% of supply

10-15% of supply

< 5% of supply

Timelock Execution Delay

72 hours

24-48 hours

< 12 hours

Emergency Proposal Bypass

Vote Delegation Required

Proposal Deposit (Slashable)

$10,000 - $50,000

$1,000 - $5,000

$0 - $500

integrating-off-chain-tools
GOVERNANCE

Integrating Off-Chain Tools like Snapshot

A guide to structuring a complete proposal lifecycle using off-chain voting with Snapshot and on-chain execution via smart contracts.

Decentralized governance often requires a two-step process: off-chain signaling and on-chain execution. Tools like Snapshot provide a gasless, flexible environment for community discussion and voting on proposals. This separation allows for thorough debate without incurring transaction fees, ensuring broader participation. Once a proposal gains sufficient off-chain consensus, the approved actions must be executed on-chain, which requires a secure and automated bridge between the two systems. This guide outlines how to set up this complete lifecycle.

The core of integration is the executor contract. This is a smart contract (e.g., on Ethereum, Arbitrum, or Optimism) that holds the authority to perform specific on-chain actions, like transferring treasury funds or upgrading a protocol. The contract's logic is simple: it checks if a proposal hash, created from the Snapshot vote details, has been officially "queued" for execution. Only a designated relayer (often a trusted multisig or a decentralized service like the Snapshot X Relayer) can call the function to queue a successful proposal, providing cryptographic proof of the vote outcome.

On the Snapshot side, you configure a validation strategy and a voting strategy. The validation strategy defines who can create proposals (e.g., token holders with a minimum balance). The voting strategy determines vote weighting (e.g., by token balance or delegated voting power). Most critically, you link the Snapshot space to your executor contract address. When creating a proposal, the execution payload is defined. This is the encoded data for the on-chain transaction—such as the target contract, function call, and parameters—that will be executed if the vote passes.

After a voting period ends successfully, the relayer submits the result to the executor contract. The contract verifies the proposal's status and stores it as queued. There is typically a timelock delay (e.g., 48 hours) between queuing and execution, providing a final safety window for the community to react to any malicious proposals. After the delay expires, any address can trigger the execute function on the contract, which performs the predefined actions. This entire flow creates a transparent and secure pipeline from community sentiment to blockchain state change.

For development, you can use the @snapshot-labs/snapshot.js SDK to interact with the Snapshot GraphQL API, fetching proposal states and results. A basic executor contract can inherit from OpenZeppelin's TimelockController. The execution payload must be carefully constructed using ethers.js or viem: encodeFunctionData for the desired function call. Always test the full lifecycle on a testnet (like Sepolia) using Snapshot's test space (demo.snapshot.org) before deploying to mainnet to ensure the proposal creation, relaying, and execution work seamlessly together.

Key considerations for a robust setup include minimizing executor contract privileges (it should only perform the specific actions voted on), using a multisig or decentralized relayer for queuing proposals, and clearly communicating the process to token holders. This pattern, used by protocols like Uniswap and Aave, balances community agility with the security and finality of on-chain transactions, creating a more resilient and participatory governance framework.

ON-CHAIN GOVERNANCE

Security Considerations and Audits

Implementing a secure on-chain proposal lifecycle requires careful design to prevent exploits, ensure voter integrity, and protect treasury assets. This guide addresses common developer questions and pitfalls.

The most frequent critical vulnerabilities in on-chain governance contracts include:

  • Reentrancy attacks: A malicious proposal can call back into the governance contract during execution to drain funds or manipulate state. Use the Checks-Effects-Interactions pattern and consider reentrancy guards.
  • Proposal parameter manipulation: Insufficient validation on proposal calldata or target addresses can allow execution of arbitrary code. Always whitelist target contracts or validate function selectors.
  • Vote manipulation via flash loans: Attackers can borrow large amounts of governance tokens to pass malicious proposals. Implement a time-weighted voting snapshot or a voting delay to mitigate this.
  • Governance capture: If a single entity holds >50% of voting power, they can pass any proposal. Consider implementing a timelock for all executable proposals, giving the community time to react.

Always conduct a formal audit before deploying a governance system to a mainnet.

ON-CHAIN PROPOSALS

Frequently Asked Questions

Common technical questions and troubleshooting for developers implementing a full on-chain governance lifecycle, from proposal creation to execution.

The standard on-chain proposal lifecycle follows a sequence of state transitions managed by a smart contract. It begins with a proposal creation phase, where a transaction is submitted with the proposal data (e.g., target contract, calldata). This is followed by a voting delay period, allowing token holders to review. Next, the voting period opens, during which delegated votes are cast. After voting ends, the contract checks if the proposal met quorum (minimum participation) and passed the vote threshold (e.g., majority for). If successful, it enters a timelock or execution delay for security. Finally, the proposal can be executed, calling the encoded function on the target contract. Failed proposals are defeated and cannot be executed.

conclusion-next-steps
IMPLEMENTATION SUMMARY

Conclusion and Next Steps

You have now configured the core components for a secure and functional on-chain governance system. This guide has walked you through the essential steps, from initial setup to proposal execution.

Your deployed system now includes a Governor contract (like OpenZeppelin's Governor) that defines the proposal lifecycle, a VotingToken for delegation and voting power, and a TimelockController to enforce a delay between proposal approval and execution. This architecture separates powers, ensuring no single entity can unilaterally execute transactions. The Timelock acts as the sole executor for the Governor, and holds the treasury funds or admin roles for the protocols you intend to govern. This setup mitigates risks like a malicious proposal executing immediately or a compromised wallet draining funds.

To interact with your new DAO, you should now focus on front-end integration and establishing operational processes. Use the Governor contract's address to connect a user interface, such as a custom dApp or a platform like Tally. Your community will need clear documentation on how to: create a proposal by calling propose(), delegate voting tokens, cast votes using castVote(), and queue/execute successful proposals via the Timelock. Consider writing scripts using frameworks like Hardhat or Foundry to automate testing of the entire proposal flow, from creation to execution, ensuring all state changes occur as expected.

For further development, explore advanced governance features. Implement gasless voting via signatures using EIP-712 and a relayer to reduce voter cost. Add proposal thresholds to prevent spam. Consider a cross-chain governance setup using LayerZero or Axelar for multi-chain treasuries. Always prioritize security: conduct audits, establish a bug bounty program, and create a crisis response plan. Monitor real-world DAOs like Uniswap or Compound for governance patterns. Your next step is to foster an active community—governance is a social contract as much as a technical one.

How to Set Up an On-Chain Proposal Lifecycle | ChainScore Guides