在前兩節的內容我們從交易開始認識比特幣及以太坊的基礎架構,隨后介紹了以太坊智慧合約運作的概念。第三節我們將來回顧區塊鏈「代幣」演進的歷史,并解析與之相關的技術。
既然要談代幣,就必須先厘清代幣的定義。用比喻來說明的話,我們現實世界中有各國發行流通的法幣,如:臺幣(NTD)、美金(USD)。然而,有些公司為了便于平臺管理或流通便利性等因素,會發行在平臺流通的「代幣」,如:湯姆熊幣、Line Points。
在區塊鏈的世界里,其實也存在類似的概念,在公鏈上流通的加密貨幣如:比特幣(BTC)、以太幣(ETH),就像是各國的法幣,普遍被稱之為「協議代幣」(在比特幣/以太坊協議下流通的代幣)。
然而,在以太坊上我們可以透過智慧合約客制化來創造出類似于代幣性質的產物,可稱之為「自定義代幣」,透過智慧合約來賦予代幣功能,類似我們傳統上理解的代幣。
「協議代幣」與「自定義代幣」我們都稱為加密貨幣(Cryptocurrency)。而「協議代幣」往往有自己的區塊鏈或類似的分散式帳本技術,不需要任何其它區塊鏈就能獨立運作。而「自定義代幣」則是利用現有的區塊鏈(絕大多數是Ethereum),透過智慧合約或其它方式來發行及運行。
本文主要是以「自定義代幣」為主題來介紹。
2017 年的ICO 浪潮開啟了大發幣時代,人人都能在以太坊區塊鏈上發行自己的代幣。但其實在以太坊上線之前便已有區塊鏈代幣(以下簡稱代幣)的存在。
區塊鏈代幣的起源:染色幣(Colored Coin)
代幣的歷史最早可以溯及到比特幣上的染色幣。但比特幣沒有智慧合約,要如何發幣呢?當時鑄造Token的做法是:我們把1 Satoshi (10^-8個Bitcoin)重新定義為1 USD。
如此一來,1 Bitcoin (100 Million Satoshi )的價值便變成了100M USD。然而這樣的做法必須具有公信力,因此鑄造的機構應該要抵押 100M的USD來擔保這100M的Satoshi具有等值100M USD的價值(但沒有機制保證鑄造機構真的有抵押)。
于是我們會說這些比特幣被染色了,因為它代表的不再是比特幣的帳面價值,而被賦予了新的價值意義,只是這個Token 透過比特幣的區塊鏈網絡來進行流通。我發送給你100 Satoshi,其實是發送給你100 USD。
但這100M的染色幣要怎么跟其它比特幣來區隔呢?于是許多鑄造商會再利用一個比特幣外部的帳本來追蹤這100M Satoshi的交易紀錄,如此來確認誰手上具有這些被「染色」的Satoshi,他們有權利可以用這些Satoshi兌換為美金。
此外,在比特幣UTXO 的架構下,若是同時交易了染色幣與比特幣,該怎么區分哪些是有染色的Satoshi 呢?一種可能的做法是:一筆交易的Output 中在前的錢堆是染色幣;在后的錢堆則是比特幣。
以上,便是最古早鑄造的Token的作法。這個作法主要的缺點是:當你把這1顆Bitcoin染色,也代表你失去了這1 Bitcoin(因為這1 Bitcoin被當作其它的用途了)。
并且當你要交易300美金( 300 Satoshi )給別人時,卻必須付出遠大于300 Satoshi的手續費給礦工,所以其實很少人這樣子鑄造。在2017年幣價突破天際后,便幾乎沒人再這樣鑄造了。
USDT 與Omni Layer
接下來的作法,便是由Tether 公司發行,赫赫有名的第一代USDT。第一代USDT 是建構在比特幣上,采用Omni Layer 的技術。做法是在比特幣上發送交易,然而交易本身不是重點,重點是在交易的OP_RETURN 中寫下訊息。
如:地址A給地址B 《10 USDT》,地址B便可以再給地址C 《4 USDT》、給地址D 《2 USDT》。如此不斷的接續下去,就像是把比特幣當作便條紙來使用一般,僅是利用比特幣的OP_RETURN內容會永久存在區塊鏈上的特性來記錄USDT的流通。
然而,若是一個地址A并沒有持有USDT,但他卻寫下了給B 《10 USDT》,這樣具有效力嗎?于是,Omni Layer便另外建立了一個Explorer來追蹤這些所有Bitcoin交易上OP_RETURN內的Omni訊息,借以得知每個地址持有的USDT。若是有地址寫下了無效的交易訊息將被自動濾掉。
以太坊ERC-20 Token
以上便是在比特幣上發行Token 常見的作法。接下來進入到以太坊的世界,由于智能合約功能的出現,一切都變得簡單了些。ERC-20 Token 是至今最常見的代幣,那么ERC-20 是什么?ERC-20 Token 是怎么鑄造出來的呢?
ERC-20是以太坊上發行代幣的協定規范,約定發行的代幣必須包含的資訊(如發行幾顆)以及代幣具有的功能(如發送與接收)和限制(如一定時間內能從錢包提領的上限)等,并且會在以太坊上建立資料庫來記錄每個地址持有的代幣數量。
舉例來說,我今天想要發行一個ERC-20 Token,取名叫Pelith Token。假設想發行一百萬顆,要怎么做到呢?
用最直白的方式來說,就是要寫一個ERC-20 代幣發行規范的智能合約,并在發行量這段程式碼中寫一百萬顆,接著把這個智能合約放入一筆交易的Input Data 中,交易的接收地址填為0x0,被礦工執行部署完成后,一百萬顆Pelith Token 便誕生了。
所以說,代幣的創造在技術上是非常容易的,無論想要發行一百萬顆、一億顆、十億顆,其實都只是智能合約內改個數字的差別,發行量的變動成本趨近于零。
所以2017 年的ICO 浪潮,才會出現這么多各式各樣的shitcoin,只要寫個智能合約和白皮書,一個代幣就此誕生了,可以開始圈錢。?。〔皇?,是募資。
真正的難處往往是代幣發行后實際的應用場景搭建和社群行銷營運,讓這個代幣被認可、讓人愿意持有及應用才是最大的困難點和成本之所在。
小結
1. 「協議代幣」往往有自己的區塊鏈或類似的分散式帳本技術,而「自定義代幣」則是利用現有的區塊鏈來發行及運行。
2. 早期比特幣上常見的代幣有改變單位定義的染色幣與把比特幣作為便條紙的Omni Layer 兩種做法。
3. 以太坊與智能合約的出現讓發行代幣在技術門檻上變得更簡易且更有統一的規范,然而應用場景搭建與社群行銷營運才是真正難處。
在上文中我們談到從比特幣開始到以太坊ERC-20 Token出現的自定義代幣發展史。下面將更著重在以太坊技術面的介紹,并在最后綜觀代幣演進發展史給予一些觀點評論。
代幣轉移的成本
大家在第1節中應該都了解到區塊鏈加密貨幣交易必須支付手續費給礦工,那么既然「自定義代幣」要透過區塊鏈來進行傳輸,當我要發送代幣給別人,支付手續費給礦工也是很合乎邏輯的。
接著要解釋的部分會用到許多第2節的概念,如果您還沒讀過,建議您先去閱讀,否則可能會有些難消化。
假設我(A)要把10 個Pelith Token(自定義代幣)轉給B,其實是發生了什么事呢?我簡單做了一張示意圖來說明。(只做概念闡釋,省略了很多可以很復雜的中間細節)
首先要知道,在區塊鏈上發行代幣不是真的發行硬幣或發行鈔票,而是建立了一個「類Excel帳本」來紀錄誰擁有多少代幣。當我們進行代幣轉移時,只是更改這個帳本上格子里的數字。
因此,當我透過智慧合約創造了Pelith Token 時,建立了一個類似Excel 的表格來追蹤所有Pelith Token 持有者的持有數量,并且這些資料會以某種形式儲存備份在每一個節點中(對,就是在全節點那200 G 左右里)。
當我要把10個Pelith Token轉給B時,我必須發送一筆接收對象為合約地址的交易,礦工看到便知道我是要對智慧合約進行操作,不是一般發送Ether給別人的交易。并且在Input Data中呼叫我要操作動作的function,輸入相對應的參數,大概會長類似下面這樣:
我要call的function格式:
transferFrom(address _from, address _to, uint256 _value)
[從address _from傳送_value數量的代幣到_to錢包地址] 填入參數:transferFrom(0xA??, 0xB??, 10)
→ transferFrom(0xA??, 0xB??, 10000000000000000000)
注:第三個參數uint256_value是10個Pelith Token,不過因為在以太坊上沒有小數點,所以進入運算時要以wei (10^-18,以太坊最小的單位)來進行,因此在10后面要補上18個0。然后轉換成類似下面這個樣子:
0x23b872dd000000000000000000000000a000000000000000000000000000000000000000000000000000000000000000b0000000000000000000000000000000000000000000000000000000000000000000000000000000000000008ac7230489e80000
再放入Input Data中。*(0xA??, 0xB??, 10)這一串function中的參數稱為“Payload”(裝載的貨物)
這些Bytecode 被礦工驗證執行后,更新了「帳本內」對應地址的Balance,隨后連同其它交易一起打包入新的區塊中。最先找到Nonce 獲得出塊權利的礦工廣播給其它節點,直到各節點同步完成,并確認區塊在最長區塊鏈中,便正式驗證我(A)把10 個Pelith Token 轉給B 了。
而以上這些動作,其實跟交易一樣須繳些許的Ether 手續費給礦工。當你的ERC-20 Token 要轉移給一個新的地址持有時(假設B 過去未曾持有過Pelith Token),我們在「帳本中」便必須要多開一個格子來記錄并追蹤這個地址的Balance。
要「多開一個格子」的價格是20,000 gas ;「更改一個現有格子內的數字」的價格是5,000 gas,在這筆交易中一共更改了A、B 兩格,故是10,000 gas。再加上交易的基本手續費21,000 gas。我執行了將10 Pelith Token 轉給B 的動作,總共花費了51,000 gas。
執行操作的Gas 總花費計算:
20,000 gas + 5,000*2 gas + 21,000 gas = 51,000 gas 手續費(Eth)= Gas Used * Gas Price
51,000 gas * 10 Gwei(fast) = 510,000 Gwei = 0.00051 ETH = 0.1 USD
(以1 Ether = 200 USD 計算)
大約3 塊臺幣,便是更改一個格子大約需付出的手續費。
至此,我們知道了轉移Token須付出的手續費。如果轉移的量很大,其實金額也是有一定量的。并且,若你的Token Transfer交易無效,被彈掉時(例如你只有10個Token卻發了20個給別人),由于必須到礦工要改格子時才會觸發error,但礦工已執行了這筆交易到觸發error為止的運算。故雖然交易失敗,手續費還是要付。
以太坊2.0 與無頭合約
最近隨著以太坊2.0 有越來越多的消息釋出,出現了一個新名詞:「無頭合約」。原本在智慧合約,當我們從Input Data 呼叫合約中的function 后,合約中的程式碼便會執行邏輯運算去更新「帳本」內的Balance。
然而,以太坊2.0的Phase 1并沒有EVM,無法執行合約中的邏輯部分。因此發布的合約中的function 會長下面這個樣子:
transferFrom(address _from, address _to, uint256 _value) {
}
原本1.0 的合約function 是長這個樣子:
transferFrom(address _from, address _to, uint256 _value)returns (bool) {
balances[_from] = balances[_from].sub(_value);
balances[_to] = balances[_to].add(_value);
emit Transfer(_from, _to, _value);
return true;
}
這是什么意思呢?就是當我們在Input Data 中呼叫了合約中的function,但function 并不會真的去更新帳本上格子里的balance。因此這個合約只是個空殼,雖然看起來有東西,但實際上卻不會執行動作。
因此當我們發送to 合約的交易,在Input Data 中輸入:
transferFrom(0xA??, 0xB??, 10)
合約并不會真的更新帳本(因為根本沒有帳本的存在),也不會同步到其它的節點中。因此這些Input Data輸入的內容只是被當作一般的備注文字訊息被寫在to合約的交易中。于是呢,又回到了比特幣Omni Layer的做法,我必須要去爬這些所有的「便條紙」上的資訊,才會知道最新各地址的余額狀態。也因此,我們發送呼叫這個合約的交易,因為不會進行邏輯執行,所以實際上可以省下非常多的gas,只需要付出交易的基本手續費21,000 gas加上些許的文字寫入gas費用。
我們回顧到目前為止4節 的內容,可以發現區塊鏈從1.0的比特幣,到2.0的以太坊,最大的升級便是智慧合約的功能,允許開發者可以客制化開發許多需要的功能。
結論
1. 在區塊鏈上發行代幣不是真的發行硬幣或發行鈔票,而是建立了一個「類Excel帳本」來紀錄誰擁有多少代幣
2. 代幣轉移時必須發送一筆接收地址為合約地址的交易,并在Input Data中呼叫合約中的function 進行操作,并付出相應的運算成本給礦工。
3. 以太坊2.0的Phase 1中由于沒有邏輯執行的功能,因此智慧合約都成了「無頭合約」,讓以太坊2.0再次被當作如Omni Layer般的「便條紙」來使用。
來源:動區動趨
評論
查看更多