EVM package deployment with ZeppelinOS - Part III Linking to mainnet
Pulling it all together
Now that you've created your first EVM package, let's go through the steps you would take to link it to your project as if you were linking directly from NPM. These commands you already know, so I'll just run through them quickly:
mkdir myproject2
cd myproject2
npm init -y
zos init myproject2
npm install [email protected]
Now we need to link the NPM package:
zos link <<name of your npm package>>
This will install your NPM package and add it to your zos.json file as a dependency. You will also now find your linked contract in the node modules folder. Open it up and you will see the ZeppelinOS project configuration files along with your contract and build folders.
For convenience, I've already deployed our linked list to NPM, so if you don't want to deploy your own, you can use:
zos link zos-linkedlist
Testing
Return to your myproject2 top level, and create a new contract to test
the linked LinkedList
contract. In your contracts folder, make a new
contract called QuickContract.sol. Note that for the import of the
LinkedList NPM module, I refer to the folder by the name "LinkedList."
As you will not be able to publish your NPM package under that name, be
sure to reference the module name according to the name you gave your
NPM package.
pragma solidity >=0.4.24 <>0.6.0;
import "zos-linkedlist/contracts/LinkedList.sol";
//The NPM package name will have it's own folder under modules
contract QuickContract {
LinkedList private _linkedlist;
function setLinkedList(LinkedList linkedlist) external {
_linkedlist = linkedlist;
}
function getHead() public view returns (bytes32) {
bytes32 _node = _linkedlist.head();
return _node;
}
function addNode(string memory _data) public {
_linkedlist.addNode(_data);
}
}
This is a fairly simple contract designed to test the basic functions of
the LinkedList.sol contract. Note that the first function
setLinkedList()
takes an instance of LinkedList
as an address. This is
how the QuickContract
knows where the LinkedList
contract is deployed,
but remember, this address will actually be the proxy contract, which
will serve as the permanent address for the contract but actually points
to the LinkedList
implementation we deployed earlier. When we call into
the proxy, the proxy will forward the contract call to the logic code as
managed by ZeppelinOS. To upgrade your contract, you can tell the proxy
to point to a new logic contract, keeping the same address but with new
logic. As upgradable smart contracts are outside of the scope of this
tutorial, I encourage you to see this article for more information.
Make sure you have your development blockchain running, as follows:
ganache-cli --port 9545 --deterministic
And then start a new session:
zos session --network local --from <<your_10th_Ganache_address_here>> --expires 3600
Now, from the top level of our project, we're going to add QuickContract to the project:
zos add QuickContract
The next command will push our changes to the blockchain:
zos push --deploy-dependencies --network local
Let's take a quick look at the flag --deploy-dependencies
while we have
deployed our NPM contract to the Ethereum mainnet. For testing purposes,
we're testing again on our local blockchain. ZeppelinOS will need to
also deploy its own copy of the LinkedList.sol to this development
blockchain in order to link to it. We only need to do this in cases
where the dependencies are not already deployed on our blockchain (since
we just created it when we started Ganache!), and we only need to do it
once. If you have successfully deployed to the mainnet, you will not
need to do this again.
As before, you need to create an instance of our contract:
zos create QuickContract
Be sure to call the LinkedList.sol contract initializer (ZeppelinOS will remind you if you forget):
zos create zos-linkedlist/LinkedList --init initialize --args "MyList"
Note that after zos create
, I have included the node_modules folder
where LinkedList.sol has been installed via NPM.
Now we can test the contract:
npx truffle console --network local
First, create an instance of our QuickContract:
truffle(local)>
quickContract = await QuickContract.at('<QuickContract-contract-address>')
Then link the contract by setting the address of our LinkedList contract:
truffle(local)>
quickContract.setLinkedList('<LinkedList-address>')
Remember that you can find your "
Time to test! First, check if a head exists:
truffle(local)> quickContract.getHead()
0x0000000000000000000000000000000000000000000000000000000000000000
Now try adding a node:
truffle(local)> quickContract.addNode("Hello World!")
And now get the head again:
truffle(local)> quickContract.getHead()
0xcfbf767713316a02071074289829821d60f486eee26333765c344cea90478d1e
// The actual bytes32 response will be unique to your project
It works!
Recap
That brings us to the end of the tutorial. Just to recap, in this tutorial you:
- learned what EVM packages are for, how they can be used, and how to deploy them.
- wrote a basic (but very useful!) linked list data structure with Solidity.
- added the LinkedList.sol contract to your ZeppelinOS project.
- tested your linked list by deploying the LinkedList.sol contract and creating an instance to test against using ZeppelinOS and Truffle.
- published your LinkedList.sol contract to the Ethereum mainnet and published it on NPM for others to use.
- created a new project from scratch, linking your deployed LinkedList to our test project.
- tested your new project using Truffle, and sure enough, it works!
Good luck with your projects! Have any questions or comments? Shoot me an email or follow me on Twitter.
Thanks to Santiago Palladino for reading early drafts and providing feedback.
- Kauri original title: EVM package deployment with ZeppelinOS - Part III Linking to mainnet
- Kauri original link: https://kauri.io/evm-package-deployment-with-zeppelinos-part-iii-li/28d6318d3afb483286aec2243cffd8a3/a
- Kauri original author: Dennison Bertram (@dennisonbertram1)
- Kauri original Publication date: 2019-03-07
- Kauri original tags: zeppelinos
- Kauri original hash: Qmcs4J3y2HuWT7b3LgRrdRKooYQ4ccNKvEEFKyyKuFf8vS
- Kauri original checkpoint: QmYRYAA1TRyDiXS6uLXdt6qS8AnW63tqJHYpUQKrdyNz7h