一份通用契約,還是為每個實例生成一份新契約?
優點與缺點是什麼,或者執行一個通用契約或為每個實例生成一個新契約。假設我提供了一份契約,以便人們可以創建自己的眾籌。每次使用合約創建新的眾籌時,最好使用“new”關鍵字生成一個具有自己資料結構的新合約。還是讓所有眾籌實例保持一個總體結構更實際?
在我的應用程序中,不同實例之間不會有互動。
根據您的經驗,在做出此類決定時應該注意什麼。
我不相信產生新實例是保持簡單的理想方法。啟動一個眾籌實例肯定會變得更加昂貴,這在汽油價格高時可能是有害的。
單例不必很複雜。您可以考慮使用定義類型、Crowdsale 和原始函式的庫來分離關注點。這可以在旨在處理所有這些問題的契約中為您提供不錯的可讀性。
單例的另一個優點是可升級邏輯的可能性,這在許多實例中會變得有些麻煩。
這裡有一個小想法可以幫助您考慮將庫用於資料結構和簡單方法:
pragma solidity 0.7.4; // SPDX-License-Identifier: Unlicensed library CrowdsaleLib { struct Crowdsale { // the "using" statement refers to this Type address owner; // this would contain the funders, targets, etc. } modifier onlyOwner(Crowdsale storage self) { require(msg.sender == self.owner, "You do not own this crowdsale"); _; } function close(Crowdsale storage self) internal onlyOwner(self) { // implement the rules // do something to self, which is the complete instance state } } contract Crowdsalw { using CrowdsaleLib for CrowdsaleLib.Crowdsale; mapping(bytes32 => CrowdsaleLib.Crowdsale) crowdsales; function close(bytes32 crowdsaleId) public { CrowdsaleLib.Crowdsale storage c = crowdsales[crowdsaleId]; c.close(); } }
希望能幫助到你。
讓事情盡可能簡單
大多數智能合約都依賴於使事情盡可能簡單。
本著這種精神,建議為每個客戶端實例化新合約,因為它減少了合約中所需的程式碼/邏輯,並將攻擊者的表面限制在所述合約上。
而且你也不會把所有的雞蛋(ETH / Tokens / Value)都放在一個籃子裡,如果確實發生的話,這會減緩合約的流失。
在談論“眾籌”時,您需要不同的合約來儲存稱為“代幣跟踪器”的“erc20 代幣”,所以您已經在這樣做了。
您還需要記住,適合一份合約的邏輯必須適合 8 百萬 gas 限制,對於這樣的合約來說,這個限制可能非常小。
現實世界的例子:
也許我們是偏執狂,但我們一直在開發的 Crowd Funding DAO 確實將這一點發揮到了極致,為每個單獨的眾籌基金的每個捐款地址創建了個人資金庫。
這是一個硬編碼 2 個輸出和 2 個控制器地址的智能合約:
輸出:
- 一 - Vault Owner(發送 eth 的錢包地址)
- 二 - Team Multi 簽名地址
控制器:
- 一 - Funding Manager 智能合約,它可以請求資金,然後將其發送到“團隊”地址,(只有當合約中的所有邏輯每次都按預期工作時才會發生)
- 二 - 保險庫所有者 - 可以要求他們的資金返還,以防他們進行“現金返還”
如果您將多個項目/地址堆疊到一個實例中,這樣的事情就不會真正可靠甚至安全。
這些金庫確實要花很多錢,但要確保除了團隊或投資者之外,沒有其他人可以從中獲得“價值”。
希望這可以幫助。