1: <?php declare(strict_types = 1);
2:
3: namespace PHPStan\Type\Helper;
4:
5: use PHPStan\Type\CompoundType;
6: use PHPStan\Type\Generic\TemplateTypeVariance;
7: use PHPStan\Type\LateResolvableType;
8: use PHPStan\Type\Traits\LateResolvableTypeTrait;
9: use PHPStan\Type\Traits\NonGeneralizableTypeTrait;
10: use PHPStan\Type\Type;
11: use PHPStan\Type\TypeUtils;
12: use PHPStan\Type\VerbosityLevel;
13: use function sprintf;
14:
15: /** @api */
16: final class GetTemplateTypeType implements CompoundType, LateResolvableType
17: {
18:
19: use LateResolvableTypeTrait;
20: use NonGeneralizableTypeTrait;
21:
22: /**
23: * @param class-string $ancestorClassName
24: */
25: public function __construct(private Type $type, private string $ancestorClassName, private string $templateTypeName)
26: {
27: }
28:
29: public function getReferencedClasses(): array
30: {
31: return $this->type->getReferencedClasses();
32: }
33:
34: public function getReferencedTemplateTypes(TemplateTypeVariance $positionVariance): array
35: {
36: return $this->type->getReferencedTemplateTypes($positionVariance);
37: }
38:
39: public function equals(Type $type): bool
40: {
41: return $type instanceof self
42: && $this->type->equals($type->type);
43: }
44:
45: public function describe(VerbosityLevel $level): string
46: {
47: return sprintf('template-type<%s, %s, %s>', $this->type->describe($level), $this->ancestorClassName, $this->templateTypeName);
48: }
49:
50: public function isResolvable(): bool
51: {
52: return !TypeUtils::containsTemplateType($this->type);
53: }
54:
55: protected function getResult(): Type
56: {
57: return $this->type->getTemplateType($this->ancestorClassName, $this->templateTypeName);
58: }
59:
60: /**
61: * @param callable(Type): Type $cb
62: */
63: public function traverse(callable $cb): Type
64: {
65: $type = $cb($this->type);
66:
67: if ($this->type === $type) {
68: return $this;
69: }
70:
71: return new self($type, $this->ancestorClassName, $this->templateTypeName);
72: }
73:
74: /**
75: * @param mixed[] $properties
76: */
77: public static function __set_state(array $properties): Type
78: {
79: return new self(
80: $properties['type'],
81: $properties['ancestorClassName'],
82: $properties['templateTypeName'],
83: );
84: }
85:
86: }
87: