@tokenfoundry/sale-contracts
v5.0.0
Published
Code for the new token foundry token and sale base contracts.
Downloads
15
Readme
sale-contracts
Code for the new token foundry token and sale base contracts.
Contracts
- Whitelistable.sol: Base contract that implements a signature based whitelisting mechanism. It inherits from
Ownable
. - DisbursementHandler.sol: Contract that is used by the sale to lock tokens until a certain timestamp. Inherits from
Ownable
. - Sale.sol: Base contract from which all sales inherit. This contract implements a basic sale structure and common functions. It inherits from
Ownable
,Whitelistable
,TimedStateMachine
andTokenControllerI
. - Vault.sol: Contract that is used by the sale to store the funds and enable refunds or allow disbursements for the project team. It inherits from
Ownable
. - TokenAllocator.sol: This contract can allocate extra tokens at the end of the sale - meaning the sale did not sell out and all tokens have not been allocated yet.
Sale Structure
Overview
This sale structure is used to maintain a totalSaleCap
in units. The units could be wei, USD or any other unit as an inputted rate is used for the wei to unit conversion calculations. Tokens are allocated during the sale. The wei price per token is determined by (1) the amount of units received at the time of contribution, which is calculated using the wei per unit conversion _rate
and (2) the pre-determined amount of saleTokensPerUnit
, which is based on the scenario in which the totalContributed
reaches the totalSaleCap
. Any remaining, unsold tokens are allocated after the sale ends, based on the number of remaining tokens and the percentage contribution from each contributor in units at the time of contribution as part of the totalContributed
raised.
Whitelisting
Instead of storing in the contract the users that are allowed to contribute, we use a signature based whitelisting.
After the user goes through an off-chain KYC process, we compute the keccak256 hash of the desired address that the contributor would like the tokens to be sent concatenanted with their contribution limit in units, the current convertion rate (units per wei) and the signature expiration timestamp, and we sign that hash using the whitelisting admin's private key. The user then has to pass those components as arguments to the contribute()
function as those parameters are from which the hash was generated. The contribute()
function must be executed before the expiration timestamp is reached.
Refunds
All funds are immediately sent to the Vault
contract (the Sale contract doesn't store funds). Those funds are locked, and if at the end of the sale the minimum threshold is not reached, 100% of the funds are available for refunds. Should refunds be neccessary, refunds will be made entirely in wei, not units. If at some point in the sale the minimum thresold is reached, a percentage of the funds is sent to the project team's wallet, and the rest is kept (locked) in the vault until the team publishes their contracts on testnet. Note that the initialWei
will be in wei as the vault contract holds wei from the sale, not units. However, the minThreshold
designated in the Sale contract is in units. When the minThreshold
is reached, should the initialWei
be more than the amount of wei received at the current conversion rates for minThreshold
, then the entirety of the current balance in the Vault is sent to the project team's wallet. After the initial transfer, the Vault
will continue to receive and hold contributions from the sale.
The Vault
contract should be owned by a multisig wallet, as the owner is able to force refunds at any moment.
State
Instructions
In order to build and test the contracts found in this repo, Truffle version > 4 is needed.
Usage
First install as a npm package in your truffle project directory:
yarn add -E @tokenfoundry/sale-contracts
Import in your contracts:
import "@tokenfoundry/sale-contracts/contracts/Sale.sol";
contract MySale is Sale {
...
}
Building
Once the repo is cloned, run yarn install
to install all the dependencies.
Running yarn compile
will compile the contract code and place the output in the build/contracts
directory.
Testing
yarn test
to run all the tests, or yarn test test/<test file>
to run a specific test.
yarn coverage
to run tests and get code coverage.
License
MIT