Repository: symfony/symfony
File: src/Symfony/Bridge/PhpUnit/DeprecationErrorHandler/Deprecation.php (PHP)

Code before:
        return false !== strpos($class, "@anonymous\0") ? (get_parent_class($class) ?: key(class_implements($class)) ?: 'class').'@anonymous' : $class;
    }

    public function originatingMethod(): string
    {
        if (null === $this->originMethod) {
            throw new \LogicException('Check with originatesFromAnObject() before calling this method.');
        }

        return $this->originMethod;
    }

    public function getMessage(): string
    {
        return $this->message;
    }

    public function isLegacy(): bool
    {
        if (!$this->originClass || (new \ReflectionClass($this->originClass))->isInternal()) {
            return false;
        }

        $method = $this->originatingMethod();
        $groups = class_exists(Groups::class, false) ? [new Groups(), 'groups'] : [Test::class, 'getGroups'];
        $declaringClass = (self::$declaringClassCache[$this->originClass][$method] ??= (new \ReflectionMethod($this->originClass, $method))->getDeclaringClass()->name);

        return 0 === strpos($method, 'testLegacy')
            || 0 === strpos($method, 'provideLegacy')
            || 0 === strpos($method, 'getLegacy')
            || strpos($this->originClass, '\Legacy')
            || \in_array('legacy', $groups($declaringClass, $method), true);
    }

    public function isMuted(): bool
    {
        if ('Function ReflectionType::__toString() is deprecated' !== $this->message) {
            return false;
        }
        if (isset($this->trace[1]['class'])) {
            return 0 === strpos($this->trace[1]['class'], 'PHPUnit\\');
        }

        return false !== strpos($this->triggeringFile, \DIRECTORY_SEPARATOR.'vendor'.\DIRECTORY_SEPARATOR.'phpunit'.\DIRECTORY_SEPARATOR);
    }

    /**
     * Tells whether both the calling package and the called package are vendor
     * packages.
     */
    public function getType(): string

Review comment (bug):
in sebastianbergmann/phpunit@8f0f8205e3a38675392da55afc573c6bb6a43f4e the visibility of `TestCase::runTest()` was changed from `protected` to `private` meaning that a `method_exists()` call inside the PHPUnit stack triggered when calling the closure referenced with `$groups` fails

Code after:
        if (null === $this->originMethod) {
            throw new \LogicException('Check with originatesFromAnObject() before calling this method.');
        }

        return $this->originMethod;
    }

    public function getMessage(): string
    {
        return $this->message;
    }

    public function isLegacy(): bool
    {
        if (!$this->originClass || (new \ReflectionClass($this->originClass))->isInternal()) {
            return false;
        }

        $method = $this->originatingMethod();
        $groups = class_exists(Groups::class, false) ? [new Groups(), 'groups'] : [Test::class, 'getGroups'];

        return 0 === strpos($method, 'testLegacy')
            || 0 === strpos($method, 'provideLegacy')
            || 0 === strpos($method, 'getLegacy')
            || strpos($this->originClass, '\Legacy')
            || \in_array('legacy', $groups($this->originClass, $method), true);
    }

    public function isMuted(): bool
    {
        if ('Function ReflectionType::__toString() is deprecated' !== $this->message) {
            return false;
        }
        if (isset($this->trace[1]['class'])) {
            return 0 === strpos($this->trace[1]['class'], 'PHPUnit\\');
        }

        return false !== strpos($this->triggeringFile, \DIRECTORY_SEPARATOR.'vendor'.\DIRECTORY_SEPARATOR.'phpunit'.\DIRECTORY_SEPARATOR);
    }

    /**
     * Tells whether both the calling package and the called package are vendor
     * packages.
     */
    public function getType(): string
    {
        $pathType = $this->getPathType($this->triggeringFile);
        if ($this->languageDeprecation && self::PATH_TYPE_VENDOR === $pathType) {
            // the triggering file must be used for language deprecations
            return self::TYPE_INDIRECT;
        }