手把手教你使用EOS多重簽名 – 保護你的資產
最近頻繁曝出用戶 EOS 被盜的事件,作為一個剛上線才 1 個多月的項目,在各種設施都不太齊全的情況下,這種新聞一旦流出,都會讓人感到 FUD(Fear、Uncertainty、Doubt),不僅你會怕,我也怕,我會想 XX 錢包會不會偷偷把私鑰上傳到服務器了?如果是這樣,我會不會被中間人攻擊啊?它們的服務器會不會被拖庫啊?我的剪切板不會也被某某軟件監聽了吧?萬一我的私鑰被「彩虹攻擊」了怎麼辦?……簡而言之,任何人都害怕自己的資產被盜,雖然這是小概率事件,但它一定會發生,要不然也不會有「墨菲定律」存在。
使用 Open Blockchain 系統,我們需要具備保護自己資產的能力,因為這個系統不具備掛失、凍結、回滾等功能。這篇文章的目的,就是在 BM 的團隊做出基於 iPhone 的硬件錢包之前,教你如何在去中心化的世界裡保護自己的財產。
相信你已經猜到了,提高錢包安全性的辦法就是多重簽名(Multiple Signatures),背後的邏輯也很簡單,如果 1 個祕鑰被破解的概率是 10^{-n}10−n,那麼使用 2 個就變成了 10^{-2n}10−2n,以此類推。你可能會說,多籤技術在 Bitcoin 誕生的時候——10年前就有了,這可不是 EOS 的專利和創新。確實如此,不過 EOS 在此基礎之上做了一些優化,在我看來,這些優化足以讓多重簽名技術更為普及,乃至於在大範圍內提升了賬戶的安全性。
EOS 對錢包的優化主要體現在兩點:
- 引進了賬戶的概念,讓原本抽象的事物更為具體,在過去,誰會把一個256位的數字(私鑰)和一個賬戶對應起來啊?如果一個數字對應一個賬戶,那誰會意識到用多個數字(私鑰)對同一個賬戶去簽名呢?但有了賬戶的概念之後,一切變得非常自然和清晰。
- 當你創建一個賬戶的時候,它天然的就對應了兩個祕鑰,也就是說,這個體系一開始就給你灌輸了:你至少要用兩個祕鑰來保護你的 EOS 及其他 Tokens。
在動手之前,我再來給你普及下 EOS 賬戶的設計邏輯,下表是我的 EOS 賬戶的設定:
![12](https://cdn.8fet.com/wp-content/uploads/2018/07/201807170609238738.png?imageslim%7CimageView2/2/w/1280/h/340/interlace/1)
![手把手教你使用EOS多重簽名 – 保護你的資產 12](http://image.zixundingzhi.com/ugQjrXwwrsPk-bkveqdLRKOgA7E=/full/0e7906b74c16dd24c1b3a7f85e9058eda2a91c49.png)
上表中,除了權限(Permission)和祕鑰(Keys)之外,還有兩欄,一個是權重(Weight),另一個是域值(Threshold),這兩個概念也至關重要,還是拿大家熟悉的轉賬來舉個例子吧,按照上表的配置,如果你想轉賬給 vitalikoneos
這個賬戶,你需要將祕鑰的權重相加,如果結果不小於域值,該筆交易才被認為是合法的,即 EOS7...
和 EOS8...
對應的私鑰都得對該筆交易簽名,它們的權重和才不小於域值 2 。同樣的道理,如果你想修改 @Active
的祕鑰,你需要用 EOS6...
和 EOS5...
所對應的祕鑰同時對這個操作進行簽名。可以看到我用了 4 對祕鑰對來管理我的賬戶,這個安全性已經非常高了。當你創建一個賬戶時,你的賬戶默認包含兩種權限:@owner
和 @active
,其中 @owner
主要用來管理其他權限的變更,例如修改 @active
對應的 Keys,新建或刪除一個 @publish
權限等;而 @active
權限在創建之初主要用來執行轉賬等合約操作,即如果你要轉出 EOS,你需要 @active
下的 Keys 對該筆交易簽名。
好了,原理講清楚了,下面我會手把手教你怎麼操作。在 BM 的錢包沒有發佈之前,最安全的錢包當然是 github
上的「命令行錢包」了,這個錢包由兩個組件組成:keosd
和 cleos
,其中 keosd
用來保管私鑰,而 cleos
提供交互命令行,並在 keosd
和 nodeos
(全節點) 之間建立通信,它們的關係如下:
上表中,除了權限(Permission)和祕鑰(Keys)之外,還有兩欄,一個是權重(Weight),另一個是域值(Threshold),這兩個概念也至關重要,還是拿大家熟悉的轉賬來舉個例子吧,按照上表的配置,如果你想轉賬給 vitalikoneos
這個賬戶,你需要將祕鑰的權重相加,如果結果不小於域值,該筆交易才被認為是合法的,即 EOS7...
和 EOS8...
對應的私鑰都得對該筆交易簽名,它們的權重和才不小於域值 2 。同樣的道理,如果你想修改 @Active
的祕鑰,你需要用 EOS6...
和 EOS5...
所對應的祕鑰同時對這個操作進行簽名。可以看到我用了 4 對祕鑰對來管理我的賬戶,這個安全性已經非常高了。當你創建一個賬戶時,你的賬戶默認包含兩種權限:@owner
和 @active
,其中 @owner
主要用來管理其他權限的變更,例如修改 @active
對應的 Keys,新建或刪除一個 @publish
權限等;而 @active
權限在創建之初主要用來執行轉賬等合約操作,即如果你要轉出 EOS,你需要 @active
下的 Keys 對該筆交易簽名。
好了,原理講清楚了,下面我會手把手教你怎麼操作。在 BM 的錢包沒有發佈之前,最安全的錢包當然是 github
上的「命令行錢包」了,這個錢包由兩個組件組成:keosd
和 cleos
,其中 keosd
用來保管私鑰,而 cleos
提供交互命令行,並在 keosd
和 nodeos
(全節點) 之間建立通信,它們的關係如下:
![2](https://cdn.8fet.com/wp-content/uploads/2018/07/201807170605052058.png?imageslim%7CimageView2/2/w/700/h/339/interlace/1)
![手把手教你使用EOS多重簽名 – 保護你的資產 2](http://image.zixundingzhi.com/ugQjrXwwrsPk-bkveqdLRKOgA7E=/full/0e7906b74c16dd24c1b3a7f85e9058eda2a91c49.png)
準備工作
首先,你要安裝 EOSIO 軟件,推薦你使用 docker,下載 EOSIO docker 鏡像,這個鏡像是官方打包的,可以放心使用
$ docker pull eosio/eos-dev
完成後,運行 keosd
:
sudo docker run -d --restart=unless-stopped --name keosd \ -v /your/eosio-wallet/path:/opt/eosio/bin/data-dir \ -v /your/eosio-wallet/path:/root/eosio-wallet \ -t eosio/eos /opt/eosio/bin/keosd \ --wallet-dir /opt/eosio/bin/data-dir \ --http-server-address=127.0.0.1:8900
上面的命令中,/your/eosio-wallet/path
需要你自行配置,keosd
管理的錢包文件會放在該路徑下。
設置 cleos
的別名,你可以將 alias
命令加到 ~/.zshrc
(macOS)或 ~/.bashrc
(Linux) 中,接著執行 cleos get info
命令獲取主網信息
$ alias cleos='sudo docker exec -i keosd /opt/eosio/bin/cleos \ --wallet-url http://127.0.0.1:8900 -u http://mainnet.eoscanada.com ' $ cleos get info { "chain_id":"aca376f206b8fc25a6ed44dbdc66547c36c6c33e3a119ffbeaef943642f0e906", ... }
確定 chain_id
的值,正確無誤後,就可以開始“試驗”了——一定要先在小額賬號上操作,避免誤操作導致的損失。
創建錢包、祕鑰、賬戶
要實現多籤,你至少需要 2 對祕鑰,祕鑰存在錢包裡,所以這裡最好也創建兩個錢包,每個錢包管理一對祕鑰,這樣你的錢包就可以分開保管,避免一個錢包洩露後兩個祕鑰都丟失的情況。
$ cleos wallet create -n w1 Creating wallet: w1 Save password to use in the future to unlock this wallet. Without password imported keys will not be retrievable. "PW5KRMedja6trXRT9Pi4z4gLN5YLE95mxQBuBKvy9UCkBaGWMNUEx" $ $ cleos wallet create -n w2 Creating wallet: w2 Save password to use in the future to unlock this wallet. Without password imported keys will not be retrievable. "PW5KT6RSfSm5cSBQ4jujBc8N8yXG6KwyphnYe8Rm1uMfFFUS5qkjF" $ $ ls /your/eosio-wallet/path w1.wallet w2.wallet
上面的命令為你創建了 2 個錢包 w1 和 w2,在 /your/eosio-wallet/path
路徑下,你可以看到這兩個錢包文件,注意: PW
開頭的密碼你一定要記錄下來,和錢包分開保管,錢包解鎖(unlock)的時候需要這個密碼。
為每個錢包創建和導入祕鑰對
$ cleos wallet create_key -n w1 Created new private key with a public key of: "EOS7bePjtecDvVwRj937B3aaaXyph1vGdAkgu5jibYJ1vfWNaCUWk" $ cleos wallet create_key -n w2 Created new private key with a public key of: "EOS4z4VM5QH4NWAGf2BpYKhHxhqM7Dti2Ssmk6XXk1v7U1kjaVPgS"
使用過老版本 EOSIO 的同學一定注意到了這個差異:新版本的 EOS 在創建祕鑰的過程中把私鑰隱藏了,且直接將私鑰導入到了錢包,這一步優化將你犯錯的可能性降至 0——讓你沒有機會複製私鑰(如果某軟件監聽了你的剪切板,再把監聽結果上傳到他們的服務器,你的私鑰就洩露了),幹得漂亮!
現在祕鑰和錢包都準備好了,還差賬號,這裡要分兩種情況考慮:
- 沒有賬號的情況下,需要創建新賬號
- 已有賬號的情況
1. 創建新賬號
如果你之前沒有賬號,就需要先創建賬號,同時用 EOS 來抵押計算(CPU)和帶寬(Bandwidth)資源、購買存儲資源(RAM),然後再執行第 2 步(如果你已有賬號,直接到第 2 步),先創建賬號:
$ cleos system newaccount --stake-net '0.1 EOS' --stake-cpu '0.1 EOS' \ > --buy-ram-kbytes 4 friends_account vitalikoneos \ > EOS4z4VM5QH4NWAGf2BpYKhHxhqM7Dti2Ssmk6XXk1v7U1kjaVPgS
上面的參數裡,friends_account
是其他人的賬號,你可以找個朋友幫你創建,這一步裡,抵押了 0.2 個 EOS,同時還購買了 4K 的內存,最後兩個參數分別是新賬號名 vitalikoneos
和該賬號對應的初始公鑰,完成這一步後,你就可以根據第 2 步來修改權限了。
2. 已有賬號
如果你已有賬號,只需將現有賬號轉移到新創建的祕鑰下即可,假設你的賬號為 vitalikoneos
,下面的命令會設置該賬號下的 @owner
祕鑰,
$ cleos set account permission vitalikoneos owner '{ "keys": [{ "key": "EOS7bePjtecDvVwRj937B3aaaXyph1vGdAkgu5jibYJ1vfWNaCUWk", "weight": 1 }, { "key": "EOS4z4VM5QH4NWAGf2BpYKhHxhqM7Dti2Ssmk6XXk1v7U1kjaVPgS", "weight": 1 }], "threshold": 2 }' -p vitalikoneos@owner executed transaction: 4e309dc8c3e0535a4d9fec7eb575d... 208 bytes 1201 us warning: transaction executed locally, but may not be confirmed by the network yet # eosio <= eosio::updateauth {"account":"vitalikoneos","permission":"owner","parent":"","auth":{"threshold":2,"keys":[{"key":"EOS...
@owner
權限設置完後,同樣的方法再設置下 @active
的權限,差異是修改 @active
權限時,需要指定 @owner
這個“擁有者”(倒數第 2 個參數),因為只有它才可以修改 @active
:
$ cleos set account permission vitalikoneos active '{ "keys": [{ "key": "EOS7bePjtecDvVwRj937B3aaaXyph1vGdAkgu5jibYJ1vfWNaCUWk", "weight": 1 }, { "key": "EOS4z4VM5QH4NWAGf2BpYKhHxhqM7Dti2Ssmk6XXk1v7U1kjaVPgS", "weight": 1 }], "threshold": 2 }' owner -p vitalikoneos@owner executed transaction: 4e309dc8c3e0535a4d9fec7eb575d... 208 bytes 1201 us warning: transaction executed locally, but may not be confirmed by the network yet # eosio <= eosio::updateauth {"account":"vitalikoneos","permission":"active","parent":"owner","auth":{"threshold":2,"keys":[{"key":"EOS...
執行成功後,你可以通過 cleos get account vitalikoneos -j
命令查看修改是否生效,你還可以通過 https://scaneos.io/ 區塊瀏覽器來查看指定賬號的權限信息。
親自試一試
修改好權限後,你應該會迫不及待的想試一下了,我們先把 2 個錢包都解鎖,然後執行 transfer
操作,可以看到轉賬成功了:
$ cleos transfer vitalikoneos other_account "0.0001 EOS" 'memo' executed transaction: ba4e886fe9e49c9d3093585273341753e 144 bytes 1064 us warning: transaction executed locally, but may not be confirmed by the network yet # eosio.token <= eosio.token::transfer {"from":"vitalikoneos","to":"other_account","quantity":"0.0001 EOS","memo":"memo"} # vitalikoneos <= eosio.token::transfer {"from":"vitalikoneos","to":"other_account","quantity":"0.0001 EOS","memo":"memo"} # other_account <= eosio.token::transfer {"from":"vitalikoneos","to":"other_account","quantity":"0.0001 EOS","memo":"memo"}
接下來我們鎖住任意一個錢包,例如 w1,然後再重複上面的轉賬操作
$ cleos wallet lock -n w1 $ cleos transfer vitalikoneos other_account '0.0001 EOS' 'memo' Error 3090003: provided keys, permissions, and delays do not satisfy declared authorizations Ensure that you have the related private keys inside your wallet and your wallet is unlocked. Error Details: transaction declares authority '{"actor":"vitalikoneos","permission":"active"}', but does not have signatures for it.
可以看到出錯了,錯誤原因是沒有滿足轉賬權限,實驗成功。至此,EOSIO 上的多重簽名實操就結束了,理解了上述操作後,你就可以獨立保管好自己的 EOS 了,同時再也不用擔心錢包被賊惦記了,是不是既很贊又很簡單的樣子?
本文來自微信:weibo_fengyajie,本文觀點不代表三點鐘財經立場,轉載請聯繫原作者。