279 lines
12 KiB
Solidity
279 lines
12 KiB
Solidity
// SPDX-License-Identifier: UNLICENSED
|
|
pragma solidity ^0.8.17;
|
|
|
|
import { Test } from "forge-std/Test.sol";
|
|
import { ECDSA } from "@openzeppelin/contracts/utils/cryptography/ECDSA.sol";
|
|
import { DeployContracts } from "../script/DeployContracts.s.sol";
|
|
import { DeploymentConfig } from "../script/DeploymentConfig.s.sol";
|
|
import { BaseTokenFactory } from "../contracts/factories/BaseTokenFactory.sol";
|
|
import { OwnerToken } from "../contracts/tokens/OwnerToken.sol";
|
|
import { MasterToken } from "../contracts/tokens/MasterToken.sol";
|
|
import { CommunityOwnerTokenRegistry } from "../contracts/CommunityOwnerTokenRegistry.sol";
|
|
import { CommunityTokenDeployer } from "../contracts/CommunityTokenDeployer.sol";
|
|
|
|
contract CommunityTokenDeployerTest is Test {
|
|
DeploymentConfig internal deploymentConfig;
|
|
|
|
CommunityTokenDeployer internal tokenDeployer;
|
|
CommunityOwnerTokenRegistry internal tokenRegistry;
|
|
|
|
address internal deployer;
|
|
|
|
address internal immutable owner = makeAddr("owner");
|
|
|
|
address internal communityAddress;
|
|
uint256 internal communityKey;
|
|
|
|
function setUp() public virtual {
|
|
DeployContracts deployment = new DeployContracts();
|
|
(tokenDeployer, tokenRegistry,,, deploymentConfig) = deployment.run();
|
|
deployer = deploymentConfig.deployer();
|
|
(communityAddress, communityKey) = makeAddrAndKey("community");
|
|
}
|
|
|
|
function test_Deployment() public {
|
|
assertEq(tokenDeployer.deploymentRegistry(), address(tokenRegistry));
|
|
assertEq(tokenDeployer.owner(), deployer);
|
|
}
|
|
|
|
function _getOwnerTokenConfig() internal view returns (CommunityTokenDeployer.TokenConfig memory, bytes memory) {
|
|
(
|
|
string memory ownerTokenName,
|
|
string memory ownerTokenSymbol,
|
|
string memory ownerTokenBaseURI,
|
|
bytes memory signerPublicKey
|
|
) = deploymentConfig.ownerTokenConfig();
|
|
|
|
CommunityTokenDeployer.TokenConfig memory ownerTokenConfig =
|
|
CommunityTokenDeployer.TokenConfig(ownerTokenName, ownerTokenSymbol, ownerTokenBaseURI);
|
|
return (ownerTokenConfig, signerPublicKey);
|
|
}
|
|
|
|
function _getMasterTokenConfig() internal view returns (CommunityTokenDeployer.TokenConfig memory) {
|
|
(string memory masterTokenName, string memory masterTokenSymbol, string memory masterTokenBaseURI,) =
|
|
deploymentConfig.masterTokenConfig();
|
|
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig =
|
|
CommunityTokenDeployer.TokenConfig(masterTokenName, masterTokenSymbol, masterTokenBaseURI);
|
|
return masterTokenConfig;
|
|
}
|
|
|
|
function _createDeploymentSignature(
|
|
uint256 _signerKey,
|
|
address _signer,
|
|
address _deployer
|
|
)
|
|
internal
|
|
view
|
|
returns (CommunityTokenDeployer.DeploymentSignature memory)
|
|
{
|
|
bytes32 digest = ECDSA.toTypedDataHash(
|
|
tokenDeployer.DOMAIN_SEPARATOR(),
|
|
keccak256(abi.encode(tokenDeployer.DEPLOYMENT_SIGNATURE_TYPEHASH(), _signer, _deployer))
|
|
);
|
|
(uint8 v, bytes32 r, bytes32 s) = vm.sign(_signerKey, digest);
|
|
return CommunityTokenDeployer.DeploymentSignature(_signer, _deployer, v, r, s);
|
|
}
|
|
}
|
|
|
|
contract SetDeploymentRegistryAddressTest is CommunityTokenDeployerTest {
|
|
event DeploymentRegistryAddressChange(address indexed);
|
|
|
|
function setUp() public virtual override {
|
|
CommunityTokenDeployerTest.setUp();
|
|
}
|
|
|
|
function test_RevertWhen_SenderIsNotOwner() public {
|
|
vm.expectRevert(bytes("Ownable: caller is not the owner"));
|
|
tokenDeployer.setDeploymentRegistryAddress(makeAddr("someAddress"));
|
|
}
|
|
|
|
function test_RevertWhen_InvalidDeploymentRegistryAddress() public {
|
|
vm.prank(deployer);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidDeploymentRegistryAddress.selector);
|
|
tokenDeployer.setDeploymentRegistryAddress(address(0));
|
|
}
|
|
|
|
function test_SetDeploymentRegistryAddress() public {
|
|
address newAddress = makeAddr("newAddress");
|
|
vm.prank(deployer);
|
|
vm.expectEmit(true, true, true, true);
|
|
emit DeploymentRegistryAddressChange(newAddress);
|
|
tokenDeployer.setDeploymentRegistryAddress(newAddress);
|
|
|
|
assertEq(tokenDeployer.deploymentRegistry(), newAddress);
|
|
}
|
|
}
|
|
|
|
contract SetOwnerTokenFactoryAddressTest is CommunityTokenDeployerTest {
|
|
event OwnerTokenFactoryAddressChange(address indexed);
|
|
|
|
function setUp() public virtual override {
|
|
CommunityTokenDeployerTest.setUp();
|
|
}
|
|
|
|
function test_RevertWhen_SenderIsNotOwner() public {
|
|
vm.expectRevert(bytes("Ownable: caller is not the owner"));
|
|
tokenDeployer.setOwnerTokenFactoryAddress(makeAddr("someAddress"));
|
|
}
|
|
|
|
function test_RevertWhen_InvalidTokenFactoryAddress() public {
|
|
vm.prank(deployer);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidTokenFactoryAddress.selector);
|
|
tokenDeployer.setOwnerTokenFactoryAddress(address(0));
|
|
}
|
|
|
|
function test_SetOwnerTokenFactoryAddress() public {
|
|
address newAddress = makeAddr("newAddress");
|
|
vm.prank(deployer);
|
|
vm.expectEmit(true, true, true, true);
|
|
emit OwnerTokenFactoryAddressChange(newAddress);
|
|
tokenDeployer.setOwnerTokenFactoryAddress(newAddress);
|
|
|
|
assertEq(tokenDeployer.ownerTokenFactory(), newAddress);
|
|
}
|
|
}
|
|
|
|
contract SetMasterTokenFactoryAddressTest is CommunityTokenDeployerTest {
|
|
event MasterTokenFactoryAddressChange(address indexed);
|
|
|
|
function setUp() public virtual override {
|
|
CommunityTokenDeployerTest.setUp();
|
|
}
|
|
|
|
function test_RevertWhen_SenderIsNotOwner() public {
|
|
vm.expectRevert(bytes("Ownable: caller is not the owner"));
|
|
tokenDeployer.setMasterTokenFactoryAddress(makeAddr("someAddress"));
|
|
}
|
|
|
|
function test_RevertWhen_InvalidTokenFactoryAddress() public {
|
|
vm.prank(deployer);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidTokenFactoryAddress.selector);
|
|
tokenDeployer.setMasterTokenFactoryAddress(address(0));
|
|
}
|
|
|
|
function test_SetOwnerTokenFactoryAddress() public {
|
|
address newAddress = makeAddr("newAddress");
|
|
vm.prank(deployer);
|
|
vm.expectEmit(true, true, true, true);
|
|
emit MasterTokenFactoryAddressChange(newAddress);
|
|
tokenDeployer.setMasterTokenFactoryAddress(newAddress);
|
|
|
|
assertEq(tokenDeployer.masterTokenFactory(), newAddress);
|
|
}
|
|
}
|
|
|
|
contract DeployTest is CommunityTokenDeployerTest {
|
|
function setUp() public virtual override {
|
|
CommunityTokenDeployerTest.setUp();
|
|
}
|
|
|
|
function test_RevertWhen_InvalidDeployerAddress() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig, bytes memory signerPublicKey) =
|
|
_getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, communityAddress, makeAddr("someone else"));
|
|
vm.prank(owner);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidDeployerAddress.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
}
|
|
|
|
function test_RevertWhen_InvalidDeploymentSignature() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig, bytes memory signerPublicKey) =
|
|
_getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, makeAddr("invalid address"), owner);
|
|
vm.prank(owner);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidDeploymentSignature.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
}
|
|
|
|
function test_RevertWhen_InvalidTokenMetadata() public {
|
|
(, bytes memory signerPublicKey) = _getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory ownerTokenConfig = CommunityTokenDeployer.TokenConfig("", "", "");
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = CommunityTokenDeployer.TokenConfig("", "", "");
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, communityAddress, owner);
|
|
|
|
vm.prank(owner);
|
|
vm.expectRevert(BaseTokenFactory.BaseTokenFactory_InvalidTokenMetadata.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
|
|
// fill `masterTokenConfig` with data
|
|
masterTokenConfig = _getMasterTokenConfig();
|
|
|
|
vm.prank(owner);
|
|
vm.expectRevert(BaseTokenFactory.BaseTokenFactory_InvalidTokenMetadata.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
|
|
// fill `ownerTokenConfig` with data and reset `masterTokenConfig`
|
|
(ownerTokenConfig,) = _getOwnerTokenConfig();
|
|
masterTokenConfig = CommunityTokenDeployer.TokenConfig("", "", "");
|
|
|
|
vm.prank(owner);
|
|
vm.expectRevert(BaseTokenFactory.BaseTokenFactory_InvalidTokenMetadata.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
}
|
|
|
|
function test_RevertWhen_InvalidSignerPublicKey() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig,) = _getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, communityAddress, owner);
|
|
|
|
vm.prank(owner);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidSignerKeyOrCommunityAddress.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, bytes(""));
|
|
}
|
|
|
|
function test_RevertWhen_InvalidCommunityAddress() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig, bytes memory signerPublicKey) =
|
|
_getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, address(0), owner);
|
|
|
|
vm.prank(owner);
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_InvalidSignerKeyOrCommunityAddress.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
}
|
|
|
|
function test_RevertWhen_AlreadyDeployed() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig, bytes memory signerPublicKey) =
|
|
_getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, communityAddress, owner);
|
|
|
|
vm.startPrank(owner);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
|
|
vm.expectRevert(CommunityTokenDeployer.CommunityTokenDeployer_AlreadyDeployed.selector);
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
}
|
|
|
|
function test_Deploy() public {
|
|
(CommunityTokenDeployer.TokenConfig memory ownerTokenConfig, bytes memory signerPublicKey) =
|
|
_getOwnerTokenConfig();
|
|
CommunityTokenDeployer.TokenConfig memory masterTokenConfig = _getMasterTokenConfig();
|
|
CommunityTokenDeployer.DeploymentSignature memory signature =
|
|
_createDeploymentSignature(communityKey, communityAddress, owner);
|
|
|
|
vm.prank(owner);
|
|
(address ownerTokenAddress, address masterTokenAddress) =
|
|
tokenDeployer.deploy(ownerTokenConfig, masterTokenConfig, signature, signerPublicKey);
|
|
|
|
assertEq(ownerTokenAddress, tokenRegistry.getEntry(communityAddress));
|
|
assertEq(OwnerToken(ownerTokenAddress).balanceOf(owner), 1);
|
|
|
|
MasterToken masterToken = MasterToken(masterTokenAddress);
|
|
|
|
assertEq(masterToken.ownerToken(), ownerTokenAddress);
|
|
assertEq(masterToken.balanceOf(owner), 0);
|
|
assertEq(masterToken.remoteBurnable(), true);
|
|
assertEq(masterToken.transferable(), false);
|
|
}
|
|
}
|