Board Configuration
Configuration Structure
BoardConfig bundles addresses, metadata, eligibility, locking, and decay settings:
struct BoardConfig {
string version;
address owner;
address underlyingToken;
uint256 opensAt;
uint256 closesAt;
Metadata boardMetadata;
AcceptanceCriteria acceptanceCriteria;
ParticipantRequirements proposerRequirements;
ParticipantRequirements supporterRequirements;
LockingConfig lockingConfig;
DecayConfig decayConfig;
}
struct LockingConfig {
uint256 lockInterval;
uint256 maxLockIntervals;
uint256 releaseLockDuration;
uint256 inactivityTimeout;
}
struct DecayConfig {
DecayCurveType curveType; // 0=linear, 1=exponential
uint256[] params; // Curve params (length depends on type)
}
struct ParticipantRequirements {
address token;
uint256 minBalance;
uint256 minHoldingDuration;
uint256 minLockAmount;
}Core Parameters
- owner: Board controller (accept, close/cancel, set timings). Use multisig/DAO when possible.
- underlyingToken: ERC20 used for locking and weight; must be set. Eligibility checks can point to a different token via
ParticipantRequirements.token. - boardMetadata: Title, body, attachments (emitted in
BoardCreated, not stored on-chain). - version: Off-chain compatibility marker for the board configuration.
- opensAt / closesAt: Timestamps gating participation;
closesAtmust be ≥opensAt(or0).
Acceptance Criteria
enum AcceptancePermissions {
Permissionless, // Anyone can accept if threshold is met
OnlyOwner // Only the board owner can accept
}
enum ThresholdOverride {
None, // Everyone (including owner) must meet threshold
OnlyOwner // Owner can bypass threshold requirement
}
struct AcceptanceCriteria {
AcceptancePermissions permissions;
ThresholdOverride thresholdOverride;
uint256 thresholdPercentTotalSupplyWAD; // Percentage of total supply (in WAD)
uint256 minThreshold; // Minimum fixed threshold
}Threshold calculation:
threshold = max(totalSupply * thresholdPercentTotalSupplyWAD / 1e18, minThreshold)Requirements:
- At least one of
thresholdPercentTotalSupplyWADorminThresholdmust be non-zero. thresholdPercentTotalSupplyWADmust be < 1e18 (100%).
Participant Requirements
proposerRequirements and supporterRequirements share the same structure:
token: ERC20/IVotes token checked for eligibility (can differ fromunderlyingToken).minBalance == 0andminHoldingDuration == 0: no balance requirement.minBalance > 0andminHoldingDuration == 0: current balance check.minBalance > 0andminHoldingDuration > 0: historical balance check (requiresIVotessupport ontoken).minLockAmountsets a minimum lock size for supporting or proposing with a lock.
Constraints:
tokencannot beaddress(0).minHoldingDuration > 0requiresminBalance > 0.minLockAmountmust be ≤minBalance.
Locking Configuration
- lockInterval: Time unit for locks and decay calculations (seconds, must be > 0).
- maxLockIntervals: Maximum number of intervals a lock can span (> 0).
- releaseLockDuration: Additional timelock after acceptance before redemption.
0allows immediate redemption after acceptance; expiration/cancellation bypasses it. - inactivityTimeout: Inactivity window after which an initiative can be expired (tracked via
lastActivityupdates on creation/support).
Decay Configuration
- curveType:
0= linear,1= exponential. - params: Curve parameters; length must match curve type.
- Linear:
[decayRate]where1e18 = 1:1linear decay per interval. - Exponential:
[decayMultiplier]per interval.
- Linear:
Validation & Errors
| Error | Condition | Fix |
|---|---|---|
SignalsFactory_ZeroAddressOwner | Owner is address(0) | Provide valid owner address |
Signals_InvalidArguments | underlyingToken or participant token is address(0) | Provide valid token address |
Signals_InvalidArguments | Both thresholds are 0 | Set at least one threshold > 0 |
Signals_InvalidArguments | Percentage threshold >= 100% | Set thresholdPercentTotalSupplyWAD < 1e18 |
Signals_InvalidArguments | Max intervals is 0 | Set maxLockIntervals > 0 |
Signals_InvalidArguments | Lock interval is 0 | Set lockInterval > 0 |
Signals_InvalidArguments | Invalid decay curve type | Use type 0 or 1 |
Signals_InvalidArguments | closesAt < opensAt | Ensure close time is after or equal to open time |
Signals_InvalidArguments | minLockAmount > minBalance or minHoldingDuration > 0 with minBalance == 0 | Adjust participant requirements |
