在我的理解中,以太坊上的智能合约一旦被推到链上就是不可变的。那么uniswap是如何不断将自己从v1升级到v2再升级到v3的呢?他们如何修改智能合约代码"他们";这里显然指的是Uniswap实验室。此外,由于它是去中心化的,Uniswap实验室没有什么特别之处,其他人也可以修改Uniswap合同吗?
Uniswap的每个版本都是一组不同的合约,部署在不同的地址上。因此,现有合同没有升级。请参阅地址列表的链接:
- v1:https://docs.uniswap.org/protocol/V1/guides/connect-to-uniswap#factory-地址
- v2:https://docs.uniswap.org/protocol/V2/reference/smart-contracts/factory
- v3:https://docs.uniswap.org/protocol/reference/deployments
除了将每个版本部署到新地址的方法之外,还有代理模式。与网络代理类似,您可以将请求重定向到目标契约,并可能在此过程中对其进行修改。如果目标地址存储在变量中,则可以在不更改实际合同字节码的情况下更改值。
pragma solidity ^0.8;
contract Proxy {
address target;
function setTarget(address _target) external {
// you can change the value of `target` variable in storage
// without chanding the `Proxy` contract bytecode
target = _target;
}
fallback(bytes calldata) external returns (bytes memory) {
(bool success, bytes memory returnedData) = target.delegatecall(msg.data);
require(success);
return returnedData;
}
}
您可以在此处阅读有关可升级代理模式的更多信息:https://docs.openzeppelin.com/upgrades-plugins/1.x/proxies
请注意,我上面的代码经过了简化,只展示了基本的代理功能。它很容易受到文章中提到的存储冲突以及对Untrusted Callee的Delegate调用的攻击。