{"id":17014166,"url":"https://github.com/olegabu/go-mimblewimble","last_synced_at":"2025-08-03T19:35:48.792Z","repository":{"id":196397710,"uuid":"194234039","full_name":"olegabu/go-mimblewimble","owner":"olegabu","description":"Library for forming and validating transactions in mimblewimble protocol","archived":false,"fork":false,"pushed_at":"2022-04-24T19:33:43.000Z","size":928,"stargazers_count":2,"open_issues_count":10,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-02-18T19:30:40.627Z","etag":null,"topics":["blockchain","hyperledger-fabric","mimblewimble","tendermint","zero-knowledge"],"latest_commit_sha":null,"homepage":null,"language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/olegabu.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null}},"created_at":"2019-06-28T08:08:04.000Z","updated_at":"2023-07-17T16:07:32.000Z","dependencies_parsed_at":"2023-09-25T04:00:53.931Z","dependency_job_id":null,"html_url":"https://github.com/olegabu/go-mimblewimble","commit_stats":null,"previous_names":["olegabu/go-mimblewimble"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/olegabu%2Fgo-mimblewimble","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/olegabu%2Fgo-mimblewimble/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/olegabu%2Fgo-mimblewimble/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/olegabu%2Fgo-mimblewimble/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/olegabu","download_url":"https://codeload.github.com/olegabu/go-mimblewimble/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247393572,"owners_count":20931813,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["blockchain","hyperledger-fabric","mimblewimble","tendermint","zero-knowledge"],"created_at":"2024-10-14T06:24:01.684Z","updated_at":"2025-04-05T20:12:36.812Z","avatar_url":"https://github.com/olegabu.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"#  An experimental wallet and library for Mimblewimble\n\nThis is a toy. Do not use in anything serious (yet).\n\n# TODO\n\n- post collides\n- issue event should print out info\n- ... then tell the wallet the transaction...\n- no need to send proof in issue tx\n- sign issue with Schnorr r*G when value*H is known\n\n## Prerequisites\n\nInstall Golang ([instructions](https://github.com/golang/go/wiki/Ubuntu)).\n```bash\nsudo add-apt-repository ppa:longsleep/golang-backports \u0026\u0026 \\\nsudo apt-get update \u0026\u0026 \\\nsudo apt-get install golang-go \u0026\u0026 \\\n\necho \"export GOPATH=~/go\" \u003e\u003e ~/.bashrc \u0026\u0026 \\\necho \"export PATH=$PATH:~/go/bin\" \u003e\u003e ~/.bashrc \u0026\u0026 \\\n. ~/.bashrc\n```\n\nInstall tools.\n```bash\nsudo apt-get install autoconf libtool libgmp3-dev\n```\n\n## Build and test\n\n```bash\ngo install -ldflags \"-linkmode external -extldflags -static\" ./...\n\ngo test -v ./wallet ./ledger\n```\n\n## Demo offline wallet\n\nThis demonstrates creation and validation of Mimblewimble transactions by the wallet.\n\nCleanup: delete wallet databases (careful! demo and tests only).\n```bash\nrm -rf ~/.mw*\n``` \n\nCreate user's master secret key in the wallet. This will also print out a mnemonic you can use to recover your key.\n```bash\nmw init\n```\n\n### Send and receive\n\nIssue coins to yourself in the wallet. Observe new `Coinbase` outputs in your wallet by `mw info` command.\n```bash\nmw issue 1\nmw info\n```\nSend 1 coin to yourself. This will create a `slate-send-\u003ctransaction uuid\u003e.json` file that the receiving party needs to \nfill in by `mw receive` command. Observe a new slate and the input that is now in `Locked` state in your wallet.\n```bash\nmw send 1\nmw info\n```\nReceive 1 coin from yourself. This will create a `slate-receive-\u003ctransaction uuid\u003e.json` file that needs to be returned \nto the sender who will turn it into a transaction by `mw finalize` command. \nObserve new `Unconfirmed` outputs, and a new response slate.\n```bash\nmw receive slate-send-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw info\n```\nFinalize the transaction. This will create a `tx-\u003ctransaction uuid\u003e.json` file that needs to be broadcast \nto the network to get validated. \nIn this offline scenario we'll skip this part and tell the wallet the transaction has been confirmed. \n```bash\nmw finalize slate-receive-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw info\n```\nTell our wallet the transaction has been confirmed by the network. \nObserve new `Confirmed` outputs and a new transaction, as well as the input turned from `Locked` to `Spent` \nin your wallet.\n```bash\nmw confirm 8668319f-d8ae-4dda-be5b-e3fd1648565e\nmw info\n```\n\n### Send an invoice and pay it\n\nYou can request a payment by creating an invoice and passing it to the payer.\n```bash\nmw invoice 1\n```\nThe payer can accept the invoice and pay it.\n```bash\nmw receive slate-send-4ef548ba-31bd-4d03-8954-9884cc907d15.json\n```\nUpon receipt of the response slate from the payer the payee will finalize to create a transaction, \njust like in the send-receive scenario with the difference that now it is the payee\nthat finalizes, not the payer.\n```bash\nmw finalize slate-receive-4ef548ba-31bd-4d03-8954-9884cc907d15.json\nmw confirm 4ef548ba-31bd-4d03-8954-9884cc907d15\n```\n\n### Issue different assets\n\nWhen an asset name is omitted the wallet issues tokens of the default asset: currency `¤`.\nTokens of any asset can be issued and tracked separately by giving their asset's name.  \n\nIssue 5 dollar stablecoins and 10 apple commodity tokens.\n```bash\nmw issue 5 $\nmw issue 10 🍎\nmw info\n```\n\nSimilarly, assets of any type can be transferred. \nIssue 5 dollars to yourself; then send, receive, and finalize to transfer of these 5 dollars.\n```bash\nmw issue 5 $\nmw info\nmw send 5 $\nmw receive slate-send-5d6cf41e-e3f6-474d-9a5c-314d9344012b.json\nmw finalize slate-receive-5d6cf41e-e3f6-474d-9a5c-314d9344012b.json\nmw confirm tx-5d6cf41e-e3f6-474d-9a5c-314d9344012b\nmw info\n```\n\n### Exchange assets\n\nYou can exchange tokens of one type of asset with another by creating a transaction that combines inputs and outputs of\ndifferent assets. This exchange is atomic thus providing a delivery vs payment guarantee.\n\nSell 2 apples for $1 by creating a transaction where you're sending 2 apples and receiving 1 dollar.\n```bash\nmw send 2 🍎 1 $\nmw receive slate-send-0b925dc8-2ef2-40d8-8c67-bd4eb804a532.json\nmw finalize slate-receive-0b925dc8-2ef2-40d8-8c67-bd4eb804a532.json\nmw confirm 0b925dc8-2ef2-40d8-8c67-bd4eb804a532\nmw info\n```\n\n### Validate transactions\n\nYou can validate any transaction serialized in [Grin](https://github.com/mimblewimble/grin) format.\n```bash\nmw validate tx-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw validate 1_grin_repost.json\n```\n\n## Demo consensus node and two online wallets\n\nThis demonstrates creation of Mimblewimble transactions by wallets of two users: Sender and Receiver \nconnected to a consensus network of one Tendermint node which records outputs and validates transactions.\n\n### Consensus node\n\nIf running for the first time generate Tendermint keys.\n```bash\nmw tendermint init\n```\nClean up: delete wallets and reset Tendermint ledger.\n```bash\nmw tendermint unsafe_reset_all \u0026\u0026 rm -rf ~/.mw*\n```\nStart Tendermint consensus node with a built-in Mimblewimble ABCI application.\n```bash\nmw node\n```\n\n### Sender\n\nStart Sender's wallet in another console to listen for transaction events from the consensus node.\n```bash\nmw init\nmw listen\n```\n\nOpen Sender's wallet in another console.\n\nIssue 1 coin to yourself in the wallet. This will create `issue-1.json` transaction file that needs to be \n broadcast to the network to get validated and its Coinbase output recorded.\nObserve a new `Coinbase` output in Sender's wallet.\n```bash\nmw issue 1\nmw info\n```\nSend this new Coinbase output to the consensus node.\n```bash\nmw broadcast issue-1.json\n```\nNow this output can be sent. This will create a `slate-send-\u003ctransaction uuid\u003e.json`.\nObserve the Coinbase output turn from `Confirmed` to `Locked` state in the sender's wallet.\n```bash\nmw send 1\nmw info\n```\n\n### Receiver\n\nOpen Receiver's wallet in another console. \n\nIf you're running it on the same host specify a separate wallet directory via `--persist` flag \nor `MW_PERSIST` env variable. \nObserve Receiver's wallet is empty.\n```bash\nexport MW_PERSIST=~/.mw_r\nmw init\nmw info\n```\n\nStart Receiver's wallet in another console in listening mode.\n```bash\nexport MW_PERSIST=~/.mw_r\nmw listen\n```\n\nReceive an input from Sender's slate file saved in the same folder. In reality users send slates to each other.  \nThis will create a `slate-receive-\u003ctransaction uuid\u003e.json`.\nObserve a new `Unconfirmed` output in Receiver's wallet.\n```bash\nmw recieve slate-send-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw info\n```\n\n### Back to Sender to finalize\n\nReturn to Sender's wallet console.\n\nPost the transaction: finalize to create a `tx-\u003ctransaction uuid\u003e.json` \nand broadcast it to consensus network to get recorded in the ledger.\n```bash\nmw finalize slate-receive-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw broadcast tx-8668319f-d8ae-4dda-be5b-e3fd1648565e.json\nmw info\n```\nObserve both Sender's and Receiver's listening wallets get a transaction event and update their databases.\nSee original Coinbase output turn to `Spent` in Sender's wallet, \nand the new output in the Receiver's turn from `Unconfirmed` to `Confirmed`.\n\n### Queries\n\nYou can query the consensus node for unspent outputs. \n \n```bash\n# all unspent outputs in the network's ledger \ncurl '0.0.0.0:26657/abci_query?path=\"output\"'\n\n# as the results in jsonRPC are base64 encoded, pipe them thru json parser and base64 decoder\ncurl '0.0.0.0:26657/abci_query?path=\"output\"' | jq -r .result.response.value | base64 -d | jq\n\n# query for a specific output by its commit\ncurl '0.0.0.0:26657/abci_query?path=\"output/09543892a4fd6a712850716ba31dc63f242978a606aaf7d995e8d5e7d0f021762f\"' | jq -r .result.response.value | base64 -d | jq\n```\n\nSimilarly, you can query for kernel excesses of all transactions recorded, and total tokens issued per asset.\n```bash\ncurl '0.0.0.0:26657/abci_query?path=\"kernel\"' | jq -r .result.response.value | base64 -d | jq\ncurl '0.0.0.0:26657/abci_query?path=\"asset\"' | jq -r .result.response.value | base64 -d | jq\n```   \n\nAsk the node to validate integrity of the world state: \nsum all unspent outputs and kernel excesses known to the network, and validate no coins have been minted out of air.\n```bash\ncurl '0.0.0.0:26657/abci_query?path=\"validate\"'\n```\n\n## Local test network\n\nCreate a consensus network of validating nodes in docker containers on a local host.\n\n### Crash Fault Tolerance\n\nThis demo will demonstrate tolerance to some nodes going offline. With the minimum of 4 nodes the network will\ncontinue to operate normally with 1 failed node: `3f+1=4`. \n\n#### Create\n\nCreate a network called `mytestnet` of the minimum 4 nodes required for BFT consensus. \nTo create more nodes, or a different network, pass arguments, ex.: `./localnet.sh 31 0 test2`. \n```bash\n./localnet.sh\n``` \nIn this script `mw tendermint testnet` generates node config files in `mytestnet` folder, \nthen `docker run` commands create containers out of a standard Linux image with folders mapped to the\ngenerated configs and the folder where `mw` is installed, and run them with `mw node`.\n\n#### Sender\n\nThe first user Sender creates his wallet on the host in the default `~/.mw` folder and connects to `node0`\nat the default address `tcp://0.0.0.0:26657`.\n\nConnect to the node to listen for events.\n```bash\nmw init\nmw listen\n```\n\nOpen another console and issue and send `apple` commodity tokens.\n```bash\nmw issue 10 apple\nmw broadcast issue-10.json\nmw send 1 apple\n```\n\n#### Receiver\n\nUser Receiver creates his wallet in `~/.mw_r` folder and connects to `node2` at `tcp://0.0.0.0:26659`.\nNote the client port 26657 maps to host's 26659.\n\nConnect to the node to listen for events.\n```bash\nexport MW_PERSIST=~/.mw_r\nexport MW_ADDRESS=tcp://0.0.0.0:26659\nmw init\nmw listen\n```\n\nOpen another console and receive the transfer.\n```bash\nexport MW_PERSIST=~/.mw_r\nexport MW_ADDRESS=tcp://0.0.0.0:26659\nmw receive slate-send-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json \n```\n\n#### Back to Sender to finalize\n\nSender finalizes and broadcasts the transaction.\n```bash\nmw finalize slate-receive-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json\nmw broadcast tx-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json\n```\n\nObserve in the listening consoles a `transfer` event from node0 update Sender's wallet,\nand the Receiver's from the event received from node2. \n\nIssue more tokens and observe `issue` events in both listening consoles: \nthe network validates and propagates transactions. \n```bash\nmw issue 1 $ \u0026\u0026 mw broadcast issue-1.json\n```\n\n#### Fail a node\n\nNow pause one container to reduce the consensus to 3 nodes and observe the events still\npropagate thru the network to the listening wallets.\n```bash\ndocker pause node1\nmw issue 1 $ \u0026\u0026 mw broadcast issue-1.json\n```\n\nPause another container and observe the events no longer propagate as the number of failed\nnodes 2 exceed BFT threshold `3f+1` for 4 nodes.\n```bash\ndocker pause node3\nmw issue 1 orange \u0026\u0026 mw broadcast issue-1.json\n```\n\nBring back at least one failed node and see the network recover and validate \nand propagate missed transactions.\n```bash\ndocker unpause node3\n``` \n\n### Byzantine Fault Tolerance\n\nWe can run some nodes in a mode where they will be double spending inputs thus exhibiting \nbyzantine behaviour. This demo will demonstrate tolerance to at least one such node with 4 nodes in the network. \n\n#### Create\n\nDelete config files and wallets from the previous demo then create a network of 4 nodes out of which 1 will double spend. \n```bash\nsudo rm -rf mytestnet/ ~/.mw*\n./localnet.sh 4 1 \n``` \n\n#### Sender\n\nIssue and send `apple` commodity tokens.\n```bash\nmw issue 1 apple\nmw broadcast issue-1.json\nmw send 1 apple\n```\n\n#### Receiver\n\nConnect to the node2 to listen for events.\n```bash\nexport MW_PERSIST=~/.mw_r\nexport MW_ADDRESS=tcp://0.0.0.0:26659\nmw init\nmw listen\n```\n\nOpen another console and receive the transfer.\n```bash\nexport MW_PERSIST=~/.mw_r\nexport MW_ADDRESS=tcp://0.0.0.0:26659\nmw receive slate-send-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json \n```\n\n#### Back to Sender to finalize\n\nSender finalizes and broadcasts the transaction.\n```bash\nmw finalize slate-receive-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json\nmw broadcast tx-3e722a37-f6a3-46a1-8e7b-c67000ddc666.json\n```\n\nObserve in the listening console a `transfer` event from node2 update Receiver's wallet. \n\n#### Attempt to double spend\n\nNow cancel the transaction we posted: this is a local operation in Sender's wallet that will let us use the inputs\nwe just spent again. Observe `apple` output turn to `Confirmed` and send this output again.   \n```bash\nmw cancel 3e722a37-f6a3-46a1-8e7b-c67000ddc666\nmw info \nmw send 1 apple\n```\n\nIn Receiver's console accept the new slate.\n```bash\nmw receive slate-send-2ce5a045-2678-4f5d-bb0f-fa5f2139deed.json\n```\n\nBack in Sender's console post the new transaction.\n```bash\nmw finalize slate-receive-2ce5a045-2678-4f5d-bb0f-fa5f2139deed.json\nmw post tx-2ce5a045-2678-4f5d-bb0f-fa5f2139deed.json\n```\n\nSender broadcast to node0 which is the malicious one, so it accepted the double spending transaction. \nHowever, the other 3 nodes voted against it so you won't see the transaction event propagate and Receiver's wallet update.\n\n#### More double spending nodes\n\nLet's recreate the network with 2 double spending nodes.\n```bash\nsudo rm -rf mytestnet/ ~/.mw*\n./localnet.sh 4 2 \n```\n\nRepeat the above exercise of sending, canceling and sending again. \nObserve no events propagate: the consensus is split between 2 correct and 2 double spending nodes.\n\nRecreate the network with 3 double spending nodes out of 4.\n```bash\nsudo rm -rf mytestnet/ ~/.mw*\n./localnet.sh 4 3\n```\n\nRepeat the above exercise but this time succeed in spending the input twice: the correct node is now in the minority.\n\n \n\n\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Folegabu%2Fgo-mimblewimble","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Folegabu%2Fgo-mimblewimble","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Folegabu%2Fgo-mimblewimble/lists"}