Introduction to Arbitrum Stylus: Write Smart Contracts in Rust
ETHGlobal·Wed, Oct 9, 2024, 12:00 AM
Join Jose FP from Arbitrum for a workshop titled, "Introduction to Arbitrum Stylus: Write Smart Contracts in Rust." Start creating Arbitrum smart contracts in Rust with their newest tech, Stylus. Stylus contracts are cost-effective, quicker, and more potent than Solidity, seamlessly interacting with EVM contracts on Arbitrum chains. Explore example contracts showcasing Stylus' capabilities in this workshop. This workshop took place at ETHGlobal London 2024, a 3-day hackathon held at the Truman Brewery in London from March 15 to 17, 2024. The event brought together the most skilled web3 developers, designers and product builders from all around the globe for a weekend-long adventure to advance the Ethereum ecosystem! ----------------- Follow us: https://x.com/ethglobal Check us out: https://ethglobal.com Email us at: hello@ethglobal.com
Transcript
[Music] hello good afternoon everyone thank you for for being here today we are going to talk about arbit stylus okay we're going to talk like what it is and a bit how interactions between solidity and R contracts work so let's start it um well first of all I'm Jose Franco I'm an integration engineer at dochain labs and these are my Twitter and handlers I don't post a lot of things on Twitter so but and offchain Labs is the they are the initial Builders of arbitrum one and arbitrum Nova chains and the developers of stylus and and orbit if you don't know what any of these means please go to our booth and we will be happy to to answer all the questions that you have and talk about this okay so today we're going to split the presentation in the workshop in two parts the first one is just an introduction to stylus what it is and we are going to see a very simple contract counter contract and then we are going to to go uh uh one level deeper and we're going to talk about interactions between contracts that are written in rest and contracts that are written in solidity we're going to talk about re-entrancy as well and see a a an example project so what is stylus Stylus is an is an upgrade to the traditional well traditional the current uh develop an SM environment for smart contracts on evm chains so basically now if you want to write smart contract usually do that in solidity or or in Viper and with stylus you will be able to to you are able to write smart contracts in rast C C C++ and other languages okay the way this works is that alongside the evm there is a new virtual machine that Brands uh executes programs written in wasm so actually any language that can compil down to wasm can run on this virtual machine and both virtual machine can speak to each other so that means that contracts in for stylus can call contracts in solidity and the other way around um these are some numbers of uh developers in these three languages that we were just mentioning just to compare um to compare among them and also to see that stylus actually enables new developers uh to be able to access the blockchain ecosystem smart contract development e ecosystem right stylus also increases the speed and reduces cost basically because generally uh program written in wasm is going to be more efficient than the one written in solidity and also memory usage is improved and yeah that means that we can see new examples of advanced cryptography generative art onchange generative art actually and any other use cases okay so right now we have an SDK for rest C and C++ if you're going to build something on stylus uh during this weekend if you want to do it on R there is a great SDK for doing that and but basically any language that can be compiled to wasm can use a stylus and actually we have examples of programs written in Sig and assembly script as well without the use of any SDK just draw uh draw wasm code and well this is a bit to show the road map of of stylus now we have an alpha version with a test net we are running we are um yeah having audits for the code once we make sure everything is safe we will enable stylus on arbit test Nets and orbit chains and finally we will submit a proposal to activate stylus in in the arbit main net chains so how to start with the stylus if you don't if you haven't done anything I I always recommend these three resources don't worry about the links because at the end of the presentation I'm going to show you a QR code that goes to our repo that has all the reference links that I'm going to show here okay so there is a quick start uh it's a page in the dogs it helps you set up your your development environment to start writing smart contracts in Rust and deploy them to the stylus test net uh stylus by example has um more information about small things I mean small details that when you write smart contracts in R you have to take into account like for example how you emit a log in a in a smart contract right stuff like that and awesome Stylus is um is a repository of of projects that have been built uh brast and other languages as well for stylus okay so you can see many more examples of of things that you can do there all right so let's see the first example of a contract this is a this is going to be a very basic um contract that just has a a counter and allows you to increment it so with this we are going to see how how the code looks like so let me go here yeah can you see the screen well can you see the code yeah okay so this is a a basic example if you have developed with r well this might be a bit familiar to you so here um I just wanted to to show you a bit what it what how uh sorry what a contract written in R look like okay so this contract is called a counter and actually we just uh declare here the the variables that we are going to use we are going to store in the contract we just have one variable it's the count uh variable it's a u 256 and then we have the functions that we can call on that smart contract down here the way we divide this is by the use of of macros so we can see here the solidity storage macro that tells stylus that we are going to Define this the struct that is going to to tell the contract what um what variables we are going to store in the in the contract right the entry point tells styl stylus where the execution of the program begins and finally the external macro tells a stylus what are the functions that you are going to be able to call from outside the contract okay if you want to play some internal function or something like that you can place it before the external uh macro and it is not going to be uh exposed to the public so this contract has three simple question uh three simple methods sorry a getter to get the the current count a set count if you want to change that and an increment okay and yeah I'm going to show you how to how to deploy it uh actually this repo is also part of the resources and you have all these scripts to to perform these individual actions like deploy get count increment and we are going to use it now to to test it so uh sorry I'm going to use this console which is I think it's bigger here all right so for example if we want to deploy this specific contract we're just going to call deploy and what this does um is that it's going to send the transaction to to to the test net in this case to deploy the contract and also activate it okay normally you will see two transactions here but because I've already deployed the same code before I don't need to activate it it's well it's a it's it's how stylist works you need two transactions deployment and activation if you activate it once you don't need to activate it again the same code if I change anything in the contract I need to activate it okay and just to show you what it does actually if you if I do this what it calls is just it uses the cargo stylus um command if you don't know what this is and don't worry the quick explains what it is it's just a util that is a tool that we use to deploy contracts to estimate gas to check if the wasm code that we have is uh compatible with stylus and yeah it's just a tool for for deploying and checking your contract so once we have the contract deploy we're just going to call yeah we're going to call a couple of functions and let me show you what these functions look like so we s the deploy we're going to call get count and for this we're going to use cast call and as you see we are going to call this as if as if it was solidity we're just going to call the get method that we saw before and then in the increment um script we are just going to call the increment method with cast send because we are changing the the storage uh value and then another get to get the new counter so let me show you this so we do contract address because we need to pass the contract address and call um get count counter is zero because we just uh deployed the contract so we do increment now just sending the transaction the test net now and there we go and the new counter is one okay all right so this is the first basic contract uh let's go back to presentation again if you go to the repository of the of this specific project um it also has all these that we just saw all this the script it explains what it does and all that okay so I say this because I'm maybe talking too fast so you can do that at your own pace later now second part of the of the workshop how to interact with other contracts as we saw we were interacting with the brass contract that we just deployed as it was solidity and this happens because because these stylus calls are what what I mentioned there solidity solidity AI equivalent meaning that you just need to know the the signature of the function that you're going to call and that's it you don't need any implementation details or anything and the way you interact with other contracts is actually the same as in solidity solidity you will import the interface uh the top of the contract or whatever you want and then inside the method where you want to make the call you just use that imported interface to make the call right so in this case if you are writing the r contract is actually the same you import the interface with this instruction so interface and then you configure and make the call with uh with call we are going to see an example now so this is an example of uh um a r program that is declaring uh solidity interface and notice that we are declaring the interface as we do in solidity we are actually using the same syntax as solidity balance of is written in in camel case and actually this is signature that you use in solidity right and when you call that contract that method what you do is that you create the variable of the interface that you just uh imported you create the call this call new what it gives you is a configuration to make the call and then you just call the balance of function you send the configuration that you just um crafted and the parameters of the call that the uh that balance off is expecting in this in this case just an account notice also that even though we used camel case to declare the interface we are now using snake case here rest um syntax okay and more things when we are creating the configuration for the call we can also um like um uh sorry we can change the values some of the some of the parameters of the call like the gas used or the value that you want to send and yeah all these parameters um all right so let's talk about bit re-entrancy because in the stylus Works a bit different um re-entrancy as you know is like one contract is calling another contract and that contract is calling the same first contract again so we say that that first contract is being re-entered all right so in stylus contracts by default this uh this is not allowed this called revert meaning that if you have a r program that calls us another Ras program and that one calls the first the call is going to revert okay um but this can be enabled by using the the re-entrance feature flag and well um if enable yeah well this will happen stylus will Flash the storage cache and it will persist the values uh that might be used by Inner C and actually you do that inner call you do those inner calls by using the new in method instead of the new one right and something cool about Stylus is that you can actually apply different Logics in the same function depending on whether or not uh call is re-entrant so you can have the same method and say okay I want this piece of logic for the first time that I'm calling this contract and then this second one for when it is re-entering the this um the contract sorry and you can know if a call is reenter or Not by using this MSG re-enter and um in um variable sorry well yeah we have some more um references here okay so let's now take a look at an example project this projects is going to to have three contracts it have an erc721 contract written in breast a nart contract written in rest and an erc20 contract written in solidity and we are going to see the following interactions so the ERC 71 is going to initialize both the art and the erc20 contract um in this specific case when calling the token URI contract of the uh the token URI method of the nft contract the image is going to be generated by the art contract so it's going to make a a call to the art contract and when minting an nft we are going to check the balance that the Minter has in the year C20 contract okay so the me will need to have uh a minimum balance of that token to be able to mean um okay the code is here so let's take a look at it yeah here all right if um I mean this code is much more complex than the than the previous one so don't worry you can take a look later at it but I'm just going to explain the the the important things that we just saw okay so in this repo we have these three folders this adart folder erc20 folder and nft folder which contains the three contracts we just mentioned right the nft contract is an uh stylus project it has the the well the main file which is the the leave RS file and here um oh yeah and it also has the erc721 implementation that we are using as a base for our nft this Bas uh also this code is based on um another code that my colleague Rachel wrote in one workshop last year so if you've seen it might look familiar to you if you've seen that Workshop so this contract what it does is that it has the following um storage variables following instruct uh so we have we are storing here the art contract address and the ERC token contract address because we will need those to make external calls and then all the variables that are exposed by are stored in the ERC 721 implementation right and well the functions that this NFD has is well the basic functions of an NFD me save meat sorry burn token uis all that okay now the ad contract is also stylus project okay this one is a bit simpler it only stores the token contract address because we will need it for one thing that we we're going to see later and then it has the generate generate art function which is going to generate the art based on a token ID and the owner okay it's going to generate the same image but the colors are going to change based on on the token ID and the and the owner of that nftd and they initialize on the getter of the of the storage variable now notice here that we have a function called generate art and and a function called generate art with owner but we are using the same macro on top of those functions which is generate art here we are telling stylus that for both method we want um we want like if we are calling this contract uh if we are calling the method generate art of this contract either of these two functions are going to be called and stus is going to determine which one based on the arguments that we pass if we pass only a token ID this method is going to be called and if we pass a token ID on an owner this method is going to be called okay um we don't necessarily necessarily need to do it this way but I'm going to show you why I did it this way later okay and finally uh the erc20 solidity contract it's just a basic erc20 contract based on the open solidity open seing implementation and just has the mint function and I've added here a mint nftd function to be able to meet the NFD from here okay so I want to show you how uh how we've implemented the interactions between the different contracts here so if we go up to the interfaces that we are importing we can see another example so we are importing here both interfaces one for the art contract and one for the erc20 and we are importing the the method that the methods that we are going to use generate art notice that we are using the the method that takes two arguments token ID and owner so we are going to call the second method of the of the two we saw and the initialize because we need need to pass the the different addresses to the to all the contracts and for the erc20 we just need to know the balance of the user who is going to meet so we just need to import that one and the set nft is for the for the special function that we added so let's take a look at how token URI method uh is implemented okay so when we call the token URI method in this Con contract as um as we mentioned before we are going to generate that image in the Arts contract which is another stylus contract right um because we are following the implementation the standard ESC 721 so we only pass a token ID and um what we do is that we get the owner of that token ID here and then we make the call to the ad contract here we just declare the well we get the address we declare the variable we craft the configuration we take just the default configuration and we call generate ad we call generate that and we pass the token ID and the owner okay and what we do in the when we receive the call in the art contract we mentioned that we are calling this one because we're passing both parameters we call the Gen art uh internal method and we create the PNG and we just um return the bay 64 uh string of that PNG right now we also have we could also have called this generate our contract only pass the token ID and give the responsibility of finding the owner of that token ID in this contract in the art contract but the problem is that if we do that the first thing that we have to do here is to find the owner is to make a call to the nft contract to find the owner of the of that token ID right and if we do that we will be re-entering the first contract so the Alternatives that we have here is we either enable re-entrancy on stylus for this contractor or we uh we do what what we did here which is we create a different method to avoid the re-entrancy call the re-entrant call okay and that's uh the stylus contract calling the the other stylus contract now if we go to the mint function we have two minting functions one means that just meanss the the token to the user who's making the call and mean to who means the token and send it to another address and they both do basically the same they call this internal method user has enough erc20 token balance and if it has enough balance it will mean the token token so when we go to this internal method we see that we are going to make a a a call to the solidity contract and we do it uh yeah like this basically it's the same as calling the RAS contract we just take the create the the the erc20 token contract variable based on the interface we imported we craft a new configuration and we just call balance off on that contract okay so we are making uh two external call one to a rest um a stylus contract and one to a solidity contract and we are doing it the same way here we are treating everything uh the same way right and finally I wanted to show you also yeah the call that we are making in the erc20 contract because this one is interesting so we are allowing a user to meet an nft from the erc20 contract and the only thing that we do is that we import the interface of the nft contract we just need the mean to function and we make the call down here to the mean to function right so remember that when we call the mean two function here we will check the balance that the user has in the erc20 contract so what's happening here is that the user the user is making a call to the solidity contract who's calling the rest contract who's then calling the solidity contract again we have a re-enter call there but this one is not going to revert because it started with solidity and it's re-entering solidity okay um yeah I hope you guys are not DIY with all these calls that we are making here and there but I I hope you get the point so basically in the end we are calling different contracts we are making calls between different contracts but we are treating the interfaces the same way um it doesn't matter if it is a stylus contract or a solidity contract and I think we have time to run some scripts here so we have in this folder in this script folder we have a set of scripts that just perform individual actions so we are going to first uh deploy the contracts we are going to use cargo stylus deploy for the for the stylus contracts and we are going to use um Forge create for the solidity contracts so we are going to brand that and see some examples there okay so let's first deploy the contract okay and here we have the same case as before because I already deployed this code in the test net I don't need to activate it it's already activated and we have we can see that here stylus program sorry stylus program with the same wasm code is already activated on chain this deploy script is also going to make an uh a call to the initialized method to just share the different uh contract addresses with the different contracts so they know so they know um where all the contracts are and they can interact with each other okay and again while we wait for this I know I'm talking too fast but in the end you are going to to be able to to to get the link to all these resources and you can follow along later so we have these three contracts here so let's first try to uh mint an nft like that without having any erc20 tokens I think it's this way okay so if I go scripts means nft this should revert because I don't have any erc20 tokens so let's mint some tokens oh I can't use that one let's mean so some tokens here wait because I don't remember now how was the variable called okay vc20 contracts I can take this one so let's mean some tokens all right so now let's try to meet an nft okay and just to show you how the image looks like uh let's let's see let's generate the image I think it's well it was called uh get token image yeah get token image but you see the image here you can see exactly how it is no I mean this script also generates an image in in the image folder okay so we can see here that it has this small Smiley in this color so we are going to transfer that to another account we have transfer nft okay and we are going to generate get the token image again well these scripts actually work uh like for example I've hardcoded everything when I transfer a token I'm always transferring the the token ID zero to the same address and yeah the same for generating the image so if we see the new image now the face is red that means that it's taking taking a different owner and yeah and I think that's all there are a bunch of scripts more that you can play with this all of this is explained in the in the repo and actually going to show you now the QR code because we are running out of time and yeah there you have it again this QR code will point to the to the re of the project we just saw with the three contracts in that Ry in the rmy of that project we are going to see all the resources that we just mentioned if you have any doubt about uh this presentation or stylus in general um you can find me find us at our booth you can also ask on telegram or Discord and I think that's it I hope I wasn't like too quick that you got everything that I wanted to say okay thank you very much w [Music]
Automatic transcript — names and jargon may be misspelled.