New Ethereum talks, every Monday. The week's conference uploads by event, in your inbox.

Loading player…

Mina zkApps 🛠 Zero Knowledge Programming with TypeScript - Jack Servia

ETHGlobalMon, Oct 9, 2023, 12:00 AM

Join Jack Servia of Mina Protocol for a workshop titled "Zero Knowledge Programming with TypeScript" Thank you for joining us for ETHSanFrancisco—our first west-coast hackathon in nearly four years. This was officially our biggest event ever 🎉 👥 1700 attendees 🗺 from 46 countries 🌱 38% new to web3 📮 284 projects And: ETHGlobal just turned five! 5️⃣🎂 Thanks to every single one of you for making this community great 💙 --------------------------- Follow us: https://twitter.com/ETHGlobal​ Check us out: https://ethglobal.co​m Email us at: hello@ethglobal.com #ethereum #web3 #blockchain #eth

Transcript

OK. Hello everyone. Thank you for being here. I'm Jack, a developer engagement engineer at O1 Labs. We are the company that created the Mina protocol, and now we continue to develop tools for it.

Em. That's what we're going to talk about today: Mina and SnarkyJS, the smart contract language for Mina. Therefore. Yes, here is our agenda. Sorry, it's a bit of a hassle for us.

I'll do it like this . Em. Good. So, first we'll talk about SnarkyJS— talk about SnarkyJS— it's a TypeScript library that can be used to create zero- disclosure proofs, and it's also a smart contract language for the Mina protocol. We will look at an example of creating a simple contract that will allow you to increment a number only if it is the next in the Fibonacci sequence.

And then we'll make it recursive, which is a strategy we can use to allow this code to...Um. Actually, we'll deal with this when we get to the appropriate moment appropriate moment . We're going to talk about the Mina protocol, which is kind of a more general...Um.

Sorry, we're just... okay, let's get started. So, SnarkyJS is a TypeScript library for defining zero- disclosure proofs, as well as a smart contract language for the Mina protocol. It looks like this It looks like this , but don't worry, we'll go into more detail about that in a second. Everything is written in TypeScript, so you can continue to use your usual tools like Prettier, ESLint, VS Code, npm.

It's very easy to learn. IntelliSense is so good that so good that most people will probably be able to just dive into the repository with ready-made code and figure it out by simply hovering over incomprehensible elements incomprehensible elements , because we have detailed descriptions of all the functionality. It is also extremely powerful. And this is for two reasons. The first is Kimchi, our evidence system, which is absolutely cutting-edge.

It has a number of features that are truly unique. And it is extremely well suited for this use case use case . First of all, it has a completely reliable setup. So there are no ceremonies. There is no "toxic waste".

She just works. We have special restrictions for Poseidon, elliptic curves, and encryption. This makes operations that you will perform frequently much more efficient. Um, the size of the proof is constant. So you can perform as many calculations as you want, and the size of the proof always remains the same, as does the difficulty of verifying it.

It is recursive, which means that you can create a proof and then check it in the process of creating another proof. And this has a lot of pretty interesting consequences, which we'll talk about a little later. Finally a little later. Finally , it's "plunkish" so we can add new features like dynamic array access and a few other things we're working on. What about the SnarkyJS library?

This is the other side of the equation. We created the SnarkyJS library to be as easy to use and expressive as possible. So yes, method chaining allows developers to easily think linearly when writing programs. You seem to think: here is my data, here is what should happen to it , and here is where it will eventually end up. This makes it clearer what is happening inside your contract compared to what is happening, for example, in code that is executed before the contract is launched.

So yeah, let's see what it looks like. Em. If we want to know if this assumption is not equal to zero, we can call the equals method and then simply add a not method to the end. We can do the same thing: if we want to add two values, we simply call the add method on white pegs and pass an argument. Therefore, custom schema values provide a level of abstraction that greatly simplifies working with data.

This is essentially a class that we have that you can extend to create, in our case, "pegs". It's like four pegs on a game board. Em. Fundamentally, zero-disclosure proofs require that everything you work with be represented in a data type called a "field" . This is essentially very similar to a 256-bit unsigned integer, except that division works completely differently here.

And yes, it's not really important to go into detail about why this is necessary, but it's a universal requirement for all modern zero- disclosure evidence systems. And that makes... programming a little more difficult, especially when you're just starting out. So this abstraction of schema values ​​will allow you to essentially define a way to convert the type that you're used to working with, like in this case, let's say a JavaScript object that has four values ​​for each of these pins, and then it will map them into these field elements for you, and do the reverse operation when it comes time to convert something from a representation in the schema to a representation that's easier to work with. And finally, many of the things finally, many of the things you need are already implemented in snarky.

js. So what we've included today included today is all of these types, efficient Poseidon hash functions, efficient encryption and decryption, efficient signatures, Merkle trees, and the recursion API. So all of these types are schema values, which are again constructed from this field element. Ultimately, they consist of a field element, but you can work with them just like you would work with a 64- would work with a 64- bit unsigned integer in any other language. Why did we choose TypeScript?

The reason is that we are ecosystem-focused, and zero- disclosure groups are great disclosure groups are great because they open the door for cryptographers to create incredible new things that make the impossible possible. But it would also be great if we could make this available to people who want to build user-centric protocols or products . And this is exactly what we strive for. We aim for the same high level of code reuse as in the JavaScript ecosystem. And yes, we'll touch on that a little later as well.

Here's a quick overview of everything we talked about so you can review the slides after the presentation and get a concise idea of ​​everything that was said. So how does SnarkyJS work? Oh, and the slides will also be available later. There is a QR available later. There is a QR code.

You can scan it, there is a lot of different information there. Everything I talked about is there. So, how does SnarkyJS work? Here it is in five sentences. This is a TypeScript library.

All information is represented in one of the types compatible with SnarkyJS, and ultimately they all consist of this field type. SnarkyJS provides classes and functions that are compatible with this field type. This allows you to represent anything you do with these types of methods as what's called an arithmetic operation called an arithmetic operation —essentially a mathematical representation of the program, which is important because we can feed it into a zero- disclosure system, which is itself a mathematical problem mathematical problem . So, a user interacting with a SnarkyJS program can run it as regular TypeScript, and then optionally pass in all the computed values. In fact, they can feed their execution trace into this generated math problem and use it to create a zero- disclosure proof.

The developer experience is very similar to working with React: it's almost regular JavaScript, but now with an additional layer that is quite expressive and helps perform specific tasks. And therefore, getting started is quite easy. So, how do smart contracts work? Developers write them in TypeScript and then deploy only the verification key in the ZK ZK app account. A verification key is a kind of commitment to code with an additional property: it can be used to verify zero- disclosure evidence generated by that code.

When we want to deploy a ZK application on the Mina network, we simply send a transaction with this verification key, and that is the only thing stored on the chain. The code itself is not in the chain, only this verification key is stored there. Users launch a smart contract in their browser and generate a zero- disclosure proof of their interaction. So the code is not executed in a chain. It runs directly in the browser.

This is cool for several reasons. Yes. We send a transaction that is proof with zero disclosure. If it is valid, the transaction is applied, and if not, it if not, it is rejected. If the Mina blockchain can verify this proof, it records all relevant state updates.

Here's what it looks like at a high level: we have a smart contract method where we pass in user-generated arguments and the state of the smart contract. This, in fact, is the state of the smart smart contract itself. It must be passed as an argument. The reason is that the smart that the smart contract is not executed on the blockchain, so we have to get the values, pass them, and execute everything ourselves. We also gain meaning for the state of the world around us.

This could be data such as block height if it is important to your transaction. As a result, we get a smart smart contract state update and a world state update. So when we run a smart run a smart contract on the Mina network, it looks something like this: if a transaction has the effect of transferring balance, say from you to me, I just send a zero- disclosure proof and two new values. One of them is your balance, which will decrease, and the other is will decrease, and the other is my balance, which will increase. If the zero-disclosure proof is valid, we know the transaction is legitimate and can simply write down these two values.

More on that later. So, how do zk apps work? You can add a smart contract to your UI repository and deploy it—that's all it takes. A smart contract is simply a set of code written in TypeScript. You can host it on GitHub, npm, or anywhere else GitHub, npm, or anywhere else .

Then you simply install it into your frontend your frontend repository using npm install. Very simple. OK. Now let's move on to the code example. The Fibonacci sequence is a series of numbers where each subsequent number is the sum of the two previous ones.

We will write a smart will write a smart contract that will calculate the next number in the Fibonacci sequence. It will have two state elements: n minus two and n minus one. And it will have one method—update. This will allow us to update n minus two and n minus one if we pass in the correct next number from the Fibonacci sequence. To write a zk application, we can simply inherit the SmartContract class from snarky.

js. So, we have a smart we have a smart contract here called the Fibonacci Sequence. We can define our state in the blockchain by simply creating variables and adding a state decorator with the type of that state as an argument. So, we create two state elements. Each of them has its own type, and they will be located directly on the Mina blockchain.

SnarkyJS takes care of the work: it confirms the changes, proves that we made them correctly, and ensures that the Mina network received the request for those changes. Uh-huh. Next, we have the deploy method, which is called directly when deploying the smart contract. The deploy arguments are typically passed through the ZK app CLI—a developer tool we'll talk about soon— we'll talk about soon— and can be left unchanged in most contracts. You can use them to configure settings during deployment, such as setting permissions for a contract or contract account.

In this case, we will also use them to initialize the values ​​of our state in the blockchain. So we'll set n minus 2 to zero and n minus 1 to one. The next step will be to add an update method that users will call . As you can see, update takes n as an argument of type Field, and we add a method decorator to it. This decorator tells SnarkyJS, “Hey, this is the code that users will call,” just like they call methods in Ethereum smart contracts.

When users call it, we have to prove the correctness of the execution and send the result to the Mina network. Therefore. It's worth noting that any argument we pass to the method, and everything that happens inside it, is completely confidential. It happens on your computer and doesn't leave it. Unless, of course, the method creates an event or changes some state in the blockchain.

Um, but even in those cases, you can send an event that is a hash of the actual value and have some sort of commitment, or you can store the hash of the value. Um, you know, it's much easier to keep even persistent data confidential this way. Hmm, but yeah, it's worth mentioning. Ahem. Finally, we will start implementing the functionality of this method.

So, in the update method, we want to get the values ​​of these state variables n-1 and n-2 in the blockchain. We simply call the get method for n-1 and n-2 and write them to the constants current n-1 and current n-2. So when a smart current n-2. So when a smart contract executes this get method, it essentially says: go to the Mina blockchain, get the values, and store them here. Ahem.

The next thing we have is, um. We will calculate what the new state should be , the next number in the Fibonacci sequence. We do this by simply calling the add method for n- add method for n- 2 and passing n-1 as an argument. So we have the sum of the last two values ​​in this new state. Um, and then we check if it's equal to the value we passed.

This assert equals statement means that if this condition is not met, it will not be possible to generate a valid proof with zero disclosure. So, if you pass anything other than the next number in the Fibonacci sequence into this method, you simply won't be able to get a valid proof with zero disclosure. And you will not be able to send a valid transaction to the Mina network. Finally, we can set this state in the blockchain to a new value. We will set n-2 as current n will set n-2 as current n -1, and n-1 as the new state.

This is simply shifting all values ​​by one step. By doing this, Mina will once again make sure that you cannot call these set methods until everything that happened has been confirmed by a valid zero- disclosure proof. This is just as safe as doing it directly on another blockchain by setting some state inside your contract. Ahem. that's kind of the general structure of it.

We usually define our on-chain state at the very beginning. We have a deployment method and then we add user-accessible methods below. So, that's cool, but what else can we do? Well, we can make it recursive, and that's a unique feature of how Mina works, at least right now, in our proof system. This means that our zero- disclosure proofs can be passed as arguments to other zero- disclosure proofs and effectively checked internally.

This means that if I have a lot of calculations, I can divide them, for example, into 10 different parts, execute each one, prove the correctness prove the correctness , and then combine these proofs into one. Yes, we can nest recursive proofs one inside the other with arbitrary branches and unions, and do this an infinite number of times. This was made possible by this ZK program. In essence, it is a smart contract, but somewhat simplified. The program is just the basic part, and the smart contract is like a superstructure on top of it.

We define a public input and some methods. We see that for private inputs we pass a proof, and the method can accept not only values ​​of type int, but also fib 1 and fib 2—the same proofs as what is generated here. So generated here. So , this program creates a proof, and then can accept the created proofs as arguments to form a new proof. We check these two proofs.

Then we do the same thing as before. This can be a pretty powerful tool in many cases. This allows, for example, to create games where users don't have to wait for blocks and pay for gas every time they make a move they make a move . You can, you know, set up the game so that, for example, I make a move. I'll prove to you that I made the right move.

You review the proof that I made the move correctly, make your move, and then prove that your move is correct, and also prove that you checked the proof of my move correctly. And so we continue in turn, and as a result we get one proof of the same size as each of the previous ones. We are not creating more and more information. We just exchange these fixed- size blocks. And finally, we have this evidence that proves the entire history of the game.

So we can send this proof to the Mina blockchain as a transaction or something like that and complete the entire game with just one transaction. So there's no need, it's actually a great user experience, like in a regular game, because you don't wait for blocks or pay transaction fees, only at the end. So, it's pretty simple. We can simply wrap our ZK wrap our ZK program in a proof class. And then we can pass it in, setting the type of argument we're passing in as this Fibonacci sequence proof, and just call the check function—if the proof is valid, we move on.

If the proof is invalid, then, again, it is impossible to generate a valid proof of this part. That's pretty cool. Okay, now let's get to the most interesting part most interesting part . It is a tool that can be used to create things, particularly for the Mina network particularly for the Mina network . Mina is a first-level blockchain that confirms its entire finalized state using these zero- disclosure recursive proofs.

This means that it is not growing. Over time, it remains a fixed size. Or at least the amount of information needed to verify Mina's current finalized state remains the same. So this means that, for example, if I have an account, I can store the root state, proof that that state was obtained legally, and all the information about my account that I need, in those 22 kilobytes. This is really cool, but it's also actually very useful, and there are a few reasons for that.

a few reasons for that. First, it is confidentiality. Ethereum smart contracts run on every node, so all information is public. Instead, Mina smart contracts run in the browser, so arguments and intermediate values are private by default. You see private by default.

You see , we only send a status update and our proof, we check the proof and then update the status if the proof is valid. This also opens the door to easier scaling of systems scaling of systems . There is no gas payment model here. ZK gas payment model here. ZK applications work off-network, and the amount of computation does not affect the transaction cost.

You can perform as many calculations as you want within a single transaction. You can make these transactions asynchronous. You can, sorry, you can make these calculations asynchronous. You can do all sorts of crazy things because it's literally TypeScript code that then proves that it worked correctly, and we get a proof of fixed size, regardless of the amount of computation. That's pretty cool.

And it can also be used to create specialized rollups for applications, like the game idea we talked about earlier. We can build... In principle, we can do it because we don't need the entire network to prove that we did something correctly. We rely on cryptography, not game theory. We can prove things in a narrower context and then only confirm the chain when necessary.

This makes it possible to create all sorts of things that would be too expensive to build even on highly scalable blockchains today. Finally, it enhances decentralization, as it is possible to verify the entire Mina state using only a small, zero- disclosure proof; so there is no need to rely on trusted third-party node operators like node operators like Infura. People can connect directly. It also makes it easier to create cities, which is pretty cool. So smart contracts on other networks can connect to the entire Mina state simply by checking the latest proof.

So, it's like, you know, there's no multi- multi- signatures or any weird, I don't know, it doesn't look like a regular bridge. Essentially, you can verify that Mina consensus is working correctly and valid up to a certain point by simply taking this most recent proof and verifying it. So, if you can write a smart write a smart contract that does this on Ethereum, then you can transfer the entire state of Mina to Ethereum without adding any additional trust assumptions, without having to lock liquidity anywhere, and, really, without anything like that . It's very simple. The user just says, "Hey, here's Mina's state," or, you know, Mina's root state and zero- disclosure proof.

I will simply call this method in the Ethereum contract, pass the root state and a zero- disclosure proof. The contract will check this proof, and if it is valid and the block height is greater than the previous one, then we will simply update the state. And that's actually very, very cool. By the way, the Nil Foundation is working on this, and they have a demo version on the testnet. So if you want, you can use the link in the QR code at the end and experiment with it.

This allows the entire state of Mina to be transferred to one of the Ethereum testnets, and it is already in the audit stage. So, we also have oracles. Users will be able to create TLS will be able to create TLS proofs that can transfer data from any website to the Mina blockchain. The way it works is that now when you go to a site, you see a lock in the browser, and that's the result of an interactive process. It essentially guarantees, "Hey, I'm really connecting to Amazon."

This is really Amazon to Amazon." This is really Amazon . I send them my credit card details. And I know that no one can see them. It provides such guarantees, but it is an interactive process interactive process .

Therefore, it is not suitable for blockchain. Amazon can prove to me that they prove to me that they are Amazon and that our interaction was like this, but they can't prove it to Ethereum. Um, because yeah, I think it's supposed to be this, you know, interactive thing interactive thing . They can't just generate some kind of signature or something some kind of signature or something that says, "Hey, everything worked out well." But with zero- disclosure evidence, you can take these interactive processes and turn them into, you know, static evidence that can be verified without interaction.

And so, doing this with Mina will allow us to, you know allow us to, you know , essentially: you can go to any website, prove that you actually visited that site, that it was that site, well, that they actually had certificates for their domain name or whatever, and that they actually sent you something. So I could, for example, prove that I logged into my bank account and they sent me a web page that said my balance was X dollars. And then I could take that evidence and, say, add it to another piece of evidence that proves Jack is a unique person by hashing his social security number or something like that and checking to see if he's on the list. And let's also check if Jack has more than, say, $1. And if I have more than one dollar, then we return a boolean value of "true".

And if not, then we return the boolean value " boolean value " false". So we can supplement this information as much as we want. And actually want. And actually , right after this presentation, we'll have a live tutorial that will allow you to create something similar for, say, a fake credit score oracle. It's just an API that returns a fake credit score and is signed.

So you can do it today with signed data. But ZK oracles will also allow you to have signed data that comes over SSL exchange. So that's pretty cool. And what else? Well, we don't really know everything that's possible yet.

And we hope that people like you will help us figure it out. There are a lot of things, probably every six months it seems like we learn about new opportunities that we didn't even know existed six months ago. And so that's the point of attending hackathons, so that people like you can create something new. There are probably many more cool things we can create that we don't even know about. And you should create them.

We have prizes. We will pay you money if you create it. Well, yes. So, where can you learn more, ask questions, and get answers? How to get started?

Very, very simple. Install ZK app CLI. This is our only tool for developers. It is very powerful and very easy to use. You launch a ZK project, give it a name, and it creates a repository with the base code.

The underlying code is simply a smart simply a smart contract that appears to add two numbers and store the result on the network. Testing is set up, linter is configured, everything is ready to go. And when it 's time to deploy, the ZK app CLI will connect to the test network and create a transaction to deploy that application. So, you can easily install it, get a project, and as I said, the easiest way to get started is to install it, create a project, look at the code, use IntelliSense, and understand how it works. This should be pretty simple.

Ways to join the community include creating ZK include creating ZK applications. This is a good thing. You can create educational content or engage in mentoring, for example, chatting on Discord, etc. Mina Foundation provides quarterly grants for work already completed . So if you do something cool, maybe in a month or two you'll get paid get paid .

And finally, these are our social media pages. Here is our Discord. Here is a link to our documentation, and you should definitely join the ZKAP developers channel on our Discord. This QR code leads to a Notion page that has slides from this presentation and links to several other talks with additional information. Links to Nil Foundation materials.

Basically, all the information you need is hidden behind this QR code. I think that's all. Thank you all for your attention. Perfectly.

Automatic transcript — names and jargon may be misspelled.