mirror of
https://github.com/adambard/learnxinyminutes-docs.git
synced 2024-12-23 17:41:41 +00:00
updated for v0.6 with fewer oracle details
This commit is contained in:
parent
efa392a1b1
commit
b2d02a50f4
@ -5,7 +5,7 @@ contributors:
|
||||
- ["Nemil Dalal", "https://www.nemil.com"]
|
||||
- ["Joseph Chow", ""]
|
||||
- ["Bhoomtawath Plinsut", "https://github.com/varshard"]
|
||||
- ["Shooter", "https://github.com/liushooter"]\
|
||||
- ["Shooter", "https://github.com/liushooter"]
|
||||
- ["Patrick Collins", "https://gist.github.com/PatrickAlphaC"]
|
||||
---
|
||||
|
||||
@ -214,7 +214,8 @@ assert(c >= a); // assert tests for internal invariants; require is used for use
|
||||
// https://github.com/OpenZeppelin/zeppelin-solidity/blob/master/contracts/math/SafeMath.sol
|
||||
|
||||
|
||||
// No random functions built in, see below for using Chainlink to get random numbers.
|
||||
// No random functions built in, you can get a pseduo-random number by hashing the current blockhash, or get a truely random number using something like Chainlink VRF.
|
||||
// https://docs.chain.link/docs/get-a-random-number
|
||||
|
||||
// Type casting
|
||||
int x = int(b);
|
||||
@ -645,7 +646,6 @@ reveal(100, "mySecret");
|
||||
// All data to start of time is stored in blockchain, so
|
||||
// anyone can observe all previous data and changes
|
||||
|
||||
|
||||
// E. Oracles and External Data
|
||||
// Oracles are ways to interact with your smart contracts outside the blockchain.
|
||||
// They are used to get data from the real world, send post requests, to the real world
|
||||
@ -663,156 +663,12 @@ reveal(100, "mySecret");
|
||||
// multiple sources and delivered on-chain, and we can use it as a "data bank"
|
||||
// of sources.
|
||||
|
||||
// We will need to be on a network that has the data already loaded.
|
||||
// Let's look at an example
|
||||
```
|
||||
# Oracles
|
||||
### Getting data from Chainlink Data Feeds
|
||||
// You can see other examples making API calls here:
|
||||
// https://docs.chain.link/docs/make-a-http-get-request
|
||||
|
||||
We will be deploying to a testnet with Chainlink. This way we can get decentralized data into our smart contracts.
|
||||
// And you can of course build your own oracle network, just be sure to know
|
||||
// how centralized vs decentralized your application is.
|
||||
|
||||
**Deploy the following contract with remix to the `Kovan` testnet. If unfamiliar, reference the start of this file.**
|
||||
|
||||
[Work with this code in Remix](https://remix.ethereum.org/#version=soljson-v0.6.7+commit.b8d736ae.js&optimize=false&evmVersion=null&gist=0c5928a00094810d2ba01fd8d1083581&runs=200)
|
||||
|
||||
We can get the price of any asset by using the `getLatestPrice` function. You can see a list of addresses for the Kovan network from the [Chainlink Documentation](https://docs.chain.link/docs/get-the-latest-price). You can also view any other address as well.
|
||||
|
||||
|
||||
```javascript
|
||||
/** This example code is designed to quickly deploy an example contract using Remix.
|
||||
* If you have never used Remix, try our example walkthrough: https://docs.chain.link/docs/example-walkthrough
|
||||
* You will need testnet ETH and LINK.
|
||||
* - Kovan ETH faucet: https://faucet.kovan.network/
|
||||
* - Kovan LINK faucet: https://kovan.chain.link/
|
||||
*/
|
||||
|
||||
pragma solidity ^0.6.7;
|
||||
|
||||
import "https://github.com/smartcontractkit/chainlink/blob/master/evm-contracts/src/v0.6/interfaces/AggregatorV3Interface.sol";
|
||||
|
||||
contract PriceConsumerV3 {
|
||||
|
||||
AggregatorV3Interface internal priceFeed;
|
||||
|
||||
/**
|
||||
* Network: Kovan
|
||||
* Aggregator: ETH/USD
|
||||
* Address: 0x9326BFA02ADD2366b30bacB125260Af641031331
|
||||
*/
|
||||
constructor() public {
|
||||
priceFeed = AggregatorV3Interface(0x9326BFA02ADD2366b30bacB125260Af641031331);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the latest price
|
||||
*/
|
||||
function getLatestPrice() public view returns (int) {
|
||||
(
|
||||
uint80 roundID,
|
||||
int price,
|
||||
uint startedAt,
|
||||
uint timeStamp,
|
||||
uint80 answeredInRound
|
||||
) = priceFeed.latestRoundData();
|
||||
return price;
|
||||
}
|
||||
}
|
||||
|
||||
```
|
||||
|
||||
### Randomness / RNG
|
||||
|
||||
Chainlink VRF (Verifiable Random Function) is a provably-fair and verifiable source of randomness designed for smart contracts. Randomness is difficult in blockchain, because blockchains are determanistic. We can get a random number by reaching outside the blockchain to an oracle.
|
||||
|
||||
Chainlink VRF then cryptographically guarantees that the random number returned is random.
|
||||
|
||||
**Deploy the following contract with remix to the `Kovan` testnet. If unfamiliar, reference the start of this file.**
|
||||
|
||||
The only additional piece we need to do here is to fund our contract with LINK. [You can see a video on funding with LINK here.](https://www.youtube.com/watch?v=4ZgFijd02Jo)
|
||||
|
||||
Once we deploy our Chainlink VRF contract, in order to `getRandomNumer` we need to fund the contract with LINK. Get some kovan testnet LINK [from this faucet](https://kovan.chain.link/). Once the transaction has gone through, in your metamask, hit `Add Token` and under `Custom Token` enter the address `0xa36085F69e2889c224210F603D836748e7dC0088`.
|
||||
|
||||
![Remix-add-token](images/solidity/remix-add-token.png)
|
||||
|
||||
NOTE: This is only the token address for Kovan.
|
||||
|
||||
Once you deploy your contract, you'll need to fund it with LINK. You can fund it with link by copying your contract address from remix, and then sending that address a few LINK from your metamask. Remember this is all testnet LINK, and we can always get more for free.
|
||||
|
||||
![Remix-add-token](images/solidity/copy-address.png)
|
||||
|
||||
![Remix-add-token](images/solidity/send-link.png)
|
||||
|
||||
And you'll be able to work with the VRF. After deploying the content, enter a number of choice into the `getRandomNumber` function. After a delay of ~1 minute, you can hit the `randomResult` button to get the random number returned.
|
||||
|
||||
```javascript
|
||||
/** This example code is designed to quickly deploy an example contract using Remix.
|
||||
* If you have never used Remix, try our example walkthrough: https://docs.chain.link/docs/example-walkthrough
|
||||
* You will need testnet ETH and LINK.
|
||||
* - Kovan ETH faucet: https://faucet.kovan.network/
|
||||
* - Kovan LINK faucet: https://kovan.chain.link/
|
||||
*/
|
||||
|
||||
pragma solidity 0.6.6;
|
||||
|
||||
import "https://raw.githubusercontent.com/smartcontractkit/chainlink/master/evm-contracts/src/v0.6/VRFConsumerBase.sol";
|
||||
|
||||
contract RandomNumberConsumer is VRFConsumerBase {
|
||||
|
||||
bytes32 internal keyHash;
|
||||
uint256 internal fee;
|
||||
|
||||
uint256 public randomResult;
|
||||
|
||||
/**
|
||||
* Constructor inherits VRFConsumerBase
|
||||
*
|
||||
* Network: Kovan
|
||||
* Chainlink VRF Coordinator address: 0xdD3782915140c8f3b190B5D67eAc6dc5760C46E9
|
||||
* LINK token address: 0xa36085F69e2889c224210F603D836748e7dC0088
|
||||
* Key Hash: 0x6c3699283bda56ad74f6b855546325b68d482e983852a7a82979cc4807b641f4
|
||||
*/
|
||||
constructor()
|
||||
VRFConsumerBase(
|
||||
0xdD3782915140c8f3b190B5D67eAc6dc5760C46E9, // VRF Coordinator
|
||||
0xa36085F69e2889c224210F603D836748e7dC0088 // LINK Token
|
||||
) public
|
||||
{
|
||||
keyHash = 0x6c3699283bda56ad74f6b855546325b68d482e983852a7a82979cc4807b641f4;
|
||||
fee = 0.1 * 10 ** 18; // 0.1 LINK
|
||||
}
|
||||
|
||||
/**
|
||||
* Requests randomness from a user-provided seed
|
||||
*/
|
||||
function getRandomNumber(uint256 userProvidedSeed) public returns (bytes32 requestId) {
|
||||
require(LINK.balanceOf(address(this)) > fee, "Not enough LINK - fill contract with faucet");
|
||||
return requestRandomness(keyHash, fee, userProvidedSeed);
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback function used by VRF Coordinator
|
||||
*/
|
||||
function fulfillRandomness(bytes32 requestId, uint256 randomness) internal override {
|
||||
randomResult = randomness;
|
||||
}
|
||||
|
||||
/**
|
||||
* Withdraw LINK from this contract
|
||||
*
|
||||
* DO NOT USE THIS IN PRODUCTION AS IT CAN BE CALLED BY ANY ADDRESS.
|
||||
* THIS IS PURELY FOR EXAMPLE PURPOSES.
|
||||
*/
|
||||
function withdrawLink() external {
|
||||
require(LINK.transfer(msg.sender, LINK.balanceOf(address(this))), "Unable to transfer");
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
[You can learn more about Chainlink from the documentation.](https://docs.chain.link/docs)
|
||||
|
||||
You can [make API calls](https://docs.chain.link/docs/make-a-http-get-request), [set timing intervals](https://docs.chain.link/docs/chainlink-alarm-clock), and so much more.
|
||||
|
||||
```javascript
|
||||
// Setting up oracle networks yourself
|
||||
|
||||
// D. Cron Job
|
||||
@ -869,17 +725,17 @@ Work with the full example below using the [`Javascript VM` in remix here.](http
|
||||
// ** START EXAMPLE **
|
||||
|
||||
// CrowdFunder.sol
|
||||
pragma solidity ^0.4.19;
|
||||
pragma solidity ^0.6.6;
|
||||
|
||||
/// @title CrowdFunder
|
||||
/// @author nemild
|
||||
contract CrowdFunder {
|
||||
// Variables set on create by creator
|
||||
address public creator;
|
||||
address public fundRecipient; // creator may be different than recipient
|
||||
address payable public fundRecipient; // creator may be different than recipient, and must be payable
|
||||
uint public minimumToRaise; // required to tip, else everyone gets refund
|
||||
string campaignUrl;
|
||||
byte constant version = 1;
|
||||
byte version = "1";
|
||||
|
||||
// Data structures
|
||||
enum State {
|
||||
@ -889,7 +745,7 @@ contract CrowdFunder {
|
||||
}
|
||||
struct Contribution {
|
||||
uint amount;
|
||||
address contributor;
|
||||
address payable contributor;
|
||||
}
|
||||
|
||||
// State variables
|
||||
@ -919,10 +775,10 @@ contract CrowdFunder {
|
||||
_;
|
||||
}
|
||||
|
||||
function CrowdFunder(
|
||||
function crowdFund(
|
||||
uint timeInHoursForFundraising,
|
||||
string _campaignUrl,
|
||||
address _fundRecipient,
|
||||
string memory _campaignUrl,
|
||||
address payable _fundRecipient,
|
||||
uint _minimumToRaise)
|
||||
public
|
||||
{
|
||||
@ -947,7 +803,7 @@ contract CrowdFunder {
|
||||
);
|
||||
totalRaised += msg.value;
|
||||
|
||||
LogFundingReceived(msg.sender, msg.value, totalRaised);
|
||||
emit LogFundingReceived(msg.sender, msg.value, totalRaised);
|
||||
|
||||
checkIfFundingCompleteOrExpired();
|
||||
return contributions.length - 1; // return id
|
||||
@ -971,7 +827,7 @@ contract CrowdFunder {
|
||||
public
|
||||
inState(State.Successful)
|
||||
{
|
||||
fundRecipient.transfer(this.balance);
|
||||
fundRecipient.transfer(address(this).balance);
|
||||
LogWinnerPaid(fundRecipient);
|
||||
}
|
||||
|
||||
@ -1000,6 +856,7 @@ contract CrowdFunder {
|
||||
}
|
||||
}
|
||||
// ** END EXAMPLE **
|
||||
|
||||
```
|
||||
|
||||
Some more functions.
|
||||
@ -1085,6 +942,11 @@ someContractAddress.callcode('function_name');
|
||||
- [Modular design strategies for Ethereum Contracts](https://docs.erisindustries.com/tutorials/solidity/)
|
||||
- [Chainlink Documentation](https://docs.chain.link/docs/getting-started)
|
||||
|
||||
## Smart Contract Development Frameworks
|
||||
- [Hardhat](https://hardhat.org/)
|
||||
- [Brownie](https://github.com/eth-brownie/brownie)
|
||||
- [Truffle](https://www.trufflesuite.com/)
|
||||
|
||||
## Important libraries
|
||||
- [Zeppelin](https://github.com/OpenZeppelin/openzeppelin-contracts): Libraries that provide common contract patterns (crowdfuding, safemath, etc)
|
||||
- [Chainlink](https://github.com/smartcontractkit/chainlink): Code that allows you to interact with external data
|
||||
|
Loading…
Reference in New Issue
Block a user