How To Build A Simple Capped Crowdsale Token Using OpenZeppelin Library — Part 1
Using Open-Zeppelin Library to build a basic capped ERC20 token sale.
Today, we are going to build a capped crowdsale with a mintable token using open-zeppelin library. (If you are a complete beginner, you should check out the previous tutorial on how to set up a solidity project and how to test a contract.) Open-zeppelin library provides basic building blocks to build an ERC20 Token on ethereum and will abstract away a lot of details for building an ERC20 token to get us up and running quicker.
Prerequisite
- Basic solidity concepts
- Understanding of ERC20 token standard and implementation
Things we will cover in the article:
- Definitions
- Open Zeppelin
- Building a crowdsale
Definitions
ERC20 Token
ERC20 is an ethereum standard for building a token. It defines a set of functions which a smart contract has to implement in order be ERC20 compliant. These standards are important to ethereum ecosystem and also helps you to make your contract robust, predictable and bug-free.
Crowdsale
A crowdsale is selling tokens to meet the financial requirements of the projects. Project share equity as a form of the token to contributors. In crypto world, crowd sales are called ICOs (Initial coin offering).
Capped Crowdsale
A project can have different types of constraints, one of them is capping. A capped crowdsale sets a limit on the total funding accepted and the number of tokens that will be distributed by the project. For example, we can cap on total ether contribution or if you want to put a cap on an investor for minimum contribution (let’s say 2 ether) and maximum contribution (let’s say 50 ether).
Benefits of a capped ICO
- A capped ICO helps investors to estimate value per token. It puts out the distribution structure and contributors get to know how many tokens are getting hold by the team and what are the plans to spend raised funds. It can also create a scarcity, thus increasing the value per token.
- Minimum and maximum contribution cap help to get more people to participate in the token distribution, you don’t want that all the token get bought by 100 people.
Mintable Token
In Mintable token, smart contract mint(create) tokens on the time of contribution. In this, you don’t permit tokens, so total supply gets decided based on total contributed ethers. Our contract will handle this logic too.
Building A Capped Crowdsale Token Using Open-Zeppelin Library
Open Zeppelin
We will use open zeppelin library to build our smart contract. Open zeppelin library provides basic building blocks to build an ERC20 Token on ethereum. It is a well-tested library and many projects use it on their production so it’s safe too.
Building a capped crowdsale contract
So let’s build a smart Capped ERC20 token. We will call our Token Example token. Below is code for ExampleToken and ExampleTokenCrowdsale.
ExampleToken.sol — Code for our Example token
ExampleTokenCrowdsale.sol — code for our crowdsale Contract
We are using open-zeppelin library which will abstract away a lot of details for building an ERC20 token and crowdsale contract. Feel free to ask questions on the comment section, if you don’t get something.
Installing OpenZeppelin Solidity
We need to install openZeppelin library using NPM.
npm install openzeppelin-solidity
Let’s go through our contracts on by one.
Our ERC20 Token — ExampleToken.sol
In this contract, we are defining ERC20 Token. One important thing to understand that open-zeppelin modularize many things, so don’t get overwhelmed with the so many file imports. If you come from the object-oriented background, then just see them as contracts inheriting interfaces and other contracts for their properties.
Let’s look at our imports, we are importing 3 contracts from the open-zeppelin library, we will go through them one by one. You can find all these files inside node_modules
under given path.
import "openzeppelin-solidity/contracts/token/ERC20/DetailedERC20.sol";import "openzeppelin-solidity/contracts/token/ERC20/StandardToken.sol";import "openzeppelin-solidity/contracts/token/ERC20/MintableToken.sol";
DetailedERC20.sol
This contract itself importing ERC20.sol
which is simply the ERC20 interface. This will be used for initializing our token. As you can see, you need to set Token name, symbol and how many decimal point it will use. For example, ethereum uses 18 decimal point, where the smallest unit is wei (1 ether= ¹⁰¹⁸ wei).
pragma solidity ^0.4.24;import "./ERC20.sol";contract DetailedERC20 is ERC20 {
string public name;
string public symbol;
uint8 public decimals;constructor(string _name, string _symbol, uint8 _decimals) public {
name = _name;
symbol = _symbol;
decimals = _decimals;
}
}
You can go on and check ERC20.sol
which is importing ERC20Basic.sol
and these two files combined have standard functions of an ERC20 token.
StandardToken.sol
This contract is a standard and well-tested implementation of ERC20 token methods. For the sake of simplicity, I am not adding contract code, you can check contract under the same path.
MintableToken.sol
This contract has our token minting logic. So let’s look at this contract closely. It’s importing ownable
and StandardToken
.
Ownable contract helps in putting access controls and managing ownership. It defines modifiers using which functions can be made owner accessible and It helps you to manage contract ownership.
Now, let’s look at out mint() function, It receives two parameters one is beneficiary account and another is a total number of tokens to be added. notice mint()
function, it’s increasing total supply
and balances
variable is available through inheriting StandardToken
contract, which maintain the balance of every contributor.
This function will be called from MintedCrowdsale
contract (we will see that in the next part of this tutorial).
pragma solidity ^0.4.24;import "./StandardToken.sol";
import "../../ownership/Ownable.sol";contract MintableToken is StandardToken, Ownable {
event Mint(address indexed to, uint256 amount);
event MintFinished();bool public mintingFinished = false;modifier canMint() {
require(!mintingFinished);
_;
}modifier hasMintPermission() {
require(msg.sender == owner);
_;
}function mint(
address _to,
uint256 _amount
)
public
hasMintPermission
canMint
returns (bool)
{
totalSupply_ = totalSupply_.add(_amount);
balances[_to] = balances[_to].add(_amount);
emit Mint(_to, _amount);
emit Transfer(address(0), _to, _amount);
return true;
}function finishMinting() public onlyOwner canMint returns (bool) {
mintingFinished = true;
emit MintFinished();
return true;
}
}
Conclusion
In this part, we have created a Capped ERC20 token using open-zeppelin library. We have talked about different basic contracts provided by open-zeppelin library and how can we use them to build a capped ERC20 token.
On To Part 2 →
Notes & Suggestions
There are a lot of things which handled by open-zeppelin library and almost every basic functionality is provided by the library. If you don’t understand something, please comment.
If you have any problem while following through this tutorial, Check out my github code.
Starting a new blockchain project, or looking for a Solidity developer?
Crowdbotics helps business build cool things with Solidity (among other things). If you have a blockchain project where you need additional developer resources, drop us a line. Crowbotics can help you estimate build time for given product and feature specs, and provide specialized Solidity developers as you need them. If you’re building with Solidity, check out Crowdbotics.