From 21d2d55db7b58f7e4a9e6d5d7a2915ba3a1bdb55 Mon Sep 17 00:00:00 2001 From: Carlos Granados Date: Mon, 19 Feb 2024 15:42:08 +0100 Subject: [PATCH] Add TemplateCovariant attribute --- README.md | 1 + composer.json | 4 +- tests/PropertyAttributeTest.php | 12 ++++++ tests/PropertyReadAttributeTest.php | 12 ++++++ tests/PropertyWriteAttributeTest.php | 12 ++++++ tests/TemplateCovariantAttributeTest.php | 37 +++++++++++++++++++ .../Property/InterfacePropertyAttribute.php | 10 +++++ .../data/Property/TraitPropertyAttribute.php | 10 +++++ .../InterfacePropertyReadAttribute.php | 10 +++++ .../TraitPropertyReadAttribute.php | 10 +++++ .../InterfacePropertyWriteAttribute.php | 10 +++++ .../TraitPropertyWriteAttribute.php | 10 +++++ .../ClassTemplateCovariantAttribute.php | 35 ++++++++++++++++++ .../InterfaceTemplateCovariantAttribute.php | 13 +++++++ ...InvalidClassTemplateCovariantAttribute.php | 14 +++++++ .../TraitTemplateCovariantAttribute.php | 18 +++++++++ 16 files changed, 216 insertions(+), 2 deletions(-) create mode 100644 tests/TemplateCovariantAttributeTest.php create mode 100644 tests/data/Property/InterfacePropertyAttribute.php create mode 100644 tests/data/Property/TraitPropertyAttribute.php create mode 100644 tests/data/PropertyRead/InterfacePropertyReadAttribute.php create mode 100644 tests/data/PropertyRead/TraitPropertyReadAttribute.php create mode 100644 tests/data/PropertyWrite/InterfacePropertyWriteAttribute.php create mode 100644 tests/data/PropertyWrite/TraitPropertyWriteAttribute.php create mode 100644 tests/data/TemplateCovariant/ClassTemplateCovariantAttribute.php create mode 100644 tests/data/TemplateCovariant/InterfaceTemplateCovariantAttribute.php create mode 100644 tests/data/TemplateCovariant/InvalidClassTemplateCovariantAttribute.php create mode 100644 tests/data/TemplateCovariant/TraitTemplateCovariantAttribute.php diff --git a/README.md b/README.md index e898268..c4d451e 100644 --- a/README.md +++ b/README.md @@ -106,4 +106,5 @@ These are the available attributes and their corresponding PHPDoc annotations: | [PropertyWrite](https://github.com/php-static-analysis/attributes/blob/main/doc/PropertyWrite.md) | `@property-write` | | [Returns](https://github.com/php-static-analysis/attributes/blob/main/doc/Returns.md) | `@return` | | [Template](https://github.com/php-static-analysis/attributes/blob/main/doc/Template.md) | `@template` | +| [TemplateCovariant](https://github.com/php-static-analysis/attributes/blob/main/doc/TemplateCovariant.md) | `@template-covariant` | | [Type](https://github.com/php-static-analysis/attributes/blob/main/doc/Type.md) | `@var` `@return` | diff --git a/composer.json b/composer.json index 3725548..ef0f341 100644 --- a/composer.json +++ b/composer.json @@ -26,8 +26,8 @@ "require": { "php": ">=8.0", "ext-simplexml": "*", - "php-static-analysis/attributes": "^0.1.4 || dev-main", - "php-static-analysis/node-visitor": "^0.1.4 || dev-main", + "php-static-analysis/attributes": "^0.1.5 || dev-main", + "php-static-analysis/node-visitor": "^0.1.5 || dev-main", "vimeo/psalm": "^5" }, "require-dev": { diff --git a/tests/PropertyAttributeTest.php b/tests/PropertyAttributeTest.php index 25b09e1..6a7a776 100644 --- a/tests/PropertyAttributeTest.php +++ b/tests/PropertyAttributeTest.php @@ -10,6 +10,18 @@ public function testClassPropertyAttribute(): void $this->assertCount(0, $errors); } + public function testInterfacePropertyAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/Property/InterfacePropertyAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testTraitPropertyAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/Property/TraitPropertyAttribute.php'); + $this->assertCount(0, $errors); + } + public function testInvalidClassPropertyAttribute(): void { $errors = $this->analyzeTestFile('/data/Property/InvalidClassPropertyAttribute.php'); diff --git a/tests/PropertyReadAttributeTest.php b/tests/PropertyReadAttributeTest.php index 1b36d3b..db3d21a 100644 --- a/tests/PropertyReadAttributeTest.php +++ b/tests/PropertyReadAttributeTest.php @@ -10,6 +10,18 @@ public function testClassPropertyReadAttribute(): void $this->assertCount(0, $errors); } + public function testInterfacePropertyReadAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/PropertyRead/InterfacePropertyReadAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testTraitPropertyReadAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/PropertyRead/TraitPropertyReadAttribute.php'); + $this->assertCount(0, $errors); + } + public function testInvalidClassPropertyReadAttribute(): void { $errors = $this->analyzeTestFile('/data/PropertyRead/InvalidClassPropertyReadAttribute.php'); diff --git a/tests/PropertyWriteAttributeTest.php b/tests/PropertyWriteAttributeTest.php index 14435b2..00bb3c6 100644 --- a/tests/PropertyWriteAttributeTest.php +++ b/tests/PropertyWriteAttributeTest.php @@ -10,6 +10,18 @@ public function testClassPropertyWriteAttribute(): void $this->assertCount(0, $errors); } + public function testInterfacePropertyWriteAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/PropertyWrite/InterfacePropertyWriteAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testTraitPropertyWriteAttribute(): void + { + $errors = $this->analyzeTestFile( '/data/PropertyWrite/TraitPropertyWriteAttribute.php'); + $this->assertCount(0, $errors); + } + public function testInvalidClassPropertyWriteAttribute(): void { $errors = $this->analyzeTestFile('/data/PropertyWrite/InvalidClassPropertyWriteAttribute.php'); diff --git a/tests/TemplateCovariantAttributeTest.php b/tests/TemplateCovariantAttributeTest.php new file mode 100644 index 0000000..519ec0a --- /dev/null +++ b/tests/TemplateCovariantAttributeTest.php @@ -0,0 +1,37 @@ +analyzeTestFile('/data/TemplateCovariant/ClassTemplateCovariantAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testInterfaceTemplateCovariantAttribute(): void + { + $errors = $this->analyzeTestFile('/data/TemplateCovariant/InterfaceTemplateCovariantAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testTraitTemplateCovariantAttribute(): void + { + $errors = $this->analyzeTestFile('/data/TemplateCovariant/TraitTemplateCovariantAttribute.php'); + $this->assertCount(0, $errors); + } + + public function testInvalidClassTemplateCovariantAttribute(): void + { + $errors = $this->analyzeTestFile('/data/TemplateCovariant/InvalidClassTemplateCovariantAttribute.php'); + $this->checkExpectedErrors($errors,[ + 'Empty @template-covariant tag in docblock for test\PhpStaticAnalysis\PsalmPlugin\data\TemplateCovariant\InvalidClassTemplateCovariantAttribute' => 10, + 'Argument 1 of PhpStaticAnalysis\Attributes\TemplateCovariant::__construct expects string, but 0 provided' => 7, + 'Argument 2 of PhpStaticAnalysis\Attributes\TemplateCovariant::__construct expects null|string, but 0 provided' => 9, + 'Attribute TemplateCovariant cannot be used on a property' => 12, + ]); + } +} diff --git a/tests/data/Property/InterfacePropertyAttribute.php b/tests/data/Property/InterfacePropertyAttribute.php new file mode 100644 index 0000000..b6e86c4 --- /dev/null +++ b/tests/data/Property/InterfacePropertyAttribute.php @@ -0,0 +1,10 @@ +')] + public array $list = []; +} + +#[Param(collection: 'Collection')] +function getNames(Collection $collection) : void { + foreach ($collection->list as $item) { + echo $item->getName(); + } +} + +#[Param(children: 'Collection')] +function listChildNames(Collection $children) : void { + getNames($children); +} diff --git a/tests/data/TemplateCovariant/InterfaceTemplateCovariantAttribute.php b/tests/data/TemplateCovariant/InterfaceTemplateCovariantAttribute.php new file mode 100644 index 0000000..7ad1c57 --- /dev/null +++ b/tests/data/TemplateCovariant/InterfaceTemplateCovariantAttribute.php @@ -0,0 +1,13 @@ +