0

I have a contract and its factory. The factory allows cloning of the contract through EIP-1167.

Although I can deploy the factory and verify it easily on etherscan: hardhat verify --network <NETWORK> <FACTORY_ADDRESS>

Validating the factory as a proxy on etherscan requires to verify the implentation. Unfortunately, this doesn't work: hardhat verify --network <NETWORK> <IMPLEMENTATION_ADDRESS>

Successfully submitted source code for contract
contracts/tmp/DummyGreeting.sol:DummyGreeting at 0x8fd5e96cd13e58cd9d90a3f7d7198e3c55892ed2
for verification on the block explorer. Waiting for verification result...

We tried verifying your contract DummyGreeting without including any unrelated one, but it failed.
Trying again with the full solc input used to compile and deploy it.
This means that unrelated contracts may be displayed on Etherscan...

Successfully submitted source code for contract
contracts/tmp/DummyGreeting.sol:DummyGreeting at 0x8fd5e96cd13e58cd9d90a3f7d7198e3c55892ed2
for verification on the block explorer. Waiting for verification result...

Error in plugin @nomiclabs/hardhat-etherscan: The contract verification failed.
Reason: Fail - Unable to verify

NomicLabsHardhatPluginError: The contract verification failed.
Reason: Fail - Unable to verify
    at SimpleTaskDefinition.verifySubtask [as action] (/mnt/c/Users/julie/workspaces/tmp/node_modules/.pnpm/@[email protected][email protected]/node_modules/@nomiclabs/hardhat-etherscan/src/index.ts:350:9)

The only workaround I found so far is deploying a dummy DummyGreeting aside and verify it. Since it happens to have the same bytecode as the implementation, etherscan will then consider implementation verified. Now with big contracts, you want to avoid the extra costly dummy DummyGreeting deployment.

Below are the related files: DummyFactory.sol:

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.15;

import "@openzeppelin/contracts/access/Ownable.sol";
import "@openzeppelin/contracts/utils/Address.sol";
import "@openzeppelin/contracts/proxy/Clones.sol";
import "./DummyGreeting.sol";

contract DummyFactory is Ownable {
    event ContractCreated(
        address indexed owner,
        address indexed target,
        string greeting
    );

    address public immutable implementation;

    constructor() {
        implementation = address(new DummyGreeting());
    }

    function make(
        string calldata greeting
    ) external onlyOwner returns (address) {
        address payable clone = payable(Clones.clone(implementation));
        DummyGreeting c = DummyGreeting(clone);
        emit ContractCreated(msg.sender, clone, greeting);
        c.initialize(
            greeting
        );
        return clone;
    }
}

DummyGreeting.sol:

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.15;

import "@openzeppelin/contracts/proxy/utils/Initializable.sol";

contract DummyGreeting is Initializable {
    string public greeting;

    function initialize(
        string memory greeting_
    )
        public
        initializer
    {
        greeting = greeting_;
    }

}
2
  • Did you solve this eventually?
    – iosifv
    Sep 8, 2022 at 13:27
  • I contacted etherscan support when I posted this. While they never replied, they must have changed something, because it started working at some point along the way
    – Syffys
    Sep 8, 2022 at 20:38

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.