diff --git a/lib/classes/deprecation.php b/lib/classes/deprecation.php index eb8fa7e416f..47f3e75a6f9 100644 --- a/lib/classes/deprecation.php +++ b/lib/classes/deprecation.php @@ -140,9 +140,10 @@ class deprecation { \ReflectionClass $rc, ?string $name, ): ?deprecated_with_reference { - if ($name === null) { - // No name specified. This may be a deprecated class. - return self::get_attribute($rc, $rc->name); + // Check if the class itself is deprecated first. + $classattribute = self::get_attribute($rc, $rc->name); + if ($classattribute || $name === null) { + return $classattribute; } if ($rc->hasConstant($name)) { diff --git a/lib/tests/deprecation_test.php b/lib/tests/deprecation_test.php index efa1fd8e48d..ac0beab12f5 100644 --- a/lib/tests/deprecation_test.php +++ b/lib/tests/deprecation_test.php @@ -227,26 +227,47 @@ class deprecation_test extends \advanced_testcase { [\core\fixtures\not_deprecated_class::class, false], [[\core\fixtures\not_deprecated_class::class], false], - // Class properties. + // Class properties in a deprecated class. [\core\fixtures\deprecated_class::class . '::deprecatedproperty', true], [[\core\fixtures\deprecated_class::class, 'deprecatedproperty'], true], - [\core\fixtures\deprecated_class::class . '::notdeprecatedproperty', false], - [[\core\fixtures\deprecated_class::class, 'notdeprecatedproperty'], false], + [\core\fixtures\deprecated_class::class . '::notdeprecatedproperty', true], + [[\core\fixtures\deprecated_class::class, 'notdeprecatedproperty'], true], - // Class constants. + // Class constants in a deprecated class. [\core\fixtures\deprecated_class::class . '::DEPRECATED_CONST', true], [[\core\fixtures\deprecated_class::class, 'DEPRECATED_CONST'], true], - [\core\fixtures\deprecated_class::class . '::NOT_DEPRECATED_CONST', false], - [[\core\fixtures\deprecated_class::class, 'NOT_DEPRECATED_CONST'], false], + [\core\fixtures\deprecated_class::class . '::NOT_DEPRECATED_CONST', true], + [[\core\fixtures\deprecated_class::class, 'NOT_DEPRECATED_CONST'], true], - // Class methods. + // Class methods in a deprecated class. [\core\fixtures\deprecated_class::class . '::deprecated_method', true], [[\core\fixtures\deprecated_class::class, 'deprecated_method'], true], - [\core\fixtures\deprecated_class::class . '::not_deprecated_method', false], - [[\core\fixtures\deprecated_class::class, 'not_deprecated_method'], false], + [\core\fixtures\deprecated_class::class . '::not_deprecated_method', true], + [[\core\fixtures\deprecated_class::class, 'not_deprecated_method'], true], + + // Class properties in a not-deprecated class. + [\core\fixtures\not_deprecated_class::class . '::deprecatedproperty', true], + [[\core\fixtures\not_deprecated_class::class, 'deprecatedproperty'], true], + + [\core\fixtures\not_deprecated_class::class . '::notdeprecatedproperty', false], + [[\core\fixtures\not_deprecated_class::class, 'notdeprecatedproperty'], false], + + // Class constants in a not-deprecated class. + [\core\fixtures\not_deprecated_class::class . '::DEPRECATED_CONST', true], + [[\core\fixtures\not_deprecated_class::class, 'DEPRECATED_CONST'], true], + + [\core\fixtures\not_deprecated_class::class . '::NOT_DEPRECATED_CONST', false], + [[\core\fixtures\not_deprecated_class::class, 'NOT_DEPRECATED_CONST'], false], + + // Class methods in a not-deprecated class. + [\core\fixtures\not_deprecated_class::class . '::deprecated_method', true], + [[\core\fixtures\not_deprecated_class::class, 'deprecated_method'], true], + + [\core\fixtures\not_deprecated_class::class . '::not_deprecated_method', false], + [[\core\fixtures\not_deprecated_class::class, 'not_deprecated_method'], false], // Non-existent class. ['non_existent_class', false], @@ -263,4 +284,68 @@ class deprecation_test extends \advanced_testcase { ['core\fixtures\not_deprecated_function', false], ]; } + + /** + * @dataProvider deprecated_ownership_provider + */ + public function test_deprecated_class( + array $reference, + string $expectedowner, + ): void { + require_once(dirname(__FILE__) . '/fixtures/deprecated_fixtures.php'); + + // All attributes for any part of a deprecated class should belong to the deprecated class. + $this->assertEquals( + $expectedowner, + deprecation::from($reference)->owner, + ); + } + + public static function deprecated_ownership_provider(): array { + return [ + // Any part of a deprecated class will emit the deprecation for the class as a whole. + [ + [\core\fixtures\deprecated_class::class], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'deprecatedproperty'], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'notdeprecatedproperty'], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'deprecated_method'], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'not_deprecated_method'], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'DEPRECATED_CONST'], + \core\fixtures\deprecated_class::class, + ], + [ + [\core\fixtures\deprecated_class::class, 'NOT_DEPRECATED_CONST'], + \core\fixtures\deprecated_class::class, + ], + + // A non-deprecated class will emit just for that feature. + [ + [\core\fixtures\not_deprecated_class::class, 'deprecatedproperty'], + \core\fixtures\not_deprecated_class::class . '::deprecatedproperty', + ], + [ + [\core\fixtures\not_deprecated_class::class, 'deprecated_method'], + \core\fixtures\not_deprecated_class::class . '::deprecated_method', + ], + [ + [\core\fixtures\not_deprecated_class::class, 'DEPRECATED_CONST'], + \core\fixtures\not_deprecated_class::class . '::DEPRECATED_CONST', + ], + ]; + } } diff --git a/lib/tests/fixtures/deprecated_fixtures.php b/lib/tests/fixtures/deprecated_fixtures.php index b8bf75a2cb0..e3c11beb7ec 100644 --- a/lib/tests/fixtures/deprecated_fixtures.php +++ b/lib/tests/fixtures/deprecated_fixtures.php @@ -47,6 +47,22 @@ class deprecated_class { } class not_deprecated_class { + protected string $notdeprecatedproperty = 'Not deprecated property'; + + #[deprecated('$this->notdeprecatedproperty')] + protected string $deprecatedproperty = 'Deprecated property'; + + const NOT_DEPRECATED_CONST = 'Not deprecated const'; + + #[deprecated('self::NOT_DEPRECATED_CONST')] + const DEPRECATED_CONST = 'Deprecated const'; + + public function not_deprecated_method() { + } + + #[deprecated('$this->not_deprecated_method()')] + public function deprecated_method() { + } } function not_deprecated_function() {