Overwrite _transfer error

Im using this function to add tax feature to my contract but remix ide giving me error.

    function _transfer(
        address sender,
        address recipient,
        uint256 amount
    ) internal virtual override {
        uint tax = (amount / 100) * 5; // 5% tax

        super._transfer(sender, recipient, amount - tax);
        super._transfer(sender, fund, tax);
    }

error is :

TypeError: Trying to override non-virtual function. Did you forget to add "virtual"? --> @openzeppelin/contracts/token/ERC20/ERC20.sol:171:5: | 171 | function _transfer(address from, address to, uint256 value) internal { | ^ (Relevant source part starts here and spans across multiple lines). Note: Overriding function is here: --> contracts/1_Storage.sol:15:5: | 15 | function _transfer( | ^ (Relevant source part starts here and spans across multiple lines).

1 Like

This error message is as clear as it can possibly be - your contract inherits a contract which implements function _transfer without declaring it virtual, hence your contract cannot override this function.

1 Like

i know. but im not sure if its safe to change openzeppelins function to virtual.

edit:this is weird. contract from openzeppelin github repo shows that _transfer is already virtual. maybe remix fetches an outdated version. thanks for the answer

1 Like

It is not.

If open-zeppelin did not declare this function virtual, then it means that they did not intend for it to be overridden.

If it's ERC20 which your contract inherits from, then that function is virtual in OZv4 but not in OZv5, which instead declares function _update as virtual.

So you should either downgrade your project from OZv5 to OZv4, or stay on OZv5 and override function _update instead of function _transfer.

1 Like