api icon indicating copy to clipboard operation
api copied to clipboard

Tiered access in Auth 2

Open tomcrane opened this issue 3 years ago • 2 comments
trafficstars

In Auth 1, the client deduced that a redirect might have happened by observing that the URL it asked for is not the id of the info.json it eventually sees (redirects are invisible to xhr). This also led to the odd scenario described by #1166, where auth services need to be asserted on the redirected, open resource rather than the authed resource.

In the above scenario there might have been a chain of redirects; the user doesn't have access to resourceA and gets redirected to resourceB; resourceB's info.json further directs them to resourceC. Imagine "premium", "economy" and "free" tiers.

The new draft always has auth services asserted for the resources they are protecting, and never redirects. The user gets a 401 from the protected probe service (which might be an info.json), but if another version is available it is provided in the location property. The assumption is that the server has decided that user can see the resource at the location property, so the client can just use that.

// 401
{
    "@context": "http://iiif.io/api/auth/2/context.json",
    "id": "https://authentication.example.org/my-video.mp4/probe",
    "type": "AuthProbeService2",
    "location": "https://authentication.example.org/my-video-lo-res.mp4",
    "label": { "en": [ "Label for my-video.mp4's probe service" ] },
    "for": "https://authentication.example.org/my-video.mp4"
}

But this isn't tiered access; it short-circuits to the one the user can see. If the probe service thinks the user can't see anything, it doesn't provide anything. The above would be a 401, with no location property. This is a lot simpler but doesn't provide a clear answer for scenarios such as the Manifest declaring the full high res version for staff, there's a watermarked version available for registered users, and nothing available for public users. Or the probe might not know the user's access to to the next tier down and require another auth flow interaction to establish it.

If the location property is a "full" content resource, such as might be declared in a Manifest, then it could carry further auth services and a chain of tiers could be established.

The IIIF Manifest declares a content resource (e.g., as the body of a painting anno - but not necessarily):

{
   "id": "https://authentication.example.org/my-video.mp4",
   "type": "Video",
   "format": "video/mp4",
   "service": [
     {    
       "id": "https://authentication.example.org/my-video.mp4/probe",
       "type": "AuthProbeService2"
     },
     {
        // access service, token service etc
     }
   ]
}

If the client has an access token (or even if it doesn't if very optimistic) if could try this probe service and get a response:

// HTTP 401
{
    "@context": "http://iiif.io/api/auth/2/context.json",
    "id": "https://authentication.example.org/my-video.mp4/probe",
    "type": "AuthProbeService2",
    "location": {
      "id": "https://authentication.example.org/my-video-economy-tier.mp4",
      "type": "Video"
      "format": "video/mp4",
      "service": [
        {    
          "id": "https://authentication.example.org/my-video-economy-tier.mp4/probe",
          "type": "AuthProbeService2"
        },
        {
           // access service, token service etc
        }
      ]
    },
    "label": { "en": [ "Label for my-video.mp4's probe service" ] },
    "for": "https://authentication.example.org/my-video.mp4"
}

The client could then probe https://authentication.example.org/my-video-economy-tier.mp4/probe:

// HTTP 401
{
    "@context": "http://iiif.io/api/auth/2/context.json",
    "id": "https://authentication.example.org/my-video-economy-tier.mp4/probe",
    "type": "AuthProbeService2",
    "location": {
      "id": "https://authentication.example.org/my-video-free-tier.mp4",
      "type": "Video"
      "format": "video/mp4"
    },
    "label": { "en": [ "Label for my-video.mp4's probe service" ] },
    "for": "https://authentication.example.org/my-video-economy-tier.mp4"
}

...as this third tier does not have auth services the client can assume that it is visible. Or if it did and the client got a 200 response, the user could see it.

The other advantage of this approach is that the client is seeing the same resource shape (with at least id and type) that it sees in the Manifest so can run it through the same processing.

tomcrane avatar Oct 25 '22 14:10 tomcrane

The other related question is whether location is the right name for this property. It was chosen to reflect the HTTP location header, but that doesn't mean a more API-resource-friendly property name could be used.

tomcrane avatar Oct 25 '22 14:10 tomcrane

In the above flow the server can of course decide to provide the open, free version straight away in the probe response, if it authenticates the user via the token but decides there's no way they can ever see the intermediate version.

The server could also provide the intermediate version without its auth services, if it knew from the token that the user can already see it. That's probably not a good idea though, it should provide the auth services to make it clear that it is protected, and just because the user can see it now doesn't mean they'll still be able to see it in 10 minutes. In fact this probably a MUST so that clients can populate whatever stores they use to track auth services.

A note though... the probe service belongs individually to each resource. But the access service and token services might be common to multiple resources. And a client may be able to use an acquired token against multiple probe services. the spec needs to be clear about what is allowed here and what is not.

tomcrane avatar Oct 25 '22 14:10 tomcrane

Resolved with publication of Auth 2.0. Now use substitute instead of location and see https://iiif.io/api/auth/2.0/#tiered-access

zimeon avatar Jun 07 '23 08:06 zimeon