rfc:inheritance_private_methods

PHP RFC: Ignore inheritance rules on private methods

Introduction

Currently, a method with the same name as a parent's method, is checked for inheritance rules regardless of the parent's method visibility.

This leads to inheritance checks being executed even if the parent's method is private. Since private methods are not callable outside of the scope they are defined in, these rules should not be applied.

The documentation explicitly states that only public and protected methods are inherited:

For example, when you extend a class, the subclass inherits all of the public and protected methods from the parent class. Unless a class overrides those methods, they will retain their original functionality.

Proposal

This RFC aims at ignoring these inheritance rules in the case of the parent method being private.

In the current state:

<?php
 
class A 
{ 
    final private function finalPrivate() { 
        echo __METHOD__ . PHP_EOL; 
    } 
} 
 
class B extends A 
{ 
    private function finalPrivate() { 
        echo __METHOD__ . PHP_EOL; 
    } 
}

Produces:

 
Fatal error: Cannot override final method A::finalPrivate()

Besides the error ocurring, the message mentions overriding which isn't applicable for private methods.

With the implementation of this RFC, the previous and the following code would compile correctly:

<?php
 
class A 
{ 
    function callYourPrivate() { 
        $this->myPrivate(); 
    }
 
    function notOverriden_callYourPrivate() {
        $this->myPrivate(); 
    } 
    final private function myPrivate() { 
        echo __METHOD__ . PHP_EOL;
    } 
}
 
class B extends A 
{ 
    function callYourPrivate() {
        $this->myPrivate(); 
    } 
    private function myPrivate() { 
        echo __METHOD__ . PHP_EOL; 
    } 
}
 
$a = new A(); 
$a->callYourPrivate(); 
$a->notOverriden_callYourPrivate();
 
$b = new B(); 
$b->callYourPrivate(); 
$b->notOverriden_callYourPrivate();  

And would produce:

A::myPrivate
A::myPrivate
B::myPrivate
A::myPrivate

The final keyword when applied to a private method should have no significance.

Open issue: Applying final to a private method could issue a compiler warning to warn the user that it doesn't have an effect.

Backward Incompatible Changes

There are no BC breaking changes.

NOTE: The construction final private function is used for instance to restrict the usage of constructors and cloning of child classes. A correct approach to attain a similar effect would be final protected function.

If the optional compiler warning is implemented this change would cause some existing applications to start issuing that warning.

Proposed PHP Version(s)

PHP 7.2

Open Issues

  • Producing a compiler warning when final private function is used.

Unaffected PHP Functionality

The inheritance rules for visible methods remains unaffected, including when these are static or declared on a trait.

Proposed Voting Choices

2/3 majority

Patches and Tests

rfc/inheritance_private_methods.txt · Last modified: 2017/09/22 13:28 (external edit)