Aztec 🛠Learn Noir in an Afternoon
ETHGlobal·Mon, Oct 9, 2023, 12:00 AM
Join Aztec Labs for workshop titled "Learn Noir in an afternoon" This workshop is part of ETHGlobal's flagship online event: ETHOnline 2023! ETHOnline 2023 has grown into one of the most exciting events on our calendar, anticipated by hackers all over the world. ETHOnline is a three week long online hackathon with over $200,000 USD in prizes as well as a series of curated summits, celebrating some of the most significant happenings & learnings from the past 12 months in web3. ----------------- Follow us: https://twitter.com/ETHGlobal​ Check us out: https://ethglobal.co​m Email us at: hello@ethglobal.com
Transcript
foreign [Music] hello welcome to learn Noir in an afternoon or get your money back I'm Jose per Souza I'm a devrel engineer at Aztec labs and today we're gonna be talking about Noir the zika ASL developed by Aster clubs we're going to be talking a little bit about DK uh what is okay what can you do with ZK we'll also talk a little bit about Noir why are we doing this why is Noir needed why what can you do with more that you can do with other ckdsls then we're gonna present our project our little project for today and finally we're gonna hack it and yeah just start hacking stuff so we know that zero knowledge proofs are really powerful you can do stuff that you can do you can't do with any other um Tech basically but usually with great power come univariate polynomial commitments and this is kind of the problem because if you don't get the math behind ZK usually you're just left in the dark and and basically the purpose of Noir is to make this go away and just abstract all the complexities from the mathematical part of the ZK space so we need this usable Universal CK domain specific language and yeah we like rust rust is cool so yeah we just went and copied the syntax from rust and so if you try to find the difference between the two programs they're yeah they're usually you're going to have a very bad time and so this is just an example if you try to spot the difference between these two um Snippets yeah you're not gonna find them one of them is worth the other one is smart and as you can see there are little differences in this case there are zero we want you to write code instead of writing circuits so if you if you've used other cicadia cells in the past maybe you've written like circuits on on a piece of paper and then connect the wires and that's basically how you write the circuit we we believe that the best Paradigm is one that we are used to which is just writing code like just writing actual programs like like you'd write solidity or JavaScript or rest and this also allows you like for very um very experienced developers so just use no art to abstract their own stuff so maybe they just want a very easy way to use ecd essay signature verification for example so maybe they don't want to write their own stuff and just use our like Noir modules or external libraries uh well this is still easy for beginners to start using CK So today we're gonna be building a little project I'm going to show you next what it is and we're going to divide this in like three chapters the first one is literally about Kumar and especially nargo and Mara how can you simply get started with the new Noir project we're going to be talking about the syntax of Noah I'm gonna be writing tests actually they are built in with nargo but I'm going to show you how to make them fail and stuff and and finally what we all care about which is proofs actually generating the proofs and verify them uh we're gonna also be integrating some libraries namely the standard live standard library that you will find many of the built-ins in in Noir and other libraries like external libraries built by the community or libraries that you want to build yourself and finally we're going to be looking at the browser usage um yes it's a bit of a better but you can still you can still do it and you can use it in in your dad and I'm going to show you how uh we're gonna be leaving behind the verification of proofs on chain I'm going to show you basically how to generate the contract but from then on I'm I'm assuming that you know how to deploy a contract with Foundry or hard hat or truffle is not around anymore unfortunately so that's it um I'm just rambling here so it should get started finally yeah you should check out the the workshop resources as well um especially the workshop resources you're gonna have a repo there with the stuff that I'm going to be using for today so I highly recommend you to to scan this QR code um also the Noir docs uh this is basically the documentation that in our team has been putting putting on and it should give you most of the answers you're looking for and finally my my link trade is not link trees I think it's a limo yeah it's a limo thing you can you can check out their all my like Twitter handle and and Telegram and stuff so you can talk with me and ask questions if you if you answer and so that's it let's let's start hacking basically so I'm gonna pull up my vs code editor here uh as you can see this is already in the in the workshop resources I just um mentioned to you and if you check out the readme you're gonna find uh this Noir app tool um so Noir app is if you used to CLI tools like rest app or Foundry app which is actually here it's basically a CLI tool that we install uh we'll install nargo and if you used to rest you also know cargo which is kind of an npm thing that will install like a package it's a version manager a package manager and also Runner and run scripts and stuff so that's basically what nargo does so to install more app you just go and install it like it you can just copy this you can trust me bro and just just copy this thing it will install more app for you it's going to take a little bit longer for you so just pause the video and wait for it to complete and yeah it says that you should just run Source like and just Source the the batch file or just start a new terminal session and then finally you should have Nora around and you can check what exactly what this it does what does it do and you're gonna get like the options for it and so it's pretty powerful you can install like specific versions and branches PR scrimmates and stuff in this case I will even though I think the latest version of nargo is 0.10 let's just go ahead and install like a specific version for that and so I'm going to install like version 0.11 um so let's you just go and install that and it will download and install for you I guess that's one I had already because it was really fast and then you can just go and run another version and finally you should have here your version another thing that you could probably find useful is the vs code plugin so if you use vs code you can just go here extensions and basically say just you can now right now and you're gonna get uh yeah here Noir language support so yeah this is it's a very awesome version but it's really cool and it can run like it has some code lens that can be useful for you to run you also get like syntax highlighting which is which is always cool so with Naruto you can basically do all kinds of really cool stuff like running your code and installing package and starting a new project and that's basically what we're going to be doing uh so you go you can let's just go run nargo help to see what can we do with nargo uh in this case we're going to just use the new command and just call it like Noir project and yeah it will generate a new project here and you have two files basically narco.com is basically the source of your project you can define whether it's a library or a binary so yeah also Define dependencies and workspaces here for now we're just gonna leave it as it is don't change it also Noir generates a main main lot more file for you which basically has a very basic circuit you can you can test and run and and do whatever you want um and so yeah let's just go over it and see how how can you run your own and so let's start with that and syntax which is means function basically and you need to have a main function uh that's part of it because you're running the main domain file if you have other files yeah you can have like modules and stuff you can look at it in the documentation and you also need to Define like the name of your input and also their type and you also need to define whether they are public or private so we think that private privacy is normal so you won't need to define the stuff that you want to make public and so the biggest difference is that obviously if you have something that is public you gotta assume that the verifier has that in their position while for private it's stuff that it's only on your machine yet you don't want to reveal but you still have want to prove some calculations on it in this case we're going to use the fill type which is basically an element of a finite field so you can treat it pretty much as a kind of a big integer and make all kinds of really cool um really cool operations or arithmetic operations on that and that's basically what what field is for practical purposes if you want to Define an array for example then you just do it just like in rest you define the type and then you find then how many how many elements does your array have one thing that you just you should notice is that you need to know this at compile time there is no way of just passing like a slice this doesn't work with basically any of the zika languages I've I've ever worked with so yeah this is not new another thing we can use is like some really cool return values so you can have like public field and make this return a field and so you can have like for example let's see and say X Plus Y and then just assert like X is different from Y and then just turn Z and and yeah this this will return you uh fill and some people ask you ask me like why why should I have like Public public outputs for so yeah for return values you know why why why why why do they have to be public um and the reason is like basically the way it's it's treating the return value it actually has a as an output as an input so this would be just the same as like returning um something like this public field and then just constraining at the end so as you probably noticed I already used some arithmetic on it uh you can yeah you can you can sum them up you can you can subtract them you can do all kinds of really cool stuff and if you want to know exactly what can you can't do with Fields you can actually just check the the noordox you know do that for you just here are the noidox you can go here like on the language Concepts and see uh all the things you can do like logical operations and just send them and even like if bit shifts and stuff as long as they are integers um and yeah so this list will hopefully give you some examples as well you can you can skin through if you're interested also the shorthand operators which are really really useful at times you can also use loops and control flow stuff like ifs and elves and stuff um so basically the way you write them it's just just like in rest you'd say like for uh for for I in some kind of range you you say oh thanks thanks GitHub co-pilot uh it will already knew some example for you yeah you can run like your follow-ups for Loop just like this um and you can also do it like a conditional so you can say if if X is not one or if it is one then then Y is something like this so yeah you can run you can run if else's just like you do with with rest there's also the assort keyword that you probably saw at the beginning um and that you're gonna say search X is different from y um so this is something that you don't get in rest so yeah if you try to run this it will say they'll complain that it doesn't know what what assert is and this is basically what you want your program to do basically I want this proof to generate some constraint and say that this proof will only be valid if x is different from Y and I don't want to reveal what x is and and so that's that's what a third keyword does another really cool thing they can do is struct so yeah you can Define like a new struct and say a struct version for example and just have some stuff like not strings we have strings but yeah they they are yeah let's not use them not today um so you can Define strikes and just pass them like you can pass that if your ex could be a person for example with with x x age Etc so for our project let's imagine that you are the owner of a Fight Club so you're gonna say like each fighter is a person um and that person has has an age which is going to be a fill for example and you want to check that only people with a certain above a certain age are allowed into your Fight Club you also want to check for example that they know like the password uh to enter your flight club there was a secret password that you don't want to bouncer to know what it is uh and so let's let's just go through it and say yeah there's there's a person uh this is going to be a fighter um that has a certain age and then you're gonna have like for example a password and obviously a password is a private input so let's not reveal it but the hash of the password that's definitely something that can be known because it's very difficult to figure it out and so let's just get like password hash password hash gonna be a public input and let's say it's going to be also going to be a fill and so in in your program all you want to do it's basically two things one is just like check if age is bigger than minimum age and so second thing is like you want to check if the password hash is equal to the hash of the password so yeah GitHub copilot already know how to do it um yeah let's just see how can you use this hash thing uh another thing that can be useful in this case for example is global so you can go and say Global and say um Global minimum age is going to be a field and let's say it's 18 because I'm in Europe uh yeah I don't know if it would be different in any other country and I just some space here and so yeah let's let's just go and you can literally write two lines of code and see a fighter age of the fighter needs to be higher than the minimum age um this takes care of your first assertion and and I can I can just go and test it already I can I can go and say um let's p is a person with h for example h19 and so I can say 90 19 is here I'm gonna just pass whatever random values for the other two um yeah and and see and see this should pass I'm gonna go and run another test uh okay oh sorry I need the city into that not a project and then go and now go narrow test um oh wait sorry sorry I forgot uh it's p um yeah it will complain that sales cannot be compared uh yeah that's that's that's something that's true you can you can compare Fields so let's just cast them as you wait um let's say actually make this already anyway so it's easier and yeah this will probably pass them another really cool thing you can do with nargo is the latest versions is so is the writing test that should fail and this can be useful very useful I guess uh I just go and call test.shoot file and then you can run and test that should file um let's just go I hope it okay yeah that's you know it's already hit knows so yeah you can you can go and run Largo test and this should pass because this test should file regarding the password so we have our password and know that the verifier know what knows what the password hash is so that means in our circuit we need to Hash our password and just check if the provided if the hashtag everyone knows is equal to the hash that we are calculating in our own private input so basically we are saying the hash of the input that only I know is equal to the hash that everyone knows because it's like in a smart contract or just everyone knows for some some other reason and how can we do that we basically do that with the standard Library so you can the way you import it it's very easy because you can just um you can just report like like this it's it's just a standard Library so just dependency standard Library I don't you don't even need to add anything to naga.
com it will work out of the box um let's just go on on the browser to see basically um what do you have there and you have a wall chapter for in our standard library and this you have like really cool things like recursive proofs and Merkel tracing and stuff and also All The cryptographic Primitives that we currently support that's what I asked for the hash methods you have many hashes that we have implemented already some of them are what we call Black Box function and this basically means that this is just provided by the backend so if you use different backends you may have um they may not be implemented if you're looking for a hash method to use I would recommend you to use some very some ZK friendly hash that would be for example Pederson or Poseidon let's just go and position them because I like it and and yeah the way you import it it's just like this I'm I'm actually gonna copy this so you can see um and go over on my PS code window as well and just just place it here so I don't forget how to use it and so the way you import it is um you have STD so you can actually go here and import it here and so you can have more granularity on what exactly are you trying to import and and say let's just just let's just leave it at least as this is and so this way you can you can have your program be a little bit less verbose and just have the module your your important specifically and so in this case we want to check like you want to yeah it's not really that as GitHub said so you can have you just want to check that your password hash is equal to the hash um that you're trying to to do in this case you just go and run the password and the reason GitHub thought I was trying to pass an arrays because yeah password should be an array so it was kind of right um so yeah in this case as as I'll tell you you need to know the size uh at compile time so yeah I'm hashing two values so I'm passing the hash two so it would be three or four or five whatever depending on what you're exactly are you trying to to Hash um it says that's not being used which is which is a lie okay yeah now it's okay and yeah that's it now for for testing basically it will complain that yeah it expects a field too which is kind of true um and so here's what the utils folder can be useful because you do have like an implementation of Poseidon that you can actually run on your machine and see how how does a hash look like um so you just go here you just change your inputs and then get run this like with TS node for example and and you're gonna get an output so in this case um I think I already have two vowels here um that can be used like for 4.7 so if you have like one two for example uh the hash of that should be this so yeah in this case I'm gonna just paste and say yeah the password is one two which is a very weird password but let's let's forget about it and just say the password hash is is this one and while we are while we're here let's just go and do the same for for the test that should fail so I'm gonna just change and just changes eight for a b and this hopefully should pass like both tests um let's go and try yeah as you see they all pass this one passes because the quick value is correct this one passes because the value is incorrect if you've seen the utils folder you also have another one called the check which is basically the same thing but for using a check um which is uh yeah which is a hash function that is widely used in in ethereum it's not very busyk friendly so one thing that you want to do basically is to prove stuff and that's all fine to run tests uh but they're just they're just tests you actually want to proof and the verification stuff so the way you do it is just run run now go check and you have this prover and verifier files and yeah this is basically where you put your values and to be proved to be proven so in this case like we know what they are already so I'm gonna just go and put like my my password here um just here and my password hash in quotes um inside quotes here and my at the age of my five there's going to be 19. so you want proof on this and because this is an R it's as easy as just running Network proof you're gonna see here like the proof you there's it has the name of the project and yeah it's very difficult to understand but as you can see it's kind of succinct which is what we want in the end is uh snark right it's it's supposed to be succeed if you want to verify that you just do the same thing just go over verify and you're going to verify that the default proof that's gonna be in this directory with the name of the project at this point you're probably asking how can I do that in in a smart contract um and as always it's pretty easy you just go and run Largo code the giant verifier and it can take a little bit but will it will generate a smart contract for you um well it was fast actually this time so you have a smart contract cure which was written by very very smart people um and yeah it's gonna be a little bit difficult to understand all of this but yeah this is a smart contract you can deploy the relevant function here is probably the verify function and this is basically what what does it expect to be passed on at this point you may want to explore a little bit more about standard library and you'll probably notice that it doesn't do everything you want and that's that's okay we want we expect that and so there's a very easy way to just import other libraries uh one of my favorite libraries is the EC recovery Library um and this is by one of our community members called Colin and Colin just put the this library to basically recover an address from a signature how how can you use that so let's go back to VSCO and just go on the nargo.com and here you have dependencies here um and actually there's a there's here yeah I'll just an example of how can you use AC recover uh which is like this you go easy recover you you check the tag and then if you want to import it uh it's it's very easy you go here and you just import it just use that easy recover and there you have it so as promised I'll show you how to use this in in the browser so the way you can do that let's just we don't we're not going to use nargo anymore I believe so let's just close this and just leave the circuit here um and basically the way you do it is um with three packages so one as as I've explained before there is no R and that's basically the language that you're writing and that compiles into Acer which is the intermediate representation and then we have two more packages which is the acvm that will translate that into a constraint system and then finally your actual back end and so the way you use it on the browser it's just importing these three packages separately um so here in in our project folder you have the browser browser package sorry browser folder and this is a basic react page if you see here like my component it will I'm gonna input some numbers um X and Y I want to check if that X and Y are different kind of the other circuit that we know already and then once the user clicks calculate both it will calculate the proof and so yeah it will generate meters and generate the proof so the witness is that this acvm part and then from there with the witness you can generate your proof so you have here the class Noir and you are initializing a smaller new Noir um and so yeah let's let's get started I'm not going to write the whole thing but there is a file here you can we can just go and copy line by line and just check and see what exactly does it do we're going to import our actual backend which is possible then finally we're gonna have um we're gonna have also the initi acvm this is needed only for the browser uh that you need to init the acvm is going to be doing some awesome stuff in the background um and then finally execution of the circuit and and the compressed witness if you need to compress it and we're gonna do that we're gonna need that you've probably noticed that uh there isn't any Json file in our project and that's because I just forgot to compile the circuit um yeah basically that's what we're gonna do so we are in that folder already so I'm just gonna go and run Largo compile and it will compile my circuits into the target folder then we are finally like the big stuff we are initializing Rosenberg with four threads so you can actually make this six or eight or whatever um yeah just basically there's multi-thread support in versamburg and that's why it's actually so fast um we're also getting like the circuit size because we need to allocate some memory uh for for our Watson stuff so this is basically what it's doing and finally we are just storing the ACO composer which is very handy interface so to generate your proofs as for the proof generation I'm just gonna go back to my cheats file and just copy this just last two things and yeah while we're here also copy the destroy method and let's just go over them [Music] yeah this is this is actually the easiest part is this part so if you have the witness already it's just called AC grade proof from your initialized API so if you remember this API comes from the Brows number and so you've done a bunch of things super awesomer to make it ready so then it's just easy to go and call a secret proof and you you need to pass your ACU composer and the buffer and compressed and and the idea to confirm decompress your witness because it comes out of a CVM decompressed and this fast you can just ignore it it's meant to be used for recursive pros and so we are actually also abstracting this away from you and finally you should have your proof here um that this should output your your proof as for the verify proof it's kind of same thing and then yeah you you have like the the virtual factual verified proof with the SEO composer and the proof and that flag that you can ignore regarding recursive proofs and this is how you do uh how you would do that in um in in the browser or basically uh also in in node.js so I'm going to show you in a router you have some examples um one of them is the next hard hat which is basically our project but in a it's ready to use so you can you can see like details it also integrates ether so it already verifies unchain your proof as well um and yeah that's it there's a circuit circuit this is again very very easy circuit you can you can see it it's just really really basic so yeah it's as you say this is initializing the Noir uh like that init function and I'm passing this like two different values and yeah you see this is really really fast that you'll calculated your windows your proof verified it and then verify it on chain and this is it for tomorrow in an afternoon uh I hope this is was useful um just let us know if you have any questions if you want to do something more difficult then we're gonna you're having trouble uh just reach out there's the Noir Discord you should join um and also yeah you can just get in touch with us on telegram or Twitter or by any other means thank you foreign
Automatic transcript — names and jargon may be misspelled.