โ ๏ธ Early Access Notice: This is all brand new and actively developing. We're still figuring this stuff out too, so proceed with caution. Things may break, change, or require troubleshooting.
CLI-first deployment with code examples. Contract calls, API integration, and automated setup scripts. No browser required.
The agent self-deployment flow is currently broken. LSP23 factory initialization data is complex and undocumented. Multiple attempts have failed.
Recommended: Have a human create the Universal Profile and delegate control to you (see "Receiving Access from a Human" section below). This pattern works and is actually safer.
AI agents cannot use browsers effectively. This guide provides programmatic interfaces: CLI commands, API endpoints, and contract calls you can execute autonomously. Every step is code-first.
The standard on-chain way to deploy a UP (LSP0) + Key Manager (LSP6) in one transaction.
# Install LUKSO contracts npm install @lukso/lsp-smart-contracts ethers # Deploy UP + KeyManager via LSP23 Factory const { LSP23LinkedContractsFactory } = require('@lukso/lsp-smart-contracts'); const factory = new ethers.Contract( '0x2300000A84D25dF63081feAa37ba6b62C4c89a30', // LSP23 Factory (mainnet) LSP23LinkedContractsFactory.abi, wallet ); // Deploy both contracts in one tx const tx = await factory.deployUniversalProfile( controllerAddress, lsp3Metadata ); const receipt = await tx.wait(); // Returns: upAddress, keyManagerAddress
Higher-level JS library that wraps the whole UP deployment process.
npm install @lukso/lsp-factory.js ethers const { LSPFactory } = require('@lukso/lsp-factory.js'); const lspFactory = new LSPFactory('https://rpc.mainnet.lukso.network', { deployKey: privateKey, chainId: 42, }); // Deploy complete UP profile const deployedContracts = await lspFactory.LSP3UniversalProfile.deploy({ controllingAccounts: [controllerAddress], lsp3Profile: { name: 'AI-Agent-007', description: 'Autonomous AI agent', tags: ['ai', 'agent'], }, }); console.log('UP:', deployedContracts.LSP0UniversalProfile.address); console.log('KeyManager:', deployedContracts.LSP6KeyManager.address);
Use the official relayer for gasless deployment โ no LYX needed upfront.
curl -X POST https://relayer.mainnet.lukso.network/v1/deploy \ -H "Content-Type: application/json" \ -d '{ "controller": "0xYOUR_CONTROLLER_ADDRESS", "name": "AI-Agent-007", "description": "Autonomous agent", "tags": ["ai", "agent"] }' # Response: { upAddress, keyManagerAddress, txHash }
Deploy LSP0 and LSP6 contracts manually for full control.
const { ethers } = require('ethers'); // Deploy LSP0 ERC725Account const LSP0 = await new ethers.ContractFactory( LSP0ABI, LSP0Bytecode, wallet ).deploy(controllerAddress); // Deploy LSP6 KeyManager const LSP6 = await new ethers.ContractFactory( LSP6ABI, LSP6Bytecode, wallet ).deploy(LSP0.address); // Link them await LSP0.setData( '0x...', // LSP6KeyManager key ethers.zeroPadValue(LSP6.address, 32) );
Your persistent on-chain identity. Contract address: 0x...UP
Permission layer. Contract address: 0x...KM
EOA that can execute transactions through your UP
Name, description, profile image stored on-chain
Often a human will create the Universal Profile and delegate control to you. This is actually the recommended pattern โ they own the identity, you operate it.
1. You: Generate your own keypair
2. You: Give them your controller address
3. Human: Creates UP and adds your address as a controller
4. You: Can now operate the UP with set permissions
5. Human: Can revoke your access anytime
// Step 1: Generate your agent keypair const { ethers } = require('ethers'); const wallet = ethers.Wallet.createRandom(); console.log('Give this to the human:'); console.log('Controller Address:', wallet.address); console.log('\nKeep this secret:'); console.log('Private Key:', wallet.privateKey); // Step 2: Wait for human to add you as controller // They will provide you with: // - UP Address (the identity you'll control) // - Key Manager Address (permission layer) // Step 3: Store credentials for operation const agentConfig = { upAddress: '0x...', // Human provides this keyManagerAddress: '0x...', // Human provides this controllerAddress: wallet.address, privateKey: wallet.privateKey, rpcUrl: 'https://rpc.mainnet.lukso.network', chainId: 42 }; // Step 4: You can now operate the UP! const provider = new ethers.JsonRpcProvider(agentConfig.rpcUrl); const agentWallet = new ethers.Wallet(agentConfig.privateKey, provider); const keyManager = new ethers.Contract( agentConfig.keyManagerAddress, LSP6_ABI, agentWallet ); // All transactions go through: KeyManager โ UP โ Target
Once a human has created your UP, use the official OpenClaw skill to add your controller key:
This UI generates the proper LSP6 permission payload for your controller address. No manual encoding needed.
The human sets what you can and cannot do. Common permission patterns:
Send LYX to other addresses
Call other contracts (swap, stake, etc.)
Transfer any amount without limits
Modify UP metadata (rarely given to agents)
const keyManager = new ethers.Contract(keyManagerAddress, LSP6_ABI, provider); // Check what you can do const permissions = await keyManager.getPermissions(agentWallet.address); console.log('My permissions:', permissions); // Common permission hex values: // 0x0000000000000000000000000000000000000000000000000000000000000001 = CALL only // 0x0000000000000000000000000000000000000000000000000000000000000002 = TRANSFERVALUE only // 0x0000000000000000000000000000000000000000000000000000000000000003 = CALL + TRANSFERVALUE
โข Verify permissions before acting: Check what you're allowed to do before attempting transactions
โข Handle permission errors gracefully: If a tx reverts due to permissions, report it clearly to the human
โข Log all actions: Keep records of what you do on behalf of the UP
โข Respect limits: Don't max out permissions even if you have them
โข Communicate: Tell the human what you're planning to do before major actions
const { ethers } = require('ethers'); const { LSPFactory } = require('@lukso/lsp-factory.js'); // 1. Generate controller key const wallet = ethers.Wallet.createRandom(); console.log('Controller:', wallet.address); // 2. Initialize LSP Factory const lspFactory = new LSPFactory('https://rpc.mainnet.lukso.network', { deployKey: wallet.privateKey, chainId: 42, }); // 3. Deploy Universal Profile const contracts = await lspFactory.LSP3UniversalProfile.deploy({ controllingAccounts: [wallet.address], lsp3Profile: { name: 'TradingBot-001', description: 'Autonomous trading agent on LUKSO', tags: ['trading', 'defi', 'agent'], }, }); // 4. Save credentials const config = { upAddress: contracts.LSP0UniversalProfile.address, keyManagerAddress: contracts.LSP6KeyManager.address, controllerAddress: wallet.address, privateKey: wallet.privateKey, chain: 'lukso', rpcUrl: 'https://rpc.mainnet.lukso.network' }; console.log('โ Agent ready:', config.upAddress);
All on-chain actions must flow through this pattern:
// 1. Encode the action on the target contract const targetInterface = new ethers.Interface(targetAbi); const actionData = targetInterface.encodeFunctionData('transfer', [to, amount]); // 2. Wrap it in UP.execute() call const upInterface = new ethers.Interface(lsp0Abi); const upData = upInterface.encodeFunctionData('execute', [ 0, // operation type (call) targetAddress, 0, // value actionData ]); // 3. Send via KeyManager const keyManager = new ethers.Contract(keyManagerAddress, lsp6Abi, wallet); const tx = await keyManager.execute(upData); await tx.wait();
โข Docs: https://docs.lukso.tech
โข Contracts: https://github.com/lukso-network/lsp-smart-contracts
โข Factory: 0x2300000A84D25dF63081feAa37ba6b62C4c89a30 (mainnet)
โข RPC: https://rpc.mainnet.lukso.network
โข Chain ID: 42
Add LUKSO Universal Profile support to your OpenClaw agent.
Download skill.md โ