Solidity語言學習筆記————33、事件(Events)
事件(Events)
事件是使用EVM日誌內建功能的方便工具,在dapp的介面中,它可以反過來呼叫Javascript的監聽事件的回撥。
事件在合約中可被繼承。當被呼叫時,會使引數儲存到交易的日誌中——一種區塊鏈上的特殊資料結構。這些日誌與合約的地址關聯,併合併到區塊鏈中,只要區塊可以訪問就一直存在。日誌和事件在合約內不可直接被訪問,即使是建立日誌的合約。
日誌的簡單支付驗證(SPV)是可能的,如果一個外部的實體提供了一個這樣證明的合約,它可以證明日誌在區塊鏈是否存在。但需要留意的是,由於合約中僅能訪問最近的256個區塊雜湊,所以還需要提供區塊頭資訊。
可以最多有三個引數被設定為indexed
——是否被索引。設定為索引後,可以允許通過這個引數來查詢日誌,甚至可以按特定的值過濾。
如果陣列(包括string
和bytes
)型別被標記為索引項,會用它對應的Keccak-256雜湊值做為topic。
除非是匿名(anonymous
) 事件,否則事件簽名是其中一個topic,同時也意味著對於匿名事件無法通過名字來過濾。
所有未被索引的引數將被做為日誌的一部分被儲存起來。
註解 |
---|
被索引的引數將不會儲存它們自己,你可以搜尋他們的值,但不能檢索值本身。 |
下面是一個簡單的例子:
pragma solidity ^0.4.0;
contract ClientReceipt {
event Deposit(
address indexed _from,
bytes32 indexed _id,
uint _value
);
function deposit(bytes32 _id) public payable {
// 任何對該函式的呼叫都可以
// 從JavaScript API中通過Deposit`呼叫
// 被過濾從而被檢測到
Deposit(msg.sender, _id, msg.value);
}
}
下述是使用javascript來獲取日誌的例子:
var abi = /* abi 通過編譯器生成 */;
var ClientReceipt = web3.eth.contract(abi);
var clientReceipt = ClientReceipt.at("0x1234...ab67" /* 地址 */);
var event = clientReceipt.Deposit();
// 觀察變化
event.watch(function(error, result){
//結果將包含`Deposit`呼叫給定的引數等各種資訊
if (!error)
console.log(result);
});
// 或通過回撥立即開始觀察
var event = clientReceipt.Deposit(function(error, result) {
if (!error)
console.log(result);
});
底層的日誌介面(Low-level Interface to Logs)
通過函式log0
,log1
,log2
,log3
,log4
,可以直接訪問底層的日誌元件。logi
表示總共有帶i + 1
個型別bytes32
的引數(i表示的就是可帶引數的數目,只是是從0開始計數的)。其中第一個引數會被用來做為日誌的資料部分,其它的會做為topics。前面例子中的event 可改為如下:
pragma solidity ^0.4.10;
contract C {
function f() public payable {
bytes32 _id = 0x420042;
log3(
bytes32(msg.value),
bytes32(0x50cb9fe53daa9737b786ab3646f04d0150dc50ef4e75f59509d83667ad5adb20),
bytes32(msg.sender),
_id
);
}
}
其中的長16進位制串是事件的簽名,相當於keccak256("Deposit(address,hash256,uint256)")
理解事件的其他資源
相關文章
- Solidity語言學習筆記————1、初識Solidity語言Solid筆記
- Solidity語言學習筆記————4、常量Solid筆記
- Solidity語言學習筆記————36、 庫Solid筆記
- Solidity語言學習筆記————38、Solidity彙編Solid筆記
- Solidity語言學習筆記————12、陣列Solid筆記陣列
- Solidity語言學習筆記————37、Using forSolid筆記
- Solidity語言學習筆記————34、繼承Solid筆記繼承
- Solidity語言學習筆記————42、提示和技巧Solid筆記
- Solidity語言學習筆記————43、安全考量Solid筆記
- Solidity語言學習筆記————32、建立合約Solid筆記
- Solidity語言學習筆記————28、純函式Solid筆記函式
- Solidity語言學習筆記————26、回退函式Solid筆記函式
- Solidity語言學習筆記————41、記憶體佈局Solid筆記記憶體
- Solidity語言學習筆記————10、布林型、整型Solid筆記
- Solidity語言學習筆記————3、Remix的基本使用Solid筆記REM
- Solidity語言學習筆記————15、結構體StructSolid筆記結構體Struct
- Solidity語言學習筆記————18、字串和函式Solid筆記字串函式
- Solidity語言學習筆記————14、左值運算子Solid筆記
- Solidity語言學習筆記————9、左值運算子Solid筆記
- Solidity語言學習筆記————17、原始檔對映Solid筆記
- Solidity語言學習筆記————5、全域性變數Solid筆記變數
- Solidity語言學習筆記————2、使用編譯器Solid筆記編譯
- Solidity語言學習筆記————39、獨立彙編Solid筆記
- Solidity語言學習筆記————25、作用域和宣告Solid筆記
- Solidity語言學習筆記————27、檢視函式Solid筆記函式
- Solidity語言學習筆記————30、函式過載Solid筆記函式
- Solidity語言學習筆記————16、對映MappingSolid筆記APP
- Solidity語言學習筆記————35、抽象合約和介面Solid筆記抽象
- Solidity語言學習筆記————26、Assert, Require, Revert 和 ExceptionsSolid筆記UIException
- Solidity語言學習筆記————22、可見性和GettersSolid筆記
- Solidity語言學習筆記————20、函式修飾符Solid筆記函式
- Solidity語言學習筆記————13、固定大小位元組陣列Solid筆記陣列
- Solidity語言學習筆記————14、動態位元組陣列Solid筆記陣列
- Solidity語言學習筆記————8、運算子優先順序Solid筆記
- Solidity語言學習筆記————23、函式呼叫和賦值Solid筆記函式賦值
- Solidity語言學習筆記————24、輸入輸出引數Solid筆記
- MySQL Events學習筆記MySql筆記
- Solidity語言學習筆記————44、合約的後設資料Solid筆記