Upgrade worked on Unit test but not in Rinkeby

I have an upgradable contract that inherits from ERC20BurnableUpgradeable like this:

// Original Contract
contract Token is ERC20BurnableUpgradeable {
    string private constant NAME = "Token Name";
    string private constant SYMBOL = "TOKEN";
    uint8 private constant DECIMAL = 18;
    function initialize() public override initializer {
        super.initialize(NAME, SYMBOL, DECIMAL);
    }
}

And I want to upgrade to a new implementation like this:

// New version Contract
contract Token is ERC20BurnableUpgradeable {
    string private constant NAME = "NEW Token Name";
    string private constant SYMBOL = "TOKEN";
    uint8 private constant DECIMAL = 18;
    function initialize() public override initializer {
        super.initialize(NAME, SYMBOL, DECIMAL);
    }

    function name() override public view returns(string memory){
        return NAME;
    }

  function getOnes() public pure returns(uint256){
        return 111;
    }
}

I created the unit test to verify the new constant value, the new function and the state of the others constants and it worked well. Furthermore, I made a further upgrade as a test by adding one function more and it worked well as well.
However when I try to deploy to Rinkeby, nothing happens, it look likes the upgrade was made correctly but when I call the getOnes function I get and error:

 cannot estimate gas; transaction may fail or may require manual gas limit

Even when I get the value of the name constant, I get the original value,“Token Name” , so it looks like the upgrade was not done.

This is the script to upgrade:

      const tokenv2Deployer = await hre.ethers.getContractFactory(Token_V2);
            const tokenv2= await upgrades.upgradeProxy(
                proxyAddress,
                tokenv2Deployer ,
            );
       etherscan.printAddress(`Contract URL: `, tokenv2.address);

So I used the prepareUpgrade function to get the new implementation address and call upgradeTo function with it, but in this case I got and error.

Warning! Error encountered during contract execution [execution reverted] 

If the new implementation is not safe to upgrade I should receive an error when I running the script but that is my doubt because I am not getting nothing from the .upgradeProxy call:

Thank you, I would really appreciate your opinion.

So when you run this script it succeeds, and the address that gets printed is the same as the address of the proxy, right?

This is probably because you tried to upgrade form an account without the right permissions.

Yes that is correct, the script didn't throw any errors and the printed address is the proxy address.

I just confirmed and I am calling the upgradeTo function from the same account from I deployed the proxycontract.

Thanks

Can you clarify how you're calling this function? Are you waiting for the upgrade transaction to mine? You should do something like this if you want to interact immediately afterwards:

            const tokenv2 = await upgrades.upgradeProxy(
                proxyAddress,
                tokenv2Deployer ,
            );
            await tokenv2.deployed();

Can you see the upgrade transaction on chain? Did the transaction go through?

I made somethig like this:

            const tokenv2 = await upgrades.upgradeProxy(
                proxyAddress,
                tokenv2Deployer ,
            );
            await tokenv2.deployed();
            const tokenName = await tokenv2.name()
            console.log(`The proxy contract ${tokenName} was already Upgrade .`); 
            const ones= await tokenv2.getOnes();
            console.log('Ones:', ones);

No I didn't see any upgrade transaction on chain.

But when I called the upgradeTo with the address I got from prepareUpgrade function I got a failed transaction with "upgrade to" as a method

If you’re using transparent proxies (the default), you can’t call upgradeTo directly on the proxy. You need to go through the proxy admin (address found in network file under .openzeppelin directory).

However, before going that route you should try and see why you didn’t see the upgrade transaction when you called upgradeProxy.

On a certain occasion I added a new feature to the same repo, nothing related to upgradeable contracts, but some changes occurred on the unknown.json files automatically, so I undid those changes on that file.
That action could be related to my current issue?.
And I take the opportunity to ask you if I should push the .openzeppelin directory up on the repository.

Thanks

Hm, no. The "unknown" JSON files are generally from your local Hardhat network you use for testing. These should be ignored, but everything else in .openzeppelin should be commited into the repository. See this section in the docs.

Got it.
I have to review why when I call upgradeProxy function any transaction is generated on chain, it is very weird.

Thanks @frangio.

Hi @frangio,
Looking for a solution, I created Box and BoxV2 contracts on my project by trying to follow this tutorial:
https://docs.openzeppelin.com/learn/upgrading-smart-contracts
Again, I could deploy the proxy but I couldn’t run the upgrade. No upgrade transaction was created.
I have my project with TypeScript, so I decided to create a new hardhat project but without TS, only with JS, I created Box and Boxv2 contracts and in this case I could upgrade Box to BoxV2.
So it looks like I have a problem realted with TS , but only happen with upgradeProxy call.
Do you have in mind any clue as to how I could solve it? Thanks.

Can you share the code with me or try to reproduce it in a smaller project and share that so I can take a look?

Sure, thanks.
This is the code that I tested with TS

//SPDX-License-Identifier: AGPL-3.0-only
pragma solidity 0.6.12;

contract Box {
    uint256 private value;

    // Emitted when the stored value changes
    event ValueChanged(uint256 newValue);

    // Stores a new value in the contract
    function store(uint256 newValue) public {
        value = newValue;
        emit ValueChanged(newValue);
    }

    // Reads the last stored value
    function retrieve() public view returns (uint256) {
        return value;
    }
}
//SPDX-License-Identifier: AGPL-3.0-only
pragma solidity 0.6.12;

contract BoxV2 {
     uint256 private value;

    // Emitted when the stored value changes
    event ValueChanged(uint256 newValue);

    // Stores a new value in the contract
    function store(uint256 newValue) public {
        value = newValue;
        emit ValueChanged(newValue);
    }

    // Reads the last stored value
    function retrieve() public view returns (uint256) {
        return value;
    }
    // Increments the stored value by 1
    function increment() public {
        value = value + 1;
        emit ValueChanged(value);
    }
}
// Script to Deploy
import { ethers, upgrades } from 'hardhat';
async function main() {
  const Box = await ethers.getContractFactory("Box");
  console.log("Deploying Box...");
  const box = await upgrades.deployProxy(Box, [42], { initializer: 'store' });
  await box.deployed();
  console.log("Box deployed to:", box.address);
}

main();
// Script to Upgrade
const { ethers, upgrades } = require("hardhat");


async function main() {
  const BoxV2 = await ethers.getContractFactory("BoxV2");
  console.log("Upgrading Box...");
  const box = await upgrades.upgradeProxy("0x93beE1386300C21c537db333760818557D853866", BoxV2);
  await box.deployed();
  console.log("Box upgraded");
}

main();

Hi @frangio, I could fix the issue, my fault.
I didn’t have ownership of the admin proxy of the project. I had to delete it and deploy it again.
Thank you very much.

1 Like