1

Openzeppelin has a solidity script initializable.sol which has some modifiers and internal functions. I wanna clear my idea on these. I am describing what i know about it, correct me if i am wrong.

modifier initializer : used in such function which is to be called only once. suppose i have a function named initialize() which uses initializer modifier. In this case the initialize() function will be called only once in one deployment of logic contract. When we upgrade our logic contract then we can call again the initialize() but only one time. Like this with each upgrade we will have one chance to call initialize()`.

modifier reinitializer: used to reinitialize a function, provided the current version is less than the version which provided in reinitializer(here). reinitializer also can be called only once in a contract. We can do like this:

 contract MyToken is ERC20Upgradeable {
      function initialize() initializer public {
          // code ..
      }
  }
 
  contract MyTokenV2 is MyToken, ERC20PermitUpgradeable {
      function initializeV2() reinitializer(2) public {
          // code ..
      }
  }

 contract MyTokenV3 is MyTokenV2 {
      function initialize3() reinitializer(3) public {
         // code ..
      }
  }
 
  contract MyTokenV4 is MyTokenV3{
      function initializeV4() reinitializer(4) public {
          // code ..
      }
  }

But after reinitializer(4) can i give reinitializer(10)? like this:

contract MyTokenV4 is MyTokenV3{
      function initializeV5() reinitializer(10) public {
          // code ..
      }
  }

So Overall logic for reinitializer is if we want to upgrade our logic contract to next version then we will have to use reinitializer. But here comes one thing that, we can call initialize() with initializer in every upgrade, so its version will automatically increase. Why do we need to use reinitializer?

disableInitializer(): used to disable further initialization of a contract, also reinitializer won't work. Used to lock a contract on its first initialization. But why do we actually need this?

1 Answer 1

0

I've seen a kinda of similar implementation with Aave V2's Versioned Initalizable scheme. (https://github.com/aave/protocol-v2/blob/master/contracts/protocol/libraries/aave-upgradeability/VersionedInitializable.sol)

Basically, you use a constant variable to determine the version number. Since constant variables are not stored in actual storage of the contract, and instead is added to the bytecode (https://ethereum.stackexchange.com/a/140629/66634 for more details on that), we are only able to call the initilization function if the version number has changed, aka only if the contract has been updated with a new implementation.

This is a pretty involved concept, let me know if you have any follow up questions about this. I think this is essentially what you are trying to build though, or something close to it.

Your Answer

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

Not the answer you're looking for? Browse other questions tagged or ask your own question.