Alert Source Discuss
⚠️ Review Standards Track: ERC

ERC-1202: Voting Interface

A general interface for voting on-chain

Authors Zainan Victor Zhou (@xinbenlv), ERC-1202 Working Group <erc1202@googlegroups.com>
Created 2018-07-08
Requires EIP-5269

Abstract

This EIP defines an API for implementing voting with smart contracts. This standard provides functionality for voting, viewing vote results, and setting voting status.

Motivation

Voting is one of the earliest examples of EVM programming and is also a key part of DAO and organizational governance processes. We expect many DAOs will ultimately need to leverage voting as an important part of their governance. By creating a voting standard for smart contracts and tokens, we can have the following benefits:

Benefits of having a standard

  1. Allow general UIs and applications to be built on top of a standardized voting interface so that more users can participate, and encourage more dApps and DAOs to think about their governance.
  2. Allow delegated voting, smart-contract voting, and automatic voting.
  3. Allow voting results to be recorded on-chain in a standard way, and allow DAOs and dApps to honor the voting results programmatically.
  4. Allow compatibility with token standards such as ERC-20 and newer standards such as ERC-777, as well as item standards such as ERC-721.
  5. Create massive potential for interoperability within Ethereum ecosystems and other systems.
  6. Allow setting voting deadlines, determining single or multiple options, and requiring voting order. (The trade-off is interface complexity; we might need an ERC-20-style approach first and later an ERC-777-style approach for advanced voting.)
  7. Record voting weights based on token amounts.
  8. Possibly allow trustworthy, privacy-safe voting and anonymous voting (with the voter address not being associated with the vote they cast, given a list of randomized or obfuscated voting options).
  9. Possibly allow rewards based on voting participation or voting results.

Non-Goal / Out of Scope

  1. Delegation: We intentionally leave delegation out of scope. A separate EIP could be proposed to address this particular use case.
  2. Eligibility or Weights: Some implementations may want voting weights or voting eligibility to be configurable. For example, OpenZeppelin’s implementation of GovernorBravo uses snapshots. Weight calculations such as quadratic voting are also outside the scope of this EIP. This EIP is intended to be flexible enough for current and future voting-weight calculations.
  3. Proposal: We intentionally leave proposals out of scope. Proposals are identified by proposalId, but the information included in a proposal, whether it is on-chain or off-chain, and whether it is executable are all left out of this proposal. A separate EIP could be proposed to address this particular use case. See one such proposal: ERC-5247.
  4. Signature Aggregations / Endorsement: When implementing contracts want to allow users to submit their vote or vote approval offline and have another account generate the transaction, signature aggregations or endorsements are outside the scope of this EIP. A separate EIP could be proposed to address this particular use case. See one such proposal here: ERC-5453.

Use-cases

  1. Decide on issuing a new token, issuing more tokens, or issuing a sub-token.
  2. Decide on creating a new item under ERC-721.
  3. Decide on electing a certain person or smart contract to be the delegated leader for a project or subproject.
  4. Decide on audit-result ownership that allows migration of a smart-contract proxy address.

Specification

  1. Compliant contracts MUST implement the IERC1202Core below
interface IERC1202Core {
    event VoteCast(
        address indexed voter,
        uint256 indexed proposalId,
        uint8 support,
        uint256 weight,
        string reason,
        bytes extraParams
    );

    function castVote(
        uint256 proposalId,
        uint8 support,
        uint256 weight,
        string calldata reasonUri,
        bytes calldata extraParams
    ) external payable returns;

    function castVoteFrom(
        address from,
        uint256 proposalId,
        uint8 support,
        uint256 weight,
        string calldata reasonUri,
        bytes calldata extraParams
    ) external payable returns;

    function execute(uint256 proposalId, bytes memory extraParams) payable external;
}
  1. Compliant contracts MAY implement the IERC1202MultiVote Interface. If the intention is for multi-options to be supported, e.g. for ranked-choices or variant weights voting, Compliant contracts MUST implement IERC1202MultiVote Interface.
interface IERC1202MultiVote {
    event MultiVoteCast(
        address indexed voter,
        uint256 indexed proposalId,
        uint8[] support,
        uint256[] weight,
        string reason,
        bytes extraParams
    );

    function castMultiVote(
        uint256 proposalId,
        uint8[] support,
        uint256[] weight,
        string calldata reasonUri,
        bytes calldata extraParams
    ) external payable;
}
  1. The compliant contract SHOULD implement the ERC-5269 interface.

Getting Info: Voting Period, Eligibility, Weight

interface IERC1202Info {
    function votingPeriodFor(uint256 proposalId) external view returns (uint256 startPointOfTime, uint256 endPointOfTime);
    function eligibleVotingWeight(uint256 proposalId, address voter) external view returns (uint256);
}

Rationale

We made the following design decisions, and here are the rationales.

Granularity and Anonymity

We created a view function, ballotOf, primarily to make it easier for people to check the vote from a certain address. This has the following assumptions:

  • It is possible to check someone’s vote directly given an address. If implementers do not want to make this so easy, they can simply reject all calls to this function. We want to make sure that we support both anonymous and non-anonymous voting. However, since all calls to a smart contract are logged in block history, there is not much secrecy unless cryptographic techniques are used. I am not sufficiently cryptography-savvy to comment on that possibility. Please see “Second Feedback Questions 2018” for a related topic.

  • It assumes that each individual address can vote for only one decision. Users can distribute their available voting power at a more granular level. If implementers want to allow this, they can ask the user to create another wallet address and grant that new address a certain amount of power. For example, in token-based voting where voting weight is determined by the amount of tokens held by a voter, a voter who wants to distribute their voting power across two different options (or option sets) can transfer some of the tokens to the new account and cast votes from both accounts.

Weights

We assume votes have weight, which can be checked by calling eligibleVotingWeight(proposalId, address voter), and that the weight distribution is either determined internally or set by the constructor.

Backwards Compatibility

  1. The support options are chosen to be uint8 for the purpose of being backward-compatible with GovernorBravo. This can be increased in the future.

Security Considerations

We expect the voting standard to be used in connection with other contracts such as token distributions, actions conducted by consensus or on behalf of an entity, multi-signature wallets, and similar systems.

The major security consideration is ensuring that the standard interface is used only for performing downstream actions or receiving upstream input (vote casting). We expect future audit tools to be based on standard interfaces.

It is also important to note, as discussed in this standard, that for the sake of simplicity this EIP is kept in a very basic form. It can be extended to support many different implementation variations. Such variations might contain different assumptions about the behavior and interpretation of actions. One example is: what does it mean if someone votes multiple times through vote?

  • Would that mean the voter is increasing their weight?
  • Would that mean they vote for multiple options in the meantime?
  • Does the latter vote override the previous vote?

Because of the flexible nature of voting, we expect that many subsequent standards will need to be created as extensions of this EIP. We suggest that any extension or implementation of this standard be thoroughly audited before being included in large-scale or high-asset-volume applications.

The third consideration is non-triviality. Some voting applications assume anonymity, randomness, time-based deadline, ordering, etc. These requirements are known to be non-trivial to achieve on Ethereum. We suggest that any applications or organizations rely on audited and time-proven shared libraries when these requirements need to be enforced in their applications.

The fourth consideration is potential abuse. When voting is standardized and put on-chain, it is possible to write another contract that rewards a voter for voting in a certain way. This creates potential issues of bribery and conflict-of-interest abuse that were previously hard to implement.

Copyright and related rights waived via CC0.

Citation

Please cite this document as:

Zainan Victor Zhou (@xinbenlv), ERC-1202 Working Group <erc1202@googlegroups.com>, "ERC-1202: Voting Interface [DRAFT]," Ethereum Improvement Proposals, no. 1202, July 2018. Available: https://eips.ethereum.org/EIPS/eip-1202.