Skip to content

Add support for generics #108

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 2 commits into
base: master
Choose a base branch
from

Conversation

HendrikN
Copy link

@HendrikN HendrikN commented Apr 18, 2025

Description

Adds support for using generics (using PHPStan types), by adding the correct phpdoc annotations to Interfaces. No actual code has been changed, so this could be released as a minor.

The next step would be completely incorporating PHPStan and use it as a QA-tool in the pipeline.

Motivation and context

Modern IDE's have support for them and this greatly enhances the DX of using this package.

fixes #107

How has this been tested?

N/A

Types of changes

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to change)

Checklist:

  • I have read the CONTRIBUTING document.
  • My pull request addresses exactly one patch/feature.
  • I have created a branch for this patch/feature.
  • Each individual commit in the pull request is meaningful.
  • I have added tests to cover my changes.
  • If my change requires a change to the documentation, I have updated it accordingly.

@HendrikN HendrikN force-pushed the feature/generic-types branch 3 times, most recently from 299343e to 9999b50 Compare April 22, 2025 06:22
@HendrikN HendrikN force-pushed the feature/generic-types branch from 9999b50 to d294a72 Compare April 22, 2025 06:24
*/
public function all();

/**
* @return \Swis\JsonApi\Client\Interfaces\ItemDocumentInterface
* @return \Swis\JsonApi\Client\Interfaces\ItemDocumentInterface<TItem>
*/
public function find(string $id);
Copy link
Member

@bbrala bbrala Apr 30, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When i check the tests, i think this return type is not correct. It seems this can also return a DocumentInterface. See RepositoryTest::it_can_find_one.

This could also mean the interface on the Document is wrong. seems a little weird, since ItemDocument is pretty much the same class with the extra getData method.

Think there is something wrong here. @JaZo any insights?

Copy link
Author

@HendrikN HendrikN Apr 30, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I had the same questions, but I didnt want to touch actual code in this PR… ItemDocument seems to follow the spec though…

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would probably make it documentinterface, since itemdocumentinterface does extend documentinterface. But that will mean some errors later with phpstan when we are calling getData.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would also make this PR mostly obsolete if find() would not resolve to an Item 😋

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The primary reason to have a CollectionDocumentInterface and an ItemDocumentInterface is to differentiate between the return types of getData. The former returns a collection and the latter an item. This stems from ancient times when generics weren't a thing. I'm okay with changing that to generics, but that would probably be a breaking change, so maybe we should leave that for now and just add a todo.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I’m fine with that

/**
* @param \Swis\JsonApi\Client\Collection<array-key, TItem>|null $data
* @return static
*/
public function setData(?Collection $data);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Return static also points at a little weirdness, why isn't that type hinted? And should it be?

interface OneRelationInterface
{
/**
* @param TItem|null $data
* @return static
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same static comment.

@bbrala
Copy link
Member

bbrala commented Apr 30, 2025

Thank so much for helping out here :)

I left some small comments, which might need the help of @JaZo. I think we are going to surface a few incinsistencies when we start running phpstan on max. :x

@bbrala bbrala requested a review from Copilot May 2, 2025 15:21
Copilot

This comment was marked as outdated.

@bbrala
Copy link
Member

bbrala commented May 2, 2025

(lets toy with copilot see what happens, boo php)

@JaZo JaZo requested a review from Copilot May 8, 2025 18:17
Copy link

@Copilot Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR introduces generic type support via PHPDoc annotations to improve static analysis and developer experience when using the package.

  • Added generics annotations to repository, document, and relation interfaces.
  • Enhanced the HasRelations trait to properly document generic relation methods.
  • Updated the Collection class and README documentation to reflect the new generics feature.

Reviewed Changes

Copilot reviewed 9 out of 9 changed files in this pull request and generated no comments.

Show a summary per file
File Description
src/Interfaces/RepositoryInterface.php Added generics to the return types of repository methods.
src/Interfaces/OneRelationInterface.php Annotated relation methods with generics for type consistency.
src/Interfaces/ManyRelationInterface.php Updated phpdoc annotations with generics on collection types.
src/Interfaces/ItemDocumentInterface.php Specified generic return type for document data extraction.
src/Interfaces/CollectionDocumentInterface.php Added generics to collection return types.
src/Concerns/HasRelations.php Enhanced relation factory methods with inline generic templates.
src/Collection.php Added generics annotations to extend the Laravel Collection class.
composer.json Removed an author entry.
README.md Expanded documentation with usage examples on generics.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Add PHPStan types
3 participants