Lukso Network
Listen Now
About This Episode
In this episode of DevNTell, Narb welcomes Yamen Merhi, a smart contract engineer at Lukso, to provide an in-depth overview of the Lukso blockchain. Lukso is an EVM-compatible network focused on creative economies, including digital identity, fashion, and social media. Merhi explains that Lukso aims to revolutionize the blockchain user experience by abstracting complex concepts like gas and transactions through innovative standards called Lukso Standard Proposals (LSPs). Key standards discussed include LSP0 (ERC725Account), which uses smart contract-based accounts to enhance security and build on-chain identity, and LSP1 (UniversalReceiver), which allows contracts to be notified of interactions like token transfers. Merhi also introduces the concept of Universal Profiles, which combine these standards to create persistent, decentralized digital identities. The presentation concludes with a live demo of the Lukso browser extension, illustrating how users can easily create and manage their Universal Profiles.
Key Takeaways
Lukso aims to improve the blockchain user experience by abstracting technical complexities using Lukso Standard Proposals (LSPs).
Smart contract-based accounts (LSP0/ERC725) provide superior security and identity capabilities compared to traditional externally owned accounts (EOAs).
Universal Profiles on Lukso combine smart contract accounts with standardized metadata to create decentralized digital identities that can interact with various dApps.
LSP1 (UniversalReceiver) and LSP1-Delegate enable sophisticated interaction logic, such as automatically rejecting certain token transfers or managing permissions via a KeyManager.
The Lukso network is EVM-compatible and currently has a public testnet, with plans for a mainnet launch and ongoing hackathons to build the ecosystem.
Featured Guest
Yamen Merhi
DevRel @ Lukso Network
Timestamps(click to jump)
Episode Transcript
Read full transcriptHide transcript
Hi everybody! Welcome to what's going to be another great DevNTell. If you didn't know, DevNTell is a 30-minute window for members of the DAO to showcase something they are passionate about or have been working on. This could be an awesome project you've been working on, demonstrating unit testing best practices, automation goodies, smart contracts, how to structure a project, etc. Basically, if you've got a passion for something, this is your opportunity to share it with the community. And today I am happy to introduce to you Yamen, who is actually a member of the Lukso network and is going to give us an overview. Take it away, Yamen.
Thanks Narb, thanks everyone for joining. Yeah, I'm going to start by giving you a quick introduction about myself. So my name is Yamen Merhi, I'm a smart contract engineer at Lukso. I have been into the blockchain space since almost 2019 and together with Jean Cavallera, we're improving, we improved the ERC-725 standard and we're building what we call Lukso Standard Proposals. And in this presentation I'm going to give you an explanation of a few of the standards as well as a quick overview of Lukso.
But before starting, I would like to mention the hackathon. So we announced a six-week virtual hackathon. It's about building around the Lukso ecosystem, utilizing the standards that we created as well as our developer tools and library. It's going to start after five days, so from 20 July to 31 August. The total prize pool is $500,000 in LYXe. It's going to be distributed on five categories. So you can build around Universal Profiles, Social and DAOs, Multiverse and Gaming, Fashion, Art, Music and Entertainment, and there's a blue sky category where you can build whatever you want, but absolutely you should build utilizing our standards and tools. So if you want to know more information about the hackathon, you can go to lukso.network/hackathon and you can join our Discord server where we have developer resources, and if you don't have any teammates you can send a message on this chat and you can team with other Discord members.
Okay, going back to who founded Lukso. So Lukso was founded by Fabian Vogelsteller and Marjorie Hernandez. Fabian was part of the Ethereum Foundation, he was the lead dApp developer there. He also authored the ERC-20 token standard, the famous token standard that we're all familiar with. And he initially wrote web3.js, the most used library to interact with smart contracts on the blockchain. We have also Marjorie Hernandez, she is the co-founder of The Dematerialised, the web3 fashion marketplace for authenticated and virtual goods.
So Lukso will be an EVM-compatible network. It will be running ETH 2.0 as consensus. It will have a very similar setup to Ethereum in terms of the Prism beacon node and the Geth clients. And currently we are running the L16 public testnet and the next step for our network team is the mainnet.
So now you're thinking it's another blockchain, it's just a similar blockchain, why we need one, why not just sticking with one blockchain? It's a valid question but it has two answers.
The first one is scalability problems. So due to the current scalability problems that blockchain have, we can't really just use one blockchain, otherwise we will end up with really high gas fees and a congested chain.
And the second reason is community. So we believe that each blockchain defines its own community. So if we're talking about the Ethereum network, we will be probably thinking of like more DeFi use cases with limiting interaction because of the high fees. And if we're thinking about Lukso, we will be talking about much more creative ideas such as digital identity and digital fashion, social media, and digital lifestyle. So at the end they are both EVM chains, what could be built on Lukso can be built on Ethereum and the opposite is right, but it's just about picking the right standards and tools.
So the aim of Lukso is really to simplify and improve the blockchain user experience because currently it's so hard, you need to download Metamask, it's hard for non-technical people. It's like you need to download Metamask, you need to write these 12 words on a paper and hide this paper, you need to understand concepts like gas, you need to deal with failing transaction, and all of this will not make sense for non-technical user and we need to abstract all of this. And we believe that blockchain should be as simple as a click of a button or like having an application that talk with the blockchain in the background. So we really need to abstract all of these complex ideas. And abstracting is not deleting, like we cannot remove the concept of gas or transactions, we need to abstract it from the user. So an example would be instead of having the users understand what's gas, we can have what we call relay services where the user subscribe to this relay service for like $10 a month and it can execute all of his transaction without him knowing what's gas or like what's gas limit or gas price.
So how we're planning to abstract all of this complexity is through the Lukso Standard Proposals and the tools that we've been creating. So on the screen you can see the first 10 LSPs and the browser extension as well as some developer tools like erc725.js and lsp-factory. So I'm going to start with explaining a few standards then going through the browser extension. The first thing that I'm going to talk about is the problem of externally owned account and identity.
So on the blockchain we have a private key that control our address. I took my address as an example. So I own two NFTs, it's the Developer DAO NFT and the ENS domain name, and what happens if my private key is gone? All of this will be gone. And this is not the like the ideal security that we're aiming for.
And this could be easily solved with smart contract-based account. So with smart contract-based account we can have more security and we can at the same time build our identity on-chain. So one standard that form the basis for the smart contract-based account is ERC-725. So using ERC-725, it can be owned by a normal externally owned account or it could be owned by another custom contract that like maybe needs two signature in order to execute. Really like you can have the owner as whatever contract you want and whatever security you can implement.
And you can perform operations such as call, create, create2, staticcall, and delegatecall. So it's more operation than the externally owned account provide. And it's formed from ERC-725Y where you can attach unlimited information to the smart contract.
So here we can see on the left a normal smart contract where we have hardcoded variables such as my name and my age. And once this contract is deployed on the network, we can't really add more variables. Like we can change the content by having setter functions but we can't add more. And in the ERC-725 contract we have a mapping of bytes32 data key mapped to bytes data value. So using this mapping we can add like a huge number of bytes32 data key and we can attach bytes data value to it.
So it would be just two function: setData that takes as an argument the data key and the data value. So the data key would be the variable name like MyName and the data value is the content of this variable which is Yamen in this case. And once this function is executed, you will have these data stored inside the smart contract, and you can go on and store like hundred and millions of entries. And the getData function help you retrieve the information that you stored, so it takes as an argument the data key and you can provide the MyName and it will return you the content of the data key.
So this is ERC-725Y. We think that ERC-725Y will be mainly used in the future because it could be used by normal smart contracts. It could be used by token and NFT, so instead of having a tokenURI function, we can add unlimited information to the asset. Also it could be used with profiles, so you can have a smart contract where it represent your profile and you can attach whatever information you want. But this, like using ERC-725Y alone will introduce a problem that I'm going to explain with an example. So let's say we have this data key, bytes32 data key, which is the hash of the word MyVariable, and we have as data value these bunch of bytes. So the problem is that these bunch of bytes can be interpreted and decoded as string and they will mean the word Yamen, but if they are decoded as number they will mean this huge decimal number. So now we have a problem of users and website to know how they should decode this data. So that's why we proposed another standard as part of the LSPs, and it's LSP2-ERC725YJSONSchema, where it's just a schema that you pass to interfaces and users and it could tell you how to handle this data. So it's the same example, we see that the valueType and the valueContent is string, so now we know we should go with the first one and not the second one.
And using this standard, we can also write other stuff to the storage other than the singleton. So you could also write arrays and mapping and mapping with grouping which is the nested mapping. So on the right you can see how they are constructed as bytes32 data keys.
So having them as bytes32 data keys maybe a little bit hard for applications to implement because they need to construct custom keys and they need to decode the data value depending on the valueType and the valueContent. That's why the team has created erc725.js and it's very simple, you just pass the schema to the ERC725 instance and you initiate it with the schema, the contract address that you want to retrieve information from, the provider, the network, and other custom configuration that you can specify. And it's as simple as querying the name of the key and it will return you the data value decoded already decoded depending on the valueContent and the valueType. So it's really easy and straightforward.
For the second topic we're going to talk about the smart contract interaction, a problem that we have in the smart contract interaction and it's informing. So there is no standard way of informing other smart contracts about some information or even a smart contract informing other smart contract about some interaction.
And I like to give this example that I found online on LinkedIn. It's an article where someone has created a token on the Ethereum mainnet and it's basically if you take the token address and import it in Metamask, you will see that you own 100 DETS. So every address on the Ethereum mainnet now own 100 DETS of token.
So it's a really like it's a dummy example but it really serve my idea of not being aware of token transfers. And I'm going to explain the token and NFT contract design. So the ERC-20 token contract act like a registry contract, so it just track the balance of addresses. So let's say you want to transfer a token from the sender, so the sender will call the transfer function and this transfer function will just decrease the balance of the sender and it will increase the balance of the recipient. The recipient will stay completely out of this interaction and it will not know about the transfer.
And it's the same in like tokens, in the ERC-721 contract. It's just a registry contract that track the ownership of a token ID. So when the sender wants to transfer, it call the transfer function and what it does is just removing the ownership from the sender and passing it to the recipient. And also the recipient is completely outside this interaction. So this, the recipient can't know about the transfer because it's an EOA and if it's a smart contract there is no standard and unified function that all smart contracts implement and we can call to notify about the transfer.
So that's why we proposed LSP1-UniversalReceiver standard where we have a unified function called universalReceiver that all smart contracts can implement. And when you want to make the contract notified about some information or some transaction, you can just call the function with some data and it's going to emit an event to the network with the data passed to it. So I like to give examples about tokens since it's the most used in the blockchain space. So if Alice wants to transfer some token to Bob, as well as updating the balance, the token contract will inform the sender and the recipient about this transfer through calling the universalReceiver function on both the sender and the recipient contract.
So this is the UniversalReceiver standard. It has something called the UniversalReceiverDelegate which is an extension to the standard where you can have write a custom logic to a contract that you deploy on the network and then you can attach this address of the contract on the universalReceiver function as the owner of this smart contract. And what will happen is whenever someone call this universalReceiver function, this universalReceiver function will forward the call to the universalReceiverDelegate and it will run the logic inside it.
So also we're going to give an example for a token transfer. Let's say Alice wants to transfer a token to Bob. The token contract will inform the sender and the recipient through the universalReceiver function. And now Bob has a universalReceiverDelegate that he linked to the universalReceiver. So now every logic that is here will be run in the same transaction. So Bob could have any logic he wants to implement. He could have a logic where he can revert on all tokens received, so this transfer will not go through and he will revert on the token transfer.
And this pattern is actually useful for people who have influence in the Web3 space like Vitalik. We often see this like silly marketing trick that tokens and protocol play, which is like sending bunch of tokens to the address of Vitalik and then they say, 'Oh look, Vitalik owns some tokens' and then they start hyping the community about it. And then Vitalik needs to follow up this transfer by either burning the tokens or selling them. And this could result in dumping some projects or dumping the market. While this could be easily avoided if like Vitalik at first didn't accept the token transfer by having a universalReceiverDelegate that revert on all token received.
And if you don't want to revert on all token received, you can have a logic where you can only accept verified tokens. So you could have this universalReceiverDelegate that reads from a registry contract of verified tokens and only accept verified tokens. And you can even go more complex logic and have a logic where you automatically sell the token received through a decentralized exchange. So really you can build anything you want with the universalReceiverDelegate. And it's not just related to the tokens and NFT, the universalReceiver function could be implemented in any smart contract.
Can we ask questions during the presentation or you want to wait?
Yeah, we can add questions but like due to the lack of time I guess if we can leave the question for the end it would be really helpful. Like I like to do such presentation in an informal way and take question while we do this presentation, but since we have only 30 minutes, I will leave the question for the end.
Yeah, I understand.
Yeah, thank you. So now we have what we call the LSP0-ERC725Account and it's basically a combination between the LSP1-UniversalReceiver, the ERC-725X, the ERC-725Y, and ERC-165 and ERC-1271. So you should be all familiar with ERC-1271 and ERC-165, so it's for interface detection here and for signature validation. So the LSP0-ERC725Account is the account that we should use on the blockchain to operate instead of the externally owned account. And since we have a contract storage that we can attach any information to it, it makes sense to have to have a data key where we can store a JSON URL that link to our name and our description and maybe an avatar or a profile image and a background image.
So you can see here, if you go to universalprofile.cloud, all of these profiles are ERC-725Account contract. And these pictures and name are fetched directly from the smart contract itself. They are not stored like on a centralized server or fetched from a centralized server, they are directly fetched from inside the smart contract in a full decentralized way. So the combination so we standardized this data key in this standard which we call LSP3-UniversalProfile-Metadata. It's just a standard where we standardized bunch of keys like the LSP3 profile.
And the combination between LSP0-ERC725Account, which is a smart contract, and the LSP3-UniversalProfile-Metadata, which is just a bunch of data keys, form what we call Universal Profiles. And basically Universal Profiles are what we can replace like they can replace our Web2 profiles and we can do whatever we want with them. So basically we can interact with any smart contract, we can send money and native tokens to other addresses, we can own assets on this Universal Profile and be notified about them, we can link a social recovery contract to the Universal Profile, we can link a password recovery, and even a KeyManager that may make different people execute through our Universal Profile based on different permissions. And if you're if your Universal Profile is representing a DAO, you can have a voting contract that sit in front of it and just like have people vote on certain proposals and then it could be executed through the Universal Profile.
And since we mentioned the KeyManager, I want to explain the LSP6. I guess it's the last standard that I'm going to explain. And basically it's a smart contract that will be that will be the owner of the LSP0-ERC725Account and it will make several devices or addresses execute through our Universal Profile. And since we have a contract storage inside since the LSP0-ERC725Account implement the ERC-725Y where we can attach any information to the Universal Profile, it makes sense to store the permission of the users inside the Universal Profile.
So here we can see the permission of Alice, she has all the permissions, and Bob he have the permission to setData. So storing the permissions inside the Universal Profile is useful for one reason. So let's say we have a KeyManager that have the feature A and we want to upgrade to a KeyManager that have feature A and feature B, we can simply just execute a transfer ownership from this KeyManager to another KeyManager and we don't need to reset every permissions because they are already stored inside the smart contract, the Universal Profile, and the KeyManager will read from the Universal Profile and nothing will be changed.
So I would like to give an example for the DAO. So let's say we have a Universal Profile for the DAO and it's owned by a KeyManager and in the Universal Profile we have different permissions. So let's say Narb has a permission to setData and also a social media manager has a permission to setData. The voting contract where all the members of the DAO can vote has the permission of execute. A social recovery is linked to change the owner. And Nader is have the permission to deploy. So we're going to start with having Narb executing through the KeyManager. So if Narb try to execute, the transaction will revert and will not go through because he has only the permission to setData. And now if he try to setData, the transaction will go through because it's his permission. And it's the same for the social media manager, and for the execute it's the same. If the voting contract is executing through the profile it's going to pass since it has the permission to execute. But if Nader try to change the owner and he have the permission to deploy, it's also it's going to be reverted since he has not the permission to change owner.
So we have all these permissions that organize what people can do, like it organize which task the users should have. So Narb will probably like setData on the Universal Profile, the links of the recording of the DevNTell sessions. But this like having these permissions is very generic, so we introduced a more specific restrictions and it's based on data keys. So now having having Narb setting data, he can he have the permission to setData so he can change almost every key that is here in the storage. And this is somehow bad because like Narb can change the data key responsible of the profile image, like Narb will not do it, but like we should we should take our yeah we should take some organization like we should organize how it's done. So now if Narb try to setData to change the profile picture, he will be able to because he can change any data key. So we came up with what we call Allowed-ERC725YKeys and it's a restriction where we can say that Narb here have the permission to setData but he has the permission only to change the DevNTell keys.
So now if he try to change the the key responsible of the profile image, the transaction will be reverted and will not go through. And if he it's the same for the social media manager, if he try to setData and change the DevNTell keys, the DevNTell recording, it will revert because it's not his Allowed-ERC725YKey.
And we have similar restrictions such as AllowedAddresses and AllowedFunctions and AllowedStandards. So here we have a person that have the permission to execute through the KeyManager and he's only allowed to talk to three addresses. So this and this and this, and if he tries to talk to another smart contract that is not here in the AllowedAddresses, it's going to revert and it's not going to go through. So also the AllowedAddresses and the Allowed-ERC725YKeys are stored inside the ERC-725Account. So everything is stored inside the Universal Profile or the ERC-725Account and the KeyManager just read and filter if he's allowed or not based on these permissions stored inside the ERC-725Account. So it's it's the same for AllowedStandards. So let's say this caller has only the standard B allowed, he can talk to smart contracts that implement the interface B and if he talk to another smart contract that don't implement the interface B, it's going to revert.
So now we we have what we call relay execution also in the KeyManager. So we see here that the caller initiated the the transaction, so now he's paying for the gas fee of all this interaction. But here we have what we call relay execution and basically what the user A can do since he have since he have permissions, he can sign the transaction, he can sign the payload of executing and pass it to a relay service where this relay service can initiate the call and pay for the gas fee. And when when the KeyManager get the signature, it's going to recover the address of the user A and check if the user A will have permissions. So it's not related to the relay service, the relay service will just initiate the transaction and it will pay for the gas fee. So this could be done if the user doesn't want to pay for the gas fee or he don't have like native coins to to pay for the gas fee. And he could agree with the relay service for a specific payment method, so maybe in fiat. And you could have such relay service that give you credits and will allow you to execute without gas if you like watch some sort of ads. So basically you can build anything you want around the Universal Profile and the KeyManager.
So now we will go through what we call token and NFT 2.0. I will not have time to explain all of this but I will just give you few ideas. So they use ERC-725Y for the metadata, so instead of having the just the tokenURI linked, they will have the ERC-725Y metadata, then you can store the images, a 3D avatar, a JSON, you can store also the creators and the token name. And basically you can notify the sender and the recipient about the transfer, you can have safer transfer check with the force boolean, you can use bytes32 for tokenID in the LSP8 contract. So the ERC-721 use numbers as tokenID, but the LSP8 contract use bytes32 as tokenID and it can represent numbers, it can represent hashed value as serial number of a like a product, and it can represent addresses. So each tokenID can be its own address. And what's cooler is that each tokenID can be a smart contract that implement ERC-725Y storage. So now if you have a game that will update the characters, the appearance of the characters, it's as simple as updating the storage of each tokenID and it will not be directly related to the LSP8, they can do it directly on the tokenID or from the from the LSP8 contract if the tokenID are owned by the contract.
So now I'm guess I have almost finished. I'm going to show you the browser extension. So this is the browser extension, you can create a profile, you can have a password, you can pick your identicon, you can keep the profile anonymous or add some profile information. So I will add my profile photo, so it's I will choose Vitalik. I will enter the username 'test-of-Vitalik' and then I will save, and you can see we're creating the profile. It's a it's a normal transaction, so all of these pictures will be stored on-chain, that's why we need to wait because it's a normal transaction. Now the profile is being created and I'm going to show you that we need to wait probably till it's done. Yeah, once once it's done. So I'm going to so just to finalize this, to know more about the LSPs, you can go to docs.lukso.tech and there is a specific page for each standard where it's explained. And also if you want to download the browser extension you go to docs.lukso.tech on the guides section there is a guide on how to install the browser extension. And if you have any question just feel free to enter the Discord server and ask the question on the development channels, we're always responding on these channels. And thank you everyone for listening, I hope all of what I explained makes sense and I'm ready to answer all of your questions. So now we see that the profile data has been changed and we see that it's just setting data on the profile, so we're setting the data on the profile and we see here that it's executed through a relay because I don't have LYX, so it's executed through the Lukso relayer. You can download it and play with it as you want, so this browser extension you can whitelist data key, you can execute, so it's fully it's fully functional. We're still adding features and we plan to simplify the the user experience, so it can be used by non-technical people so it's probably have more like simple terms and like it's still in early stages but it's fully functional. You can create a Universal Profile with it.
Yeah, thanks everyone for listening. I'm ready to answer all of your questions.
Yeah, well done. Well done, Yamen. This is really cool. Can't wait to start playing with this on my own. Gang, is there any questions? We can take a few minutes here to answer anything you may have for Yamen.
Yeah, I have a question. So where two Universal Profiles send money to each other, it's possible to revert a transaction that you don't want to accept. Does it mean that the transaction keeps on staying like pending until someone accepts your transaction?
So basically let me reshare my screen and explain it. So we know we like using the blockchain we can't really keep something pending, it will be directly executed. So if we have this universalReceiverDelegate that revert on the token received, it's already deployed on the network. So when Alice want to transfer the token to Bob, it will call the transfer function. The transfer function will inform the universalReceiver of Alice. Alice don't have a universalReceiverDelegate, so the transfer will go through. And then the token contract will inform the universalReceiver of Bob. This universalReceiver function will call the universalReceiverDelegate and in this universalReceiverDelegate you will have a logic. So this logic is already written in the contract and this contract is already deployed, so all of this will happen in the same transaction. So it will go here and it will read that this contract will have a revert line and all of this will be reverted. So it's not waiting for another transaction, it's in the same transaction.
Yeah, I understand. Thanks. Thanks for clarifying. Awesome.
Cool.
Any other question?
I'm sure folks will probably have more questions as the gears start turning and they get new ideas for new stuff to build. But seeing where we are with time and purpose of the recording, I think maybe we'll call it here, but everyone is welcome to stay after the fact to ask any further questions or what not. So with that, thank you very much, Yamen, for coming on and giving us this awesome overview. And I want to wish everybody a very happy Friday or weekend wherever wherever you may be. And we're trying something new today, so Developer DAO's very own MintKudos, we're going to be actually giving Kudos today instead of POAPs. So I'll be dropping a link that everybody can use to claim a Kudos from MintKudos and Yamen, I'll also send you your special link for your speaker Kudos. So with that, I will stop the recording and wish everybody a awesome rest of your day.
Listen On
Share This Episode
Share on XWatch Episodes Live!
Subscribe to our event calendar and never miss a live episode.
View Event Calendar