Hinweis/Notice: this article is available in Englisch as well, here is the link: BitcoinJ 05 Create Watching Wallet En.
Ein spannendes Randthema sind die sogenannten „Watching Wallets“ oder „Beobachtungs Wallets“. Diese Wallets sehen ganz normal aus, enthalten Transaktionen und daraus resultierend haben sie auch ein Guthaben („Balance“). Ihnen fehlen allerdings die privaten Schlüssel zu den Adressen, so das keine Überweisungen von diesen Wallets aus möglich sind.
Die offizielle Webseite zur Bibliothek BitcoinJ umschreibt zwar die grundsätzliche Vorgehensweise für die Umwandlung, allerdings fehlen ein paar Schritte und in der Folge wird das „Watching Wallet“ ohne zurückliegende Transaktionen erstellt und hat auch kein ausgewiesenes Guthaben.
Das folgende Programm erstellt ohne weitere Interaktion des Benutzers aus dem vorhandenen Wallet (benannt durch den Dateinamen „filenameFullWallet“, z.B. „bitcoinj02createwallet.wallet“) ein Watching Wallet mit einem zusätzlichen „W“ am Ende des Dateinamens, bei meinem Beispiel wäre es „bitcoinj02createwalletW.wallet“.
Noch zwei wichtige Hinweise: Zum einen müssen eventuell vorhandene Watching Wallets und dazugehörende SPV-Dateien manuell gelöscht werden, ansonsten stoppt das Programm. Zum Anderen ist für die Umwandlung und Aktualisierung des Wallets eine Onlineverbindung zwingend notwendig. Dieser Schritt kann auch schon einmal 1 bis zu 3 Minuten dauern, habt also Geduld und unterbrecht das Programm nicht vorzeitig (Hinweis: in der Konsole könnt Ihr den notwendigen Download verfolgen).
Zur Nutzung benötigt Ihr diverse Bibliotheken zur Nutzung von BitcoinJ – ladet Euch diese aus dem separaten Github-Archiv (https://github.com/java-crypto/BitcoinJ_Libraries) herunter und bindet Sie über Eure Entwicklungsumgebung ein.
Ich zeige Euch hier die gekürzte Version der Konsolenausgabe, die vollständigen Ausgaben auf die Konsole findet Ihr in meinem Github-Repository.
Fehlermeldung falls die neu zu erzeugenden Wallet-Dateien schon vorhanden sind:
1 2 3 4 |
BitcoinJ 05 Erzeuge ein Watching Wallet von einem normalen Wallet Die existierende Datei muss manuell gelöscht werden: bitcoinj02createwalletW.wallet Die existierende Datei muss manuell gelöscht werden: bitcoinj02createwalletW.spvchain Bitte loeschen Sie die oben genannten Dateien von Hand. Das Programm wird nun beendet. |
Konsole:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 |
Fehlermeldung: BitcoinJ 05 Erzeuge ein Watching Wallet von einem normalen Wallet Die existierende Datei muss manuell gelöscht werden: bitcoinj02createwalletW.wallet Die existierende Datei muss manuell gelöscht werden: bitcoinj02createwalletW.spvchain Bitte loeschen Sie die oben genannten Dateien von Hand. Das Programm wird nun beendet. BitcoinJ 05 Erzeuge ein Watching Wallet von einem normalen Wallet Wir nutzen das Bitcoin Testnetz und nicht das Mainnetz Laden des originalen Wallets: bitcoinj02createwallet.wallet Das laden war erfolgreich: bitcoinj02createwallet.wallet ********************************************************************************** Ausgabe des originalen Wallets: bitcoinj02createwallet.wallet Wallet Balances: 0.01626622 BTC ESTIMATED 0.01626622 BTC AVAILABLE 0.01626622 BTC ESTIMATED_SPENDABLE 0.01626622 BTC AVAILABLE_SPENDABLE Transactions: 0 pending 2 unspent 2 spent 0 dead Last seen best block: 1669600 (2020-03-12T10:22:01Z): 00000000bfdc0927b5c5ccd2b6d6e7c77002b6207a2bf57d2ca7897c93b44506 Keys: Earliest creation time: 2020-02-29T09:44:25Z addr:mjLMNLydrmt2JerdCSc8sZCTMuujMXpero,tb1q980nq50prlpulx3t9r46jxa9csd8qh4ltz0en6 hash160:29df3051e11fc3cf9a2b28eba91ba5c41a705ebf creationTimeSeconds:1582969466 [2020-02-29T09:44:26Z] (imported) ... Seed birthday: 1582969465 [2020-02-29T09:44:25Z] Ouput script type: P2PKH Key to watch: tpubD8WRr3vpDwybtseRYzbP739wJw4vSMcRAvw6QifMh5ZNJTKwp5QRmymsjjLHp6kZqMPAVEqsZcAfqSApUS8mtLbwzyxAM5XFQMh3eZ73PRy Lookahead siz/thr: 100/33 addr:miaLUm4yeBv7XEfx9u9LXCeCvS9Y7GL3gE hash160:218c24dd87b2b87a3405518512cbd6e6dfa1c9f6 (M, root) .. >>> UNSPENT: -0.001425 BTC total value (sends 0.00575738 BTC and receives 0.00433238 BTC) confidence: Seen by 10 peers (most recently: 2020-03-12T10:17:14Z). Appeared in best chain at height 1669600, depth 1. Source: NETWORK 3b04ff0742625ad5123e3a6bc74b407fde68e098c97244bd6a413b9550effe34 updated: 2020-03-12T10:07:00Z purpose: USER_PAYMENT in PUSHDATA(72)[3045022100f873e0f5d4d3b9302aaa2cb374443e000a5c2e17cdd44bb4389056a36ab935880220632dd6451bcf235f20393f3545eaec98a0159fda9281031eb1851bf5e5f90cc301] PUSHDATA(33)[0325eab72b88d818f9b61456586151eeeafed64687c0ea666e8b9c64d57074a435] 0.00575738 BTC P2PKH addr:myA5v3sQo4VdhFGNJ9Gv22aRLnw7q7KhDw outpoint:905277665a3eb6cd1cf0af30b00f15db3ec6fc7ae86b3c150aa2fdcdb589d0b1:0 out HASH160 PUSHDATA(20)[41a37afc980ac078df37b24f2a687102f79b0ab3] EQUAL 0.0012 BTC P2SH addr:2MyEHka6Whdt87LyK3VuUGGfuWkNTtSD3Hj out DUP HASH160 PUSHDATA(20)[446f865811cad957a865e4514e83f1234bf708d8] EQUALVERIFY CHECKSIG 0.00433238 BTC P2PKH addr:mmkoqyZzzP9fPS6LD6i1xPy7UtAkX1YLi7 fee 0.00100446 BTC/kB, 0.000225 BTC for 224 bytes ... >>> SPENT: -0.005225 BTC total value (sends 0.01098238 BTC and receives 0.00575738 BTC) confidence: Seen by 5 peers (most recently: 2020-03-11T13:55:19Z). Appeared in best chain at height 1669539, depth 62. Source: NETWORK 905277665a3eb6cd1cf0af30b00f15db3ec6fc7ae86b3c150aa2fdcdb589d0b1 updated: 2020-03-11T13:41:17Z purpose: USER_PAYMENT in PUSHDATA(71)[304402201c175385ce3dd9ca411060949b3f5bfc16840623236aee73bb88002ab5cdb0fc0220797f97d2fedf72de4493e7c745cd7b0f55ee416a4f84adb95815d418545dfead01] PUSHDATA(33)[02c8508a80ac5c29b891a443b599e827155a71cb9ab702c3745a083bbbdc98155a] 0.01098238 BTC P2PKH addr:n3YE2rPKNhefnjrSHvEScXazNaSyeK52ML outpoint:18866d7e03a0b8958769382afe24ff7671fbc911cbdf3006fd1fbb3a3c49c4cf:0 out DUP HASH160 PUSHDATA(20)[c17fe3e9ea4561d70dc255a266d5eab4c8e10997] EQUALVERIFY CHECKSIG 0.00575738 BTC P2PKH addr:myA5v3sQo4VdhFGNJ9Gv22aRLnw7q7KhDw spent by:3b04ff0742625ad5123e3a6bc74b407fde68e098c97244bd6a413b9550effe34:0 out HASH160 PUSHDATA(20)[41a37afc980ac078df37b24f2a687102f79b0ab3] EQUAL 0.005 BTC P2SH addr:2MyEHka6Whdt87LyK3VuUGGfuWkNTtSD3Hj fee 0.00100896 BTC/kB, 0.000225 BTC for 223 bytes ... We created the watching wallet: bitcoinj02createwalletW.wallet Determistic watchingKey serializePubB58 (full) : tpubD8WRr3vpDwybtseRYzbP739wJw4vSMcRAvw6QifMh5ZNJTKwp5QRmymsjjLHp6kZqMPAVEqsZcAfqSApUS8mtLbwzyxAM5XFQMh3eZ73PRy Determistic watchingKey serializePubB58 (watching): tpubD8WRr3vpDwybtseRYzbP739wJw4vSMcRAvw6QifMh5ZNJTKwp5QRmymsjjLHp6kZqMPAVEqsZcAfqSApUS8mtLbwzyxAM5XFQMh3eZ73PRy ********************************************************************************** Ausgabe des Wallets vor der Reorganisation: bitcoinj02createwalletW.wallet Wallet Balances: 0.00 BTC ESTIMATED ... Transactions: 0 pending ... Last seen best block: 0 (time unknown): null Wallet is watching. Keys: Earliest creation time: 2020-02-29T09:44:25Z Key birthday: 1582969465 [2020-02-29T09:44:25Z] Ouput script type: P2PKH Key to watch: tpubD8WRr3vpDwybtseRYzbP739wJw4vSMcRAvw6QifMh5ZNJTKwp5QRmymsjjLHp6kZqMPAVEqsZcAfqSApUS8mtLbwzyxAM5XFQMh3eZ73PRy Lookahead siz/thr: 100/33 addr:mogznRmPEcfXBJimuGM8CojsWUtPVfQ3VM hash160:59a73e67ba416d45b46da3be18b9f3f0004ee364 (M/0H, account) ... Laden des Wallets in das WalletAppKit: bitcoinj02createwalletW.wallet Das Programm benötigt nun einen Onlinezugang, bitte haben Sie etwas Geduld (circa 1 bis 2 Minuten)... ********************************************************************************** Ausgabe des Wallets nach der Reorganisation: bitcoinj02createwalletW.wallet Wallet Balances: 0.01646622 BTC ESTIMATED 0.01646622 BTC AVAILABLE 0.00 BTC ESTIMATED_SPENDABLE 0.00 BTC AVAILABLE_SPENDABLE Transactions: 0 pending 4 unspent 2 spent 0 dead Last seen best block: 1669830 (2020-03-15T12:40:32Z): 000000000000005cbc5daaf9e32636f46d1c16bfe166d9ec7640880a4f61dacf Wallet is watching. Keys: Earliest creation time: 2020-02-29T09:44:25Z Key birthday: 1582969465 [2020-02-29T09:44:25Z] Ouput script type: P2PKH Key to watch: tpubD6NzVbkztN62gkBwS81yzkMy1AZnVSpZbFnW1N19z86T7EXV9rs15Ln5Ym1M1Utk4BzH6q5vSDvGNQ9K1H72j3LTqw2JBbH6792WyMst7gc Lookahead siz/thr: 100/33 addr:mogznRmPEcfXBJimuGM8CojsWUtPVfQ3VM hash160:59a73e67ba416d45b46da3be18b9f3f0004ee364 (M/0H, account) ... >>> UNSPENT: 0.0001 BTC total value (sends 0.00 BTC and receives 0.0001 BTC) confidence: Appeared in best chain at height 1669682, depth 149. Source: NETWORK 147ceb133fb04577e6e724e46e8792042ba02bdd01086792505aec6583ffb9f5, wtxid 09d433eecce782483c6ec3779d7a3ea34b0f8fbbf8109d9b300d358d2f26cd43 updated: 2020-03-13T14:03:06Z version 2 time locked until block 1669680 purpose: UNKNOWN in PUSHDATA(22)[00148843535b110ab5f67b1d6388b350009ce2aaa934] witness:3043021f1fe86526bc4e43006becacbafbe7d07094632d0d019a11ea632122aaeb527f022064249f853f35dc4dc85a590567f4187f65f84aa25ce74f104e0e532f136f183b01 0330d63066810f1520108a45ecee1becaa0d01dd1b50cc6b37ceb9bd8cf74c9d84 unconnected outpoint:207cb72e6db8188ceb0d376bd0ae7327e7963ec2ddf52b96a42b6c268f16c8ea:1 sequence:fffffffe out DUP HASH160 PUSHDATA(20)[51fd9d4bf19749a00f87b5166bd4ebbd93e0661c] EQUALVERIFY CHECKSIG 0.0001 BTC P2PKH addr:mnzUr2qbm8gDQQoMjz3k9UhiPuNq6QDFA5 out HASH160 PUSHDATA(20)[7d987bfed51da64f7c621f3c38803f21835dca1a] EQUAL 0.08772392 BTC P2SH addr:2N4hK84XafPwXBi7tq21PBySQ2dp4umdiqc ... Die Konvertierung war erfolgreich. |
Quellcode:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 |
/* * Herkunft/Origin: http://javacrypto.bplaced.net/ * Programmierer/Programmer: Michael Fehr * Copyright/Copyright: Michael Fehr * Lizenttext/Licence: verschiedene Lizenzen / several licenses * getestet mit/tested with: Java Runtime Environment 11.0.5 x64 * verwendete IDE/used IDE: intelliJ IDEA 2019.3.1 * Datum/Date (dd.mm.jjjj): 15.03.2020 * Funktion: 05 wandelt das Wallet in ein Watching Wallet um * Function: 05 converts a wallet to a watching wallet * * Sicherheitshinweis/Security notice * Die Programmroutinen dienen nur der Darstellung und haben keinen Anspruch auf eine korrekte Funktion, * insbesondere mit Blick auf die Sicherheit ! * Prüfen Sie die Sicherheit bevor das Programm in der echten Welt eingesetzt wird. * The program routines just show the function but please be aware of the security part - * check yourself before using in the real world ! * * Sie benötigen diverse Bibliotheken (alle im Github-Archiv im Unterordner "libs") * You need a lot of libraries (see my Github-repository in subfolder "libs") * verwendete BitcoinJ-Bibliothek / used BitcoinJ Library: bitcoinj-core-0.15.6.jar * my Github-Repository: https://github.com/java-crypto/BitcoinJ * libs in my Github-Repo: https://github.com/java-crypto/BitcoinJ_Libraries * */ import org.bitcoinj.core.ECKey; import org.bitcoinj.core.NetworkParameters; import org.bitcoinj.crypto.DeterministicKey; import org.bitcoinj.kits.WalletAppKit; import org.bitcoinj.params.TestNet3Params; import org.bitcoinj.wallet.UnreadableWalletException; import org.bitcoinj.wallet.Wallet; import java.io.File; import java.io.IOException; public class BitcoinJ05ConvertWatchingWallet { static WalletAppKit kit; public static void main(String[] args) throws UnreadableWalletException, IOException { System.out.println("BitcoinJ 05 Erzeuge ein Watching Wallet von einem normalen Wallet"); String filenameFullWallet = "bitcoinj02createwallet.wallet"; String filenameWatchingWallet = "bitcoinj02createwalletW.wallet"; // check for existing filenameWatchingWallet files // files are .wallet and .spvchain boolean foundOldWatchingFiles = false; if (new File(filenameWatchingWallet).exists()) { System.out.println("Die existierende Datei muss manuell gelöscht werden: " + filenameWatchingWallet); foundOldWatchingFiles = true; } if (new File(filenameWatchingWallet.replace(".wallet", ".spvchain")).exists()) { System.out.println("Die existierende Datei muss manuell gelöscht werden: " + filenameWatchingWallet.replace(".wallet", ".spvchain")); foundOldWatchingFiles = true; } if (foundOldWatchingFiles == true) { System.out.println("Bitte loeschen Sie die oben genannten Dateien von Hand. Das Programm wird nun beendet."); System.exit(0); } System.out.println("\nWir nutzen das Bitcoin Testnetz und nicht das Mainnetz"); NetworkParameters netParams = TestNet3Params.get(); //NetworkParameters netParams = MainNetParams.get(); System.out.println("\nLaden des originalen Wallets: " + filenameFullWallet); final File fullWalletFile = new File(filenameFullWallet); Wallet fullWallet = null; if (fullWalletFile.exists()) { System.out.println("Das laden war erfolgreich: " + filenameFullWallet); fullWallet = Wallet.loadFromFile(fullWalletFile); } else { System.out.println("Walletdatei nicht gefunden: " + filenameFullWallet); System.exit(0); } System.out.println("**********************************************************************************"); System.out.println("Ausgabe des originalen Wallets: " + filenameFullWallet); System.out.println(fullWallet.toString()); // create the watching wallet System.out.println("We created the watching wallet: " + filenameWatchingWallet); DeterministicKey fullWatchingKey = fullWallet.getWatchingKey(); System.out.println("Determistic watchingKey serializePubB58 (full) : " + fullWatchingKey.serializePubB58(netParams)); long fullKeyBirthday = fullWatchingKey.getCreationTimeSeconds(); DeterministicKey watchingWatchingKey = DeterministicKey.deserializeB58(fullWatchingKey.serializePubB58(netParams), netParams); System.out.println("Determistic watchingKey serializePubB58 (watching): " + watchingWatchingKey.serializePubB58(netParams)); Wallet watchingWallet = Wallet.fromWatchingKeyB58(netParams, watchingWatchingKey.serializePubB58(netParams), fullKeyBirthday); System.out.println("**********************************************************************************"); System.out.println("Ausgabe des Wallets vor der Reorganisation: " + filenameWatchingWallet); System.out.println(watchingWallet.toString()); watchingWallet.saveToFile(new File(filenameWatchingWallet)); watchingWallet.reset(); // force to reimport the spv-file // need an online access to reorg the spv-file and re-import the transactions System.out.println("Laden des Wallets in das WalletAppKit: " + filenameWatchingWallet); System.out.println("Das Programm benötigt nun einen Onlinezugang, bitte haben Sie etwas Geduld (circa 1 bis 2 Minuten)..."); kit = new WalletAppKit(netParams, new File("."), filenameWatchingWallet.replace(".wallet", "")) { @Override protected void onSetupCompleted() { if (wallet().getKeyChainGroupSize() < 1) { wallet().importKey(new ECKey()); } } }; kit.startAsync(); // start the communication kit.awaitRunning(); // wait for completion System.out.println("**********************************************************************************"); System.out.println("Ausgabe des Wallets nach der Reorganisation: " + filenameWatchingWallet); System.out.println(kit.wallet().toString()); System.out.println("Die Konvertierung war erfolgreich."); } } |
Alle Quellcodes zum Bitcoin findet Ihr zum Download in meinem Github-Repository BitcoinJ, welches Ihr über diesen Link erreicht: https://github.com/java-crypto/BitcoinJ. Alle Programme sind unter Java 11 lauffähig (vermutlich auch unter Java 8) und wurden mit intelliJ IDEA entwickelt, welches für dieses Programm aber nicht notwendig ist.
Noch ein Wort zum Thema „Lizenz“: Die von mir erstellten Beispiele selber stehen unter der „Unlicense“-Lizenz, allerdings werden zur Laufzeit diverse Bibliotheken eingebunden, welche zum Teil ganz eigene Lizenzen mitbringen. Darauf kann ich in meinen Lizenzhinweisen nicht hinweisen.
Letzte Bearbeitung: 18.03.2020