From 5f47c15571f8b8f616febcdc872ff5ddc70155aa Mon Sep 17 00:00:00 2001 From: Alexey Date: Mon, 25 Feb 2019 11:23:07 -0800 Subject: [PATCH 01/12] Relationship with no "data" member. Fixed #92 (#93) --- .travis.yml | 2 + CHANGELOG.md | 7 +++- phpunit.xml.dist | 3 +- src/EmptyRelationship.php | 31 +++++++++++++++ src/Error/SourceParameter.php | 2 +- src/Error/SourcePointer.php | 2 +- src/Internal/RelationshipMember.php | 10 +++++ src/Internal/ToManyMember.php | 5 ++- src/Link/AboutLink.php | 2 +- src/Link/FirstLink.php | 2 +- src/Link/LastLink.php | 2 +- src/Link/NextLink.php | 2 +- src/Link/PrevLink.php | 2 +- src/Link/RelatedLink.php | 6 +-- src/Link/SelfLink.php | 6 +-- src/Meta.php | 4 +- src/ToMany.php | 6 +-- test/CompoundDocumentTest.php | 4 +- test/ResourceObjectTest.php | 58 +++++++++++++++++++++++++++++ 19 files changed, 132 insertions(+), 24 deletions(-) create mode 100644 src/EmptyRelationship.php create mode 100644 src/Internal/RelationshipMember.php diff --git a/.travis.yml b/.travis.yml index 8ba1558..fe3c026 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,6 +1,8 @@ language: php php: - '7.1' + - '7.2' + - '7.3' before_script: - composer install diff --git a/CHANGELOG.md b/CHANGELOG.md index 86ca5ab..9185eeb 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [2.1.0] - 2019-02-25 +### Fixed +- Relationship without data property (#92) + ## [2.0.1] - 2018-12-31 ### Changed - Downgraded min required php version to 7.1 @@ -14,5 +18,6 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - v2 initial release -[Unreleased]: https://github.com/json-api-php/json-api/compare/2.0.1...HEAD +[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.0...HEAD +[2.1.0]: https://github.com/json-api-php/json-api/compare/2.0.1...2.1.0 [2.0.1]: https://github.com/json-api-php/json-api/compare/2.0.0...2.0.1 diff --git a/phpunit.xml.dist b/phpunit.xml.dist index 48bfa68..884a29a 100644 --- a/phpunit.xml.dist +++ b/phpunit.xml.dist @@ -3,8 +3,7 @@ bootstrap="vendor/autoload.php" stopOnFailure="false" verbose="true" - colors="true" - syntaxCheck="true"> + colors="true"> ./test diff --git a/src/EmptyRelationship.php b/src/EmptyRelationship.php new file mode 100644 index 0000000..1482792 --- /dev/null +++ b/src/EmptyRelationship.php @@ -0,0 +1,31 @@ +name = $name; + $this->obj = combine($member, ...$members); + } + + /** + * @param object $o + */ + public function attachTo($o): void + { + child($o, 'relationships')->{$this->name} = $this->obj; + } +} diff --git a/src/Error/SourceParameter.php b/src/Error/SourceParameter.php index 05b711a..f3bc37a 100644 --- a/src/Error/SourceParameter.php +++ b/src/Error/SourceParameter.php @@ -2,8 +2,8 @@ namespace JsonApiPhp\JsonApi\Error; -use JsonApiPhp\JsonApi\Internal\ErrorMember; use function JsonApiPhp\JsonApi\child; +use JsonApiPhp\JsonApi\Internal\ErrorMember; final class SourceParameter implements ErrorMember { diff --git a/src/Error/SourcePointer.php b/src/Error/SourcePointer.php index 84815db..0af0b5b 100644 --- a/src/Error/SourcePointer.php +++ b/src/Error/SourcePointer.php @@ -2,8 +2,8 @@ namespace JsonApiPhp\JsonApi\Error; -use JsonApiPhp\JsonApi\Internal\ErrorMember; use function JsonApiPhp\JsonApi\child; +use JsonApiPhp\JsonApi\Internal\ErrorMember; final class SourcePointer implements ErrorMember { diff --git a/src/Internal/RelationshipMember.php b/src/Internal/RelationshipMember.php new file mode 100644 index 0000000..3746dee --- /dev/null +++ b/src/Internal/RelationshipMember.php @@ -0,0 +1,10 @@ +validateFieldName($name); $this->name = $name; diff --git a/test/CompoundDocumentTest.php b/test/CompoundDocumentTest.php index 3d62ff9..7441200 100644 --- a/test/CompoundDocumentTest.php +++ b/test/CompoundDocumentTest.php @@ -253,11 +253,11 @@ public function testIncludedResourceMayBeIdentifiedByAnotherLinkedResource() /** * A compound document MUST NOT include more than one resource object for each type and id pair. - * @expectedException \LogicException - * @expectedExceptionMessage Resource apples:1 is already included */ public function testCanNotBeManyIncludedResourcesWithEqualIdentifiers() { + $this->expectException('LogicException'); + $this->expectExceptionMessage('Resource apples:1 is already included'); $apple = new ResourceObject('apples', '1'); new CompoundDocument($apple->identifier(), new Included($apple, $apple)); } diff --git a/test/ResourceObjectTest.php b/test/ResourceObjectTest.php index 37e845f..3541c8d 100644 --- a/test/ResourceObjectTest.php +++ b/test/ResourceObjectTest.php @@ -4,6 +4,7 @@ use JsonApiPhp\JsonApi\Attribute; use JsonApiPhp\JsonApi\DataDocument; +use JsonApiPhp\JsonApi\EmptyRelationship; use JsonApiPhp\JsonApi\Link\RelatedLink; use JsonApiPhp\JsonApi\Link\SelfLink; use JsonApiPhp\JsonApi\Meta; @@ -152,6 +153,63 @@ public function testRelationshipWithEmptyMultiIdLinkage() ); } + public function testRelationshipWithNoData() + { + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "id": "1", + "relationships": { + "empty": { + "links": { + "related": "/foo" + } + } + } + } + } + ', + new DataDocument( + new ResourceObject( + 'basket', + '1', + new EmptyRelationship('empty', new RelatedLink('/foo')) + ) + ) + ); + + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "id": "1", + "relationships": { + "empty": { + "links": { + "related": "/foo", + "self": "/bar" + }, + "meta": { + "foo": "bar" + } + } + } + } + } + ', + new DataDocument( + new ResourceObject( + 'basket', + '1', + new EmptyRelationship('empty', new RelatedLink('/foo'), new SelfLink('/bar'), new Meta('foo', 'bar')) + ) + ) + ); + } + public function testCanNotCreateIdAttribute() { $this->expectException(\DomainException::class); From bc68950744ee9ba056dda5ca4b3b4fc935ef8d3c Mon Sep 17 00:00:00 2001 From: Alexey Date: Mon, 9 Sep 2019 12:43:33 -0700 Subject: [PATCH 02/12] Fix travis builds (#96) --- .travis.yml | 4 ++-- examples/compound_doc.php | 1 - test/CompoundDocumentTest.php | 1 - test/benchmarks/compound10k.php | 1 - 4 files changed, 2 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index fe3c026..59e3899 100644 --- a/.travis.yml +++ b/.travis.yml @@ -9,5 +9,5 @@ before_script: - mkdir build/logs -p script: - - vendor/bin/php-cs-fixer fix -v --dry-run - - phpunit --coverage-clover build/logs/clover.xml + - ./vendor/bin/php-cs-fixer fix -v --dry-run + - ./vendor/bin/phpunit --coverage-clover build/logs/clover.xml diff --git a/examples/compound_doc.php b/examples/compound_doc.php index ddb6fd9..aef8cbf 100644 --- a/examples/compound_doc.php +++ b/examples/compound_doc.php @@ -33,7 +33,6 @@ new Attribute('body', 'First!'), new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) - ); $comment12 = new ResourceObject( 'comments', diff --git a/test/CompoundDocumentTest.php b/test/CompoundDocumentTest.php index 7441200..d3328a1 100644 --- a/test/CompoundDocumentTest.php +++ b/test/CompoundDocumentTest.php @@ -38,7 +38,6 @@ public function testOfficialDocsExample() new Attribute('body', 'First!'), new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) - ); $comment12 = new ResourceObject( 'comments', diff --git a/test/benchmarks/compound10k.php b/test/benchmarks/compound10k.php index c1a0ae2..d220851 100644 --- a/test/benchmarks/compound10k.php +++ b/test/benchmarks/compound10k.php @@ -48,7 +48,6 @@ new Attribute('body', 'First!'), new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) - ); $comment12 = new ResourceObject( 'comments', From 2338d0f8c4f9e97583beaad32e56148498deedce Mon Sep 17 00:00:00 2001 From: Alexey Date: Mon, 9 Sep 2019 21:14:20 -0700 Subject: [PATCH 03/12] Add "ext-json" as a dependency to composer.json, allow phpunit 8.0. (#97) --- README.md | 2 +- composer.json | 6 ++++-- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 8e831cf..6909798 100644 --- a/README.md +++ b/README.md @@ -63,7 +63,7 @@ First, take a look at the examples. All of them are runnable. - [Simple Document](./examples/simple_doc.php) (the same as above) - [Extensive Compound Document](./examples/compound_doc.php) -The library API and use-cases are expressed in comprehensive suite of tests. +The library API and use-cases are expressed in a comprehensive suite of tests. - Data Documents (containing primary data) - [with a single Resource Object](./test/DataDocument/SingleResourceObjectTest.php) - [with a single Resource Identifier](./test/DataDocument/SingleResourceIdentifierTest.php) diff --git a/composer.json b/composer.json index 50b9f32..76bbb66 100644 --- a/composer.json +++ b/composer.json @@ -11,10 +11,12 @@ } ], "require": { - "php": ">=7.1" + "php": ">=7.1", + "ext-json": "*" + }, "require-dev": { - "phpunit/phpunit": "^7.0", + "phpunit/phpunit": "^7.0||^8.0", "friendsofphp/php-cs-fixer": "^2.13" }, "autoload": { From 4fb3c7a30b6f155f41fb2dc167934f4dc0acdf7b Mon Sep 17 00:00:00 2001 From: Sergey Braga Date: Tue, 10 Sep 2019 20:16:17 +0300 Subject: [PATCH 04/12] Add "@internal" annotation to attachTo() (#94) --- examples/compound_doc.php | 1 + src/Attribute.php | 1 + src/EmptyRelationship.php | 1 + src/Error.php | 1 + src/Error/Code.php | 1 + src/Error/Detail.php | 1 + src/Error/Id.php | 1 + src/Error/SourceParameter.php | 1 + src/Error/SourcePointer.php | 1 + src/Error/Status.php | 1 + src/Error/Title.php | 1 + src/ErrorDocument.php | 3 +-- src/Included.php | 1 + src/Internal/Attachable.php | 1 + src/JsonApi.php | 1 + src/Link/AboutLink.php | 1 + src/Link/FirstLink.php | 1 + src/Link/LastLink.php | 1 + src/Link/NextLink.php | 1 + src/Link/PrevLink.php | 1 + src/Link/RelatedLink.php | 1 + src/Link/SelfLink.php | 1 + src/Meta.php | 4 ++++ src/NullData.php | 1 + src/PaginatedCollection.php | 1 + src/Pagination.php | 1 + src/ResourceCollection.php | 1 + src/ResourceIdentifier.php | 2 ++ src/ResourceIdentifierCollection.php | 1 + src/ResourceObject.php | 2 ++ src/ToMany.php | 1 + src/ToNull.php | 1 + src/ToOne.php | 1 + test/CompoundDocumentTest.php | 1 + test/benchmarks/compound10k.php | 1 + 35 files changed, 40 insertions(+), 2 deletions(-) diff --git a/examples/compound_doc.php b/examples/compound_doc.php index aef8cbf..c9feae0 100644 --- a/examples/compound_doc.php +++ b/examples/compound_doc.php @@ -34,6 +34,7 @@ new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) ); + $comment12 = new ResourceObject( 'comments', '12', diff --git a/src/Attribute.php b/src/Attribute.php index ba1f50b..d45834c 100644 --- a/src/Attribute.php +++ b/src/Attribute.php @@ -22,6 +22,7 @@ public function __construct(string $name, $val) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/EmptyRelationship.php b/src/EmptyRelationship.php index 1482792..659a9df 100644 --- a/src/EmptyRelationship.php +++ b/src/EmptyRelationship.php @@ -23,6 +23,7 @@ public function __construct(string $name, RelationshipMember $member, Relationsh /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error.php b/src/Error.php index 35b7b8d..ba0e3a0 100644 --- a/src/Error.php +++ b/src/Error.php @@ -23,6 +23,7 @@ public function __construct(ErrorMember ...$members) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/Code.php b/src/Error/Code.php index 6705037..a03b827 100644 --- a/src/Error/Code.php +++ b/src/Error/Code.php @@ -21,6 +21,7 @@ public function __construct(string $code) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/Detail.php b/src/Error/Detail.php index dfeb86d..f4d169c 100644 --- a/src/Error/Detail.php +++ b/src/Error/Detail.php @@ -21,6 +21,7 @@ public function __construct(string $detail) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/Id.php b/src/Error/Id.php index 40eb903..11c5b10 100644 --- a/src/Error/Id.php +++ b/src/Error/Id.php @@ -21,6 +21,7 @@ public function __construct(string $id) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/SourceParameter.php b/src/Error/SourceParameter.php index f3bc37a..3e48461 100644 --- a/src/Error/SourceParameter.php +++ b/src/Error/SourceParameter.php @@ -22,6 +22,7 @@ public function __construct(string $parameter) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/SourcePointer.php b/src/Error/SourcePointer.php index 0af0b5b..d6cecaa 100644 --- a/src/Error/SourcePointer.php +++ b/src/Error/SourcePointer.php @@ -19,6 +19,7 @@ public function __construct(string $pointer) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/Status.php b/src/Error/Status.php index 0d396f6..6be53aa 100644 --- a/src/Error/Status.php +++ b/src/Error/Status.php @@ -21,6 +21,7 @@ public function __construct(string $status) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Error/Title.php b/src/Error/Title.php index 1c18f2c..2226f53 100644 --- a/src/Error/Title.php +++ b/src/Error/Title.php @@ -22,6 +22,7 @@ public function __construct(string $title) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ErrorDocument.php b/src/ErrorDocument.php index e4a52e5..4d4fe73 100644 --- a/src/ErrorDocument.php +++ b/src/ErrorDocument.php @@ -12,10 +12,9 @@ final class ErrorDocument implements \JsonSerializable { private $obj; - public function __construct(Error $error, ErrorDocumentMember ...$members) + public function __construct(ErrorDocumentMember ...$members) { $this->obj = (object) []; - $error->attachTo($this->obj); foreach ($members as $member) { $member->attachTo($this->obj); } diff --git a/src/Included.php b/src/Included.php index 220270b..5b2dbd4 100644 --- a/src/Included.php +++ b/src/Included.php @@ -40,6 +40,7 @@ public function validateLinkage(PrimaryData $data): void /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Internal/Attachable.php b/src/Internal/Attachable.php index edd2de2..0178295 100644 --- a/src/Internal/Attachable.php +++ b/src/Internal/Attachable.php @@ -9,6 +9,7 @@ interface Attachable { /** * @param object $o + * @internal */ public function attachTo($o): void; } diff --git a/src/JsonApi.php b/src/JsonApi.php index c895bb6..3c1e08b 100644 --- a/src/JsonApi.php +++ b/src/JsonApi.php @@ -22,6 +22,7 @@ public function __construct(string $version = '1.0', Meta $meta = null) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/AboutLink.php b/src/Link/AboutLink.php index 6035330..e317ca8 100644 --- a/src/Link/AboutLink.php +++ b/src/Link/AboutLink.php @@ -12,6 +12,7 @@ final class AboutLink implements ErrorMember /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/FirstLink.php b/src/Link/FirstLink.php index 755a12b..af13251 100644 --- a/src/Link/FirstLink.php +++ b/src/Link/FirstLink.php @@ -12,6 +12,7 @@ final class FirstLink implements PaginationLink /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/LastLink.php b/src/Link/LastLink.php index c11b2e0..037b228 100644 --- a/src/Link/LastLink.php +++ b/src/Link/LastLink.php @@ -12,6 +12,7 @@ final class LastLink implements PaginationLink /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/NextLink.php b/src/Link/NextLink.php index 39f5641..c2ba366 100644 --- a/src/Link/NextLink.php +++ b/src/Link/NextLink.php @@ -12,6 +12,7 @@ final class NextLink implements PaginationLink /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/PrevLink.php b/src/Link/PrevLink.php index f38d94b..b612450 100644 --- a/src/Link/PrevLink.php +++ b/src/Link/PrevLink.php @@ -12,6 +12,7 @@ final class PrevLink implements PaginationLink /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/RelatedLink.php b/src/Link/RelatedLink.php index 7434423..c1924ee 100644 --- a/src/Link/RelatedLink.php +++ b/src/Link/RelatedLink.php @@ -12,6 +12,7 @@ final class RelatedLink implements RelationshipMember /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Link/SelfLink.php b/src/Link/SelfLink.php index 5a9a31f..fde232b 100644 --- a/src/Link/SelfLink.php +++ b/src/Link/SelfLink.php @@ -14,6 +14,7 @@ final class SelfLink implements DataDocumentMember, ResourceMember, Relationship /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Meta.php b/src/Meta.php index 5b9a2c3..758c3bb 100644 --- a/src/Meta.php +++ b/src/Meta.php @@ -26,6 +26,10 @@ public function __construct(string $key, $value) $this->value = $value; } + /** + * @param object $o + * @internal + */ public function attachTo($o): void { child($o, 'meta')->{$this->key} = $this->value; diff --git a/src/NullData.php b/src/NullData.php index 03cd15e..bbb3dbc 100644 --- a/src/NullData.php +++ b/src/NullData.php @@ -8,6 +8,7 @@ final class NullData implements PrimaryData { /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/PaginatedCollection.php b/src/PaginatedCollection.php index c4a51da..15e3cc7 100644 --- a/src/PaginatedCollection.php +++ b/src/PaginatedCollection.php @@ -24,6 +24,7 @@ public function __construct(Pagination $pagination, Collection $collection) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/Pagination.php b/src/Pagination.php index 42f2ef7..674f375 100644 --- a/src/Pagination.php +++ b/src/Pagination.php @@ -20,6 +20,7 @@ public function __construct(PaginationLink ...$links) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ResourceCollection.php b/src/ResourceCollection.php index e2f0c4b..f337ad5 100644 --- a/src/ResourceCollection.php +++ b/src/ResourceCollection.php @@ -19,6 +19,7 @@ public function __construct(ResourceObject ...$resources) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ResourceIdentifier.php b/src/ResourceIdentifier.php index 6967856..2974492 100644 --- a/src/ResourceIdentifier.php +++ b/src/ResourceIdentifier.php @@ -35,6 +35,7 @@ public function __construct(string $type, string $id, Meta $meta = null) /** * @param object $o + * @internal */ public function attachTo($o): void { @@ -43,6 +44,7 @@ public function attachTo($o): void /** * @param object $o + * @internal */ public function attachToCollection($o): void { diff --git a/src/ResourceIdentifierCollection.php b/src/ResourceIdentifierCollection.php index 5e87189..84b8887 100644 --- a/src/ResourceIdentifierCollection.php +++ b/src/ResourceIdentifierCollection.php @@ -19,6 +19,7 @@ public function __construct(ResourceIdentifier ...$identifiers) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ResourceObject.php b/src/ResourceObject.php index bab4f25..20ce548 100644 --- a/src/ResourceObject.php +++ b/src/ResourceObject.php @@ -61,6 +61,7 @@ public function registerIn(array &$registry): void /** * @param object $o + * @internal */ public function attachTo($o): void { @@ -77,6 +78,7 @@ public function attachAsIncludedTo($o): void /** * @param object $o + * @internal */ public function attachToCollection($o): void { diff --git a/src/ToMany.php b/src/ToMany.php index 0811006..c0a7278 100644 --- a/src/ToMany.php +++ b/src/ToMany.php @@ -29,6 +29,7 @@ public function __construct(string $name, ResourceIdentifierCollection $collecti /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ToNull.php b/src/ToNull.php index 4e30861..8b2d3f1 100644 --- a/src/ToNull.php +++ b/src/ToNull.php @@ -23,6 +23,7 @@ public function __construct(string $name, ToOneMember ...$members) /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/src/ToOne.php b/src/ToOne.php index dcd2e7a..dbbd7ac 100644 --- a/src/ToOne.php +++ b/src/ToOne.php @@ -28,6 +28,7 @@ public function __construct(string $name, ResourceIdentifier $identifier, ToOneM /** * @param object $o + * @internal */ public function attachTo($o): void { diff --git a/test/CompoundDocumentTest.php b/test/CompoundDocumentTest.php index d3328a1..bb013ce 100644 --- a/test/CompoundDocumentTest.php +++ b/test/CompoundDocumentTest.php @@ -39,6 +39,7 @@ public function testOfficialDocsExample() new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) ); + $comment12 = new ResourceObject( 'comments', '12', diff --git a/test/benchmarks/compound10k.php b/test/benchmarks/compound10k.php index d220851..513518b 100644 --- a/test/benchmarks/compound10k.php +++ b/test/benchmarks/compound10k.php @@ -49,6 +49,7 @@ new SelfLink('http://example.com/comments/5'), new ToOne('author', new ResourceIdentifier('people', '2')) ); + $comment12 = new ResourceObject( 'comments', '12', From 5a683218ea20258ccc0cfe9ba0ae677925c60d50 Mon Sep 17 00:00:00 2001 From: Alexey Date: Thu, 19 Dec 2019 13:59:57 -0800 Subject: [PATCH 05/12] ResourceIdentifier to allow multiple meta props (fixes #99) (#100) --- .travis.yml | 1 + CHANGELOG.md | 7 ++++++- src/ResourceIdentifier.php | 4 ++-- test/DataDocument/SingleResourceIdentifierTest.php | 8 ++++++-- 4 files changed, 15 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index 59e3899..b2a600d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,6 +3,7 @@ php: - '7.1' - '7.2' - '7.3' + - '7.4' before_script: - composer install diff --git a/CHANGELOG.md b/CHANGELOG.md index 9185eeb..d565111 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [2.1.1] - 2019-12-19 +### Fixed +- ResourceIdentifier does not allow multiple meta members (#99) + ## [2.1.0] - 2019-02-25 ### Fixed - Relationship without data property (#92) @@ -18,6 +22,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - v2 initial release -[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.0...HEAD +[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.1...HEAD +[2.2.0]: https://github.com/json-api-php/json-api/compare/2.1.0...2.1.1 [2.1.0]: https://github.com/json-api-php/json-api/compare/2.0.1...2.1.0 [2.0.1]: https://github.com/json-api-php/json-api/compare/2.0.0...2.0.1 diff --git a/src/ResourceIdentifier.php b/src/ResourceIdentifier.php index 2974492..dff34f8 100644 --- a/src/ResourceIdentifier.php +++ b/src/ResourceIdentifier.php @@ -16,7 +16,7 @@ final class ResourceIdentifier implements PrimaryData */ private $id; - public function __construct(string $type, string $id, Meta $meta = null) + public function __construct(string $type, string $id, Meta ...$metas) { if (isValidName($type) === false) { throw new \DomainException("Invalid type value: $type"); @@ -26,7 +26,7 @@ public function __construct(string $type, string $id, Meta $meta = null) 'type' => $type, 'id' => $id, ]; - if ($meta) { + foreach ($metas as $meta) { $meta->attachTo($this->obj); } $this->type = $type; diff --git a/test/DataDocument/SingleResourceIdentifierTest.php b/test/DataDocument/SingleResourceIdentifierTest.php index 92a91d5..1d12a77 100644 --- a/test/DataDocument/SingleResourceIdentifierTest.php +++ b/test/DataDocument/SingleResourceIdentifierTest.php @@ -36,7 +36,10 @@ public function testExtendedDocument() "data": { "type": "apples", "id": "1", - "meta": {"apple_meta": "foo"} + "meta": { + "apple_meta": "foo", + "bar": [42] + } }, "links": { "self": "/apples/1" @@ -51,7 +54,8 @@ public function testExtendedDocument() new ResourceIdentifier( 'apples', '1', - new Meta('apple_meta', 'foo') + new Meta('apple_meta', 'foo'), + new Meta('bar', [42]) ), new SelfLink('/apples/1'), new JsonApi(), From 1f74ccf36fa80149401b94f279a3d535acb3bd49 Mon Sep 17 00:00:00 2001 From: Alexey Date: Thu, 30 Jan 2020 13:03:12 -0800 Subject: [PATCH 06/12] Add a self link to the paginated collection example (#102) --- test/PaginationTest.php | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/test/PaginationTest.php b/test/PaginationTest.php index 17ee668..7add66f 100644 --- a/test/PaginationTest.php +++ b/test/PaginationTest.php @@ -10,6 +10,7 @@ use JsonApiPhp\JsonApi\Link\LastLink; use JsonApiPhp\JsonApi\Link\NextLink; use JsonApiPhp\JsonApi\Link\PrevLink; +use JsonApiPhp\JsonApi\Link\SelfLink; use JsonApiPhp\JsonApi\PaginatedCollection; use JsonApiPhp\JsonApi\Pagination; use JsonApiPhp\JsonApi\ResourceCollection; @@ -33,7 +34,8 @@ public function testPaginatedResourceCollection() "first": "http://example.com/fruits?page=first", "last": "http://example.com/fruits?page=last", "prev": "http://example.com/fruits?page=3", - "next": "http://example.com/fruits?page=5" + "next": "http://example.com/fruits?page=5", + "self": "http://example.com/fruits?page=4" } } ', @@ -49,7 +51,8 @@ public function testPaginatedResourceCollection() new ResourceObject('apples', '1'), new ResourceObject('apples', '2') ) - ) + ), + new SelfLink('http://example.com/fruits?page=4') ) ); } From 33235447a5b3e27809adc1a98f88484b3506788a Mon Sep 17 00:00:00 2001 From: Alexey Date: Thu, 30 Jan 2020 23:17:21 -0800 Subject: [PATCH 07/12] Create FUNDING.yml (#103) --- .github/FUNDING.yml | 2 ++ 1 file changed, 2 insertions(+) create mode 100644 .github/FUNDING.yml diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml new file mode 100644 index 0000000..66a983e --- /dev/null +++ b/.github/FUNDING.yml @@ -0,0 +1,2 @@ +custom: "https://www.paypal.me/f3ath" + From 4eb1497ffe1dd685716a66f92ceb1561d7bc7045 Mon Sep 17 00:00:00 2001 From: Alexey Date: Mon, 16 Mar 2020 18:53:17 -0700 Subject: [PATCH 08/12] Allow RelatedLink in Document. Fixes #104 (#105) * Allow RelatedLink in Document. Fixes #104 --- CHANGELOG.md | 9 +++++-- composer.json | 1 - src/Internal/Identifier.php | 2 +- src/Link/RelatedLink.php | 3 ++- src/PaginatedCollection.php | 2 +- test/DataDocument/ManyResourceObjectsTest.php | 27 +++++++++---------- .../SingleResourceIdentifierTest.php | 15 ++++++----- 7 files changed, 33 insertions(+), 26 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d565111..3f4bc42 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,10 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [2.1.2] - 2020-03-16 +### Fixed +- Related links must be allowed inside relationship documents (#104) + ## [2.1.1] - 2019-12-19 ### Fixed - ResourceIdentifier does not allow multiple meta members (#99) @@ -22,7 +26,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - v2 initial release -[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.1...HEAD -[2.2.0]: https://github.com/json-api-php/json-api/compare/2.1.0...2.1.1 +[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.2...HEAD +[2.1.2]: https://github.com/json-api-php/json-api/compare/2.1.1...2.1.2 +[2.1.1]: https://github.com/json-api-php/json-api/compare/2.1.0...2.1.1 [2.1.0]: https://github.com/json-api-php/json-api/compare/2.0.1...2.1.0 [2.0.1]: https://github.com/json-api-php/json-api/compare/2.0.0...2.0.1 diff --git a/composer.json b/composer.json index 76bbb66..ffcd77e 100644 --- a/composer.json +++ b/composer.json @@ -13,7 +13,6 @@ "require": { "php": ">=7.1", "ext-json": "*" - }, "require-dev": { "phpunit/phpunit": "^7.0||^8.0", diff --git a/src/Internal/Identifier.php b/src/Internal/Identifier.php index fa435a1..f8f9e47 100644 --- a/src/Internal/Identifier.php +++ b/src/Internal/Identifier.php @@ -8,8 +8,8 @@ interface Identifier { /** - * @internal * @param array $registry + * @internal */ public function registerIn(array &$registry): void; } diff --git a/src/Link/RelatedLink.php b/src/Link/RelatedLink.php index c1924ee..1def33c 100644 --- a/src/Link/RelatedLink.php +++ b/src/Link/RelatedLink.php @@ -3,10 +3,11 @@ namespace JsonApiPhp\JsonApi\Link; use function JsonApiPhp\JsonApi\child; +use JsonApiPhp\JsonApi\Internal\DataDocumentMember; use JsonApiPhp\JsonApi\Internal\LinkTrait; use JsonApiPhp\JsonApi\Internal\RelationshipMember; -final class RelatedLink implements RelationshipMember +final class RelatedLink implements RelationshipMember, DataDocumentMember { use LinkTrait; diff --git a/src/PaginatedCollection.php b/src/PaginatedCollection.php index 15e3cc7..e59c66f 100644 --- a/src/PaginatedCollection.php +++ b/src/PaginatedCollection.php @@ -33,8 +33,8 @@ public function attachTo($o): void } /** - * @internal * @param array $registry + * @internal */ public function registerIn(array &$registry): void { diff --git a/test/DataDocument/ManyResourceObjectsTest.php b/test/DataDocument/ManyResourceObjectsTest.php index 3a2be82..54736e2 100644 --- a/test/DataDocument/ManyResourceObjectsTest.php +++ b/test/DataDocument/ManyResourceObjectsTest.php @@ -5,6 +5,7 @@ use JsonApiPhp\JsonApi\Attribute; use JsonApiPhp\JsonApi\DataDocument; use JsonApiPhp\JsonApi\JsonApi; +use JsonApiPhp\JsonApi\Link\RelatedLink; use JsonApiPhp\JsonApi\Link\SelfLink; use JsonApiPhp\JsonApi\Meta; use JsonApiPhp\JsonApi\ResourceCollection; @@ -33,24 +34,23 @@ public function testExtendedDocument() ' { "data": [{ - "type": "apples", + "type": "people", "id": "1", "attributes": { - "color": "red", - "sort": "Fuji" + "name": "Martin Fowler" }, "meta": {"apple_meta": "foo"} },{ - "type": "apples", + "type": "people", "id": "2", "attributes": { - "color": "yellow", - "sort": "Gala" + "name": "Kent Beck" }, "meta": {"apple_meta": "foo"} }], "links": { - "self": "/apples" + "self": "/books/123/relationships/authors", + "related": "/books/123/authors" }, "jsonapi": { "version": "1.0" @@ -61,21 +61,20 @@ public function testExtendedDocument() new DataDocument( new ResourceCollection( new ResourceObject( - 'apples', + 'people', '1', - new Attribute('color', 'red'), - new Attribute('sort', 'Fuji'), + new Attribute('name', 'Martin Fowler'), new Meta('apple_meta', 'foo') ), new ResourceObject( - 'apples', + 'people', '2', - new Attribute('color', 'yellow'), - new Attribute('sort', 'Gala'), + new Attribute('name', 'Kent Beck'), new Meta('apple_meta', 'foo') ) ), - new SelfLink('/apples'), + new SelfLink('/books/123/relationships/authors'), + new RelatedLink('/books/123/authors'), new JsonApi(), new Meta('document_meta', 'bar') ) diff --git a/test/DataDocument/SingleResourceIdentifierTest.php b/test/DataDocument/SingleResourceIdentifierTest.php index 1d12a77..165a625 100644 --- a/test/DataDocument/SingleResourceIdentifierTest.php +++ b/test/DataDocument/SingleResourceIdentifierTest.php @@ -4,6 +4,7 @@ use JsonApiPhp\JsonApi\DataDocument; use JsonApiPhp\JsonApi\JsonApi; +use JsonApiPhp\JsonApi\Link\RelatedLink; use JsonApiPhp\JsonApi\Link\SelfLink; use JsonApiPhp\JsonApi\Meta; use JsonApiPhp\JsonApi\ResourceIdentifier; @@ -17,13 +18,13 @@ public function testMinimalDocument() ' { "data": { - "type": "apples", + "type": "companies", "id": "1" } } ', new DataDocument( - new ResourceIdentifier('apples', '1') + new ResourceIdentifier('companies', '1') ) ); } @@ -34,7 +35,7 @@ public function testExtendedDocument() ' { "data": { - "type": "apples", + "type": "companies", "id": "1", "meta": { "apple_meta": "foo", @@ -42,7 +43,8 @@ public function testExtendedDocument() } }, "links": { - "self": "/apples/1" + "self": "/books/123/relationships/publisher", + "related": "/books/123/publisher" }, "jsonapi": { "version": "1.0" @@ -52,12 +54,13 @@ public function testExtendedDocument() ', new DataDocument( new ResourceIdentifier( - 'apples', + 'companies', '1', new Meta('apple_meta', 'foo'), new Meta('bar', [42]) ), - new SelfLink('/apples/1'), + new SelfLink('/books/123/relationships/publisher'), + new RelatedLink('/books/123/publisher'), new JsonApi(), new Meta('document_meta', 'bar') ) From fcecfd38ee5ea58885cfb70e6033eb3983c4fc10 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?The=20=D0=9A=D0=BE=D0=BD=D1=8C?= Date: Mon, 12 Oct 2020 17:41:38 -0700 Subject: [PATCH 09/12] NewResourceObject to allow omitting id in resources to-be-created (#108) --- CHANGELOG.md | 9 +- README.md | 1 + src/Internal/Attachable.php | 1 + src/Internal/BaseResource.php | 61 ++++++++++ src/Internal/PrimaryData.php | 2 +- src/NewResourceObject.php | 20 ++++ src/ResourceObject.php | 31 +---- test/NewResourceObjectTest.php | 207 +++++++++++++++++++++++++++++++++ 8 files changed, 302 insertions(+), 30 deletions(-) create mode 100644 src/Internal/BaseResource.php create mode 100644 src/NewResourceObject.php create mode 100644 test/NewResourceObjectTest.php diff --git a/CHANGELOG.md b/CHANGELOG.md index 3f4bc42..9b5bc97 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,13 +6,17 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [2.2.0] - 2020-10-12 +### Added +- `NewResourceObject` to allow omitting `id` in resources to-be-created (#108) + ## [2.1.2] - 2020-03-16 ### Fixed - Related links must be allowed inside relationship documents (#104) ## [2.1.1] - 2019-12-19 ### Fixed -- ResourceIdentifier does not allow multiple meta members (#99) +- `ResourceIdentifier` does not allow multiple meta members (#99) ## [2.1.0] - 2019-02-25 ### Fixed @@ -26,7 +30,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - v2 initial release -[Unreleased]: https://github.com/json-api-php/json-api/compare/2.1.2...HEAD +[Unreleased]: https://github.com/json-api-php/json-api/compare/2.2.0...HEAD +[2.2.0]: https://github.com/json-api-php/json-api/compare/2.1.2...2.2.0 [2.1.2]: https://github.com/json-api-php/json-api/compare/2.1.1...2.1.2 [2.1.1]: https://github.com/json-api-php/json-api/compare/2.1.0...2.1.1 [2.1.0]: https://github.com/json-api-php/json-api/compare/2.0.1...2.1.0 diff --git a/README.md b/README.md index 6909798..2272090 100644 --- a/README.md +++ b/README.md @@ -70,6 +70,7 @@ The library API and use-cases are expressed in a comprehensive suite of tests. - [with null data](./test/DataDocument/NullDataTest.php) - [with multiple Resource Objects](./test/DataDocument/ManyResourceObjectsTest.php) - [with multiple Resource Identifiers](./test/DataDocument/ManyResourceIdentifiersTest.php) + - [with a new Resource (no id)](./test/NewResourceObjectTest.php) - [Compound Documents](./test/CompoundDocumentTest.php) - [Error Documents](./test/ErrorDocumentTest.php) - [Meta Documents (containing neither data nor errors)](./test/MetaDocumentTest.php) diff --git a/src/Internal/Attachable.php b/src/Internal/Attachable.php index 0178295..f11bbba 100644 --- a/src/Internal/Attachable.php +++ b/src/Internal/Attachable.php @@ -8,6 +8,7 @@ interface Attachable { /** + * Adds this object's data to $o * @param object $o * @internal */ diff --git a/src/Internal/BaseResource.php b/src/Internal/BaseResource.php new file mode 100644 index 0000000..48e8635 --- /dev/null +++ b/src/Internal/BaseResource.php @@ -0,0 +1,61 @@ +obj = (object) ['type' => $type]; + $this->type = $type; + + $this->addMembers(...$members); + } + + /** + * @param ResourceMember ...$members + * @internal + */ + protected function addMembers(ResourceMember ...$members): void + { + $fields = []; + foreach ($members as $member) { + if ($member instanceof Identifier) { + $member->registerIn($this->registry); + } + if ($member instanceof ResourceField) { + $name = $member->name(); + if (isset($fields[$name])) { + throw new \LogicException("Field '$name' already exists'"); + } + $fields[$name] = true; + } + $member->attachTo($this->obj); + } + } + + /** + * @param object $o + * @internal + */ + public function attachTo($o): void + { + $o->data = $this->obj; + } +} diff --git a/src/Internal/PrimaryData.php b/src/Internal/PrimaryData.php index aeeb7ad..c15b956 100644 --- a/src/Internal/PrimaryData.php +++ b/src/Internal/PrimaryData.php @@ -5,6 +5,6 @@ /** * @internal */ -interface PrimaryData extends Attachable, Identifier +interface PrimaryData extends Attachable { } diff --git a/src/NewResourceObject.php b/src/NewResourceObject.php new file mode 100644 index 0000000..0f54e5b --- /dev/null +++ b/src/NewResourceObject.php @@ -0,0 +1,20 @@ +obj = (object) ['type' => $type, 'id' => $id]; - $fields = []; - foreach ($members as $member) { - if ($member instanceof Identifier) { - $member->registerIn($this->registry); - } - if ($member instanceof ResourceField) { - $name = $member->name(); - if (isset($fields[$name])) { - throw new \LogicException("Field '$name' already exists'"); - } - $fields[$name] = true; - } - $member->attachTo($this->obj); - } + parent::__construct($type, ...$members); + $this->obj->id = $id; $this->type = $type; $this->id = $id; } diff --git a/test/NewResourceObjectTest.php b/test/NewResourceObjectTest.php new file mode 100644 index 0000000..6182ad9 --- /dev/null +++ b/test/NewResourceObjectTest.php @@ -0,0 +1,207 @@ +assertEncodesTo( + ' + { + "data": { + "type": "apples", + "attributes": { + "title": "Rails is Omakase" + }, + "meta": {"foo": "bar"}, + "relationships": { + "author": { + "meta": {"foo": "bar"}, + "data": null + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'apples', + new Meta('foo', 'bar'), + new Attribute('title', 'Rails is Omakase'), + new ToNull( + 'author', + new Meta('foo', 'bar') + ) + ) + ) + ); + } + + public function testRelationshipWithSingleIdLinkage() + { + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "relationships": { + "content": { + "data": {"type": "apples", "id": "1"} + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'basket', + new ToOne('content', new ResourceIdentifier('apples', '1')) + ) + ) + ); + } + + public function testRelationshipWithMultiIdLinkage() + { + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "relationships": { + "content": { + "data": [{ + "type": "apples", + "id": "1" + },{ + "type": "pears", + "id": "2" + }] + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'basket', + new ToMany( + 'content', + new ResourceIdentifierCollection( + new ResourceIdentifier('apples', '1'), + new ResourceIdentifier('pears', '2') + ) + ) + ) + ) + ); + } + + public function testRelationshipWithEmptyMultiIdLinkage() + { + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "relationships": { + "content": { + "data": [] + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'basket', + new ToMany('content', new ResourceIdentifierCollection()) + ) + ) + ); + } + + public function testRelationshipWithNoData() + { + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "relationships": { + "empty": { + "links": { + "related": "/foo" + } + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'basket', + new EmptyRelationship('empty', new RelatedLink('/foo')) + ) + ) + ); + + $this->assertEncodesTo( + ' + { + "data": { + "type": "basket", + "relationships": { + "empty": { + "links": { + "related": "/foo", + "self": "/bar" + }, + "meta": { + "foo": "bar" + } + } + } + } + } + ', + new DataDocument( + new NewResourceObject( + 'basket', + new EmptyRelationship('empty', new RelatedLink('/foo'), new SelfLink('/bar'), new Meta('foo', 'bar')) + ) + ) + ); + } + + public function testResourceFieldsMustBeUnique() + { + $this->expectException(\LogicException::class); + $this->expectExceptionMessage("Field 'foo' already exists"); + new NewResourceObject( + 'apples', + new Attribute('foo', 'bar'), + new ToOne('foo', new ResourceIdentifier('apples', '1')) + ); + } + + public function testNameValidation() + { + $this->expectException(\DomainException::class); + new NewResourceObject('invalid:id'); + } +} From 1bc2e2155cb9a91c43571fe5a7a9198dbf166766 Mon Sep 17 00:00:00 2001 From: Michal Vrchota Date: Wed, 27 Jul 2022 00:17:21 +0200 Subject: [PATCH 10/12] Suppress deprecated notices in PHP 8.1 (#111) --- src/CompoundDocument.php | 1 + src/DataDocument.php | 1 + src/ErrorDocument.php | 1 + src/MetaDocument.php | 1 + 4 files changed, 4 insertions(+) diff --git a/src/CompoundDocument.php b/src/CompoundDocument.php index 7e84887..a01c84d 100644 --- a/src/CompoundDocument.php +++ b/src/CompoundDocument.php @@ -19,6 +19,7 @@ public function __construct(PrimaryData $data, Included $included, DataDocumentM $this->doc = combine($data, $included, ...$members); } + #[\ReturnTypeWillChange] public function jsonSerialize() { return $this->doc; diff --git a/src/DataDocument.php b/src/DataDocument.php index d8b986d..3678afa 100644 --- a/src/DataDocument.php +++ b/src/DataDocument.php @@ -18,6 +18,7 @@ public function __construct(PrimaryData $data, DataDocumentMember ...$members) $this->value = combine($data, ...$members); } + #[\ReturnTypeWillChange] public function jsonSerialize() { return $this->value; diff --git a/src/ErrorDocument.php b/src/ErrorDocument.php index 4d4fe73..554c8d5 100644 --- a/src/ErrorDocument.php +++ b/src/ErrorDocument.php @@ -20,6 +20,7 @@ public function __construct(ErrorDocumentMember ...$members) } } + #[\ReturnTypeWillChange] public function jsonSerialize() { return $this->obj; diff --git a/src/MetaDocument.php b/src/MetaDocument.php index 72ca320..45199c9 100644 --- a/src/MetaDocument.php +++ b/src/MetaDocument.php @@ -13,6 +13,7 @@ public function __construct(Meta $meta, MetaDocumentMember ...$members) $this->doc = combine($meta, ...$members); } + #[\ReturnTypeWillChange] public function jsonSerialize() { return $this->doc; From ba2c50d7497abd127a7e1fc1373b4c9f38d28b9d Mon Sep 17 00:00:00 2001 From: Kara Date: Tue, 26 Jul 2022 17:47:30 -0700 Subject: [PATCH 11/12] Create php.yml --- .github/workflows/php.yml | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 .github/workflows/php.yml diff --git a/.github/workflows/php.yml b/.github/workflows/php.yml new file mode 100644 index 0000000..eae93ab --- /dev/null +++ b/.github/workflows/php.yml @@ -0,0 +1,36 @@ +name: PHP Composer + +on: + push: + branches: [ "master" ] + pull_request: + branches: [ "master" ] + +permissions: + contents: read + +jobs: + build: + + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v3 + + - name: Validate composer.json and composer.lock + run: composer validate --strict + + - name: Cache Composer packages + id: composer-cache + uses: actions/cache@v3 + with: + path: vendor + key: ${{ runner.os }}-php-${{ hashFiles('**/composer.lock') }} + restore-keys: | + ${{ runner.os }}-php- + + - name: Install dependencies + run: composer install --prefer-dist --no-progress + + - name: Run test suite + run: composer run-script test From e34075c8335cb3512e38059c13a9a37217d3a178 Mon Sep 17 00:00:00 2001 From: Kara Date: Tue, 26 Jul 2022 18:10:35 -0700 Subject: [PATCH 12/12] PHP 8 (#112) --- .gitignore | 2 + .php-cs-fixer.php | 16 ++++ .php_cs.dist | 53 ------------- .travis.yml | 14 ---- CHANGELOG.md | 11 ++- composer.json | 8 +- examples/compound_doc.php | 4 +- examples/simple_doc.php | 4 +- phpunit.xml.dist | 28 +++---- src/Attribute.php | 16 ++-- src/CompoundDocument.php | 18 ++--- src/DataDocument.php | 17 ++--- src/EmptyRelationship.php | 20 ++--- src/Error.php | 17 ++--- src/Error/Code.php | 19 ++--- src/Error/Detail.php | 19 ++--- src/Error/Id.php | 19 ++--- src/Error/SourceParameter.php | 20 ++--- src/Error/SourcePointer.php | 17 ++--- src/Error/Status.php | 19 ++--- src/Error/Title.php | 19 ++--- src/ErrorDocument.php | 19 +++-- src/Included.php | 36 +++------ src/Internal/Attachable.php | 9 ++- src/Internal/BaseResource.php | 37 ++++----- src/Internal/Collection.php | 7 +- src/Internal/DataDocumentMember.php | 7 +- src/Internal/ErrorDocumentMember.php | 7 +- src/Internal/ErrorMember.php | 7 +- src/Internal/Identifier.php | 12 +-- src/Internal/LinkTrait.php | 17 ++--- src/Internal/MetaDocumentMember.php | 7 +- src/Internal/PaginationLink.php | 4 +- src/Internal/PrimaryData.php | 7 +- src/Internal/RelationshipMember.php | 7 +- src/Internal/ResourceField.php | 4 +- src/Internal/ResourceFieldTrait.php | 23 +++--- src/Internal/ResourceMember.php | 7 +- src/Internal/ToManyMember.php | 7 +- src/Internal/ToOneMember.php | 7 +- src/JsonApi.php | 21 +++-- src/Link/AboutLink.php | 13 ++-- src/Link/FirstLink.php | 13 ++-- src/Link/LastLink.php | 13 ++-- src/Link/NextLink.php | 13 ++-- src/Link/PrevLink.php | 13 ++-- src/Link/RelatedLink.php | 13 ++-- src/Link/SelfLink.php | 13 ++-- src/Meta.php | 49 ++++++------ src/MetaDocument.php | 17 ++--- src/NewResourceObject.php | 10 +-- src/NullData.php | 14 ++-- src/PaginatedCollection.php | 33 ++------ src/Pagination.php | 12 ++- src/ResourceCollection.php | 22 ++---- src/ResourceIdentifier.php | 39 +++------- src/ResourceIdentifierCollection.php | 22 ++---- src/ResourceObject.php | 39 +++------- src/ToMany.php | 30 +++----- src/ToNull.php | 16 ++-- src/ToOne.php | 26 ++----- src/functions.php | 20 +++-- test/BaseTestCase.php | 10 +-- test/CompoundDocumentTest.php | 76 ++----------------- .../ManyResourceIdentifiersTest.php | 13 ++-- test/DataDocument/ManyResourceObjectsTest.php | 13 ++-- test/DataDocument/NullDataTest.php | 10 +-- .../SingleResourceIdentifierTest.php | 13 ++-- .../DataDocument/SingleResourceObjectTest.php | 13 ++-- test/ErrorDocumentTest.php | 13 ++-- test/ExamplesTest.php | 10 +-- test/JsonApiTest.php | 10 +-- test/LinkObjectTest.php | 10 +-- test/MetaDocumentTest.php | 10 +-- test/MetaTest.php | 10 +-- test/NewResourceObjectTest.php | 28 +++---- test/PaginationTest.php | 13 ++-- test/ResourceIdentifierTest.php | 7 +- test/ResourceObjectTest.php | 49 +++++------- test/benchmarks/compound10k.php | 4 +- 80 files changed, 538 insertions(+), 826 deletions(-) create mode 100644 .php-cs-fixer.php delete mode 100644 .php_cs.dist delete mode 100644 .travis.yml diff --git a/.gitignore b/.gitignore index f22a32d..c195581 100644 --- a/.gitignore +++ b/.gitignore @@ -3,3 +3,5 @@ composer.phar /vendor/ /composer.lock /.php_cs.cache +.php-cs-fixer.cache +.phpunit.result.cache diff --git a/.php-cs-fixer.php b/.php-cs-fixer.php new file mode 100644 index 0000000..acd1414 --- /dev/null +++ b/.php-cs-fixer.php @@ -0,0 +1,16 @@ +exclude('somedir') + ->notPath('src/Symfony/Component/Translation/Tests/fixtures/resources.php') + ->in(__DIR__); + +$config = new PhpCsFixer\Config(); +return $config->setRules([ + '@PSR12' => true, + 'array_syntax' => ['syntax' => 'short'], + 'braces' => [ + 'allow_single_line_closure' => true, + 'position_after_functions_and_oop_constructs' => 'same'], +]) + ->setFinder($finder); \ No newline at end of file diff --git a/.php_cs.dist b/.php_cs.dist deleted file mode 100644 index 06b82a3..0000000 --- a/.php_cs.dist +++ /dev/null @@ -1,53 +0,0 @@ -files() - ->name('*.php') - ->in(__DIR__ . '/examples') - ->in(__DIR__ . '/src') - ->in(__DIR__ . '/test'); -return PhpCsFixer\Config::create() - ->setUsingCache(true) - ->setRiskyAllowed(true) - ->setRules([ - '@PSR2' => true, - 'array_syntax' => ['syntax' => 'short'], - 'binary_operator_spaces' => true, - 'cast_spaces' => true, - 'concat_space' => true, - 'declare_strict_types' => true, - 'include' => true, - 'is_null' => true, - 'lowercase_cast' => true, - 'mb_str_functions' => true, - 'method_separation' => true, - 'native_function_casing' => true, - 'no_blank_lines_after_class_opening' => true, - 'no_blank_lines_after_phpdoc' => true, - 'no_empty_statement' => true, - 'no_extra_consecutive_blank_lines' => true, - 'no_leading_import_slash' => true, - 'no_leading_namespace_whitespace' => true, - 'no_trailing_comma_in_singleline_array' => true, - 'no_unused_imports' => true, - 'no_whitespace_in_blank_line' => true, - 'object_operator_without_whitespace' => true, - 'ordered_imports' => true, - 'phpdoc_align' => true, - 'phpdoc_indent' => true, - 'phpdoc_no_access' => true, - 'phpdoc_no_package' => true, - 'phpdoc_order' => true, - 'phpdoc_scalar' => true, - 'phpdoc_trim' => true, - 'phpdoc_types' => true, - 'psr0' => true, - 'short_scalar_cast' => true, - 'single_blank_line_before_namespace' => true, - 'single_quote' => true, - 'standardize_not_equals' => true, - 'strict_comparison' => true, - 'ternary_operator_spaces' => true, - 'trailing_comma_in_multiline_array' => true, - 'whitespace_after_comma_in_array' => true, - ]) - ->setFinder($finder); diff --git a/.travis.yml b/.travis.yml deleted file mode 100644 index b2a600d..0000000 --- a/.travis.yml +++ /dev/null @@ -1,14 +0,0 @@ -language: php -php: - - '7.1' - - '7.2' - - '7.3' - - '7.4' - -before_script: - - composer install - - mkdir build/logs -p - -script: - - ./vendor/bin/php-cs-fixer fix -v --dry-run - - ./vendor/bin/phpunit --coverage-clover build/logs/clover.xml diff --git a/CHANGELOG.md b/CHANGELOG.md index 9b5bc97..22fd9fe 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,14 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ## [Unreleased] +## [3.0.0] - 2022-07-26 +### Changed +- The package is migrated to PHP 8.1 + +### Removed +- Support for PHP 7 and older versions +- Compound document validation logic is dropped + ## [2.2.0] - 2020-10-12 ### Added - `NewResourceObject` to allow omitting `id` in resources to-be-created (#108) @@ -30,7 +38,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - v2 initial release -[Unreleased]: https://github.com/json-api-php/json-api/compare/2.2.0...HEAD +[Unreleased]: https://github.com/json-api-php/json-api/compare/3.0.0...HEAD +[3.0.0]: https://github.com/json-api-php/json-api/compare/2.2.2...3.0.0 [2.2.0]: https://github.com/json-api-php/json-api/compare/2.1.2...2.2.0 [2.1.2]: https://github.com/json-api-php/json-api/compare/2.1.1...2.1.2 [2.1.1]: https://github.com/json-api-php/json-api/compare/2.1.0...2.1.1 diff --git a/composer.json b/composer.json index ffcd77e..5a7e2b9 100644 --- a/composer.json +++ b/composer.json @@ -1,6 +1,6 @@ { "name": "json-api-php/json-api", - "description": "An attempt to express JSON API specs (jsonapi.org) in object-oriented way as a set of PHP 7 classes", + "description": "JSON API specs (jsonapi.org) as a set of PHP classes", "type": "library", "prefer-stable": true, "license": "MIT", @@ -11,12 +11,12 @@ } ], "require": { - "php": ">=7.1", + "php": ">=8.1", "ext-json": "*" }, "require-dev": { - "phpunit/phpunit": "^7.0||^8.0", - "friendsofphp/php-cs-fixer": "^2.13" + "phpunit/phpunit": "^9.0", + "friendsofphp/php-cs-fixer": "^3.9" }, "autoload": { "psr-4": { diff --git a/examples/compound_doc.php b/examples/compound_doc.php index c9feae0..1d0cbbb 100644 --- a/examples/compound_doc.php +++ b/examples/compound_doc.php @@ -1,4 +1,6 @@ - - - - - ./test - - - - - ./src/ - - + + + + + ./src/ + + + + + ./test + + diff --git a/src/Attribute.php b/src/Attribute.php index d45834c..8276746 100644 --- a/src/Attribute.php +++ b/src/Attribute.php @@ -1,4 +1,6 @@ -validateFieldName($name); $this->name = $name; $this->val = $val; @@ -24,8 +25,7 @@ public function __construct(string $name, $val) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { child($o, 'attributes')->{$this->name} = $this->val; } } diff --git a/src/CompoundDocument.php b/src/CompoundDocument.php index a01c84d..7a15492 100644 --- a/src/CompoundDocument.php +++ b/src/CompoundDocument.php @@ -1,27 +1,25 @@ -validateLinkage($data); + public function __construct(PrimaryData $data, Included $included, DataDocumentMember ...$members) { $this->doc = combine($data, $included, ...$members); } - #[\ReturnTypeWillChange] - public function jsonSerialize() - { + public function jsonSerialize(): object { return $this->doc; } } diff --git a/src/DataDocument.php b/src/DataDocument.php index 3678afa..20d0e7c 100644 --- a/src/DataDocument.php +++ b/src/DataDocument.php @@ -1,26 +1,25 @@ -value = combine($data, ...$members); } - #[\ReturnTypeWillChange] - public function jsonSerialize() - { + public function jsonSerialize(): object { return $this->value; } } diff --git a/src/EmptyRelationship.php b/src/EmptyRelationship.php index 659a9df..2c123bb 100644 --- a/src/EmptyRelationship.php +++ b/src/EmptyRelationship.php @@ -1,4 +1,6 @@ -name = $name; + public function __construct( + private readonly string $name, + RelationshipMember $member, + RelationshipMember ...$members + ) { $this->obj = combine($member, ...$members); } @@ -25,8 +28,7 @@ public function __construct(string $name, RelationshipMember $member, Relationsh * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { child($o, 'relationships')->{$this->name} = $this->obj; } } diff --git a/src/Error.php b/src/Error.php index ba0e3a0..8a222fe 100644 --- a/src/Error.php +++ b/src/Error.php @@ -1,4 +1,6 @@ -error = (object) []; + public function __construct(ErrorMember ...$members) { + $this->error = (object)[]; foreach ($members as $member) { $member->attachTo($this->error); } @@ -25,8 +25,7 @@ public function __construct(ErrorMember ...$members) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->errors[] = $this->error; } } diff --git a/src/Error/Code.php b/src/Error/Code.php index a03b827..40455dd 100644 --- a/src/Error/Code.php +++ b/src/Error/Code.php @@ -1,30 +1,23 @@ -code = $code; + public function __construct(private readonly string $code) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->code = $this->code; } } diff --git a/src/Error/Detail.php b/src/Error/Detail.php index f4d169c..217c43d 100644 --- a/src/Error/Detail.php +++ b/src/Error/Detail.php @@ -1,30 +1,23 @@ -detail = $detail; + public function __construct(private readonly string $detail) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->detail = $this->detail; } } diff --git a/src/Error/Id.php b/src/Error/Id.php index 11c5b10..371884f 100644 --- a/src/Error/Id.php +++ b/src/Error/Id.php @@ -1,30 +1,23 @@ -id = $id; + public function __construct(private readonly string $id) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->id = $this->id; } } diff --git a/src/Error/SourceParameter.php b/src/Error/SourceParameter.php index 3e48461..d344d64 100644 --- a/src/Error/SourceParameter.php +++ b/src/Error/SourceParameter.php @@ -1,31 +1,25 @@ -parameter = $parameter; + public function __construct(private readonly string $parameter) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { child($o, 'source')->parameter = $this->parameter; } } diff --git a/src/Error/SourcePointer.php b/src/Error/SourcePointer.php index d6cecaa..c33d0b1 100644 --- a/src/Error/SourcePointer.php +++ b/src/Error/SourcePointer.php @@ -1,28 +1,25 @@ -pointer = $pointer; + public function __construct(private readonly string $pointer) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { child($o, 'source')->pointer = $this->pointer; } } diff --git a/src/Error/Status.php b/src/Error/Status.php index 6be53aa..2083373 100644 --- a/src/Error/Status.php +++ b/src/Error/Status.php @@ -1,30 +1,23 @@ -status = $status; + public function __construct(private readonly string $status) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->status = $this->status; } } diff --git a/src/Error/Title.php b/src/Error/Title.php index 2226f53..1352eb5 100644 --- a/src/Error/Title.php +++ b/src/Error/Title.php @@ -1,31 +1,24 @@ -title = $title; + public function __construct(private readonly string $title) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->title = $this->title; } } diff --git a/src/ErrorDocument.php b/src/ErrorDocument.php index 554c8d5..4cb70b5 100644 --- a/src/ErrorDocument.php +++ b/src/ErrorDocument.php @@ -1,28 +1,27 @@ -obj = (object) []; + public function __construct(ErrorDocumentMember ...$members) { + $this->obj = (object)[]; foreach ($members as $member) { $member->attachTo($this->obj); } } - #[\ReturnTypeWillChange] - public function jsonSerialize() - { + public function jsonSerialize(): object { return $this->obj; } } diff --git a/src/Included.php b/src/Included.php index 5b2dbd4..96a1edb 100644 --- a/src/Included.php +++ b/src/Included.php @@ -1,40 +1,29 @@ -key(); if (isset($this->resources[$key])) { - throw new \LogicException("Resource $resource is already included"); + throw new LogicException("Resource $resource is already included"); } $this->resources[$key] = $resource; - $resource->registerIn($this->identifiers); - } - } - - public function validateLinkage(PrimaryData $data): void - { - $registry = []; - $data->registerIn($registry); - foreach ($this->resources as $resource) { - if (isset($registry[$resource->key()]) || isset($this->identifiers[$resource->key()])) { - continue; - } - throw new \LogicException('Full linkage required for '.$resource); } } @@ -42,8 +31,7 @@ public function validateLinkage(PrimaryData $data): void * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { foreach ($this->resources as $resource) { $resource->attachAsIncludedTo($o); } diff --git a/src/Internal/Attachable.php b/src/Internal/Attachable.php index f11bbba..01de494 100644 --- a/src/Internal/Attachable.php +++ b/src/Internal/Attachable.php @@ -1,16 +1,17 @@ -obj = (object) ['type' => $type]; - $this->type = $type; + $this->obj = (object)['type' => $type]; $this->addMembers(...$members); } @@ -32,17 +30,13 @@ public function __construct(string $type, ResourceMember ...$members) * @param ResourceMember ...$members * @internal */ - protected function addMembers(ResourceMember ...$members): void - { + protected function addMembers(ResourceMember ...$members): void { $fields = []; foreach ($members as $member) { - if ($member instanceof Identifier) { - $member->registerIn($this->registry); - } if ($member instanceof ResourceField) { $name = $member->name(); if (isset($fields[$name])) { - throw new \LogicException("Field '$name' already exists'"); + throw new LogicException("Field '$name' already exists'"); } $fields[$name] = true; } @@ -54,8 +48,7 @@ protected function addMembers(ResourceMember ...$members): void * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->data = $this->obj; } } diff --git a/src/Internal/Collection.php b/src/Internal/Collection.php index e0e73d0..cd8b8d6 100644 --- a/src/Internal/Collection.php +++ b/src/Internal/Collection.php @@ -1,7 +1,8 @@ -link = (object) ['href' => $url]; + $this->link = (object)['href' => $url]; foreach ($metas as $meta) { $meta->attachTo($this->link); } diff --git a/src/Internal/MetaDocumentMember.php b/src/Internal/MetaDocumentMember.php index 27aded5..e204a70 100644 --- a/src/Internal/MetaDocumentMember.php +++ b/src/Internal/MetaDocumentMember.php @@ -1,10 +1,11 @@ -name; } } diff --git a/src/Internal/ResourceMember.php b/src/Internal/ResourceMember.php index b20e3b0..ba4918d 100644 --- a/src/Internal/ResourceMember.php +++ b/src/Internal/ResourceMember.php @@ -1,10 +1,11 @@ -obj = (object) [ + public function __construct(string $version = '1.0', Meta $meta = null) { + $this->obj = (object)[ 'version' => $version, ]; - if ($meta) { - $meta->attachTo($this->obj); - } + $meta?->attachTo($this->obj); } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->jsonapi = $this->obj; } } diff --git a/src/Link/AboutLink.php b/src/Link/AboutLink.php index e317ca8..fdafefd 100644 --- a/src/Link/AboutLink.php +++ b/src/Link/AboutLink.php @@ -1,21 +1,22 @@ -about = $this->link; } } diff --git a/src/Link/FirstLink.php b/src/Link/FirstLink.php index af13251..dfc5b6a 100644 --- a/src/Link/FirstLink.php +++ b/src/Link/FirstLink.php @@ -1,21 +1,22 @@ -first = $this->link; } } diff --git a/src/Link/LastLink.php b/src/Link/LastLink.php index 037b228..a2215b8 100644 --- a/src/Link/LastLink.php +++ b/src/Link/LastLink.php @@ -1,21 +1,22 @@ -last = $this->link; } } diff --git a/src/Link/NextLink.php b/src/Link/NextLink.php index c2ba366..082fbcc 100644 --- a/src/Link/NextLink.php +++ b/src/Link/NextLink.php @@ -1,21 +1,22 @@ -next = $this->link; } } diff --git a/src/Link/PrevLink.php b/src/Link/PrevLink.php index b612450..d38d025 100644 --- a/src/Link/PrevLink.php +++ b/src/Link/PrevLink.php @@ -1,21 +1,22 @@ -prev = $this->link; } } diff --git a/src/Link/RelatedLink.php b/src/Link/RelatedLink.php index 1def33c..501c2ec 100644 --- a/src/Link/RelatedLink.php +++ b/src/Link/RelatedLink.php @@ -1,22 +1,23 @@ -related = $this->link; } } diff --git a/src/Link/SelfLink.php b/src/Link/SelfLink.php index fde232b..0168cb1 100644 --- a/src/Link/SelfLink.php +++ b/src/Link/SelfLink.php @@ -1,23 +1,24 @@ -self = $this->link; } } diff --git a/src/Meta.php b/src/Meta.php index 758c3bb..ebec4dc 100644 --- a/src/Meta.php +++ b/src/Meta.php @@ -1,7 +1,10 @@ -key = $key; - $this->value = $value; - } - /** - * @param object $o - * @internal - */ - public function attachTo($o): void - { - child($o, 'meta')->{$this->key} = $this->value; + /** + * @param object $o + * @internal + */ + public function attachTo(object $o): void { + child($o, 'meta')->{$this->key} = $this->value; + } } -} diff --git a/src/MetaDocument.php b/src/MetaDocument.php index 45199c9..14f0334 100644 --- a/src/MetaDocument.php +++ b/src/MetaDocument.php @@ -1,21 +1,20 @@ -doc = combine($meta, ...$members); } - #[\ReturnTypeWillChange] - public function jsonSerialize() - { + public function jsonSerialize(): object { return $this->doc; } } diff --git a/src/NewResourceObject.php b/src/NewResourceObject.php index 0f54e5b..44364f1 100644 --- a/src/NewResourceObject.php +++ b/src/NewResourceObject.php @@ -1,4 +1,6 @@ -data = null; } - - public function registerIn(array &$registry): void - { - } } diff --git a/src/PaginatedCollection.php b/src/PaginatedCollection.php index e59c66f..ffc9050 100644 --- a/src/PaginatedCollection.php +++ b/src/PaginatedCollection.php @@ -1,43 +1,22 @@ -pagination = $pagination; - $this->collection = $collection; +final class PaginatedCollection implements PrimaryData { + public function __construct(private readonly Pagination $pagination, private readonly Collection $collection) { } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $this->collection->attachTo($o); $this->pagination->attachTo($o); } - - /** - * @param array $registry - * @internal - */ - public function registerIn(array &$registry): void - { - $this->collection->registerIn($registry); - } } diff --git a/src/Pagination.php b/src/Pagination.php index 674f375..dc2c642 100644 --- a/src/Pagination.php +++ b/src/Pagination.php @@ -1,4 +1,5 @@ links = $links; } @@ -22,8 +21,7 @@ public function __construct(PaginationLink ...$links) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { foreach ($this->links as $link) { $link->attachTo($o); } diff --git a/src/ResourceCollection.php b/src/ResourceCollection.php index f337ad5..592dd21 100644 --- a/src/ResourceCollection.php +++ b/src/ResourceCollection.php @@ -1,19 +1,19 @@ -resources = $resources; } @@ -21,18 +21,10 @@ public function __construct(ResourceObject ...$resources) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->data = []; foreach ($this->resources as $resource) { $resource->attachToCollection($o); } } - - public function registerIn(array &$registry): void - { - foreach ($this->resources as $resource) { - $resource->registerIn($registry); - } - } } diff --git a/src/ResourceIdentifier.php b/src/ResourceIdentifier.php index dff34f8..cf1cf88 100644 --- a/src/ResourceIdentifier.php +++ b/src/ResourceIdentifier.php @@ -1,44 +1,33 @@ -obj = (object) [ + $this->obj = (object)[ 'type' => $type, 'id' => $id, ]; foreach ($metas as $meta) { $meta->attachTo($this->obj); } - $this->type = $type; - $this->id = $id; } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->data = $this->obj; } @@ -46,13 +35,7 @@ public function attachTo($o): void * @param object $o * @internal */ - public function attachToCollection($o): void - { + public function attachToCollection(object $o): void { $o->data[] = $this->obj; } - - public function registerIn(array &$registry): void - { - $registry[compositeKey($this->type, $this->id)] = true; - } } diff --git a/src/ResourceIdentifierCollection.php b/src/ResourceIdentifierCollection.php index 84b8887..794789e 100644 --- a/src/ResourceIdentifierCollection.php +++ b/src/ResourceIdentifierCollection.php @@ -1,19 +1,19 @@ -identifiers = $identifiers; } @@ -21,18 +21,10 @@ public function __construct(ResourceIdentifier ...$identifiers) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->data = []; foreach ($this->identifiers as $identifier) { $identifier->attachToCollection($o); } } - - public function registerIn(array &$registry): void - { - foreach ($this->identifiers as $identifier) { - $identifier->registerIn($registry); - } - } } diff --git a/src/ResourceObject.php b/src/ResourceObject.php index 416d423..f65d575 100644 --- a/src/ResourceObject.php +++ b/src/ResourceObject.php @@ -1,4 +1,6 @@ -obj->id = $id; $this->type = $type; - $this->id = $id; } - public function identifier(): ResourceIdentifier - { + public function identifier(): ResourceIdentifier { return new ResourceIdentifier($this->type, $this->id); } - public function key(): string - { + public function key(): string { return compositeKey($this->type, $this->id); } - public function registerIn(array &$registry): void - { - $registry = array_merge($registry, $this->registry); - } - /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $o->data = $this->obj; } /** * @param object $o */ - public function attachAsIncludedTo($o): void - { + public function attachAsIncludedTo(object $o): void { $o->included[] = $this->obj; } @@ -57,13 +42,11 @@ public function attachAsIncludedTo($o): void * @param object $o * @internal */ - public function attachToCollection($o): void - { + public function attachToCollection(object $o): void { $o->data[] = $this->obj; } - public function __toString(): string - { + public function __toString(): string { return $this->key(); } } diff --git a/src/ToMany.php b/src/ToMany.php index c0a7278..afe4987 100644 --- a/src/ToMany.php +++ b/src/ToMany.php @@ -1,4 +1,6 @@ -validateFieldName($name); $this->name = $name; $this->members = $members; - $this->collection = $collection; } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $rel = child(child($o, 'relationships'), $this->name); $rel->data = []; $this->collection->attachTo($rel); @@ -40,9 +39,4 @@ public function attachTo($o): void $member->attachTo($rel); } } - - public function registerIn(array &$registry): void - { - $this->collection->registerIn($registry); - } } diff --git a/src/ToNull.php b/src/ToNull.php index 8b2d3f1..cbaec93 100644 --- a/src/ToNull.php +++ b/src/ToNull.php @@ -1,4 +1,6 @@ -validateFieldName($name); $this->name = $name; $this->members = $members; @@ -25,8 +26,7 @@ public function __construct(string $name, ToOneMember ...$members) * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo(object $o): void { $obj = combine(...$this->members); $obj->data = null; child($o, 'relationships')->{$this->name} = $obj; diff --git a/src/ToOne.php b/src/ToOne.php index dbbd7ac..eb86853 100644 --- a/src/ToOne.php +++ b/src/ToOne.php @@ -1,4 +1,6 @@ -validateFieldName($name); $this->name = $name; $this->obj = combine($identifier, ...$members); - $this->identifier = $identifier; } /** * @param object $o * @internal */ - public function attachTo($o): void - { + public function attachTo($o): void { child($o, 'relationships')->{$this->name} = $this->obj; } - - public function registerIn(array &$registry): void - { - $this->identifier->registerIn($registry); - } } diff --git a/src/functions.php b/src/functions.php index df50e2d..5a08291 100644 --- a/src/functions.php +++ b/src/functions.php @@ -1,32 +1,30 @@ -attachTo($obj); } return $obj; } -function child($o, string $name) -{ +function child($o, string $name): mixed { if (!isset($o->{$name})) { - $o->{$name} = (object) []; + $o->{$name} = (object)[]; } return $o->{$name}; } -function isValidName(string $name): bool -{ +function isValidName(string $name): bool { return preg_match('/^(?=[^-_ ])[a-zA-Z0-9\x{0080}-\x{FFFF}-_ ]*(?<=[^-_ ])$/u', $name) === 1; } -function compositeKey(string $type, string $id): string -{ +function compositeKey(string $type, string $id): string { return "{$type}:{$id}"; } diff --git a/test/BaseTestCase.php b/test/BaseTestCase.php index eca3598..e649b2c 100644 --- a/test/BaseTestCase.php +++ b/test/BaseTestCase.php @@ -1,13 +1,13 @@ -expectException(\LogicException::class); - $this->expectExceptionMessage('Full linkage required for apples:1'); - $create_doc(); - } - - public function documentsWithoutFullLinkage(): array - { - $included = new Included(new ResourceObject('apples', '1')); - return [ - [ - function () use ($included) { - return new CompoundDocument(new NullData(), $included); - }, - ], - [ - function () use ($included) { - return new CompoundDocument(new ResourceCollection(), $included); - }, - ], - [ - function () use ($included) { - return new CompoundDocument(new ResourceIdentifier('oranges', '1'), $included); - }, - ], - [ - function () use ($included) { - return new CompoundDocument( - new ResourceIdentifierCollection( - new ResourceIdentifier('oranges', '1'), - new ResourceIdentifier('oranges', '1') - ), - $included - ); - }, - ], - [ - function () use ($included) { - return new CompoundDocument( - new ResourceCollection(new ResourceObject('oranges', '1'), new ResourceObject('oranges', '1')), - $included - ); - }, - ], - ]; - } - - public function testIncludedResourceMayBeIdentifiedByLinkageInPrimaryData() - { + public function testIncludedResourceMayBeIdentifiedByLinkageInPrimaryData() { $author = new ResourceObject('people', '9'); $article = new ResourceObject( 'articles', @@ -233,8 +175,7 @@ public function testIncludedResourceMayBeIdentifiedByLinkageInPrimaryData() $this->assertNotEmpty($doc); } - public function testIncludedResourceMayBeIdentifiedByAnotherLinkedResource() - { + public function testIncludedResourceMayBeIdentifiedByAnotherLinkedResource() { $writer = new ResourceObject('writers', '3', new Attribute('name', 'Eric Evans')); $book = new ResourceObject( 'books', @@ -254,8 +195,7 @@ public function testIncludedResourceMayBeIdentifiedByAnotherLinkedResource() /** * A compound document MUST NOT include more than one resource object for each type and id pair. */ - public function testCanNotBeManyIncludedResourcesWithEqualIdentifiers() - { + public function testCanNotBeManyIncludedResourcesWithEqualIdentifiers() { $this->expectException('LogicException'); $this->expectExceptionMessage('Resource apples:1 is already included'); $apple = new ResourceObject('apples', '1'); diff --git a/test/DataDocument/ManyResourceIdentifiersTest.php b/test/DataDocument/ManyResourceIdentifiersTest.php index eb12973..2d4728d 100644 --- a/test/DataDocument/ManyResourceIdentifiersTest.php +++ b/test/DataDocument/ManyResourceIdentifiersTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -26,8 +26,7 @@ public function testMinimalDocument() ); } - public function testExtendedDocument() - { + public function testExtendedDocument() { $this->assertEncodesTo( ' { diff --git a/test/DataDocument/ManyResourceObjectsTest.php b/test/DataDocument/ManyResourceObjectsTest.php index 54736e2..a555e0c 100644 --- a/test/DataDocument/ManyResourceObjectsTest.php +++ b/test/DataDocument/ManyResourceObjectsTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -28,8 +28,7 @@ public function testMinimalDocument() ); } - public function testExtendedDocument() - { + public function testExtendedDocument() { $this->assertEncodesTo( ' { diff --git a/test/DataDocument/NullDataTest.php b/test/DataDocument/NullDataTest.php index 05746cd..4bb759d 100644 --- a/test/DataDocument/NullDataTest.php +++ b/test/DataDocument/NullDataTest.php @@ -1,4 +1,5 @@ assertEncodesTo( ' { @@ -26,8 +25,7 @@ public function testMinimalDocument() ); } - public function testExtendedDocument() - { + public function testExtendedDocument() { $this->assertEncodesTo( ' { diff --git a/test/DataDocument/SingleResourceIdentifierTest.php b/test/DataDocument/SingleResourceIdentifierTest.php index 165a625..3eea202 100644 --- a/test/DataDocument/SingleResourceIdentifierTest.php +++ b/test/DataDocument/SingleResourceIdentifierTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -29,8 +29,7 @@ public function testMinimalDocument() ); } - public function testExtendedDocument() - { + public function testExtendedDocument() { $this->assertEncodesTo( ' { diff --git a/test/DataDocument/SingleResourceObjectTest.php b/test/DataDocument/SingleResourceObjectTest.php index dfa25a1..0d19dde 100644 --- a/test/DataDocument/SingleResourceObjectTest.php +++ b/test/DataDocument/SingleResourceObjectTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -29,8 +29,7 @@ public function testMinimalDocument() ); } - public function testExtendedDocument() - { + public function testExtendedDocument() { $this->assertEncodesTo( ' { diff --git a/test/ErrorDocumentTest.php b/test/ErrorDocumentTest.php index 9a9131d..cb0bc4c 100644 --- a/test/ErrorDocumentTest.php +++ b/test/ErrorDocumentTest.php @@ -1,4 +1,5 @@ assertEncodesTo( ' { @@ -36,8 +35,7 @@ public function testMinimalExample() ); } - public function testExtensiveExample() - { + public function testExtensiveExample() { $this->assertEncodesTo( ' { @@ -82,8 +80,7 @@ public function testExtensiveExample() ); } - public function testMultipleErrors() - { + public function testMultipleErrors() { $this->assertEncodesTo( ' { diff --git a/test/ExamplesTest.php b/test/ExamplesTest.php index ba7a1cf..7dc5da4 100644 --- a/test/ExamplesTest.php +++ b/test/ExamplesTest.php @@ -1,23 +1,21 @@ assertJson(`php $file`); } - public function examples() - { + public function examples() { return [ [__DIR__.'/../examples/compound_doc.php'], [__DIR__.'/../examples/simple_doc.php'], diff --git a/test/JsonApiTest.php b/test/JsonApiTest.php index 49c5982..8a5ce91 100644 --- a/test/JsonApiTest.php +++ b/test/JsonApiTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { diff --git a/test/LinkObjectTest.php b/test/LinkObjectTest.php index a69443c..00a9a78 100644 --- a/test/LinkObjectTest.php +++ b/test/LinkObjectTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( '{ "data": {"type": "apples", "id": "1"}, diff --git a/test/MetaDocumentTest.php b/test/MetaDocumentTest.php index 7893dae..1837f3e 100644 --- a/test/MetaDocumentTest.php +++ b/test/MetaDocumentTest.php @@ -1,4 +1,5 @@ assertEncodesTo( ' { @@ -29,8 +28,7 @@ public function testMetaDocument() /** * A meta document may contain jsonapi member */ - public function testMetaDocumentWithExtraMembers() - { + public function testMetaDocumentWithExtraMembers() { $this->assertEncodesTo( ' { diff --git a/test/MetaTest.php b/test/MetaTest.php index 67d3097..c8d8d93 100644 --- a/test/MetaTest.php +++ b/test/MetaTest.php @@ -1,14 +1,14 @@ -expectException(\DomainException::class); $this->expectExceptionMessage("Invalid character in a member name 'invalid:name'"); new Meta('invalid:name', '1'); diff --git a/test/NewResourceObjectTest.php b/test/NewResourceObjectTest.php index 6182ad9..a2fc94e 100644 --- a/test/NewResourceObjectTest.php +++ b/test/NewResourceObjectTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -51,8 +51,7 @@ public function testFullFledgedResourceObject() ); } - public function testRelationshipWithSingleIdLinkage() - { + public function testRelationshipWithSingleIdLinkage() { $this->assertEncodesTo( ' { @@ -75,8 +74,7 @@ public function testRelationshipWithSingleIdLinkage() ); } - public function testRelationshipWithMultiIdLinkage() - { + public function testRelationshipWithMultiIdLinkage() { $this->assertEncodesTo( ' { @@ -111,8 +109,7 @@ public function testRelationshipWithMultiIdLinkage() ); } - public function testRelationshipWithEmptyMultiIdLinkage() - { + public function testRelationshipWithEmptyMultiIdLinkage() { $this->assertEncodesTo( ' { @@ -135,8 +132,7 @@ public function testRelationshipWithEmptyMultiIdLinkage() ); } - public function testRelationshipWithNoData() - { + public function testRelationshipWithNoData() { $this->assertEncodesTo( ' { @@ -188,8 +184,7 @@ public function testRelationshipWithNoData() ); } - public function testResourceFieldsMustBeUnique() - { + public function testResourceFieldsMustBeUnique() { $this->expectException(\LogicException::class); $this->expectExceptionMessage("Field 'foo' already exists"); new NewResourceObject( @@ -199,8 +194,7 @@ public function testResourceFieldsMustBeUnique() ); } - public function testNameValidation() - { + public function testNameValidation() { $this->expectException(\DomainException::class); new NewResourceObject('invalid:id'); } diff --git a/test/PaginationTest.php b/test/PaginationTest.php index 7add66f..a9307d8 100644 --- a/test/PaginationTest.php +++ b/test/PaginationTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -57,8 +57,7 @@ public function testPaginatedResourceCollection() ); } - public function testPaginatedResourceIdentifierCollection() - { + public function testPaginatedResourceIdentifierCollection() { $this->assertEncodesTo( ' { diff --git a/test/ResourceIdentifierTest.php b/test/ResourceIdentifierTest.php index 5dcd959..eb479ee 100644 --- a/test/ResourceIdentifierTest.php +++ b/test/ResourceIdentifierTest.php @@ -1,14 +1,13 @@ expectException(\DomainException::class); new ResourceIdentifier('invalid:id', 'foo'); } diff --git a/test/ResourceObjectTest.php b/test/ResourceObjectTest.php index 3541c8d..b565d7d 100644 --- a/test/ResourceObjectTest.php +++ b/test/ResourceObjectTest.php @@ -1,4 +1,6 @@ -assertEncodesTo( ' { @@ -63,8 +63,7 @@ public function testFullFledgedResourceObject() ); } - public function testRelationshipWithSingleIdLinkage() - { + public function testRelationshipWithSingleIdLinkage() { $this->assertEncodesTo( ' { @@ -89,8 +88,7 @@ public function testRelationshipWithSingleIdLinkage() ); } - public function testRelationshipWithMultiIdLinkage() - { + public function testRelationshipWithMultiIdLinkage() { $this->assertEncodesTo( ' { @@ -127,8 +125,7 @@ public function testRelationshipWithMultiIdLinkage() ); } - public function testRelationshipWithEmptyMultiIdLinkage() - { + public function testRelationshipWithEmptyMultiIdLinkage() { $this->assertEncodesTo( ' { @@ -153,8 +150,7 @@ public function testRelationshipWithEmptyMultiIdLinkage() ); } - public function testRelationshipWithNoData() - { + public function testRelationshipWithNoData() { $this->assertEncodesTo( ' { @@ -210,29 +206,25 @@ public function testRelationshipWithNoData() ); } - public function testCanNotCreateIdAttribute() - { + public function testCanNotCreateIdAttribute() { $this->expectException(\DomainException::class); $this->expectExceptionMessage("Can not use 'id' as a resource field"); new Attribute('id', 'foo'); } - public function testCanNotCreateTypeAttribute() - { + public function testCanNotCreateTypeAttribute() { $this->expectException(\DomainException::class); $this->expectExceptionMessage("Can not use 'type' as a resource field"); new Attribute('type', 'foo'); } - public function testCanNotCreateIdRelationship() - { + public function testCanNotCreateIdRelationship() { $this->expectException(\DomainException::class); $this->expectExceptionMessage("Can not use 'id' as a resource field"); new ToOne('id', new ResourceIdentifier('apples', '1')); } - public function testCanNotCreateTypeRelationship() - { + public function testCanNotCreateTypeRelationship() { $this->expectException(\DomainException::class); $this->expectExceptionMessage("Can not use 'type' as a resource field"); new ToOne('type', new ResourceIdentifier('apples', '1')); @@ -242,8 +234,7 @@ public function testCanNotCreateTypeRelationship() * @dataProvider invalidCharacters * @param string $invalid_char */ - public function testAttributeMustOnlyHaveAllowedCharacters(string $invalid_char) - { + public function testAttributeMustOnlyHaveAllowedCharacters(string $invalid_char) { $this->expectException(\DomainException::class); $this->expectExceptionMessage('Invalid character in a member name'); new Attribute("foo{$invalid_char}bar", 'plus can not be used'); @@ -253,15 +244,13 @@ public function testAttributeMustOnlyHaveAllowedCharacters(string $invalid_char) * @dataProvider invalidCharacters * @param string $invalid_char */ - public function testRelationshipMustOnlyHaveAllowedCharacters(string $invalid_char) - { + public function testRelationshipMustOnlyHaveAllowedCharacters(string $invalid_char) { $this->expectException(\DomainException::class); $this->expectExceptionMessage('Invalid character in a member name'); new ToNull("foo{$invalid_char}bar"); } - public function invalidCharacters() - { + public function invalidCharacters() { return [ ['+'], ['!'], @@ -271,8 +260,7 @@ public function invalidCharacters() ]; } - public function testResourceFieldsMustBeUnique() - { + public function testResourceFieldsMustBeUnique() { $this->expectException(\LogicException::class); $this->expectExceptionMessage("Field 'foo' already exists"); new ResourceObject( @@ -283,8 +271,7 @@ public function testResourceFieldsMustBeUnique() ); } - public function testNameValidation() - { + public function testNameValidation() { $this->expectException(\DomainException::class); new ResourceObject('invalid:id', 'foo'); } diff --git a/test/benchmarks/compound10k.php b/test/benchmarks/compound10k.php index 513518b..44664fd 100644 --- a/test/benchmarks/compound10k.php +++ b/test/benchmarks/compound10k.php @@ -1,4 +1,6 @@ -