IoT
仮想通貨
iota
DAG
tangle

IOTA:【技術解説】マルチシグを理解し実装する。

 MAMの記事と合わせて、Tangleの柔軟性が伝わって欲しい。

IOTA(アイオータ)とは

おなじみ初心者向けの解説サイトを念のためここに列挙しておく。

IOTA日本語ファンサイト 実質IOTA日本公式サイト。というのもIOTA公式の情報を日本語訳して掲載しているからである。初心者向けの情報も多く掲載されている。
ホワイトペーパー英語 日本語 Tangleについての概要は序盤までで、それ以降は安全性、想定される攻撃とその耐性について高度な数学で説明している。後半は初心者向きではない。
Redditの初心者向けスレッド(英語) 僕はここから始まった。
IOTA Guide(英語) ホワイトペーパーが理学部なら、これは工学部。

前提知識

 今まで書いた記事の中でもIOTAの基礎部分は以下の3つで説明した。

IOTA:【入門】トランザクション大解剖!ウォレットは裏で何をやっているか。
IOTA:【技術解説】送金APIから紐解くBundleの全容。
IOTA【技術解説】署名と承認。 - 改訂版

マルチシグとは?

 英語に直すと、Multisig。意味は複数署名。特に取引所などで行われる高額な取引を、一つのSeedに結びつけるのが不安な時、複数のSeedを同時に用意しないと送金の署名ができないアカウントを作るために利用される。また、取引の記録はTangleに残るが、はたから見てもどの取引が普通のもので、どれがマルチシグのものかは分からない。

アドレス生成のディープな話

 IOTAのTangleでどうそれを実現したかをみる前に重要な概念、普通のアドレスの生成とsecurityの関係について今までより一歩深く理解する必要がある。
 さて、まず普通のアドレスはどう生成されるのか。大まかな手順を略図にした。
address_gen.png
 Seed、Private Key、digests、addressという長旅を経てaddressは生成されることが何となく分かっただろうか?

Private Keyとは

 それではSeedの次に生成されるPrivate Keyについて見てみよう。

key.js
var Signing = require('../lib/crypto/signing/signing');
var Converter = require('../lib/crypto/converter/converter');

var seed = 'ABMUSHI9TEST';

// 今回はindexを固定して考える。
var index = 0;

//  Private Keyを返す関数
var getKey = function(seed,index,security){
    var key_trits = Signing.key(Converter.trits(seed),index,security);  // private key
    var key = Converter.trytes(key_trits);    // tryteに変換
    return key;
}

// Private Keyをsecurity 1~3まで生成してみる。
for(var s=1;s<4;s++){
    var key = getKey(seed,index,s);
    console.log('- - - - - - - - - - - - - - - - - - - - -');
    console.log('security: ',s);
    console.log('private key length: ',key.length);
    console.log('private key: ',key);
}
結果
- - - - - - - - - - - - - - - - - - - - -
security:  1
private key length:  2187
private key:  XUXGEZIDZJNUTRGHLXZLMTHQZIPGVCEDYZCYZPCGSXRRZTPFOCFFOC9W9ALKIQCVGZNVZJKNVKIEYHPWBIANTSWGFXQBIMBQLXNTGXKH9MSZYQUMDRNVWZVDBWLJZCMLAWJHUTJZARVELQEXIDCTLTSFYMVVLMNXFYUUGB9TVVEOPV9FFKQZTQONILV9FJCWZDRRITITAPTSOXRXCPWYJKNFONXJLFOIHKJWBWGKYYNUTKC9DWAMXSLFRBGMWKUIDD9CTJFKXEKEXMHWSWAR9GNGKAMHYQNOPLJORZFWHIXEGBBILATMSKHGN99ERIMNHQDZPBMOJOGNWCEBTQPABBRKOPXPYKFHUZDWSHWNDTLTUBFTGVGCYZYFQDUMRJ9IQMVFCZJZJHRVYREOEFNPDTJKMYLOKPKKLMEEEDIFHKAYBVEMXL9OWMEYMQYBVEONSTNWEPCSP9MNZNBOLICIHXYIQMBWALHDQNWCJD9LMGHSJWEHAWIIHE9GHRRSBMLQKWSQNCMAEOPHZRICNMTTYXH9KHBOCDADSECURFTE9YKGTVZHYFYHVHDDHL9Q9JJTTJJUWIZWIMTDAUI9DTFJENYLLLRQ9XIWMCQ9BPZRKZVLXTO9MCQCEALKCNVWGROTJNFVSLTYDMISCOQU9VRVNLBGGEAAR9XOYQOOKYXQJJTROWVQYBKO9URAFTMUW9ABBBCOABUO9GFDZBGACBLQQNYQYAIUKBVJGWRBUZYOJTIPO9GGSEJBUGNQPXYBIMMFPHNVOLTBGKP9AMGBFALZJLXQZMWZKAJURQRRKSKAYWQERERQCOQFABBAXL9MRCCRVFYMLUQATBFHLNISISIXKVYCEPMZKD9HSOKIL9YNVYVIVJHYNVDQEQ9HUZZHPDURFYBDUWRKCCHQDESPHZRPJOOWAUWCX9K9QYSROEDCTVWLLGECJDWI9KEZZAVKRTRHSHPTUQJOLNCBSDQMYTNFWGMYOIRS9RIQFABDTDKRTSZZSKVUUOIUORSDZGNQYXHIOFCYVQHFMBXFXRGLYRPZYWIRPRZXDRBIENSMSJVJMMUMHZPXGQHLDWKWCLVIYL9MQHMUXHHZYDFI9AAZOXFEGY9TTZMYWUVZXCJBWRSPXNTIZXCG9DSFGAHVQHIMYTZ9FFMOIGWVNTFDYNJDZDCGFMQFNHYXJMXLKSREUSAWVCWLUTBUNK9WXTWGDWZXSQCWCCHEZWZQWFRPEPUYDXWUTIVMITLRVWDBKHERHITJKBTKZDLWVKSJSUPSQJUEPKC9QTJIGKQGPRMRUHIWYPYSHCYUQXQRN9IJBDPRLYTADHVFQRBZNOPNBWXFLQIOMEMXFGMZ9SBVBTHHXFHDIIRKSGMZAPIKBXYDCEAQLSTTXDPQ9ASORJUZLMNOKQNXMJCTH9KZLBPNWVMBJSQXDEMFWWBNVQZXCJYRXEMBSSGWLVNOIEIZD9EJEWGHICEXOJZAEHJTJHTENPSZFERQBJZPX9NQOHGBYSUMKUXZDJ9FHEZUW9SMQHWMMNRJTKSAMWGKMDWCMB9ARCODYEXSRVBDFWXDHMEY9CT9QXTZNELVWSOHSJYPMQGKVFRNMUNQAPTVMVVFVNNBBBQAMOWSMETCHHMRWLXWWOEMFOEAZWMPLGSUZRS9PIUHMZOXBQKEQUBPRZICPQCSEVUMLLKTWC9VGZJEXDBAXVTMYYSACYQVJTIVIEZDI9SUHVLFKZEJAYEEYEBFCQFMIZZIATDDBNZQESSNXVEYFJRJSHHGQQDRGVDVLYMQKSRMOWMSNIISJYGIAWJKEHMWKDYEAEAETSST9JMYNC9KI9MMZGNADIJRYDKLXEFUZTMJEB9DBSPVOXVXLMGCXDXRQTZRUWLMHCXTSRZNGZDAFF9IYUZWISUBGNUEYTOPHDHFRJOVUVHUXIHLJHMJG9SSHMLRUULBJYGKHUQYAQOT9GHTXX9LCZLLEIMXYKIZHGSVHGSPA9GSKLLMIJ9WYL9DLODOWNXTMHJFZBIOIRVRBZIPAYDNRLZODNJQWATHOWMGACVPLDEANJXFETDCVFDOFGECVOWWXJQJEGAACIZBYFHDMIIMZHRMGJZSJDTVCUPDZKDFHWKVDZB9NILRXDGPHVVQBGGMDXDEVDMRXOTRJSNIEMXJVTDYHGTOLUIPSBCERYJSUQDGLQWVCBPPCLSVGVD
- - - - - - - - - - - - - - - - - - - - -
security:  2
private key length:  4374
private key:  XUXGEZIDZJNUTRGHLXZLMTHQZIPGVCEDYZCYZPCGSXRRZTPFOCFFOC9W9ALKIQCVGZNVZJKNVKIEYHPWBIANTSWGFXQBIMBQLXNTGXKH9MSZYQUMDRNVWZVDBWLJZCMLAWJHUTJZARVELQEXIDCTLTSFYMVVLMNXFYUUGB9TVVEOPV9FFKQZTQONILV9FJCWZDRRITITAPTSOXRXCPWYJKNFONXJLFOIHKJWBWGKYYNUTKC9DWAMXSLFRBGMWKUIDD9CTJFKXEKEXMHWSWAR9GNGKAMHYQNOPLJORZFWHIXEGBBILATMSKHGN99ERIMNHQDZPBMOJOGNWCEBTQPABBRKOPXPYKFHUZDWSHWNDTLTUBFTGVGCYZYFQDUMRJ9IQMVFCZJZJHRVYREOEFNPDTJKMYLOKPKKLMEEEDIFHKAYBVEMXL9OWMEYMQYBVEONSTNWEPCSP9MNZNBOLICIHXYIQMBWALHDQNWCJD9LMGHSJWEHAWIIHE9GHRRSBMLQKWSQNCMAEOPHZRICNMTTYXH9KHBOCDADSECURFTE9YKGTVZHYFYHVHDDHL9Q9JJTTJJUWIZWIMTDAUI9DTFJENYLLLRQ9XIWMCQ9BPZRKZVLXTO9MCQCEALKCNVWGROTJNFVSLTYDMISCOQU9VRVNLBGGEAAR9XOYQOOKYXQJJTROWVQYBKO9URAFTMUW9ABBBCOABUO9GFDZBGACBLQQNYQYAIUKBVJGWRBUZYOJTIPO9GGSEJBUGNQPXYBIMMFPHNVOLTBGKP9AMGBFALZJLXQZMWZKAJURQRRKSKAYWQERERQCOQFABBAXL9MRCCRVFYMLUQATBFHLNISISIXKVYCEPMZKD9HSOKIL9YNVYVIVJHYNVDQEQ9HUZZHPDURFYBDUWRKCCHQDESPHZRPJOOWAUWCX9K9QYSROEDCTVWLLGECJDWI9KEZZAVKRTRHSHPTUQJOLNCBSDQMYTNFWGMYOIRS9RIQFABDTDKRTSZZSKVUUOIUORSDZGNQYXHIOFCYVQHFMBXFXRGLYRPZYWIRPRZXDRBIENSMSJVJMMUMHZPXGQHLDWKWCLVIYL9MQHMUXHHZYDFI9AAZOXFEGY9TTZMYWUVZXCJBWRSPXNTIZXCG9DSFGAHVQHIMYTZ9FFMOIGWVNTFDYNJDZDCGFMQFNHYXJMXLKSREUSAWVCWLUTBUNK9WXTWGDWZXSQCWCCHEZWZQWFRPEPUYDXWUTIVMITLRVWDBKHERHITJKBTKZDLWVKSJSUPSQJUEPKC9QTJIGKQGPRMRUHIWYPYSHCYUQXQRN9IJBDPRLYTADHVFQRBZNOPNBWXFLQIOMEMXFGMZ9SBVBTHHXFHDIIRKSGMZAPIKBXYDCEAQLSTTXDPQ9ASORJUZLMNOKQNXMJCTH9KZLBPNWVMBJSQXDEMFWWBNVQZXCJYRXEMBSSGWLVNOIEIZD9EJEWGHICEXOJZAEHJTJHTENPSZFERQBJZPX9NQOHGBYSUMKUXZDJ9FHEZUW9SMQHWMMNRJTKSAMWGKMDWCMB9ARCODYEXSRVBDFWXDHMEY9CT9QXTZNELVWSOHSJYPMQGKVFRNMUNQAPTVMVVFVNNBBBQAMOWSMETCHHMRWLXWWOEMFOEAZWMPLGSUZRS9PIUHMZOXBQKEQUBPRZICPQCSEVUMLLKTWC9VGZJEXDBAXVTMYYSACYQVJTIVIEZDI9SUHVLFKZEJAYEEYEBFCQFMIZZIATDDBNZQESSNXVEYFJRJSHHGQQDRGVDVLYMQKSRMOWMSNIISJYGIAWJKEHMWKDYEAEAETSST9JMYNC9KI9MMZGNADIJRYDKLXEFUZTMJEB9DBSPVOXVXLMGCXDXRQTZRUWLMHCXTSRZNGZDAFF9IYUZWISUBGNUEYTOPHDHFRJOVUVHUXIHLJHMJG9SSHMLRUULBJYGKHUQYAQOT9GHTXX9LCZLLEIMXYKIZHGSVHGSPA9GSKLLMIJ9WYL9DLODOWNXTMHJFZBIOIRVRBZIPAYDNRLZODNJQWATHOWMGACVPLDEANJXFETDCVFDOFGECVOWWXJQJEGAACIZBYFHDMIIMZHRMGJZSJDTVCUPDZKDFHWKVDZB9NILRXDGPHVVQBGGMDXDEVDMRXOTRJSNIEMXJVTDYHGTOLUIPSBCERYJSUQDGLQWVCBPPCLSVGVDYSCKGXUBGYRAZJDAQYCNFWZSLKOYJSRCGVJZHTSXMFBKCDNBJR9HKEEE9ALGASHEYLABOUKKUYCGEWLNZRQIBXWMIPLDXZXDJNVTOCLSQUPTEQIFLCSWUJOLWI9TWMSF9HZWBZCIYOQITAAMIBHQGDJKSXWRHPLYICVYOKYZUXFVUCZUTRBSKTKOQYURAXLLPNJNY9QVCQBG9ZNEJBXCTFHROGTXL99PWAPFKJOBIE9FEICTTX9GOUFOCABPFRDFOHRQWYLMDJYWPTUULBFBTMEXLNWCHVPEASRREAQ9TXKRJRMKPDPHPKOEKCCHOR9BDGZ9RUEXBVJVBWMKUEZNXEKQYZZCHAWPFKUTWCIDM9JHNXUJOS9HDDZSQZMIUFCHJYJHTOYKRPYP9DRGNYDRDCYKNE9BZQONWFHORWTVAKUIGX9SAPJTAEBOSUHIAPUMDNPMWLHGPPKFZGWBLLFATYUZOK9HRJBDYPHIEDGMNVRDBJCKGQOOQFBVHBGLSVHPWCROQZANFBJGW9QEE9WVTUPFMULPKGKHXSBGPJSNXVPXVGYFYAITGJAJYOWHNHGSKVCK9SKCOYHRGGSDYO9ILEPPZLXECTTI9GGFXNN9GOWUSGOLEDJ9XHOAVZIKJRPLTALVQG9DRTYNS9ZUUTZAJHJSPCKMKKQKQKSTDINPJVXYDYAHDGFWINGFKXFW9DSHTTABQNVHD9ZPCFDISQNVL9NHDYMPPNQJUVWIHXUMVJ9ZXZKIRHQQWQVRMTOYAPOWHFXMGCXJFTJFJBMFLAJHHEURVHPRQNDOXQTGBKU9XDKHVIVCCLWDSBIDLCOWMEJJMXDONHHTUANKKOYFURF9DTVAAFQEMCBVZBQZMJQIFHRISLFXGQMUMZNYNOXYDDYWFHVIQJNJVKVWXUTWBMTBXQSCWXDTZZQVWELRFLAGXNXSDPKKMKUIHN9SSOHKNZAZCOYGUKFXJIDDLECPVINKENDMKWJLGCWKZPPQQAAONUOYFVTWVBTFDBUYYHHDZUCXMVNNUVBOGD9KOIMONVTZBGFX9FRVCTNRBWJVJSJOUZBXBNTKQUVZIOEUDNOL9WYUG9FLKJVHOJWBVLMKWMJPRMQDTEQLXAFECHPZYHPQZFSEPDNQGPRMITSQCQFMAZSSAFOKNRPMUK9JOKAKHUZAZYIURHQYUGAVNHN9TXJLDFWSJSWEAEWQCGLLR9ZDBRXNNZWWPDYF9LWFKMPHLYLHIWWCEXFJOCWXWTPK9ICCLEOOKAXWDPK9P9FWXSSRZBKRNWZPJYYWYYSVCODB9JVLFH9E9YOTUSGHRFGFGSVDHX9BYBTGLYCTRKOEVUFVWMIPRPWCMLNBTPG9CB9NNLQCYCIF9PVUCZ9OZRQDEIIJOWWCKZEYHCE999WPXMUFQSISGJCHZVTLPFHSYHJXHTVBIMEUXXJWUWQHNNQPHV9CVSQQRCMSRWPKRTYZLBOKZXTCFMDHOVXITWWHEJLYPYRNQTLXBUNSSUAASYVKLRTZZWMVYCKBNVDKSLO9DXCMOITHA9DCUSOIKWNHI9QJKLVKGIC9HYYWSBYD9OJQRHY9UPJULCAYZQTHSATYKTPEWAVTRTNO9VYGLEKUYHOLMBHWNRSKYTOPDDFQNDTOSBDWIAVWRAWGXFLJCL9LBJNVZHVZVKLRKIYDVMZSDHKZIPPI9EWEAJ9NUPHHR9KAWUNS9NT9JJDWPIUCNBYDLVCTBFACTETDVGZVZSDKXQXUBKXAPULERN9CIYATKGKPJAUSJ9YNRVBCLGRZZYDVJGWA9IVQBASIWVZGHTKNTEKDXBYZXQQTSXYOSEEHB9YJDKXPLIUQSSWBHKIGMTKRXUAELSJZXRGMXJWXCWVJBCXSZWVPXWHJWXBOFGZBIWZHHUFULCKHSDKJRKZZ9FPTUCBHESQ9DNIGWEZGWTHQCOMHXGW9AGMYHBQ9WSLIRGPUYIAAOKYZVNDRKBFWGYRSJLIAEXLXQPFGZTQPHNFEUWQLNXPDYXQOZ9MUAUH9JU9SWCJAAWRZZXKWYFFOGRPPOQJQPXGNUPOXLRRYZPDDTHMKVAXPZPADZKENHZHACAZZHMCAFVC9QVQXPKSDDLLSD9NQLZRPKUKXZZYRKSTKHYK9LZIYXCQXIKMNJKYBWLPG9GSEJPKGIFYNTZTOINIZBBHMUJTYGMAJXZZOYXB
- - - - - - - - - - - - - - - - - - - - -
security:  3
private key length:  6561
private key:  XUXGEZIDZJNUTRGHLXZLMTHQZIPGVCEDYZCYZPCGSXRRZTPFOCFFOC9W9ALKIQCVGZNVZJKNVKIEYHPWBIANTSWGFXQBIMBQLXNTGXKH9MSZYQUMDRNVWZVDBWLJZCMLAWJHUTJZARVELQEXIDCTLTSFYMVVLMNXFYUUGB9TVVEOPV9FFKQZTQONILV9FJCWZDRRITITAPTSOXRXCPWYJKNFONXJLFOIHKJWBWGKYYNUTKC9DWAMXSLFRBGMWKUIDD9CTJFKXEKEXMHWSWAR9GNGKAMHYQNOPLJORZFWHIXEGBBILATMSKHGN99ERIMNHQDZPBMOJOGNWCEBTQPABBRKOPXPYKFHUZDWSHWNDTLTUBFTGVGCYZYFQDUMRJ9IQMVFCZJZJHRVYREOEFNPDTJKMYLOKPKKLMEEEDIFHKAYBVEMXL9OWMEYMQYBVEONSTNWEPCSP9MNZNBOLICIHXYIQMBWALHDQNWCJD9LMGHSJWEHAWIIHE9GHRRSBMLQKWSQNCMAEOPHZRICNMTTYXH9KHBOCDADSECURFTE9YKGTVZHYFYHVHDDHL9Q9JJTTJJUWIZWIMTDAUI9DTFJENYLLLRQ9XIWMCQ9BPZRKZVLXTO9MCQCEALKCNVWGROTJNFVSLTYDMISCOQU9VRVNLBGGEAAR9XOYQOOKYXQJJTROWVQYBKO9URAFTMUW9ABBBCOABUO9GFDZBGACBLQQNYQYAIUKBVJGWRBUZYOJTIPO9GGSEJBUGNQPXYBIMMFPHNVOLTBGKP9AMGBFALZJLXQZMWZKAJURQRRKSKAYWQERERQCOQFABBAXL9MRCCRVFYMLUQATBFHLNISISIXKVYCEPMZKD9HSOKIL9YNVYVIVJHYNVDQEQ9HUZZHPDURFYBDUWRKCCHQDESPHZRPJOOWAUWCX9K9QYSROEDCTVWLLGECJDWI9KEZZAVKRTRHSHPTUQJOLNCBSDQMYTNFWGMYOIRS9RIQFABDTDKRTSZZSKVUUOIUORSDZGNQYXHIOFCYVQHFMBXFXRGLYRPZYWIRPRZXDRBIENSMSJVJMMUMHZPXGQHLDWKWCLVIYL9MQHMUXHHZYDFI9AAZOXFEGY9TTZMYWUVZXCJBWRSPXNTIZXCG9DSFGAHVQHIMYTZ9FFMOIGWVNTFDYNJDZDCGFMQFNHYXJMXLKSREUSAWVCWLUTBUNK9WXTWGDWZXSQCWCCHEZWZQWFRPEPUYDXWUTIVMITLRVWDBKHERHITJKBTKZDLWVKSJSUPSQJUEPKC9QTJIGKQGPRMRUHIWYPYSHCYUQXQRN9IJBDPRLYTADHVFQRBZNOPNBWXFLQIOMEMXFGMZ9SBVBTHHXFHDIIRKSGMZAPIKBXYDCEAQLSTTXDPQ9ASORJUZLMNOKQNXMJCTH9KZLBPNWVMBJSQXDEMFWWBNVQZXCJYRXEMBSSGWLVNOIEIZD9EJEWGHICEXOJZAEHJTJHTENPSZFERQBJZPX9NQOHGBYSUMKUXZDJ9FHEZUW9SMQHWMMNRJTKSAMWGKMDWCMB9ARCODYEXSRVBDFWXDHMEY9CT9QXTZNELVWSOHSJYPMQGKVFRNMUNQAPTVMVVFVNNBBBQAMOWSMETCHHMRWLXWWOEMFOEAZWMPLGSUZRS9PIUHMZOXBQKEQUBPRZICPQCSEVUMLLKTWC9VGZJEXDBAXVTMYYSACYQVJTIVIEZDI9SUHVLFKZEJAYEEYEBFCQFMIZZIATDDBNZQESSNXVEYFJRJSHHGQQDRGVDVLYMQKSRMOWMSNIISJYGIAWJKEHMWKDYEAEAETSST9JMYNC9KI9MMZGNADIJRYDKLXEFUZTMJEB9DBSPVOXVXLMGCXDXRQTZRUWLMHCXTSRZNGZDAFF9IYUZWISUBGNUEYTOPHDHFRJOVUVHUXIHLJHMJG9SSHMLRUULBJYGKHUQYAQOT9GHTXX9LCZLLEIMXYKIZHGSVHGSPA9GSKLLMIJ9WYL9DLODOWNXTMHJFZBIOIRVRBZIPAYDNRLZODNJQWATHOWMGACVPLDEANJXFETDCVFDOFGECVOWWXJQJEGAACIZBYFHDMIIMZHRMGJZSJDTVCUPDZKDFHWKVDZB9NILRXDGPHVVQBGGMDXDEVDMRXOTRJSNIEMXJVTDYHGTOLUIPSBCERYJSUQDGLQWVCBPPCLSVGVDYSCKGXUBGYRAZJDAQYCNFWZSLKOYJSRCGVJZHTSXMFBKCDNBJR9HKEEE9ALGASHEYLABOUKKUYCGEWLNZRQIBXWMIPLDXZXDJNVTOCLSQUPTEQIFLCSWUJOLWI9TWMSF9HZWBZCIYOQITAAMIBHQGDJKSXWRHPLYICVYOKYZUXFVUCZUTRBSKTKOQYURAXLLPNJNY9QVCQBG9ZNEJBXCTFHROGTXL99PWAPFKJOBIE9FEICTTX9GOUFOCABPFRDFOHRQWYLMDJYWPTUULBFBTMEXLNWCHVPEASRREAQ9TXKRJRMKPDPHPKOEKCCHOR9BDGZ9RUEXBVJVBWMKUEZNXEKQYZZCHAWPFKUTWCIDM9JHNXUJOS9HDDZSQZMIUFCHJYJHTOYKRPYP9DRGNYDRDCYKNE9BZQONWFHORWTVAKUIGX9SAPJTAEBOSUHIAPUMDNPMWLHGPPKFZGWBLLFATYUZOK9HRJBDYPHIEDGMNVRDBJCKGQOOQFBVHBGLSVHPWCROQZANFBJGW9QEE9WVTUPFMULPKGKHXSBGPJSNXVPXVGYFYAITGJAJYOWHNHGSKVCK9SKCOYHRGGSDYO9ILEPPZLXECTTI9GGFXNN9GOWUSGOLEDJ9XHOAVZIKJRPLTALVQG9DRTYNS9ZUUTZAJHJSPCKMKKQKQKSTDINPJVXYDYAHDGFWINGFKXFW9DSHTTABQNVHD9ZPCFDISQNVL9NHDYMPPNQJUVWIHXUMVJ9ZXZKIRHQQWQVRMTOYAPOWHFXMGCXJFTJFJBMFLAJHHEURVHPRQNDOXQTGBKU9XDKHVIVCCLWDSBIDLCOWMEJJMXDONHHTUANKKOYFURF9DTVAAFQEMCBVZBQZMJQIFHRISLFXGQMUMZNYNOXYDDYWFHVIQJNJVKVWXUTWBMTBXQSCWXDTZZQVWELRFLAGXNXSDPKKMKUIHN9SSOHKNZAZCOYGUKFXJIDDLECPVINKENDMKWJLGCWKZPPQQAAONUOYFVTWVBTFDBUYYHHDZUCXMVNNUVBOGD9KOIMONVTZBGFX9FRVCTNRBWJVJSJOUZBXBNTKQUVZIOEUDNOL9WYUG9FLKJVHOJWBVLMKWMJPRMQDTEQLXAFECHPZYHPQZFSEPDNQGPRMITSQCQFMAZSSAFOKNRPMUK9JOKAKHUZAZYIURHQYUGAVNHN9TXJLDFWSJSWEAEWQCGLLR9ZDBRXNNZWWPDYF9LWFKMPHLYLHIWWCEXFJOCWXWTPK9ICCLEOOKAXWDPK9P9FWXSSRZBKRNWZPJYYWYYSVCODB9JVLFH9E9YOTUSGHRFGFGSVDHX9BYBTGLYCTRKOEVUFVWMIPRPWCMLNBTPG9CB9NNLQCYCIF9PVUCZ9OZRQDEIIJOWWCKZEYHCE999WPXMUFQSISGJCHZVTLPFHSYHJXHTVBIMEUXXJWUWQHNNQPHV9CVSQQRCMSRWPKRTYZLBOKZXTCFMDHOVXITWWHEJLYPYRNQTLXBUNSSUAASYVKLRTZZWMVYCKBNVDKSLO9DXCMOITHA9DCUSOIKWNHI9QJKLVKGIC9HYYWSBYD9OJQRHY9UPJULCAYZQTHSATYKTPEWAVTRTNO9VYGLEKUYHOLMBHWNRSKYTOPDDFQNDTOSBDWIAVWRAWGXFLJCL9LBJNVZHVZVKLRKIYDVMZSDHKZIPPI9EWEAJ9NUPHHR9KAWUNS9NT9JJDWPIUCNBYDLVCTBFACTETDVGZVZSDKXQXUBKXAPULERN9CIYATKGKPJAUSJ9YNRVBCLGRZZYDVJGWA9IVQBASIWVZGHTKNTEKDXBYZXQQTSXYOSEEHB9YJDKXPLIUQSSWBHKIGMTKRXUAELSJZXRGMXJWXCWVJBCXSZWVPXWHJWXBOFGZBIWZHHUFULCKHSDKJRKZZ9FPTUCBHESQ9DNIGWEZGWTHQCOMHXGW9AGMYHBQ9WSLIRGPUYIAAOKYZVNDRKBFWGYRSJLIAEXLXQPFGZTQPHNFEUWQLNXPDYXQOZ9MUAUH9JU9SWCJAAWRZZXKWYFFOGRPPOQJQPXGNUPOXLRRYZPDDTHMKVAXPZPADZKENHZHACAZZHMCAFVC9QVQXPKSDDLLSD9NQLZRPKUKXZZYRKSTKHYK9LZIYXCQXIKMNJKYBWLPG9GSEJPKGIFYNTZTOINIZBBHMUJTYGMAJXZZOYXBNVQTNHRIEUFARKQKQJCTQDDPQWQSPUIZFGQXILXYYADVLRZEVLXSZLPEEFMSCVLYIFFAYPIWWT9VFSJTDZVOCYZABVOQEGFEFMJIWEEKFKBBNIALMMJLMNZDZPDSSPMDQYWGDCAZCRKBLABJUXVZ9EOSKJLJRVWKOYHUVHRASW9PRAUAK9DGXVLTBQEYIKNHOXKLXZTFSEQF9VTCAKVYEONZFOVJVXNAPPOYWPQXZKQJQFLNCU9MQRJETHDVDYWRCVLWYQXXOXMKZUPWHWLVKZACNNYBDZLFQSYNOAWSAWHYGOGVZACBOCSXD9JVVIUG9LRZBHQNTZEBGT9JZNPFDWMIKCIOMUSSKROUEWYHJKKGTSEUTKOJDXGGVHVSAMUXAFVWPNX9YZTK9FE9FPJUCPEERLGWKNIXZUTJFUARMZSMJEFEUKFOIDMDPOCZGGUFMARX9MMWAJNNF9BB9SOLKZMGATMZJKINKGMAEZFVTFUQVVYJKCAGSFBNVIOZVJFGOYZJDMNPPZOTVAZCFXDKRIJOGXVAF9SADRSRPSKSDQJJAWXSVIKDFQ9UJYVHJQSRNYWEPPOUSOXGCRIVIOUZHI9MYGJITK9EGDSIADVKE9STUQSJBETYHJUUHESVEVKSUHUGWENDRL9UVYNGGETSBOKKAGDNFJXRYHPWQPEADGKB9NFHPDWTFKXSTZVLEEDVJMGEINXXPKDPMHVGBMNYKDEL9UZXGTUTOVQSCYAG9WZUPBEIWQXVNAGPKPHUYKCWUFXRVVYMCOBGOCEBBIOXELLWPUHFT9CEMFXXGHMROYGDOQUQYKNIVJLQZSOBZXSUBUICNLYI9DGHIFJLLGXJEEESYOMPOMAARGSWCP9JUUBLCVXDVRLGNB9DBCDLLEWEWL9IXVVWNIILBVV9FRZVCKKMIEICOBRLFWHXGERNEBXBRRKUEIMLHDZNFIKOPOBFUSJTAYHKJCC9ZZJNPLSJSZUVLQGABB9YZMCPBLGZV9KGRGOKBNERFUMUQKWKOPDCLXFCDNYS9UYDCOADJPLMWVAQRGUODVHGAXNBUPE9JSAJBWCQPOZTKMCONEQNFDAIFQJLOUJBHBRANLLUOSVNLGGQMWA9ACLSLFTNFMDXFECYXAQHTIQYHEFQTAYBKFMKIODBBCVRBHULD9MDLRUNS9OQCWPMO9O9T9GZVETNBAC99FVKSC9OCTKLDGFP9AXHHFUYGYAEHPJOCQREFTLAQJ9LPWUAGQBSOFQKOAGBATJGQCDXZPCYETMCWMWEFFPPFTJMIPZJJECIZAMXHHKVW9BFJPHVETSGBSTCVOWOSLPXLQZML9GGFRXDILRKMRTCKY9QFKAJBHNPSDHMYMNWN9LXTDFAWYNYXMGUKA9PKF9ODRTVODLNEVYNGIXGRUCAOKDQKRWHGWDCDTPFQYPTVLXZLLGHAYRSGZCSDTKZSLHLQWMNIBXHGCMESHZC9ZYDIZZOCPNCXVJCFYXPLMUKDMSTZ9TXBZLRZFVIESPANDIPSVTKDOCAVBRX9YXSJREVTECYLPHLHQPCZQBRYLVGVNUVRZECKJSJTZDMBPAKFQJPSVGQYKZGIPAANEZBBAGPKNETDVHGQFXMGK9PL9WWFGCHAKG9AIDEDQIJBDRQYILF9VOGNSNNHFYNNXJICWUJLIDW9UXKKXFLYAEXTZMRCVK9SAFCYCXYBRBLWLXMSSCYFMEZTYLWTYLIILFIVLDMFTLPZAUAPUPROWSIAMHRBB99ANFBMSN9HFUMKSKKYLBNFFNHWUQVV9GDOUROUMGOKETZTH9TKQNVBRKHIVPHQJYVVWUKNSSNXESUFYDCGKSRAJTTYBNI9UZADJQZPGEUOUEMRLWAJWVOCGEBXFKJNNBBNVWYWJI9DMNBVBDDNDWQNUGKMVKFBHUYDGBXTJTJPJAPIIQWFIYYDXTCWUFAQCV9ESE9LWEICQFTQLNJ9WA9RHAGXLMALACCBSCXMGZTLOEMCNSOQIBEPAJIQOMKICTFQXDJLYRCJNMEGJBCWCBAE9XWCERGTJARMLMHEEYXYSQMRPSBN9LXVASSGLI9SOJDTSFLNKNITVLJUZFVMSEKGBCIKOQQFCVLAWT9QJCUGOYRBUXLSELLKNNRSLLNTLNNBHOBGQHDZDXYBKSQFUMYWEQSLOECSCHDQKS9TKBQQWSAVBT9SJX

Private Keyはご覧の通り長いトライト文字列である。また、今回は省略したがindexを変えるとPrivate Keyの値も変わる。(長さは変わらない。)

digestとは

digests.js
var Signing = require('../lib/crypto/signing/signing');
var Converter = require('../lib/crypto/converter/converter');

var seed = 'ABMUSHI9TEST';

// 今回はindexを固定して考える。
var index = 0;

// digestを得る関数
var getDigests = function(seed,index,security){
    var key_trits = Signing.key(Converter.trits(seed),index,security);  // private key
    var digest_trits = Signing.digests(key_trits);  // digest trits
    var digest = Converter.trytes(digest_trits); // tryteに変換
    return digest;
}

// digestをsecurity 1~3まで生成してみる。
for(var s=1;s<4;s++){
    var digest = getDigests(seed,index,s);
    console.log('- - - - - - - - - - - - - - - - - - - - -');
    console.log('security: ',s);
    console.log('digest length: ',digest.length);
    console.log('digest: ',digest);
}
結果
- - - - - - - - - - - - - - - - - - - - -
security:  1
digest length:  81
digest:  OUHUMCXMVPJVCKKKNRJLZXMXKVFWDNPGDUKDKJCQFEXFXYDNFLJQHCEAPFCZVNFPCIJITBPDGVQOUYGHY
- - - - - - - - - - - - - - - - - - - - -
security:  2
digest length:  162
digest:  OUHUMCXMVPJVCKKKNRJLZXMXKVFWDNPGDUKDKJCQFEXFXYDNFLJQHCEAPFCZVNFPCIJITBPDGVQOUYGHYCBGPOYSCSDUGDFMJFFOZQRDKCUHOGIRLFOMFNJGITVWFYZNJDSMJJTAPBMQ9PZI9ARRSHYOMYFKLIROWA
- - - - - - - - - - - - - - - - - - - - -
security:  3
digest length:  243
digest:  OUHUMCXMVPJVCKKKNRJLZXMXKVFWDNPGDUKDKJCQFEXFXYDNFLJQHCEAPFCZVNFPCIJITBPDGVQOUYGHYCBGPOYSCSDUGDFMJFFOZQRDKCUHOGIRLFOMFNJGITVWFYZNJDSMJJTAPBMQ9PZI9ARRSHYOMYFKLIROWAVMRWHOBWLGLFJXTIFAVKNDTQZ9P9AHPBEFO9BVSVKIAFIXWAVIOEZBLZCCRSXNSWWSPKYCMUUGZZKYZFW

 ここまでPrivate Keydigestsについて見てきたが、文字の羅列を軽く飛ばし読みしてしまった人のために概略図を用意した。以下の図はseed=ABMUSHI9TESTを使った上のプログラムで生成された通りのものを図示した。
key_digest.png
 気づいたかもしれないが、securityによって変わるのは結果の後半部分だけで、前半部分はどれも同じであることだ。つまり、securityの違いによって、最終的に生成されるPrivate Keyとdigestの長さは変化するが、値の変化は増えた部分だけに限定される。一応プログラムの実行結果も目で確認してほしい(スクロールバーが長くて面倒だと思うが...)。

アドレス生成

 さて、アドレスの長さは常に81トライトだ。しかし、digestは81トライト以上であることもある(security>1の時)。つまり、どんな長さ(81の倍数)のdigestからでもアドレスは生成される。
 大げさな話、security=10に設定した場合、Private Keyは21870(=2187*10)トライト、digestは810(=81*10)トライトのものが生成されるが、結局アドレスは81トライトで生成される。
 また、アドレスはさっき図で見たPrivate Keyやdigestのような前半の共通部分といったパターンは現れず、ランダムな81トライトである。

address_gen2.png

 マルチシグ(複数署名)はこのどんな長さ(81の倍数)のdigestからでもランダムな81トライトのアドレスが生成されるという特徴を生かして、他の普通の送金と見分けがつかない形でTangleに取引を書き込むことができる。

マルチシグ大解剖

 さて、今まで見てきたのは前哨戦。普通のアドレスがどう生成されるかだ。ここからついにマルチシグの話に移る。

マルチシグアドレス

 マルチシグの例を考える際に今回は二人の署名責任のあるAさんとBさんがいると考える。二人はそれぞれ異なるSeedを所有していて互いに相手のSeedを知らない。
 まず、この二人で共同管理するマルチシグアドレスというものを生成する。呼び方が違うとはいってもマルチシグアドレスは81トライトの文字列で、端から見ても普通のアドレスと全く同じである。
しかし、違うのはその生成方法だ。まず、マルチシグアドレス生成に使われるのは二人のdigestだ。Aさん、Bさんそれぞれが任意にindexsecurityを選んでdigestを生成する。
twoDigests.png
 重要なのはこの二人のdigestは互いに見せ合って良いことだ。二人のアイデンティティであるSeed、またPrivate Keyは秘密にしておく代わりに、このdigestを共同管理の証として見せ合う。
 次に、この集まった2つのdigestを単純に文字列の足し算(繋げる)をする。(足した結果できたdigestは外から見るとsecurity=5のdigestに見える。)そして、その1つにまとまったdigestを普通のdigestをアドレスにしたのと同じ方法でアドレスにする。
twoDigests2.png
 こうして完成したのがマルチシグアドレスである。二つの異なるSeedから異なる長さのdigestを作って足し合わせてできた長い1つのdigestを81トライトのアドレスにする。これが一連の流れである。
 もちろん、三人以上のdigestを集めれば複数人で管理するアドレスを生成できる。

マルチシグの署名

 では、この生成したマルチシグアドレスに100[Gi]という大金を送ったとしよう。(マルチシグアドレスに送金するプロセスはいつも通り。普通のウォレットからできる。)
 異なるのは、マルチシグアドレスの残高を使うときだ。残高を引き落とす際には必ず署名が必要になる。マルチシグというくらいなのでこの署名を複数人で行う。
 では、まずBundleを生成しよう。今回は例として50[Gi]をアドレスxxxに支払う(出力)とする。そして、その50[Gi]の調達元(入力)として先ほどのマルチシグアドレス(BID...)を指定する。また、普通の個人署名取引とは違い、マルチシグアドレスから引き出した後のお釣り用の差額出力アドレスは手動で作る必要がある。その際は再度二人それぞれがさっきと違うindexからdigestを出して、マルチシグアドレスを生成するか、もちろんもうマルチシグアドレスに出力しなくていい場合は、普通のアドレスを指定してもいい。少なくとも普通の送金とは違って差額出力用アドレス生成は自動ではない。
 署名はそれぞれが各々のPrivate Keyから生成する。署名作成方法は以前の解説と変わらない。署名されるデータは先ほど作成したBundleのハッシュ(正確にはNormalized Bundle Hash)。二人が同じBundleハッシュに対して署名する。(Bundleハッシュの計算にはsignatureFragmentは使われない。)
 sig.png
 結果、二人分の署名が作成される。今回、Aさんのsecurity2、Bさんは3だったので、Aさんの署名は4372トライト、Bさんの署名は6561トライトになる。この合計10935トライトの署名をBundleの入力部signatureFragmentに保管する。*詳細
 signatureFragmentは一つあたり2187トライトなので、5つ(5=10935/2187)のTransactionオブジェクトが入力部に作られる。
 この結果できるBundleは以下のような構造をもつ。
bundle.png
 図では署名をAさん、Bさん由来で色分けしているが実際は見分けがつかない。つまり、これがsecurity=5の普通の送金なのか、5人のsecurity=1で作られたマルチシグ送金なのか、二人のsecurity=2と一人のsecurity=1の合計3人のマルチシグ送金なのか...etc.、はTangle上を見るだけでは分からない。
 また、今回の例だとdigestをAさん、Bさんの順で繋げていったため、署名の保管もその順番と同じにしないといけない。

マルチシグの承認

 承認は簡単だ。というのも単純に普通の送金のsecurityが高いバージョンと考えればいいからだ。承認プロセスはここの説明通り。最後に返されるアドレスが入力アドレス(今回の例ならBIDSBA...)と一致すれば承認される。

実際にやってみる

公式のコードはこちら。この章ではこれを参考にしていく。

マルチシグアドレス生成

multisig.js
var IOTA = require('../lib/iota');
var Signing = require('../lib/crypto/signing/signing');
var Converter = require('../lib/crypto/converter/converter');

var iota = new IOTA({'host':'http://localhost','port':14265});

//  実際に実装するときはもちろんSeedを見せない。
//  その代わりにdigestを見せあう。
var seed1 = 'SEED9999';     //  署名する人その1
var seed2 = 'TEST9999';     //  署名する人その2

//  ここで署名者全員分のdigestを集める。
var digest1 = iota.multisig.getDigest(seed1, 0, 3);     //  digestその1
var digest2 = iota.multisig.getDigest(seed2, 0, 3);     //  digestその2

var Address = iota.multisig.address;

// マルチシグアドレスの生成
var address = new Address()

    // 1つ目のdigestを吸収。
    .absorb(digest1)
    // 2つ目にdigestを吸収。
    .absorb(digest2)
    // 最終処理
    .finalize();

console.log("MULTISIG ADDRESS: ", address);

// マルチシグアドレスは有効か確認。有効ならtrueが返される。
var isValid = iota.multisig.validateAddress(address, [digest1, digest2]);

console.log("IS VALID MULTISIG ADDRESS:", isValid);
結果
MULTISIG ADDRESS:  9CSNAXLWIMQOCAWGNDDWSCQWCKQWZCXPZBNOWA9RPIDRSOMG9IBLNYTOFBLEHMEXMTCMMFJWPXJEHPUCW
IS VALID MULTISIG ADDRESS: true

 上のコードは公式サンプルから持ってきたが、どうも肝心のマルチシグアドレス生成の部分が読みにくい。ここを分かりやすく書き直してみた。

書き直し
// 二人のdigestを単純に繋げる。
var digests = Converter.trits(digest1 + digest2);

// マルチシグアドレスの生成
var address = Converter.trytes(Signing.address(digests));
結果
MULTISIG ADDRESS: 9CSNAXLWIMQOCAWGNDDWSCQWCKQWZCXPZBNOWA9RPIDRSOMG9IBLNYTOFBLEHMEXMTCMMFJWPXJEHPUCW
IS VALID MULTISIG ADDRESS: true

同じアドレスが生成された。

追記
オフラインでSeedを動的に入力してマルチシグアドレスを生成できるコードも書いた。こちらから。

送金

 実は公式のソースコードにもコメントされているように、それをそのまま使うのはよくない。
 ちなみに保存ディレクトリは~/iota.lib.js/example/だ。
 興味のない人は次の送金(改良版)まで飛ばしてもよい。

サンプルコードの問題点

問題点1
// First co-signer uses index 0 and security level 3
var digestOne = iota.multisig.getDigest('ABCDFG', 0, 3);

// Second cosigner also uses index 0 and security level 3 for the private key
var digestTwo = iota.multisig.getDigest('FDSAG', 0, 3);

 二人のSeedを変数として集める人が必要になり、結局マルチシグの責任分散を達成できていない。このコードでこうするしか無い理由は以下の部分で署名追加(addSignature関数)を連続的に行なっているからである。

問題点2
// Define remainder address
var remainderAddress = iota.utils.noChecksum('NZRALDYNVGJWUVLKDWFKJVNYLWQGCWYCURJIIZRLJIKSAIVZSGEYKTZRDBGJLOA9AWYJQB9IPWRAKUC9FBDRZJZXZG');

iota.multisig.initiateTransfer(input, remainderAddress, multisigTransfer, function(e, initiatedBundle) {

    if (e) {
        console.log(e);
    }

    iota.multisig.addSignature(initiatedBundle, address, iota.multisig.getKey('ABCDFG', 0, 3), function(e,firstSignedBundle) {

        if (e) {
            console.log(e);
        }

        iota.multisig.addSignature(firstSignedBundle, address, iota.multisig.getKey('FDSAG', 0, 3), function(e,finalBundle) {

            if (!e) {
                console.log("IS VALID SIGNATURE: ", iota.utils.validateSignatures(finalBundle, address));
            }
        });
    });
})

 この問題点はTransferオブジェクトの生成Bundleの署名・生成を全て一回にまとめていることから起きている。解決策として、望ましいのは最初にTransferオブジェクト(送金の雛形)を作った後、三人別々にSeedやPrivate Keyを誰にも見せることなく、コマンドラインから入力を促して署名を行えるようにすることだろうか。

 そして、最後の問題点はこのコードを実行してもTangleにアタッチされない。つまり、送信の処理を書いていないことだ。コードは最後にfinalBundleというものを生成して終わりだ。本当はこれを送信しなければならない。
 ちなみに送信(Tangleにアタッチ)の方法は以下の通りになる。

attachToTangle
//  Bundleをトライトに変換する。
var bundleTrytes = [];
finalBundle.forEach(function(tx){
    bundleTrytes.push(Utils.transactionTrytes(tx));
});
//  おまじない(順番を逆にする。)
var trytes = bundleTrytes.reverse();

//  trytesをTangleにアタッチする。
//  depth = 5
//  minWeightMagnitude = 14
iota.api.sendTrytes(trytes,5,14,function(error,success){
    if(error){
        console.error(error);
    }else{
        console.log('- - attached!');
        console.log('Bundle: ', success);
    }
});

送金(改良版)

 ここからが本番なので全ての手順を初めから説明する。
 まず、マルチシグアドレスから送金するためにそれ用のアドレスを三人署名で作ってみよう。
 同じ方法で今回は3人のSeedからindex=1securityがそれぞれ3,3,2というパターンでマルチシグアドレスOFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETYを生成した。このマルチシグアドレスに51i残高作り、このアドレスを使って複数署名送金のテストを始める。

送金元アドレス(入力用マルチシグアドレス)生成

input_address.js
var IOTA = require('../lib/iota');
var Signing = require('../lib/crypto/signing/signing');
var Converter = require('../lib/crypto/converter/converter');

var iota = new IOTA({'host':'http://localhost','port':14265});

//  indexの値。
//  あとで署名の時使うため覚えておく。
var index = 1;

var seed1 = 'SAMPLEABMUSHI999AAA...';
var seed2 = 'SAMPLEABMUSHI999BBB...';
var seed3 = 'SAMPLEABMUSHI999CCC...';

var digest1 = iota.multisig.getDigest(seed1, index, 3);
var digest2 = iota.multisig.getDigest(seed2, index, 3);
var digest3 = iota.multisig.getDigest(seed3, index, 2);

//  digestを足し合わせる。
var digests = Converter.trits(digest1 + digest2 + digest3);

//  マルチシグアドレスの生成。
var input_address = Converter.trytes(Signing.address(digests));

console.log("MULTISIG ADDRESS: ", input_address);
console.log('index: ',index);

var isValid = iota.multisig.validateAddress(input_address, [digest1, digest2, digest3]);
console.log("IS VALID MULTISIG ADDRESS:", isValid);
結果
MULTISIG ADDRESS:  OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY
index:  1
IS VALID MULTISIG ADDRESS: true

 このOFW...51iの残高を作る。
 (マルチシグアドレス宛に送金するのは普通通りだ。特別なのはマルチシグアドレスから送金する時だ。これをもう少しで説明する。)
 APIの記事で紹介したgetBalancesOFW...のアドレスを見てみる。

getBalancesの結果
{ balances: [ '51' ],
  references: [ 'NWSZIIHOMJDOPKJQODCINQBJBWOEXZNCCUSIOJ9BENJXGZTDYXSWKXAYGBFQEZEYGKYVJHOXOLSTZ9999' ],
  milestoneIndex: 324447,
  duration: 694 }

 よし。準備完了だ!(実は一回目、Seedを入力ミスしてこんがらがったためやり直している。)

送金してみる

 ついにマルチシグアドレスからの送金・署名の時間だ。

send_multisig.js
var IOTA = require('../../lib/iota');
var Utils = require('../../lib/utils/utils');  //  トライト変換に使う。
const readline = require('readline');
const rl = readline.createInterface({
      input: process.stdin,
      output: process.stdout
});

var iota = new IOTA({'host':'http://localhost','port':14265});

//  送金額
var value = 47;

//  マルチシグアドレス。(入力アドレス。今さっき生成した51入っているアドレスのこと。)
//  index: 1, security: 3,3,2
var input_address = 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY';

//  相手の受け取りアドレス(これは何でもいい)
var receiver_address = 'VLRVBXGUTJCXPTJARJBOE9SRIPHDULMUGITHVDOXYBYCJRRHUKDXSDTLKRJMLISJPBXWCZJYAP9VGOCPA';

//  差額出力用アドレス。用意しておく。(これも何でもいい。今回は律儀に新しいマルチシグアドレスを次のindexで生成した。)
//  index: 2, security: 3,3,2
var remainder_address = 'I9ZKHUCOJDDUADUECCAZAGJDGPCTQEZEKQMKNRJKSOPLPUZQHTACKNOJUBHVSJZNFZZVLIWFGHLXWVCAX';

//  Transferオブジェクトの配列
var transfers = [{
    address:iota.utils.noChecksum(receiver_address),    //  送金先のアドレス
    value:value,    //  送金額
    message:'',     //  メッセージ(今回は空)
    tag:'ABMUSHI9TEST'}];   //  タグ

//  全員のsecurityの合計
//  なぜ必要かというとまずBundleの大きさ(Transactionオブジェクトの数)を把握しておく必要があるからだ。
var security_sum = 8;   //  8 = 3+3+2

//  入力アドレス(マルチシグアドレス)の設定
var input = {address:input_address,securitySum:security_sum};

//  署名のための関数。再帰処理で署名が終わるまでループ。
var sign = function(security_sum,count,bundle,input_address){
    //  もし必要なsecurity数が集まったら、
    if(count == security_sum){
        console.log('Finish signing. Checking signature...');
        var isValid = iota.utils.validateSignatures(bundle, input_address);
        if(isValid){
            console.log("IS VALID SIGNATURE: ", isValid);
            console.log('- - attaching to Tangle');
            //  Bundleをトライトに変換する。
            var bundleTrytes = [];
            bundle.forEach(function(tx){
                bundleTrytes.push(Utils.transactionTrytes(tx));
            });
            //  おまじない(順番を逆にする。)
            var trytes = bundleTrytes.reverse();

            //  trytesをTangleにアタッチする。
            //  depth = 5
            //  minWeightMagnitude = 14
            iota.api.sendTrytes(trytes,5,14,function(error,success){
                if(error){
                    console.error(error);
                    rl.close();
                }else{
                    console.log('- - attached!');
                    console.log('Bundle: ', success);
                    rl.close();
                }
            });
        }else{
            console.error('Error: INVALID SIGNATURE.');
            rl.close();
        }
        return;
    }else if(count > security_sum){
        console.error('Error: security sum does not match.');
        return;
    }
    var seed = ''
    var index = 0;
    var security = 2;

    //  マルチシグアドレスの元になったSeedをキーボード入力していく。
    //  必ずマルチシグアドレス生成の時のdigestの順番で入れていく。
    //  コマンドラインにSeedが丸見えだがその解決方法は好みに合わせて下され...
    rl.question('Type your Seed: ', (answer) => {
        if(answer.length == 81){
            seed = answer;
        }else{
            console.log('Seed must be length of 81-trytes');
            return;
        }

        //  マルチシグアドレスのindexをキーボード入力。
        rl.question('What\'s your index: ', (answer) => {
            if(answer >= 0){
                index = parseInt(answer);
            }else{
                console.log('index must be >= 0');
                return;
            }
            //  マルチシグアドレスのsecurityをキーボード入力。
            rl.question('What\'s your security: ',(answer) => {
                if(answer>0){
                    security = parseInt(answer);
                    count += security

                    console.log('Adding signature...');

                    //  入力した情報を使ってaddSignatureする。
                    iota.multisig.addSignature(bundle, input_address, iota.multisig.getKey(seed, index, security), function(error,nextBundle){
                            if(error){
                                console.error(error);
                            }else{
                                //  再帰呼び出し
                                sign(security_sum,count,nextBundle,input_address);
                            }
                    });
                }else{
                    console.log('security must be > 0');
                    return;
                }
            });
        });
    });
}

//  Transferオブジェクト初期化
iota.multisig.initiateTransfer(input, remainder_address, transfers, function(error, initiatedBundle) {
    if (error) {
        console.log(error);
    }
    sign(security_sum,0,initiatedBundle,input_address);
});

 何が起きるかは下の結果をみると分かりやすいかもしれない。1つずつ、digestを早く足した人からSeedをキーボード入力していく。1つのSeed入力後、そのindexsecurityを順に聞かれるので入力する。今回入力に使うマルチシグアドレスはindex = 1に設定したことを思い出して欲しい。(上のコードinput_address.jsを見直そう。input_addressとして生成した。)また、三人のsecurity3,3,2の順で合計8だったことも覚えておく必要がある。

結果
Type your Seed: SAMPLEABMUSHI999AAA...
What's your index: 1
What's your security: 3
Adding signature...
Type your Seed: SAMPLEABMUSHI999BBB...
What's your index: 1
What's your security: 3
Adding signature...
Type your Seed: SAMPLEABMUSHI999CCC...
What's your index: 1
What's your security: 2
Adding signature...
Finish signing. Checking signature...
IS VALID SIGNATURE:  true
- - attaching to Tangle
- - attached!
Bundle: [ { hash: 'LVIIF9XPK9MZVOBZWFCVAISLEN9SUWEUDYFVZWMELBYGVHSMMV9RJVAWWWLQMISRGBMTZGZZMLCAZ9999',
    signatureMessageFragment: '999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999',
    address: 'VLRVBXGUTJCXPTJARJBOE9SRIPHDULMUGITHVDOXYBYCJRRHUKDXSDTLKRJMLISJPBXWCZJYAP9VGOCPA',
    value: 47,
    obsoleteTag: 'XCMUSHI9TEST999999999999999',
    timestamp: 1515630373,
    currentIndex: 0,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'LABUMSIT99LTEOFZZIEOGXZGDPYRWRMQNC9RXN9J9QAIMLFHEITNCMJISIVWECEQNBK9WMIOXECQZ9999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630550292,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'EAORAIJBKWDTAWAKUMOIHWETXCX' },
  { hash: 'LABUMSIT99LTEOFZZIEOGXZGDPYRWRMQNC9RXN9J9QAIMLFHEITNCMJISIVWECEQNBK9WMIOXECQZ9999',
    signatureMessageFragment: 'TRBTRPASFIXDHAEPZSNLQVVAVFMFVSPZDGYEXAODHMQFBKKFEXUOHIUDLYFYUPZYFVHNNYSTZGHPOPCXCLDK9BZBYUBTEBQMDDSDREZSUSWWKFY9HQVGUQKCVNKUORGLAAXYTXYPZQSCMESX9BYMSKV9MCPEUBPXRBIWTZIEOCSWZFWPZMY9QYYQFRYCZZHPOQEMNMTCQMZESFMVIYPQBMWOJKLTK9REAUDZPEWAEGXGZXMKAZCRLZTQTU9FBNPPQDUGUYRDJDTAMNLKMHENJA9LOBTINVCIHSNNUSIHCFYYOKGGUSMQXNUJONOUIASSQPU9XMWHGVYRTPARBTDHFSJQAKZYJPTNPRFWFRIJLKWHFSZPKRWHHPBCRBQMWBTTTCRDJRXJPKVNGOZUQLEHYGD9VOFLGUFKPYMV9YDBT9JDVIUURFDFKROORBDWDJ9HGFMJXY9PAURICJMJVDYIKKHSZWJVSPZWYWTZGDBPBBSVKSGKHQLBDEZUGMMQGVCKABZFIQZLNXFWYHMBXFNCXGUFQGPIFDKGKGIWLWJPDKBRJ9VIIG9EXIDTAOVILENLVUNCACOBUMZGGFVKDYMGZBIHZ9TNLHACWUNYMTZYJWLIBKQPMNMPL9RFTRNUYHOWWCSKATEZEBJQTYOSWTYHEOTQXWYTEOLKMINOMNJVSQOSCMKAFKVIYHUDGW9QPUOYMHEBJVGHQRXC9IIQNYEDPAUSWSWMALRXIIJTVKASEWQEIOBKVLZGSNUN9F9CF9JOGX9ZORQACKKHLKKAOCRJLEPGJNSKWNRDNVANWHFZIYWDARLVBYGJBFXREJWSHVCAXVBTNOWVHCZFPWXUEYPIGGCKTXALPWKKRRKUJTNARDXPPEKOUWXCGLMOYD9ICULQRYOKJKADLCOVLWCODGXZNURWIDHCKYOLQJWZGUPSBYTFTYWEGHEOMHLYDYPJSXZDEZ9WV9JYVW9A9YOVZWKRGGTBEKJXYIFPCXMVHVLSEJXG9NHQNGICLCITWWMJDGQVFHRLKYGOHGLKHZGYFOSPHWFTHJWSAQPARJTWSNWHZPCIOGMDIXWUNAJ9KKPEAMJALXQFJKKDSQJAYSMZWJVOVBSQAVPRFKZFVPHGAYKRHWEYMZGPTIQUK9BTASGSKUYNLAPFYPKP9LQAKTOOSWMLQGXOGGNKNGBJJXKAVOYVWTYNCUKXVGUZZQSOVLALCLWRCE9M9LZWOISNVQYTCMGHVTA9BSYXNFQCLIRLOGREVMZEDTFUFNMUUEIAK9YTDKWRZOQZHI9LJPPDGAP9U9OVKGNLUYYLNTV9ZRRKLD9SMYCBCLG9UXNSDKOQYEZIXZDUU9HBPANUKSBRFCRF9RHAWFHPWQJOEWYEZIVQAPEBOJMYOXVUVTPHYPKTLVSLPHTLRPZLMXISHMCAVKBCJABOKADS9IGMNZJBEMXFGNZMKADUECMXCCTOKUGSCPYHZOUZQJTXGAONWEJ9PL9BQBIFHDITRWGFKNZTUEDZQSXTBCTYPLKPIIBHUKUUCMMSSRSSHZ9CNJVUQTLYB9UACGOIRTQKAMKKECLGKGBULVRBWZYLTNWHOAERPUPWQXEBG9HFGY9HUVIPKIELZMDZLBSCGSJU99NMGYOIUBQSSBJGZRSFDZCBKGGODFDEAXHQIPUJPMXIRF9TNVWRJNJOEWJYNVCDDWMRUWOYTRWOZYLMRNCVT9LWDNKWOHV9PUOAJHCOQNINNWNHBBMRMYJUXFQSYCSKLBUUCTSISEVXWQKNOOJBASDV9FIRKD9BCKFDUORPQFBEGQTLYJSUOHGVUBEGYUCVQYQCEBCETPLTPP9FVCCSFUPIBUAYDSHOZKYUUAYDAZJXBECNRXDGZPOPN9WHSSPBHKFSUUSIIHNBVSKNPCFPDMSRDO9PWEQZQXLNDV9XPGIFGRAQGYAXWDP9TFKMWQP9NSYEOLNXFVODRZJUEKBNMWXVVYCDHNOJFLWUWNGLUNVFYRTB9ROGSGLMVRWWBTVMNPVNNOVHDTQQTMTLDXAY9UBXHEAOVGZSUIAHKKDHBPM9FYXWVJROTZDSUQXSCZITBSDMHRSCIWUUPMNTLNZGRZQOV9ORDTMWCDVRBAAMCMHZHFAYMNUQQOSEPUANDHGDAYSCBZAB9GDZINJUAIQMKKODVCBVG9ZVSRLKEWJXDSZBCQLOUUX',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: -51,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 1,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'YTWSOIGPPBWYWJT9KAIZZALOSS9XCDCEULLYDTPPK9UDETNOMXROCBBOITX9GCEJQCRWIJJHDOON99999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630548234,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'FGSYLLJIQSFCSLGFMBHFGEZBBSR' },
  { hash: 'YTWSOIGPPBWYWJT9KAIZZALOSS9XCDCEULLYDTPPK9UDETNOMXROCBBOITX9GCEJQCRWIJJHDOON99999',
    signatureMessageFragment: '9F9MSPWZBKUZONODAZWDIDCIRHYECHHEUQWMXSDIWSJ9DQGMQYQZQKLGAUVKTGHKPQZOSYDRVQYVDQCBXKBNFILQXOYALQWF9VOTCKARJCRKNUDD9OGCAXKGHAIKZKQCMOCHFRLFQFJEZQFAWPKJ9EKKBYJLXQATXDIIIOTBEYGIFGKQLYWRKAGAUGQTFZNGYVUQABPYFLBPXBZ9FIVCGOWZRL9BDAR9OGSVOFCKDENAVRKHKYBDMNAVMTEHWIOKOPQWOTATRHDIABXSLMKAXEHYWOSNWXVBANEKFDQAHDDAWCA9DE9URXPAWOBZXAMOLEOYJEZLKYENZGNEEUJXLYLJZDRYQWQ9PPFNVQDWPVULIEEEKOCLUUTCYNCQ9ZSEFLBWIXHOTCBAGWRYGK9XDKIZHFCREPAUHRPMVFWMLCDCRFBYGFBLQJL9OLMGPPIFBVJPP9QAFABMTGDWHGMVPRUMQZIG9RAZCVN9ICFGPSSEXX9CLHUAIEYBLX9N99NZGNUWYSJBWMUMVRGFXKFDQFEVFEFVMNPUGZGOYYMEWPBHG99AA9Y9YXWWLXRACXXXA9JUYUJBZNHTPXJWWBHJOAOXFOIENYHDZJDVOZKYWGUFZJUXTLBKVSYPJVOZOTNPSUGFROQAYMCPRINGNXCWUZVITHPXJFMVDMCRATWLCPVRICDGSRBNYIEWMBUDMXWAYVDDSFWKYMIZNPWSDGEHKCXEDHJURXLKFANZY9SPGPPBOXYK9KSAKRJIRGYVFNREYSDDPIUKIKVKLTKCNAIKEKSZTLEEPJULOFXWOGKNRBJZCPGWDPWCOEKOJVJJ9Z9XZHHDNEOCCMCLMYJLT9FDONJGVLNQDFNDOPAZPZJPHEXDBSPLLOH9DFZNVNYTUPSLLCIATRJATXVDESD9DOMQFPMXYZXIBDSCGXHZHZIFIQFBSYPQSADBHJCXOKEL9NVHKTADFVBWFHQXZJIUSSHMXODBXZVIWAQWXOUZLVTOGRPIKCFGFMVNHENVSRHCBJRAJQ9SLWTFKDAEYANKSQAWLCLAWDKHWMDUBGKNYQRHXRGWEOSTFGQXPPNAYKDHRFCT9WPXCXXOKVTIDP9YRVFDYBFREWXIUHOBBDUHOSLSZXXPLZADPUZXHZBLZYUSBTGHO9WZJDNEYFZFQVTXDMKDZRWKUXOVDYAJTZZXHRLFZWOCAVZWILQGTSXXJHHDQZDMHMVUOVQNNJWVGEHYBJMEOGLGSXWAJABBYQTKDHPHKKVNZTDAZNYIHNYLBKLXGVD9RDSYEZITPQBHONX9DXKHIUFFYUBWDGISZOAXWQZWEJV9OCEBKTCLQITXSNFUVEBPGSZIBWKSXGIRGRVTLPAAGJMXD9XOFGIYZ9KUVJHGCVWDHMDXNDJTEJNBDVDNNZHOZPRZQOUCAC9VJKYTUBYZVBTQVVBBESKMPSIMWVAIKDRJFCVBQACDAJTVKTDIKLAGVHHAZNJTZKTLHNXJLXNA9QMMDFVPXIWRILKXXSC9LSXMVUCHJSTFIEUIGOLDZATNECCGLMPNQANXUOYNHFIXGCGIGHALGVAADPBAZ9PHSZHHVUPRSOC9GCFVOXRA9VOFMOKPZHWABFNLERXFNALXCI9WRMFVNZEKNLKAKNMQAV9UVWIDJUYJTDRAGZWKHJUNWNWDGLMGKLJGNWHZQZMWSKKUHFLXHIDYNWCGCQFDSNCDTEZNSPPGDZPVUYMXTHUMUWUDBJRJLDCPLKEPRV9RKHVPAMVOA9OQSREPMGRVZNZYRUV9UA9YVBYEUGGWPCMJLFDKSDBSZLUXEGQGAIRCLKFVPAXBZMTASHBJXGRMI9ILTPELXIRBKZPLOVDJLEKEQSZQBCWCPEVLQEVSPJJYLTKUGM9MYDEJYWHYYMXFVFADUOXOQEPKANTSASDPERBVEH9TPLCFPNCBZWMONOXIHYN9GX9XMYYJIUSRRUQHPPWK9LPWCRAGKLLLMEMBOXDYP9ABQUWPQZJB9KRYKVRMKYZJX9R9EL9DQFCIXILQWZKHUONZQFLTTSPAEDHI9T99GGEGHUUFDGVMBTFLJZNIN9VLSZOXHWBBGAMWGVWJCRANE9XNZRXNODHJIZBLB9HXLRLYTVJNESECZUENLTOOPBRCOIMD9GHSMAEOBBVZSC9CCJZXQGYDOUZARTDSCOYDRAFMUU9GLYX',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 2,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'ERPK9PKIWBDKJMUNLKLHVRILGUPTQYW9THWCCYYOMF9XD9HRDIXQKTPOT9NQDDKKSBKBJJTCD9LF99999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630543701,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'YYJCTLLFJTMUEXJMFIQXFNOPVOK' },
  { hash: 'ERPK9PKIWBDKJMUNLKLHVRILGUPTQYW9THWCCYYOMF9XD9HRDIXQKTPOT9NQDDKKSBKBJJTCD9LF99999',
    signatureMessageFragment: 'STXYSFODRIDGHWCXKYHCZLJCTTFJTULOCJCQFNTPBOJ9AZENMCOFIY9O9DQZKDMVQCHNFTTWZAAAUBQEZVVFHMCCJBLBCA9APDOCLZSPPTWNWSXANBZLXSYTSFHXWXWNVIWQBOOEOGEPNOCLEFVXJMSXSSKGQR9OP9MVYHZRTXNMLFNUCXMUXWXNZGPMGCGIOKVZHNFDTOXFIDWDGCT9MYJIPNZVBKFGIYUSOPXA9RGYTWMMNTANGMRONTUXB9HARKPHWXASDZWBJRPVIFXPYT9NAIUALUAAZETVWWVBFDBSXRDDVCMZ9HMZHLHYLNTFLFLWFUAYOWQKZCDEQYYJTJFOYNVVIBUWJYSFUYXVVQB9JJOJKDYX9CSFVESLSXBORBBRAOZLGKIZLBKOKICIWAHLLMJXTTJHUKRGOJVGPQ9RRMOMCNQFDQ9LFMWZAKYSAKBISKLQSCZJQFKRBILZWF9MPIZYN9HPXBSKCZXGAMPKWHSCRL9BCJMRPMLQTFJPYTAVKDQVC9FSZ9QYTCHABEZNJGANCWHIL9WFEJKXSQTSBTZYXATALW9MYKFZNSSBZPHXIJZLWPDZTPKULDQCXSWAVAMTERDZPNXIGPZHKEPT99HDZ9LRB9DFTTJSQBBLMMMRHDBYCEDIAMMPKK9IFUMAXULXDANAFG9FKU9YU9LZQCRWEDXDMUNYYURWDUCE9LNLONOAGLYUYYRLNHJLCEQDWVKZQWXABQQBGIZZEAOPLIOXOCICBGVSPFVYJAFTUAQDZEWNR9HCEKKSQKPWWYHJAK9WRXDLSHB9RZIGUXLRS9JRTVLNEQGAQRCFZQZZATMTDPSEFDGJT9AAMKHOAJSZRQBMRSTHJMHUUUISCYEONWV9GMGUVSLHMNYXOSJHGKUYAMTDUDRCXMS9SEUDWPOJDUUQNZUXKL9TYQZYEQM9FQBKJXBO9MNSWQAJCHMUZGD9OSSICMUDDRAIYFNCNYGUCFTOX9JU9LJLVWEQGCKFDKJT9KAEIQ9CQDNLDWCKYRHDJXHPRJZGEPCBZZHOHN9QAYBOWO9BRNKHNNWJPPPEWAWNCWUYK9NVMFWMELZYQLIQHSUWZSZBNCGPJSLNVPKCCSHMJWFQQJMQKHNGCCLGNDSBOYLDKIKDFXBFJSCOGVDXTB9DYCPLIEEVPNQA9FQPJTUZEE9N9DVXNOJGZLWEZB9ZZSLXDLECOREXRCWAKOBJAIOWQGIEHVFNAYQHJABOMI9GNWPUSIJGJCIPVBNMOFDLVFEGDWCXADKNSWDG9OAZXDRTGH9INUWCASZOURIBVDAJAQHPQJOGMJTHEIAOPIRYHFSIWQWKQFAZSRFCFSYVFEAFSQKUXGEMNTUFVEUYCBPMSEETXBHVEDZZXZNSSQEEIAQ9XELETSUO9EOMOXVXJZFL9YSRBBNSVDUPDADYEAMSCRRKHEYMJZWZJUIWZBWNEWZAUVNWULRLZLPZCAROVMFJQJGUAQ9FTZYEXAZOPZWYDFWRACXTWVLBJRHSSOQZJKXSV9TZCXLQSIMTGYWFSYCDUEYHWOWFELVOTWKDSAQZROHCBV9BZIUJOT9FXVT9ZSABIKEMVYGCREDKBFGCGM9SB9ICLPSNJZU9ISTQ99FANOZMSU9ZID9CRDZYLHGPKUTJMSZHHJWUNDTVGTOWONMCETPSXMJBMWJP9IPTQNVLDBSFMFMYXEPPZXHKZZ9RKGMZWYIEHC9XQWDERYETHCOFUETKRJBYQMRTEVIVNEE9FWIILFYHMDMGIUMAKWVQLVRTFZCIU9MOFZHVMCH9JHGPHMXJQBPGHCQGSQYTRRONEOMHJXTVOVYAJNDMDOOZWCPWC9MZE9NS9DGIYNGLFWCDERLAAYKTCFMJYAXUCLCMIZHWWROTYTVTUKQUQNVQYALSNUTZLNUFYFWC9NUAOXH9TAVOAOABIPXPLNBZPSYPP9YIHUHQAEFNZTXNTJOTMEEPT9PRYXQFCDHBGONRJ9QNBZGZRFIDSYPOOZUBEH99QUSTQY9LCFRNBZVMLMFHZKBDPPEOPNMSZQGCUJWAPWKIPLNBFAV9KZSBBOEYEAJTYMHKFBDNLMEVOQKHVPMSYVSCDCYQBXTLDZJDPHRCMXFBXPLUESHMYGBGYLUURNFWXPDXCRVJMEKEGDNOWH9NKRGYDPVUKKPPDQ9LYVPIGKGSGUD',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 3,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'FUQULMD99YFTUSGKEKBCMD9WAULFYVFNZERTH9XSSUVEK9PUAE9MSNPTDTALUEPVKSQPNQIYPU9OA9999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630528797,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'DDKJTEAGDMHKBBWQVUDIBACWGBT' },
  { hash: 'FUQULMD99YFTUSGKEKBCMD9WAULFYVFNZERTH9XSSUVEK9PUAE9MSNPTDTALUEPVKSQPNQIYPU9OA9999',
    signatureMessageFragment: 'ZQGESRLFQKPBUKWIEYGU9BNE9PUNAEUDKKNRMEY99JJVACTEFHUIYUYAMHGAZPRXNCNQBDJDFPLKWY9EBRSFWNOLPKVN9LKIZYPPWOAMGCSXZZAIHPXGJAJNNEUPD9XJZLVBNYY9ZQEWDSIZNEJKRJUMBSZPY9GPWDNSRVECKBGZBDUYJUM9UCMBSCHMMBUYXDGLVV9HTYBSXCTEEGXRDBXPIRWTPDQDGZXFGAUUXUFMCRPBMLDPGYYJXXHRISTYEZUSFDIDDWEKRIDRPFZCYGPNNHELZDZYYEZELGCPWODNQUEGYYQZKCBAAQM9WFITWNSZLO9DLCTXHJWAVXIHWH9YLHKTGWJKIOUMAJEYUHN9VYCVAYYOHUOAWUFWBUNHIXKLVJNYILIIODLYYVZUWEFBS9CHTBEGH9GXCUCGETVQSBNBLAVIXV9HYXU9VRFFMDWCJAZQC9GUUUYHGRIPNRKPLRCKMEGDYRGNDWVLUUACLCEEZKIOYYWOLTLNZSKRIZ9XTHSQZYVJCCIWFORZ9MUX9OB9RNELHNPWXENNXKMYFUODFLYYOUYITIFAVCDSPWBKVXSEAIQFKXCUMOXR9HZXTXFADONUSPIRXLJMHOJYQWDPLPZCXLDQXYFJGLXJBSKQDTCZTACKUZAKJCBNRCQAJCABBEDQMWYGVTSHCUVLFXPDDSDBAIDIWFSNMNYVLV9UVRSUXFSK9VQCYWKXPDUPADXCBRMLRVQYPOFOSADZNQTURBSZQ9ZUTVALVTVLJTYHRAROJUVBDOPOZQCTPBXEJDJDZNUGUYXVCJVB9ZPHYTGXDLXK9IOPXL9IDWBLVYLZESVQBISFR9XNEGJHTBYEPYCUK9KHUEEZ9F9DJWMLQH9XXYNEQBELQEDKDSZIMLMUNXSGIFJVSJMOZVUNOITJ9FU9FOXNHWSFYSLGACFUZWSVFTGSXSOKIISDMJUEJYTSIDWDUZJAXNVFHRUBYWSLNWBYFKIFCTULJPPRRNFRUQWSH9ALNY9CGUKPKKUPNUSGECVIUHTRBPFCCRKTFXFPGFEZCZRCHWJGNFUTIAFLJHLU9PJZRPGLBYAYUEKIVJAKINRITWRKSPYRXKZDSAJLOZTFSGFCGVDDNQQAEDILPXCZAGY9STZKXXQFCODIJHIBEGEZXQYNEDVUPUUNHIKFDLDRPEDDICNTAKFTPMEMGUNVTUAZWULJFQCGL9XGC9EJQNWWLKFGZWOATL99PLCIJQRZ9YDURUXIHBAUHFWVECTVRDTNVIJOGJEDXNKMUODMVCVOVMPELAOWAJATZNQDDFXXLWMN99FGIEINGDJJRQYRRNGMHXAKFZEWAHUFAXNJPXLYAHVYWSAUQOACXMSDINBGZDQWW9RSCVOHHUKVCJAMOWKYZQPBIESRF9TNUFMZSGIFDQMCCNEEMWRRPKT9DZGD99EUQPWOGKTCFDBKYNGYDYZBVW9AOTPQMYSOGLLBPXHGGHTGWPMMFLTSB9XNWCOPYPSDFSJ9CUQUOJBNYANFIAJFWPRWXBQRH9MNAHXGCXRBPBMO9OUY99YMZU9MLMADR9TCOHO9YHYEHDQDGNQDBFANMIRM9WMIDBUJCRJRJAQZJVXOUNKAEAHAZJJFMMFVFUEJJZZRG9EOSNNBYYZSAOSHHFRQPVLMKIZCGLGPNNTJP9ORRBXMAQQNIZUMDMTUBPGXSGKNWJKXGAFWNGIPWXCWUSHSXPPLBCOZWQLGGQPJ9TCOQQ9OTTNMCIZTHALHFFZBPYXNWW9BUTOTTXWFYKBKIDSE9EVSFPEUPGIYFEHJQPHR9YBBIYCODKS9UXJQQZHFIBVIYJFBJQIQBTVOFHIXSJWUDOQBM9WVWLNNAG9FFLCVHVURHBPFDYXRKGOSISQHGAGADHKR9ZBVIJFAJSARYJAVRCROOA9KMVEFZLDDYJIGBFWSXBABBQUCMRDASEUQJAOHUVQPXLXPHGKPEJZVBURMGLTBDRONU9RDNIXVOFRJQBEEWQAEZBMIHOS9FITLLRXZM9TNXEUULHYIVBXSSVVSEETYIMSPRX9CDPW9PAHCZ9ANLRBELIUKIWHZZGNRYODEUTMFQAZYDPBEIWBABYHNDDICAOR9CK9WDVEACDHEOUVVPTVKDDDXBMLPZGBKDOJTBMNIWETYSIFKEXBHVQNJRFCLXE9VXHSJNXHQU9Z',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 4,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'FE9KYENWGFDYXJSTFEHYCZML9X9CZUGYQZBENQUVVWGMXDK9NBBBOEUUNRDDNEAHNQFXLDZEUZCD99999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630523916,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'TVTWQCLUVMJDKCLFSQVBJADS9AP' },
  { hash: 'FE9KYENWGFDYXJSTFEHYCZML9X9CZUGYQZBENQUVVWGMXDK9NBBBOEUUNRDDNEAHNQFXLDZEUZCD99999',
    signatureMessageFragment: 'HZMCELYNGDGWW9ICKBNN9SXCNVJFXSXHL9VONUUQH9JSYPEJGFCGGSJUZMSTHCZUM9PXDHZJIVZ9MNVJBOPSUYUGWULZFOZUVOGIIAZWMXQHIEBEPDHBJXENZPYEA9KQ9PJVTLBJOBBJKOMATBNNX9ZETPNSPKFRFCPNJDMGMHYON9ESOTSDQOQVNH9ABAIMKFCCYUPRMKRGPWEIBYY9ABNFWPGQDFOWTCPHNEOVJKBSMWLAN9DYKZCQTNB9P9YAAEXDGNWEGAJXOICV9MNMJOPHKXUWEXSPWX9YASMU9RDEHLXLHWRZAAYDZDEAOOGLFNTXCCZ9VFLHUHXANNLGGOXELRYRQNSSQXJQOOQQVCTEUYVVQKTJH9ZBBTPJXTPAJYNSG9IQSBKBMMEVMFGRXXHGMOTTQPNFCFEVPWJP9QLTMKP9FYTDUJF9ZEIUXZUTAMTDSI9BQGDGRYILKKIIXQE9UOSWXXKHYEHVIDFLEDLYRUTQJIEGCQYZDUWZIIVMZFTOJQKOYNFLDOHYXFNFWWNOAZELAECZLWKIJMHTJAACEYDVMJ9HJAYVQKHHLWFDLPEKWQJZ9XDWPHBAQGNDBWHLQKBPEKALQIGAJVKUGPFPBHMBVLROPZLHKZWUUZ9SPZNUG9OW9WPHH9XFB9PSCXJDGHOA9NWSUU9PLUABUTYMARAJMEOBFEHOXYYJFEPDMRAJJVWVYRQVGVYT9IQFLLLKBCGWJZDOUXKYTTGBASFZXFVOYONDAIZXTIBLTDHFHPXALRBZXSUQZ9K9REXFBCDKWSHSOUFRDCOQJWPAMXMAWJRKWVOOPNV9FRVBQALKOCLFZXMLFZCKHDILPUGAFIMWBOYYPFQMKPNEETWZYIPLGZKMZFPKZU9IOYDEBW9BRETWQVWEOCZ9CSRVSRMPIQSTPVXKH9YV9WAJICJDAKIHQCQQPGSPYVIFNMVTZZRHLSFWSIQPYJRZPKEKRUHCWIQMKHJFP9XWQOY9GEQZ9XKXVNCEXHMWIFNFVETBFHVYQNQOPJOKHEUHJWBLUNJHHZXADGNGYWKNBCHGQIEQTTJLFACEWJIJHUPOMLSVGNTPKVCGALTT9IGCUDFQNBKGFP9YEBMMU9UHXSNWONXDHTFIAWLYXACPBKALJHXWSLCXWDBNTM9TLAMA9WCGZJELANRNKBYARMXXJHBWBPQFXCY9MCIXGNCZNJGGWPBIEYXOC9HVKGIGLWRUTNBYFGMUSGFMXIATJYVATYHKTXYE9EP9KNQLHSLIZFDKLUXXFFHMDSFTLHTGYN9G9CADVO9ZNRPACDGMWQRISEGUIIOJRBAIAWHYJKYWWMBYLUQFH9QGFTYYRTHJWDKQ9HMBHQJCCITSD9BTULRMD9GYMRJSQSGJOGJWPTNDUTF9LBKMLQPBFPUVCIFYKQQUWDYSDRM9PNWQGROJI9UJHVBQOCUC9ORRBFYOWYVETAUXOVYINHEIHDIZEYSRHGDCRAZZJZCYKLPMWCDNQZTFGHJZUHPJXADPIEARKSMPLWAGCBTCCSRNMM9D9LALRERSUGONRLAIFWONPA9ZFQCD9ERCGEHRVNZLBKTCRZGMHTOAEEPEBVSEZGZNIQJCIJNFCPNVM9RWJYVM9HYWSFGDKIWS9PMXZKUCBSMX9DXQNMYGTXQ9URH9YVGGNSLBGSDPWEAPXJGYJJOGUINYBXCNMV9D9KNRTWBPXOOBICHSGOLCR9SJDPRGWMJJCRZVJHAKMMMEZGVSKWLU9OTXDYFOZVAWZRWVUPNJCAPHIIJMX9VHKPSYQIZOCUBN9QAFARCHHNAPNSRAUPQFMYHPBIBXJYLETSTDLSWCFIVLKDVTSQEHRRKINAO9FATSNBZOXWSMPUVSZMBN9FBFQCYWCLGHPEXKWUKZSLQPNEGLKUSJFQRLUSQTNBK9XAPCEDHJGUCNNWXA9QPKBYEAVMIKDHPLTYKJYJKKHBLUEGQZCCNPIZSLLVSZZAGKEXBRTPHSSIPBTG9KFRKT9VSYKKUM9DPZNMDRENWRZMUJKZIGVVVWSWUQMFRO9SUARRZQYBUOYFFOALGIMVEFHDOZAYZGBBZGVIIGAEDOWTJFWZT9WBLB9KZHGWABKVJKMBI9RUA9GOIVLZ9IRDRNFKHGVXUEFFSHIXKFFY9PSIDVHFCRSZEVOCMKDKJKIGJKORKXFS9CKQB',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 5,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'ZJHDSLHYDAKYXPUWUXDEJBINN9UTFUSUYJDLXLLIOMPNATTQJSAMXHJUYTACSYYRXNKHYZFJOUCH99999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630515249,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'PUAMQRUMVKMFUVHMY9IGKFLSLAW' },
  { hash: 'ZJHDSLHYDAKYXPUWUXDEJBINN9UTFUSUYJDLXLLIOMPNATTQJSAMXHJUYTACSYYRXNKHYZFJOUCH99999',
    signatureMessageFragment: 'GYXQHZOEKQEHTCPQDBKAHSTJLIISTVRSE9OIVBSOXHGIBGBAFWYZJIVQSTY9VJLUXR9XRHLHARXGSGWGBZRNBZFEUGASBCOAFVNXYA9MAJIRDHHDQQLBYK9KVTMPXZGUMUMSIRUGDNIBVETJGOGODMIFVLBXALQJ9WNVQHWGXGLUF9SHKNLENLYCZXEVFFKDAQOTVEVZNAK9HQQJZNLXWDS9STRNEETGRCUZPMKPQXFQMHMJXJDQKNBY9ECUYJTFMGUOIPVVQGUDIWQDQUAYDCSXYYISVT9EFUSQNMLOTNJEIUUTPYBETVQBEOURDWNXK9QYUSMLJIKKPBXMU9OARZHGPGZH9EOPHPLUCFVZVVNURSULP9PDOFHUN9ILITZBNHJOKEZQIDMHHLMFDRDOXHOJZZAHGP9PLYDSEARWMDZMVWVKNZVDCUFLZHPL9VNBRLOJ9KCSI9JKYGHCAIM9WAVGXYUHNZWONCEKBCAMXQ9ATNPHUOSMRLJZYOLZHHG9JZNIZNSNQTWWZPMGVP9NLAASYSAEMLSPZPLDZDD9CQJCRNONXVXEXICLKGVNZLRBMVPFPGEAHGOXSSXSQCANL9IYAGMZCOBHEXOGE9LWYWFVDTNSGWOISBBXRGCXVJYJTEWLEBFZZ9RSYYNRGYFGLFYULFOYWVFAGJRGMJERHXTSWOTQRSJKUKYMWCEFGXKXAMFPADAIJAGNRGZJBWAXEVQNDVRAMNUGO9MR9MJHQOGBOQPSL9VVRRAHJGPPIWNNHUNEGJGQEHADHHQOADKUKHPLAXWODEJRQHWGZVSKUDZTZFZHPV9TROWRVDACAJIEZPBRBRLJOPQYFKCOEKGVQHHCPLVFG9CLRANDDEVRD9RQGMNWJXWKVLGIMRZWNECUHKELIJQISOWJE9PPNEDYQLJUK9REPRJKQE9OQBLFJNQRCGHTXAELXPVDJBREZDHIANEHDJMWUKOWUHTFQHPCXGSCPVMP9S9VPH9LHIYJTUNHWQRRUZEQGACABWIFVXXRMUOJEIHT9LTXHAJIHYMVNPNNXSIHWEQJPYVFGSVKHOQRVAOCY9TETEUQINOEGYGFD9VUJRHVX9HTBKCYUSQVIUHVW9NMLIMEMTLTYRBNWXSXQZVQNFASVZMUIWVCLKTIZYJZXGFPKAF9YLLEHCRGNBYGTYPYGAFICROYAGBESMWKJXSM9TXUYZEFQXPCDBDTJF9IGFCEQZTLXYKXMUNSHJAFYW9QZNJDLXTZLHNJYIIHMGAHNUBSTGZKEMUSBSHIVSKLL9KZKNQOAWAA9OIBGEAFLSWXHBIIYHIKEVMRHXEYVWBJPRPQCFBTSELSLQYPITAGPJPTCTHH9TWJ9WVUJNIZVKDXWOLKDPPSNACOFAMRS9QWMSLECXSYSVZFVYJTXAKTMSWDKJH9OTDGFHJJBQPYKLAWTFFZPWMOTBQXSSIVBECRBBTKKPBUZXXASUBPTHWMKASKHMLJNTRUVQSLYBRMANCK9POISDSQBLKRNVXBNKEFECFAZSXUBOKDDYRK9FD9FVGQXCSTWDBTSLPVXGHFVNASNZSYBV9XV9IACFCXFYAXWZCOUUDLMVBKXFHBTDDTVIOILMVNH9JVFWPARHNY9EMYFGRZJTJLXNXDTYQLUAOZL9EXJLWJECWYYGHOC9IHADWKRUMIIZVFRLNPLSUZYDOCJCLYMACYDSCG9TVZQOUGZUEADCYZEEYQZCSGVHYEKDAHQAMGCBTSA9D9FCWPALICDDLUINFLUNYDWYEUMRU9IDLMSBDVUDQWZLVYYEKD9KTL9D9FKZDPVYJAELWAWYHVZURMLAIZAOCEYSXOJCMMMLKWJUNBYZJTAZSKGJBG9QYHV9IBIYWFO9YZCMJNOAAGWKZWLDOLBKSNJORWNXAYKCEYWZHUXJGMQSIAIYBWQUFQSDBHVMENIEKGEFAYDK9BSWDICWQR9SRXJSZAHHYOSAQFUERIXXM9DHYNEXFODRSYFEKNIMOGQEAHVCKHHPPUHBZWJIMCQWRNXGUCEPB9UYGRCQKHSUPGJBYMZXEPRLIUVBJTF9DDNXNSZVQWPJDJZACF9CGJEHVVOBBTSXBWCJSKOBLLQXWGH9UKBUJPWMSWWMXWLSKESKJSDN9INSZVLOQJJTVJFACOCNRUXFHRSE9NE9RVJKU9BUSBGYUNWYCLW9A',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 6,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'GSEXVYTSRCYU9IVIQY99GBDXQAAC9YYDGOFNTUAJOEZWBLFTJ9NHPAEOXMRZEAEH9HSUDYJGFUDGA9999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630510410,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'MIQCZZZDVAKZVWDJJZUDYOIP9GG' },
  { hash: 'GSEXVYTSRCYU9IVIQY99GBDXQAAC9YYDGOFNTUAJOEZWBLFTJ9NHPAEOXMRZEAEH9HSUDYJGFUDGA9999',
    signatureMessageFragment: 'ZO9XEPDWPPXUFOTCBOPSDPBDEQGTKHZCTF9VOYHBVCGBLG9PKZDYOVPOXFGCNESMWEQDOEMOWJKKRJKUBVWHYGTOEQCATNUZCYHSEMYDSHIKGZQTUTESYWZQCRTPH9AZHTXYRVTSEE9ALKCFJLNQTMXKBFZQNPXRPYUERRRA9RPVODEAXMUDTSKWXIFXAQK9PCAQYPBJMFRPJCO9VNORAKFYSTFGYSSXLCITF9RIYBYG9SLRIAW9EXIAXTBTCCMIXKGJJMBCTHCWDNJBPHOESUNTQ9RYYTEAMWYJWPIYKSUGDCPSSOHIHBYIPGNGVLDKHXBYFTVUVDGRQMCJXGOUICUCCVPYAPTILUANVEXONYQMNDJXRDQRGIJITRMSYAAFQUTMXKWIIPRD9ECDCQGHXNNDPLTYSANABH9TJ9O9LBUQJJHUDWWW9BGQFVGORWISUVF9HKGTJVQYAKVWKMFEVCSKBH9ZRTIJNLKXEZ9PQVDLMYTWDDKDWQQVDEWRSSYI9ARPMD9LIRGFCWZMUOSSBMZNSNVE9LZWWHSVLTIRFBBMVEMIWCAVSJZKBRXGFHNAQTVOIQYQZJSMPFHGVJWETGGAKMHRL9BPMAYGPEZXVAYIGIPYAAELVHFZSHXRPAVFEJEPZUSZDBSFFEGFSEXFGTRQKKOWBFWFEUKXKUKBAZFMYUCSJAP9RIJAICXMVIDJSRCDEYIGT9SOECYFGALRYKRZCGQATSONYARONESZMOOLCHLHXENWCLOTHKGDWOWZAFGJ9BUTVPSF9C9CQKDUJ99ZTYYRYWLYKKYLMLJYKCXBMXTANXNBIVISTVQQMRVHJT9OBWIWWCAZFL9OEJAMYXYEHRSJMQJIIXIKDYD9SRACXNTVVN9HNFSUYKBOBPUXUQDCZPNOKPGYSHXPNLVNSPRSSLRONKRGQLTARPXULKCKQLCTYC9UQELOZMOXBPYAVNKITUZONHVWD9HTSAIQVPQMPVRWMQDLYFGMEXMNTYVULZWGNZYSWGVZYIYLEWQVXFNVGRFGDTSHWLMCKJDUEBRR9HJLBEMTUVNRJQFQNUZKEVIEZONESCBDUUSTIHWNKPPRYDQAFYNTSKCIKDXLYBD9BBXOMXFYFWXESQASAWGFNXRBHW9AZPZYBCVZWMKMGQL9FFGXLNVYWUANYPIESBVAOQRTQAKGTWMGWXTJ9SEAZAI9JMHXLZWXWJRXCBWRRFFIJQHHDHELYYWOGUNYWVZGCVP9IMKTW9MWZAA9MDOELDQCLP9WCWTDRHTDYBGXGIGFLNQHQARPBI9XCHMVXNKLP9EZZAKFKDXPFBFIMQKUBCSMMGTIFXA9RBPUBFSWX9DCWVVKAEOSTXCNHWMJ9UXSEHDDVQARZUKHWXNVRNGFOEBK9SSKQCTKBWPIRGSNRANOGWKLVNRMLNFIWYHFUCOXFROAWPSSHGRPDFUTFBAHBBWKYZBGLDZXPFFPTDMVNDJGKYMIVOOGLEUWEWOPNMGHCUAVQUIKXOAAQAQADBGVVZAUNCNJHGAYRNQWAQHCDYCNTTODGTOYBFZFXAXT9DPPMHIZCNPNTNKJUAUPP99T9ETO9JGEXEFUQTMRFXTROXUWKOMIIDRSTPAKEPDXWDOWIMPHUFLHFUZMJX9VSD9EYEVHNUZDWGAYNHZBIZFKPSWRUAJ9VLOGPHNEBWPUFQ9KGXXQGBCDKZ99BPKGHRV9ODLVOCPXHVOMRFCUAUBYUNDWH9FCQEYURHGJOALYQKOWTIDSXMTQXSILEHWTIPJADUKGTOMZFDTUYSDXRTANNXWPLEHDQIEA9WTRAWETMFC9ALALP9RWXDDHVZQEVUIGGURQDWHAXEXOATDJLMTYHAQVMQDDUUZFSS9BXOMV9A9TCZVZEEWAKOAZHLAKBMAVNXTSDGPHBDVLASCTWCRQUJTCN9QZTOJUEMKIDLTHYUEBCCVBLQBBDEZJMRZPFCGGAEOPSKOXCDGRTFAHKUOJPFMZQLQB9QVPJTGDPFKUDZLAGA9MXSYWEWMNVJTIWPWPMHZEJBGMAOKIMGXEKPZSBFWXJWOACVLTZPGKQGS9WMOSCYUTLWSKEIPTQFMWRGVDFB9DPMNGGZAQA9PESVENBCPBEGGOFPXYDTYCONBWRNFOWWIXD9GTXSPRIXWORFOAWHSLPNPCPCEG9SE9INLVSPSQAU9BMUZ',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 7,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'SATFMJ9WR9IVVAALKAGF9QAQJLINROOUUTLZUPXVUESNQQRJLDCNYTNUFMIXIQQRUCKWXZMLCDDQZ9999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630509654,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'BCAPNPGLMARXVHFWZSQPLXTRQWR' },
  { hash: 'SATFMJ9WR9IVVAALKAGF9QAQJLINROOUUTLZUPXVUESNQQRJLDCNYTNUFMIXIQQRUCKWXZMLCDDQZ9999',
    signatureMessageFragment: 'BQPPWXTJZZXOWIRRUUQUCXLPLNJMDLNM9ZJQ99KGFSOEDTZQYVMCGOSVQBAKWSBRLIHLMCFAUZJEOZFRZETWTVYEUDZA9PARQEEKBXDDNICDEQGSIXDVHAUWAK9SRENJAZMVH9NDMUPTTVYBWEAJBFSQL9NZDUGNWBBZA9IQJQABNWBJWJEBSZSEQQGMBVPIICB9WWBNSHRUUCGQGQPGQIGCPQPNXOCNBTGZCJPDIKYYPQCOJD9OLZHPXHLS9IILRJYZQWNLFAKAPWJWHNP9VQECILEUER9RURMDHYEIAPODAHSPJSHZQEGKTZJBJTWQSHYWAWKSTXCCEB9NGKLUBEYJXBHRNZEJUEHGZAH9Z9WNSPIFKWJREKISHATGQQZKARBCYKMPWTXLBLAWYLLAAPJPJUGNFQVOMJA99Z9SGDNCQBKTRQFXNGWHLVXNKOCHVBNLOMGPVC9VLBFHXZQZ9EQTYSWSRAMMCAQUAATMCKMWVLAFRCPMEDQBYCBGSSTLVCSJODPWFAYDKGJQEGWRCDDJZWFSNGME9RNMKNBGSXDXDDAHHBFRDXDRLOPZSICCWBUCIGJCFIRKSTUZNDBBQLBIWFRODBOHKO9UZRTKPQNDNGJPDPWGDNDVJQTCYZCFLZBIDTLBFUWL9BOGDMPUTYDMOCZTHREC9PCDTAQDWDWBRYTZTMMW9HHIXK9OWEQGZ9JSHYMDSUSNBFLTCSEGHKNPCIDSZRY9ADFBTY9TSNJRYSBNMBTCQAURIPWHZDTAGYXUWZEOL9YPDSZRKHUIUIEVVLPIXVFBE9WXRRYGLBQNYWCNFFHEYKKJCVZAWDFCSCOREWRZBNYAY9BODWPBWNF9OWJOZWAODQOCL9FFRDVVWYWZYYJBXZUFCCDDAOGVMRCG9FECXQIXHQEEYEXM9XHCRDXIAIFVAJNKIWQGJQYPGJNVZIMETASKJBZPMSQPGLQZFUBYBRI9K9TVBZQHFPIOMCADBH9HHJBVPRDOXLVAJENL9LYUHQYYGRLWIPIHEDGSVNXSCOHITV9JUHPGRDPAUFQUYCSZMENELKMDLKOD9C9QHEHRYECTWVTPMWKIFIGFTWZWWTNBTIBEPMSJXBFUCKL9FKLWWOBBIQFQZSUVF9QCJTVZQFNPJPJPCEWGY9QIFQOQIZ9JZXVLCEYYV9BEWXKNNVXUGWWYUGDQBIXWIASDHTQJFCFVPCGLDW9F9YIYWLBKS9KEGBHLJELCYTTZUSPBTHYT9CSVLACBEGHSLVTHUOHAFHQSYHYRNSLVCCALXWTUJZ9DUUDDLRRYK9ZNIQIVFTYBSGGSNODHRMGIVPKLLENLXPZBAMZ9YPEYMPMXCPKEEYU9HGDAOQERZYBVAXYAKJLNZPAVGKDGJACWYWZHPDOTFUZVFOOQGIGSXCPYQFUGRZADCEHLPRLVHXTEFSCEARIQXFIZVBVXDSJHBBEHSCBYANEIKDBPNPIONDMVIHVLJSZRYKKUKNZUMTRQHPINLLFHIAMDQOPDPDYIONBLKSBTEZDHIWGZPRBEJLYYUQHMXTWCASVZVMWVSIKR9YYORTGLZLLPSIUCJWXH9ESJRKXER9CKZCVBWGYHKUXSW9VYQ9PB9WNOKVRWMR9FZBUHRQHSPQAEHCTYSXFFBSIPCLKZUANUPOAIOOVB9NVLJXITYQHAPFZWJWXVABNVCSXCTJWXRKDSDGDI9PWJWVNNJCVPKZOVBVWAMFBCCAULANWEGH9SXKEMALVV9WKW9FZ9AKKJKWHVWYPAJBLAQZWCHEHJUZQFYENDEZHMOARMS9ZTJXPGZPUTBRBHAXKHKTJJFYFPIV9TIOPTHTSEYKBFIRLDCGFBJBPOANNWPFHKQLBTFLZWONPAOJTB9FTIRH9OSSCVPVDBGIKSUBSIHMATPBENJRGANT9MUMI9GZ9WTVRIAFIPPSFISAOLQEHZJTBAML9QIUUZXRPYMUBZCLBGXVZDTYASS9GBYIREHGPTWVEKXAGNPOQHQPAEEEHDTVBOWEJKRIABPQXM9QKUJZIYAACGUYCRSADE9KYVCE9VTIQXPPYCJCJTMHZRDMUAGBLJDIZWBPAPO9QLJGHXZVISJMFEYOXGKWMCJDCBWXQSOADAUNJQAKHKIWSIWCYMZQQZDTMZVITOQTGPAJAIRYHUKGVKKK9GYBSVCFDDHPUQYJGYGIX',
    address: 'OFWVBVKIEGFRPHRTIKUNBBFJCTXRTEPLCRQKLWOXUTOCXN9BJFDUZTJUNGHLRNDASQJXQTMSMXEGQLETY',
    value: 0,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 8,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'SQWUIMFPBSOFUNPGYZDSDEYZSTO9EEURKSN9XLFLUVHLKUPAURDSRMPZFIIECXPRKZJM9CPSSLUHZ9999',
    branchTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630500892,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'QGDKNKJUDBKULQY9MMGPKKBVYYK' },
  { hash: 'SQWUIMFPBSOFUNPGYZDSDEYZSTO9EEURKSN9XLFLUVHLKUPAURDSRMPZFIIECXPRKZJM9CPSSLUHZ9999',
    signatureMessageFragment: '999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999',
    address: 'I9ZKHUCOJDDUADUECCAZAGJDGPCTQEZEKQMKNRJKSOPLPUZQHTACKNOJUBHVSJZNFZZVLIWFGHLXWVCAX',
    value: 4,
    obsoleteTag: 'ABMUSHI9TEST999999999999999',
    timestamp: 1515630374,
    currentIndex: 9,
    lastIndex: 9,
    bundle: 'QCBSTDJJI9QZEUNRSBZGBWHFPXGVRBDNEJNIHA9LXUHZARTWQG9JPLEN9IHOLVGTUNNAQRLIGJYGACKGZ',
    trunkTransaction: 'LAFKZNNFXLCUSBZXYUWZLLYHMJIFWWFSXQMMQFZTYVEHGS9LRNREHZ9BTJR9OXRRBXWKBALYQAWZA9999',
    branchTransaction: 'PDOFFCHPVPYJELGFTVWBSNVPHYEXDMPEXGIJEXPTWQIONY9RZLNVWTWJ9NGPROADVWTKNOPEDC9B99999',
    tag: 'ABMUSHI9TEST999999999999999',
    attachmentTimestamp: 1515630494846,
    attachmentTimestampLowerBound: 0,
    attachmentTimestampUpperBound: 12,
    nonce: 'BNDEFGHNQFJOIBYDMICRAJWKLFZ' } ]

 ちゃんとBundle内のTransaction数も10個だ。出力部1つ。入力部8つ(=3+3+2)。差額出力部1つ。ちなみにtheTangle.orgから見てみるとこうなっている。ペンディング地獄で再アタッチしたせいで、二つBundleが表示されるのは気にしないで欲しい。

最後に

 もうそろそろIOTAについて触れていないのはIRIの裏側くらいになってきた。(「くらい」とは言ってもそれがIOTAの大半以上を支えている。)しかし、P2Pや通信の根底まで遡るのは自分には無理なのでやらないだろう。
 今後は何かMAMやマルチシグなどを使って実験的なことを記事にできたらと思う。
 Ethereumとつなぐ将来も見据えてスマートコントラクト、データマーケットを試すために統計や機械学習、そしてRasberyPiについて調べてみるのもいいかもしれない。あ、あとフルノードの運用コストと効率も。承認率なども...。うむ、まだ思いつくことはたくさんあるみたいだ。

 ただ、何よりコミュニティに貢献する。今までは一人閉じこもってソースコード読書ばっかりしていた。「書を捨てて街に出よう」とでも言うのか、一旦落ち着いたことで外に関わることがついにできそうだ。フルノード関連やBundle、APIの質問があればどんどん訪ねてくださいませ。

Twitter:油ムシ@abmushi

 ではまた!

参考文献

公式Github:iota.lib.js/examples/multisig.js
Pyota:Multisignature