api-platform / core

The server component of API Platform: hypermedia and GraphQL APIs in minutes
https://api-platform.com
MIT License
2.43k stars 863 forks source link

[Hydra] How to know if a property is a collection of one entity ? #912

Closed fmata closed 7 years ago

fmata commented 7 years ago

Hi,

I created a PHP client for Hydra, it works but I have some problem yet. I parse the full document http://*/doc.jsonld to discover all the API resources, properties and operations available.

For example, the API exposes 2 resources User and Address. User class has a property User::addresses which is a collection of Address, as usual.

But the Hydra documentation for User::addresses is :

        {
          "@type": "hydra:SupportedProperty",
          "hydra:property": {
            "@id": "#User/addresses",
            "@type": "rdf:Property",
            "rdfs:label": "addresses",
            "domain": "#User"
          },
          "hydra:title": "addresses",
          "hydra:required": false,
          "hydra:readable": true,
          "hydra:writable": true
        }

It's true that is a property, but in real the range is Address and there is no way to know that is a collection of Address.

I tought may be I could decorate DocumentationNormalizer (especially DocumentationNormalizer::getProperty) but I am not sure it's the convenient way and respectful of Hydra spec.

I am thinking a lot but I imagine the spec indicates a proper way to know if a property is an array of a type or not ?

Thanks.

dunglas commented 7 years ago

I created a PHP client for Hydra, it works but I have some problem yet.

Great! Is it open source? I'm interested to take a look.

About the specific problem, maybe @lanthaler has a hint?

fmata commented 7 years ago

Yes I think I can open source it, I will discuss with my team. I need to polish some things before.

For the parsing concerns I inspired me by @lanthaler projects (JsonLD library and HydraConsole).

lanthaler commented 7 years ago

It is currently not straightforward to describe that something is a Collection of X (you'd need to use OWL to do so). The example above, however, doesn't say anything about the range of that property.

I am thinking a lot but I imagine the spec indicates a proper way to know if a property is an array of a type or not ?

Please note that an array is not the same thing as a collection. A collection is a resource by itself.

That being said, I made a proposal to express whether one or multiple values are expected quite a while ago but we didn't reach consensus: https://github.com/HydraCG/Specifications/issues/35#issuecomment-40874094

dunglas commented 7 years ago

@lanthaler thanks for your answer!

Do you have an example of using OWL to do that? It will be useful to add this in the documentation generated by API Platform because it's a common problem and I've already stumbled into it.

How can we help you to reach consensus about https://github.com/HydraCG/Specifications/issues/35#issuecomment-40874094?

fmata commented 7 years ago

@lanthaler thanks for your answer.

I +1 @dunglas, may be you could give us an example to implement in API Platform ?

Waiting an official way to do it, I think I have to do it :

I tought may be I could decorate DocumentationNormalizer (especially DocumentationNormalizer::getProperty) but I am not sure it's the convenient way and respectful of Hydra spec.

@dunglas what do you think about it ?

lanthaler commented 7 years ago

This should do the trick, but please double check

ex:issues rdfs:range
   hydra:Collection, [
   owl:equivalentClass [
       owl:onProperty hydra:member ;
       owl:allValuesFrom ex:Issue
   ]
] .
dunglas commented 7 years ago

Thanks you very much for your help Markus. I'll submit a patch to add this.

fmata commented 7 years ago

@dunglas any news ?

I can open a PR to provide my fix but it's not spec compliant... In ApiPlatform\Core\Hydra\Serializer\DocumentationNormalizer::getProperty() I add a property "multiple" in "hydra:property".

...
$property = [
            '@type' => 'hydra:SupportedProperty',
            'hydra:property' => [
                '@id' => $propertyMetadata->getIri() ?? "#$shortName/$propertyName",
                '@type' => $propertyMetadata->isReadableLink() ? 'rdf:Property' : 'hydra:Link',
                'rdfs:label' => $propertyName,
                'domain' => $prefixedShortName,
                'multiple' => $propertyMetadata->getType() && $propertyMetadata->getType()->isCollection(),
            ],
            'hydra:title' => $propertyName,
            'hydra:required' => $propertyMetadata->isRequired(),
            'hydra:readable' => $propertyMetadata->isReadable(),
            'hydra:writable' => $propertyMetadata->isWritable(),
        ];
...
dunglas commented 7 years ago

@fmata it's still on my todolist... Fell free to open a PR it will definitely help! What do you think about implementing the solution proposed by @lanthaler instead of adding a non-standard extension?

(ping @mauchede, it is probably related to your problem).

fmata commented 7 years ago

@dunglas PR opened.

I'm sorry but I can not see how to implement the solution provided by @lanthaler but let me know if you want help me :)

dunglas commented 7 years ago

Here is a try but I'm really not sure it's valid. @lanthaler would you mind checking please?

(Removed, invalid, see next comment)

dunglas commented 7 years ago

I've posted my proposal on the Hydra ML: https://lists.w3.org/Archives/Public/public-hydra/2017Jun/0010.html I'm waiting for feedback before implementing it.

fmata commented 7 years ago

Cool :) I follow your thread and if you are ok I can implement it

dunglas commented 7 years ago

I'm ok but I prefer that some Hydra/OWL guru valid it before you waste your time!

lanthaler commented 7 years ago

Replied on the list. Main question related to this issue: why would you want to use a collection for a single entity?

soyuka commented 7 years ago

When it's a filtered entity for example?

dunglas commented 7 years ago

@fmata, we now have a valid example using OWL: https://lists.w3.org/Archives/Public/public-hydra/2017Jun/0012.html Can you update your PR (if you're busy I can do it).

Thanks!

fmata commented 7 years ago

@dunglas I will do it in the next days. I saw you are waiting a new response from the list, I will check