0

This question already has an answer here:

This might have been answered somewhere else, but I couldn't find a 100% satisfying answer. I have the following contracts:

Contract One {}

Contract Two is One{}

Contract Three is Two {}

All the contracts are in separate files, being imported. I fail to understand the concept of upgrades in this case, since when I compile the contract Three in Truffle, everything else is imported and compiled at that point.

Assuming I have functions in contract Three that set the new addresses of contracts One and Two, what is the procedure of upgrading? I fail to understand the complete logic, and would appreciate a detailed description of this process. Basically, what I want is to be able to change contracts One and Two later (adding more functions, changing stuff) without affecting data structs that are on contract Three.

marked as duplicate by Ismael, Richard Horrocks, Achala Dissanayake, Vignesh Karthikeyan, eth Jul 2 '18 at 22:52

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

  • Can you explain more what you mean by "upgrading?" Do you mean somehow changing an already deployed contract? Or are you talking about deploying a new contract with different code? – smarx Jul 2 '18 at 2:45
  • Since contracts are immutable, "upgrade" would mean creating a new contract with the needed changes, and "telling" the Third contract to use the new one instead of the old one, without loosing any data that is on the Third one. Basically, One and Two more look like function libraries. – Ruham Jul 2 '18 at 2:49
  • There are techniques for doing this, but they generally undermine the whole point of smart contracts. (Why would someone trust a smart contract that can be "upgraded?") – smarx Jul 2 '18 at 2:57
  • True, however, if I miss something (necessary functional, for example, or a bug in logic), I would like to be able to have a chance to add changes. Basically, this would mean "soft forking" the contract, where the functional is new, without bugs, but the data and the transaction records are the same. – Ruham Jul 2 '18 at 3:01
2

You will never be able to update anything using the paradigm given in your question. There is only one contract here - Three, which embeds the attributes and functions of contracts One and Two. Once deployed, you can no longer update it.

If you want to be able to update the functionality of One or Two embedded in Three, then Three has to hold:

  • A reference to One and an onlyOwner function which can change that reference
  • A reference to Two and an onlyOwner function which can change that reference

For example:

interface IOne {
    // Define your functions here
}

interface ITwo {
    // Define your functions here
}

contract One is IOne {
    // Implement your functions here
}

contract Two is ITwo {
    // Implement your functions here
}

contract Three is Ownable {
    IOne public one;
    ITwo public two;
    constructor(IOne _one, ITwo _two) public {
        one = _one;
        two = _two;
    }
    function setOne(IOne _one) external onlyOnwer {
        one = _one;
    }
    function setTwo(ITwo _two) external onlyOnwer {
        two = _two;
    }
}

See here for the implementation of Ownable.

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