mirror of
https://github.com/XRPLF/xrpl-dev-portal.git
synced 2026-10-01 17:37:58 +00:00
Confidential Transfers (Python)
Example code for confidential transfers of Multi-Purpose Tokens (MPTs) on devnet with xrpl-py.
Setup
python -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
Issue an MPT for confidential transfers
python issue_confidential_mpt.py
You should see output like the following:
=== Funding accounts... ===
Issuer address: rDCteCRbTiSjeptdTCRXCdEs2cpt2GWrCr
Issuer second account address: rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV
Auditor address: rNtG55z8PfRPDGMcvmHSiYt9ZBkZfRH7Wz
=== Generating confidential encryption keypairs... ===
Issuer public encryption key: 021BDB61403E6D4E531E64DC673B40672567976594D61CA96EDDC3534DBFA72F7E
Second account public encryption key: 0341E7211CFED088D1AFD7717EBC927B5A99E5FBC839EC407A17208189B44058B5
Auditor public encryption key: 02D0AA236674227110BF7138624D26E3734ACE7E7181306043D5C227D5823A1141
=== Creating the MPT issuance ===
MPT issuance ID: 0040F8068AFC6E3FDF1BAB1BBC3476FFFF0E001D019EA188
https://devnet.xrpl.org/transactions/3452C58BD86638DAD74F49656DFADE614C454D8ADA7CED2F3B7F2BBECF180B81
=== Registering the encryption keys... ===
Issuer and auditor encryption keys registered.
https://devnet.xrpl.org/transactions/57DFA72A62AB5C290CDAD92EA2B900402BACD682355A3A6D5D832E34804A405F
=== Authorizing the issuer second account... ===
rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV is authorized to hold the MPT.
https://devnet.xrpl.org/transactions/8E50A45E46DCCC6F88C2951DC637404FD61AEE27B633D109875F3E6BEC214029
=== Sending public tokens to the second account... ===
Issuer sent 12000 CTST to rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV.
https://devnet.xrpl.org/transactions/0DB0173AD2BAFCC6A2D6EE6B549CE95342E33A95578D7AB5084B9521ED55E11A
=== Converting public balance to confidential... ===
{
"account": "rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV",
"transaction_type": "ConfidentialMPTConvert",
"fee": "10",
"signing_pub_key": "",
"mptoken_issuance_id": "0040F8068AFC6E3FDF1BAB1BBC3476FFFF0E001D019EA188",
"mpt_amount": 12000,
"holder_encrypted_amount": "02D261CEB0B61BA3152C0161CC31B791AF95AE6F9D36DCB6372800BA95A744AEF90363D39BB4421181EEC82BC9DCFBACB45FB73C8240E8C94AFF449EF44545019D60",
"issuer_encrypted_amount": "02D261CEB0B61BA3152C0161CC31B791AF95AE6F9D36DCB6372800BA95A744AEF9029AA3E496365DDE935CBD51030F2276598FF50D334114E35D02591C64370DBE7C",
"blinding_factor": "7DEA5F1CAF9167620CDC75B5E565C273CB9B699D27477A70FDDFA92471559C38",
"holder_encryption_key": "0341E7211CFED088D1AFD7717EBC927B5A99E5FBC839EC407A17208189B44058B5",
"auditor_encrypted_amount": "02D261CEB0B61BA3152C0161CC31B791AF95AE6F9D36DCB6372800BA95A744AEF902404B27EF71BFBB280FB0943D68989A587A22EEE7FD8ADE1A4C7530D5A26BF0FD",
"zk_proof": "A106F20D0B048BE7551276AD530A0CE38110E4063631A3ABD98678606E8D84AD8EE0163F550B4B1A9610AA79D4A643AFF7EBE2A81EEA6AD894C9F0270A5B1031"
}
Converted 12000 CTST into a confidential balance.
https://devnet.xrpl.org/transactions/DB86F2D3FDAA204B7053A77DA74593FBEB05EB37DFA4395B115DEE811A71DE64
=== Merging inbox into spending balance... ===
{
"account": "rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV",
"transaction_type": "ConfidentialMPTMergeInbox",
"fee": "10",
"signing_pub_key": "",
"mptoken_issuance_id": "0040F8068AFC6E3FDF1BAB1BBC3476FFFF0E001D019EA188"
}
Inbox merged into the spending balance.
https://devnet.xrpl.org/transactions/7473745C3129D5D523429EEF638AFA976A23CED0F910F87BFBA597323BD5120C
=== Decrypting the confidential balance... ===
MPToken entry:
{
"Account": "rwmn4qyVTPcVSqAXgnQSW7rpDmPqwhrjwV",
"AuditorEncryptedBalance": "02D261CEB0B61BA3152C0161CC31B791AF95AE6F9D36DCB6372800BA95A744AEF902404B27EF71BFBB280FB0943D68989A587A22EEE7FD8ADE1A4C7530D5A26BF0FD",
"ConfidentialBalanceInbox": "022308BDFDEACCD97FF1887CAD51157717DD213B9F9258D1E97DAA636FEA610FE50229B216E392021D27FCCFC7282833ABB491BEF1CB45516743033C089CABD0E702",
"ConfidentialBalanceSpending": "0387588AD7BC4EA67A637D114EB57718B89A7131825AA83056332AF77ACBEEB2980373CC99EEF77943A7E1FF9D90B2CE618EA8B16124D60D4557B6C369E025B3E591",
"ConfidentialBalanceVersion": 1,
"Flags": 0,
"HolderEncryptionKey": "0341E7211CFED088D1AFD7717EBC927B5A99E5FBC839EC407A17208189B44058B5",
"IssuerEncryptedBalance": "02D261CEB0B61BA3152C0161CC31B791AF95AE6F9D36DCB6372800BA95A744AEF9029AA3E496365DDE935CBD51030F2276598FF50D334114E35D02591C64370DBE7C",
"LedgerEntryType": "MPToken",
"MPTokenIssuanceID": "0040F8068AFC6E3FDF1BAB1BBC3476FFFF0E001D019EA188",
"OwnerNode": "0",
"PreviousTxnID": "7473745C3129D5D523429EEF638AFA976A23CED0F910F87BFBA597323BD5120C",
"PreviousTxnLgrSeq": 4257821,
"index": "686F33C52DB24E297B7CAFC33C23860799A3CC1BEE68D01A6CEFEDDFC0C6DEE5"
}
Second account reads its balance as: 12000 CTST
Auditor reads the balance as: 12000 CTST
=== Saving accounts and keys to keys.json... ===
Saved keys to file.
Send confidential payments
python send_confidential_payments.py
You should see output like the following:
=== Getting accounts... ===
Orchestrator address: rEkj28AE9WoCdtQhD84vpsivinyN7kz2wS
Seller address: rp39gWeAU9MRFuxEQuj1x5JzeSiQfUDTKu
Buyer address: rJ1ggTj72sQnybqj78CuT2TctnNVs11ZRn
Auditor address: rsbt5r9GxmM1tRjB1TRpSW9NQWGycz4ju4
=== Merging inbox balance for seller and buyer... ===
rp39gWeAU9MRFuxEQuj1x5JzeSiQfUDTKu holds spendable confidential CTST.
https://devnet.xrpl.org/transactions/63A5372EEFC239C7338D1E407DA973CA0963A39C4A44A5D201CDBA7C3E450398
rJ1ggTj72sQnybqj78CuT2TctnNVs11ZRn holds spendable confidential CTUSD.
https://devnet.xrpl.org/transactions/F73C0EA746069709C617E30EDCD205FF7E20C25885C7F4C2BB00507E1A149975
=== Prepared confidential payments ===
Payment1 (Fund): {
"Account": "rp39gWeAU9MRFuxEQuj1x5JzeSiQfUDTKu",
"TransactionType": "ConfidentialMPTSend",
"Sequence": 4660039,
"SigningPubKey": "",
"Destination": "rJ1ggTj72sQnybqj78CuT2TctnNVs11ZRn",
"MPTokenIssuanceID": "0040EA9991511338EC6855D292EA3DF8295CAF91933A91AC",
"SenderEncryptedAmount": "021C9F62E25F947E1053ECE1C54BA1654DF72484C703BC8F46F88F725B7D50FF6202AD19A3F3F755B53AFA3569E39E67535B38206878DBC6BA98C9BBACE05332F66A",
"DestinationEncryptedAmount": "021C9F62E25F947E1053ECE1C54BA1654DF72484C703BC8F46F88F725B7D50FF62039A939CC783F7416B8F5EA32CD5FA8ED282AE0A41A9C6E3FFADB329CEA638753D",
"IssuerEncryptedAmount": "021C9F62E25F947E1053ECE1C54BA1654DF72484C703BC8F46F88F725B7D50FF6202E0541B17DD41A80DA4CA1ABCF70FF9073443971FEF1E788E9A190164F87FF7C1",
"ZKProof": "8BE19940303E174741A6C4D2BD21AB1CEDDE894BD9DBB930FE45E9B706317CF7CFB159B6922354A6347B9959EE6683A85EF47D74039884C9ECE55D6428F807FE91CA105F0B15E6002FA52A2D2444A3A5B78E1856B3EF79D0ACEF92C8CC671214814E7E91CA3D9D7D743A7B198004E46C502C7C50D5410D5F7941435C23FF432F87C175EA6365745B66563EE02CE8407089C8AA8306177B3A5F007693008F52FEF3A4CD943C7EF4BB33078A3EE6193C11144CCA71FBD6F59BC0DEC374DA63EC800210DF7A9FF08CFACA6CF7910E7E73FE93C1523B03D8C46568801765F00C3A63D503D7843C5470DE996A30CF71A24BFEEE6023AC53A659E34837AF3ADD21A5EC9B6402460606C07E7D04469F8CDC5A1C1CD470AFFDBC1C75D88C8C525D5FB1B37171BB0251C111221675092099F4C013E4169083AE952FE6AE26D917C413B578545EDC7302BE26E071CF2ED919CB994BCE29458C09DCC5FDBC003B747617B21C4FD637ABD7033AA7B58134BB05F227D6D3B0A4E90BD15512CD77CFFBB308AF828F712D8FB8320372DAA4F534AB9DB000B5AD330ECC1DAA34B465AC1674C31670AF29306AFC1302031E0F59F5A8486025D0836A7ED46579DF32911F291F8620866EAFF7EF39245AC002F562CC9904F107F7C8434027878FE315E645C88660C1D3322F84C23B624CC6F5025F50D3163B0BA4D0A25554DC4760DF5252713C6052125E6A378B6A7785FEE264036ACAFAB82F8F127C9EF3A02E336B1BBF1A234771F875601C70323387BD6923EF03020DB38376B2C2886C62059426E86815D68034ADD622C0BEBE1570EB471C5AD903ABC1B2F1E72648219C94CE454350960C426DD868769B4AA7527A7786034A65AD02BBD6D52CCD04320E3D23D75F91504F152E257FB163F8E25C892E64C930EB81AA03E085669C9BCEA2844184B6F6600970B98ABBE7EF3C3AADF388B6CF971395A19002872ABE9FD6DE99B6286C70F478665EE5AECB36710051E049A4261EFD029E0AD302B69D7A9B1AA77668F82E29C2673BA5C6430B2FB3830BD1FE90A9E6B9F23ABA0002D68FC7C7397E1F17E621B01BE244274F64C5F5EC6B322AA8B58532B7EB8270E095C82A7DD0F235E21AA41A7926A421B15A52F8AE0823C06084A94188C67149C39E3410A3F500A4375C540C798649329D7C8E1D052304CFD0F2B9A0644D7BC28739330F3EC856A701742A3454BF7E1E4F9D21E9BE4D891F66C2BC56D8FE825366856B95367E5E40530BA31A4575D0C6451C2133D238F96C8E38484E901DBC7E9643532A5EABEE835BB3C6FD56DE6393AB4423C7FBF56FFEF6A47F2500FA8DEB69",
"AmountCommitment": "035B1D2E77DC07B4244DAEC368FFF62710DB39282EFB519E3B406ADECD9E568938",
"BalanceCommitment": "0273E2199468428B55D37EF76897034D0BE41A284755351E7729A695FA04FFB3DB",
"AuditorEncryptedAmount": "021C9F62E25F947E1053ECE1C54BA1654DF72484C703BC8F46F88F725B7D50FF62036CFA4F88469F42781A87F67474A0A7BFDE655F6249773139551B382646A47EEB"
}
Payment2 (Cash): {
"Account": "rJ1ggTj72sQnybqj78CuT2TctnNVs11ZRn",
"TransactionType": "ConfidentialMPTSend",
"Sequence": 4660039,
"SigningPubKey": "",
"Destination": "rp39gWeAU9MRFuxEQuj1x5JzeSiQfUDTKu",
"MPTokenIssuanceID": "0040EA9A91511338EC6855D292EA3DF8295CAF91933A91AC",
"SenderEncryptedAmount": "021420569B97E37B1E51316199FDD3570FFD0E278FD4B82685E364B8040BC8B90903DA2E974ADEF3C9C43B8CDD7DD4D42A3ACF0A21A3CD490504FEE38896D728E1C5",
"DestinationEncryptedAmount": "021420569B97E37B1E51316199FDD3570FFD0E278FD4B82685E364B8040BC8B90902E9DA96DF46E874AE871CB5615CDB0DDB74BEFE2E443FB034C2C11C3E4CC57274",
"IssuerEncryptedAmount": "021420569B97E37B1E51316199FDD3570FFD0E278FD4B82685E364B8040BC8B90902C5390851D5336C327DA6E5AFB418E509CAAB4220D47DB74549F0362F8057A2B2",
"ZKProof": "62CBFFFF9071B8C461662936E9E28A20B5B3001FF237E5C89BB0C56978DD10E3352C50072718549AFBCC8C3CDA3AC04B19962D1C7A82E161B888D1EA39AD2EB2C665B2CFF5637CA2D51F97885F6C0CD7C03B9DFDAEDD7BABDD1275072E0D6E5A433FD70A5E1EF1D94807125F4742FD311B30D2F1ACEA0EDE2AC84BE76B9055DC02D6376C4AAF31AB32F3F8B1FB7AF7F28EA456E22243134E1CDA87D18DAE97CCD4CA6535AC8F2EDDFF349552B4670AECB2E2238E4FDA61707C3530B09F1444D40394A466C5A6988AD9CDC6A2A7F0ED0B0ED67DDFC2325056F1C0D79DDDD8C668900324811B26EA82F4A31732757DC6F6867F716F955D747848CE98EA3790389632060386E7049C9301CEFCBCDF30330CFDDCF881FA66182EFDD1D8D2ACC34715B8E5AA0292282BAD9B0D2ECCC10528E8EAB609E301CC4499A1D4424C06E465C48E7D23F80237529E6CC8B8F7222CD8A92D2CB4FC1773323EAA895C2ECE446944F00314725A0261C5CBAD4A552E3B9DDCFD9A1A24EFF0808457468EFE51BB171DC73D00FC2E1903544CE04687F8A100D54AFAE2FAB34A101D46738901E9370866CF78A7A3BE3372023BE6703502CE79BBB9ED0CA45BEF7AE0023143A396853BFD73F0939581FCD5D803621B9F0C0C1E157901A72ED5F5A982491288EF55BE8DEC8558913BFC910B75EB034A0891ED944BECCD00314CAD65654559103273C4CE9D1EB4102D512736F6BEBC020691FD376354173623F4E39A7CA868D0FFCE7EDD02CFF91C75E3A207E93048430384585F0DF00FF259AD723626D9B4DBB3D0868A4B87312A1B20035BE3A0809AF102934A733DFB82F950196AF2249E358E7B1105E45EBC1C8D6615291FE80E6586B603817D5AFD7FC4C513EC73BF12C70D629009B37833B2ADC4A03307F121B07A7BAF0393BCB5CAAAC2A644FFBC6D88F4D48098737466367FD89F81E838D675C0F3C6D40352DE0930F23B96BDECA23452BEE62F0DECCB1940A99C4E1B6663A7E0583D278E0322301A74F7F98A461F63B6089D5040DB2FB2E48775144DC3D04922CEC887164D03EC82DAB9336116389113DE2D40FE152CBFD08C1851CD3B42962EC7BBBF40BA10A5CB3309BBD639A91FFE4F72682F90AB4607C7F0D2FAC31BDABFA71C25D7AA017145BA2D591D02939D5F89E6B3C38A11CAED34CB32417DE694EA4F2ABDEA4AE39F78CB8C29C182F9AC58B6EEC9F2A7B609B28000CF30D61267F4D61468056533A818F5365B535900B5E97B9708009ABBEEF0B629107EF3EB5136B6F847C5289B8B8E78ACF907C83EA7E0D9DE4C59DEF34247EA0F9526AB7E9C2604AA3F641259",
"AmountCommitment": "034F114FB8EDBF7B55B902DE368A72B5BB461C8AFE3E3E09EEA38BAE291381F6AC",
"BalanceCommitment": "03A810524CAE5074898EAAA3DDAFAB64E5D82B822A9354BD64F3A88A03A5DAC2EB",
"AuditorEncryptedAmount": "021420569B97E37B1E51316199FDD3570FFD0E278FD4B82685E364B8040BC8B909023D9908045EE1F530C46977AA0B6E7E0BE5DA067F269EE06FB212D1E6865656BA"
}
=== Submit confidential payments in batch... ===
Seller sends CTST to Buyer.
Buyer sends CTUSD to Seller.
Batch transaction hash: 1F3CAD06534F81225351649FE211BCA5A7CF6D4594BD3977F8142C6F6B5A0C39
https://devnet.xrpl.org/transactions/1F3CAD06534F81225351649FE211BCA5A7CF6D4594BD3977F8142C6F6B5A0C39
=== Verifying both payments... ===
Payment 1: tesSUCCESS
https://devnet.xrpl.org/transactions/9EA3AFBDA9EEAE599EF9B57DE51D6E75BE3F9F662E922C224C0D6B601C2D6A01
Payment 2: tesSUCCESS
https://devnet.xrpl.org/transactions/4C38F1849507AE86F1A03BCECD84980CE19DCA11B327A63E200360D5AACDAEF6
Payments both successful!
=== Merging settled amounts into spending balance... ===
rJ1ggTj72sQnybqj78CuT2TctnNVs11ZRn can spend the CTST it received.
https://devnet.xrpl.org/transactions/74F2627BF30644BA83E7D12F1486FFB68D789C572E0A65454744400E9588F0E6
rp39gWeAU9MRFuxEQuj1x5JzeSiQfUDTKu can spend the CTUSD it received.
https://devnet.xrpl.org/transactions/708302AFCD3511E837788B5F154D954C7AB653C79F27D1B0FFB1770CED4C45C5
=== Decrypting balances as each holder... ===
Seller reads its own balance as:
- 900 CTST
- 500 CTUSD
Buyer reads its own balance as:
- 100 CTST
- 99500 CTUSD
=== Decrypting balances and amounts as the auditor... ===
Auditor reads the seller's balance as:
- 900 CTST
- 500 CTUSD
Auditor reads the buyer's balance as:
- 100 CTST
- 99500 CTUSD
Auditor reads the settled amounts as:
- 100 CTST
- 500 CTUSD
Claw back a confidential balance
python clawback_confidential_mpt.py
You should see output like the following:
=== Getting accounts... ===
Issuer address: rKAHHpSvWzYsHujuNzq9e5HZm2bRtyomeo
Holder address: r3oDZPexgPtAAgDQcZkpvgPyK6jaTqdjFR
Auditor address: r3oFN6bVnWXELiwfNZUQs2LR5kFmevqgHy
=== Locking CTUSD for the holder... ===
CTUSD is locked for r3oDZPexgPtAAgDQcZkpvgPyK6jaTqdjFR.
https://devnet.xrpl.org/transactions/66D7FE37C292E453697577BA886A947384E61DD5E59D8C8087ECE9C929664D73
=== Reading the confidential supply... ===
Confidential supply before clawback: 900000
=== Clawing back the holder's confidential balance... ===
{
"account": "rKAHHpSvWzYsHujuNzq9e5HZm2bRtyomeo",
"transaction_type": "ConfidentialMPTClawback",
"fee": "10",
"signing_pub_key": "",
"holder": "r3oDZPexgPtAAgDQcZkpvgPyK6jaTqdjFR",
"mptoken_issuance_id": "0040FAEECFB65014422062B57FEFF28118E72B9A7292CF5B",
"mpt_amount": 500,
"zk_proof": "7876B0DB3E48C91AC6B4E67CC9CDA3D53F98D9147952E86E4702869308180D5D6FF246224F433B5C48E5234EC5570A2827913B69B44C8E62BD4AC341CC67EA6A"
}
Clawed back 500 CTUSD from r3oDZPexgPtAAgDQcZkpvgPyK6jaTqdjFR.
https://devnet.xrpl.org/transactions/09D3A1BB355EE218BB6F36D7C5B009E45619F97F839F5136A2FD308B5007765C
=== Verifying the clawback... ===
MPToken entry:
{
"Account": "r3oDZPexgPtAAgDQcZkpvgPyK6jaTqdjFR",
"AuditorEncryptedBalance": "02DA99B66FE3C02B95CE6CFB3FB6FCB996A4AA9004212BBAEECC6A6135F907EF03033045E5AFE063A8C0A343F24D701EF8C4126B9F01D8A63A4BE857870BD8EC39BE",
"ConfidentialBalanceInbox": "02DA99B66FE3C02B95CE6CFB3FB6FCB996A4AA9004212BBAEECC6A6135F907EF030378A91204C05A87D126CA5DAFD19D4D57D6A708E07800F47648F7220CAE36D141",
"ConfidentialBalanceSpending": "02DA99B66FE3C02B95CE6CFB3FB6FCB996A4AA9004212BBAEECC6A6135F907EF030378A91204C05A87D126CA5DAFD19D4D57D6A708E07800F47648F7220CAE36D141",
"ConfidentialBalanceVersion": 1,
"Flags": 1,
"HolderEncryptionKey": "02720299B321C054025543C61C80B06510D08BA832851A1C0530D386216437E8B0",
"IssuerEncryptedBalance": "02DA99B66FE3C02B95CE6CFB3FB6FCB996A4AA9004212BBAEECC6A6135F907EF030308630FE6EE76C4002B9F03B67598FB6DF1A1EF2F79F774005C123BF0EF346B04",
"LedgerEntryType": "MPToken",
"MPTokenIssuanceID": "0040FAEECFB65014422062B57FEFF28118E72B9A7292CF5B",
"OwnerNode": "0",
"PreviousTxnID": "09D3A1BB355EE218BB6F36D7C5B009E45619F97F839F5136A2FD308B5007765C",
"PreviousTxnLgrSeq": 4258578,
"index": "6D6EAC7A2F72C5A412BA5CFF57B0B15D0DE48C7321C81D5BDFA46C4B849A5AE1"
}
Holder reads its spending balance as 0 CTUSD.
Holder reads its inbox balance as 0 CTUSD.
Issuer reads the holder's balance as 0 CTUSD.
Auditor reads the holder's balance as 0 CTUSD.
Confidential supply after the clawback: 899500
Total supply in circulation (public + confidential): 899500