Solidity
未記錄字元串的索引事件
我在使用事件的 Solidity 智能合約中遇到了一個奇怪的問題。我通過以下兩種方式創建了活動:-
1. event Event1(string assetName, address toAdd); 2. event Event1(string indexed assetName, address indexed toAdd);
現在,如果我執行我的智能合約並且我指定了方法 1,那麼事件會列印在控制台日誌中,而如果我使用方法 2,那麼事件不會列印在控制台日誌中。
有人可以澄清一下嗎?
注意:不粘貼整個合約程式碼
string
和的組合indexed
不起作用。要了解原因,請查看事件參數如何儲存在區塊鏈中。所有執行的交易都會生成一個交易收據,其中包含一個名為 的屬性
logs
。您可以使用 查找收據eth.getTransactionReceipt("0x...")
。在交易收據中,所有未
indexed
包含在data
屬性中的事件參數。此屬性可以保存任意長度的值。但是,indexed
未儲存在data
屬性中但以topics
. 這允許過濾器工作。對於固定大小的參數類型,這是可以的。條目的大小
topics
足以容納 Solidity 支持的所有固定類型。但是,string
可以有任意長度。為了仍然能夠將這些值儲存在主題中,Solidity 創建了值的散列,該散列最終出現在主題中。好處是過濾器仍然可以工作,因為您可以創建要過濾的值的雜湊值。缺點是 web3 無法解碼該值,因為這需要反向執行散列函式。
要解決此問題,您有兩種選擇。您可以
indexed
從參數中刪除,因此它儲存在data
欄位中並且不再散列成為主題的一部分。或者,您更改參數的類型,例如 intobytes32
或另一個。哪個合適取決於您的情況。
您可以通過為同一屬性創建 2 個參數來解決此問題,一個已編入索引,另一個未編入索引,例如:
event Event1(string indexed indexedAssetName, address indexed toAdd, string assetName);
然後將相同的值傳遞給兩者,如下所示:
emit Event1("assetName", address, "assetName");
搜尋時使用索引參數,輸出時使用另一個參數。