HydraCG / Specifications

Specifications created by the Hydra W3C Community Group
Other
138 stars 26 forks source link

Define client-initiated pagination #102

Open lanthaler opened 8 years ago

lanthaler commented 8 years ago

In issues #41 and #42 we defined how to represent collections and paginated collections. It became clear that people want a mechanism to tell a clients how to control pagination and how jump directly to specific pages/views.

Requirements/desired features are collected at https://www.w3.org/community/hydra/wiki/Client-initiated_pagination

tpluscode commented 5 years ago

AFAICT, the current recommendation is to use search property to allow the client to narrow down/navigate through a collection.

In te use cases we have:

{
    "search": {
        "@type": "IriTemplate",
        "template": "http://example.com/api/events{?search}",
        "variableRepresentation": "BasicRepresentation",
        "mapping": [
            {
                "@type": "IriTemplateMapping",
                "variable": "search",
                "property": "freetextQuery",
                "required": true
            }
        ]
    }
}

I think we can simply provide some well-known properties like freetextQuery to support common scenario while not being too invasive.

tpluscode commented 5 years ago

To jump to a specific page, the server could add a variable to the template and for starters add a mapping.

{
-  "template": "http://example.com/api/events{?search}",
+  "template": "http://example.com/api/events{?search,page}",
  "mapping": [
+  {
+    "@type": "IriTemplateMapping",
+    "variable": "page",
+    "property": "page",
+    "required": false
+  }
  ]
}

Not too happy about page but any other name I can think of suggests a data type. Typically the pages are numbers, but we cannot enforce that on APIs.

tpluscode commented 5 years ago

Another common design choice could be skip/take approach:

{
-  "template": "http://example.com/api/events{?search}",
+  "template": "http://example.com/api/events{?search,limit,offset}",
  "mapping": [
+  {
+    "@type": "IriTemplateMapping",
+    "variable": "limit",
+    "property": "take",
+    "required": false
+  },
+  {
+    "@type": "IriTemplateMapping",
+    "variable": "offset",
+    "property": "skip",
+    "required": false
+  }
  ]
}
angelo-v commented 5 years ago

~How do we associate the IriTemplate with a PartialCollectionView?~ You wrote it: hydra:search

tpluscode commented 5 years ago

@angelo-v the template is not directly related to the Collection(View).

Templates can be used for links (search or any other) to let the client fill in the blanks.

angelo-v commented 5 years ago

But in this case it would be related to a Collection via hydra:search?

angelo-v commented 5 years ago

I am also not happy with "page" What does it mean? The page itself is identified by an URI. So it is a page number? But it doesn't have to be numeric. It is some kind of page identifier that is only valid in the context of the API...

If you want to navigate to a specific page, just use it's ID (=URI). Client does not know the URI yet? How comes it wants to navigate to a specific page, without knowing what page that is? I guess the skip/take approach is what fits this better.

tpluscode commented 5 years ago

But in this case it would be related to a Collection via hydra:search?

Yes. Just saying that template has wider scope than just collections

I am also not happy with "page" What does it mean?

I agree. This will be hard to really name. As the portion of a URL, the "page" variable, it can be anything. Often numeric, but I would not want Hydra to really enforce that. That's why I named with a very broad term.

The page itself is identified by an URI

We don't really have a term for Page so there is no real clash there. Instead there are views.

I also considered pageId but that would be confused with the URI. Maybe smth like pageSpecifier?

tpluscode commented 5 years ago

Client does not know the URI yet? How comes it wants to navigate to a specific page, without knowing what page that is?

Yes, very good points, which we should address in a more general terms of describing the template.

For example, I'd like to have the flexibility to define constraints of a template variable.

{
  "@type": "IriTemplateMapping",
  "variable": "page",
  "property": "page",
  "constraints": [{
    "type": "xsd:integer",
    "min": 1,
    "max": 20
  }]
}

This way the server could precisely control the client by letting it know what are the valid inputs.

This goes way beyond collections though, and I'd like to discuss about templates and constraints in general.

angelo-v commented 5 years ago

This goes way beyond collections though, and I'd like to discuss about templates and constraints in general.

We should discuss this in a seperate issue. Regarding this specific use case are we all fine with the skip/take approach?

alien-mcl commented 5 years ago

For example, I'd like to have the flexibility to define constraints of a template variable.

I was thinking about that. Also I'm keen to provide a default value that would be used by the server if not provided.