Inheritance Assignment

Post your solution to the inheritance assignment here. Or ask questions :slight_smile:

2 Likes

Hi Filip
I don’t see any link as mentioned.
your instructions/ Can yousend the “Destroyer” link.
Thanks

Guy

Sorry about that. I have updated the lecture now :slight_smile:

pragma solidity 0.5.12;

contract Destroyable{

address public owner;


 modifier onlyOwner(){
    require(msg.sender == owner);
    _; //Continue execution
    
    function close() public onlyOwner{
        selfdestruct(owner);
    }

}

1 Like
  1. I opened a new file called Destruction:
import "./ownable.sol";
pragma solidity 0.5.12;

contract SelfDestruct is Ownable {
  
     function toSuicide() public onlyOwner{
       selfdestruct (msg.sender);
       }
    
}

in the HelloWorld contract :

import "./ownable.sol";
import "./Destruction.sol";
pragma solidity 0.5.12;
contract HelloWorld is Ownable, SelfDestruct{
1 Like

After looking at the solution - isn’t msg.sender is already “address payable”?
why do we need to convert it again to a “payable address receiver”?
Thanks.

2 Likes

Good question. I assume you are talking about this line of code.

address payable creator = msg.sender;

You are correct that msg.sender is already a payable address. But what we do in the code is not a conversion. We are saving msg.sender to a variable. And if we want the address to remain payable, we need to save it to a payable address. If we were to save msg.sender to a non-payable address variable, then it wouldn’t be payable anymore.

This would be a “conversion” (from payable msg.sender to non payable creator).

address creator = msg.sender;

I hope it became clearer now :slight_smile:

2 Likes

Yes.Thank you. understand that It is not a conversion…but can we avoid the saving of msg.sender as a variable and use:

function destroy() public onlyOwner {
    // address payable receiver = msg.sender;
    selfdestruct(msg.sender);
  }

It works…and only the owner can destroy the contract so it looks quite safe.

Are there any issues that I am not aware of involved?

2 Likes

Yes, that’s absolutely safe. That’s a better solution than to use a variable as a go-between. But sometimes people find it clearer and easier to read when we break the code up into multiple steps.

2 Likes

created new contract Destroyable:

import "./Ownable.sol";
pragma solidity 0.5.12;

contract Destroyable is Ownable{
    
    function destroyContract() public onlyOwner {
        selfdestruct(msg.sender);
    }
}

added to main contract:

import "./Ownable.sol";
import "./Destroyable.sol";
pragma solidity 0.5.12;

contract HelloWorld is Ownable, Destroyable{
1 Like

Destructible contract which inherits from Ownable.

pragma solidity 0.5.12;

import "./Ownable.sol";

contract Destructible is Ownable {
    
    function destroy() public onlyOwner {
        selfdestruct(msg.sender);
    }
}

HelloWorld contract which inherits from Destructible contract.

pragma solidity 0.5.12;

import "./Destructible.sol";

contract HelloWorld is Destructible{...
}
1 Like
import "./Ownable.sol";
pragma solidity 0.5.12;

contract Destroyable is Ownable {
    function close() public onlyOwner {
      selfdestruct(owner);
    }
}
1 Like

Inheritance - Assignment

import"./Ownable.sol";

pragma solidity 0.5.12;

contract Destroyable is Ownable{

    function DESTROY() public onlyContractOwner {
        selfdestruct(msg.sender);
    }

}

Dont forgett to inharit the contract by import it to its child contract “HelloWorld”.

import"./Ownable.sol";
import"./Destroyable.sol";

pragma solidity 0.5.12;

contract HelloWorld is Ownable, Destroyable {
1 Like

In this case the inheritance structure looks like:
Ownable <= Destroyable <= HelloWorld

Given that Destroyable inherits from Ownable, it’s not necessary to specify HelloWorld is Ownable, Destroyable though both appear to work. It may be more informative to specify both though doing so is redundant. What is the convention in this case?

“Ownable.sol”:

pragma solidity 0.5.12;

contract Ownable {
    address payable public owner;
    
    modifier onlyOwner() {
        require(msg.sender == owner, "Caller must be contract owner");
        _; // continue execution
    }
    
    constructor() public {
        owner = msg.sender;
    }
}

“Destroyable.sol”:

import "./Ownable.sol";

pragma solidity 0.5.12;

contract Destroyable is Ownable {
    function close() public onlyOwner {
        selfdestruct(owner);
    }
}

“HelloWorld.sol”:

import "./Destroyable.sol";

pragma solidity 0.5.12;

contract HelloWorld is Destroyable {
// etc...
}
1 Like

import “./Ownable.sol”;
pragma solidity 0.5.12;

contract Destroyable is Ownable{
function close() public onlyOwner { //onlyOwner is custom modifier
selfdestruct(msg.sender); // owner is the owners address
}
}

1 Like

In the Ownable.sol file:

pragma solidity 0.5.12;

contract Ownable {
   address public owner;

   modifier onlyOwner() {
       require(msg.sender == owner);
       _;
   }

  constructor() public {
      owner = msg.sender;
  } 
}

In the Destroyable.sol file:

import "./Ownable.sol";
pragma solidity 0.5.12;

contract Destroyable is Ownable {
   function close() public onlyOwner { 
       selfdestruct(msg.sender);
   }      
}

In the HelloWorld contract file:

import "./Ownable.sol";
import "./Destroyable.sol";
pragma solidity 0.5.12;

contract HelloWorld is Ownable, Destroyable { 

etc etc

1 Like

There isn’t much to be said about Mine.sol, except that I want the contract address to be private, for tax purposes.

pragma solidity 0.5.12;
contract Mine {
   address private Me;
   modifier onlyMe() {
       require(msg.sender == Me);
       _;
   }
  constructor() public {
      Me = msg.sender;
  } 
}

CanVanish.sol is just a wrapper around selfdestruct(). It does not need the ‘_;’ as the contract ceases to exist mid-execution of .poof():

import "./Mine.sol";
pragma solidity 0.5.12;

contract CanVanish is Mine {
     function poof() public onlyMe{
       selfdestruct (msg.sender);
       }
}

And the requisite includes and inheritance are the only change to the business-end:

import "./Mine.sol";
import "./CanVanish.sol";
pragma solidity 0.5.12;
contract MyVaporWareContract is Mine, CanVanish{ ...
2 Likes

Destroyable.sol:
import “./Ownable.sol”;
pragma solidity 0.5.12;

contract Destroyable is Ownable{

function destroyContract() public onlyOwner {
    selfdestruct(msg.sender);
}

}

added to HelloWorld.sol contract:

import “./Ownable.sol”;
import “./Destroyable.sol”;
pragma solidity 0.5.12;

contract HelloWorld is Ownable, Destroyable{

1 Like

Destroyable is Ownable , then

function close() public onlyOwner {
selfdestruct(msg.sender);
}

Then Hello word is Destroyable.

1 Like

Destroyable:

pragma solidity 0.5.12; //compiler version of solidity

import "./Ownable.sol";

contract Destroyable is Ownable {

    function destroy() public onlyOwner { //onlyOwner is custom modifier
    
        selfdestruct(owner);  // `owner` is the owners address
    }

} 

Ownable:

pragma solidity 0.5.12; //compiler version of solidity

contract Ownable { //Ownable functions and state variables

    address payable public owner; //Modified "owner" state variable to payable address

...

}

helloWorld:

import "./Ownable.sol"; //imports Ownable file in same folder

import "./Destroyable.sol";

pragma solidity 0.5.12; //compiler version of solidity

contract helloWorld is Ownable, Destroyable { 

...

}
1 Like