9.8 KiB
Use JSON Home for Version/Extension discovery
The Keystone server provides version discovery as a response to the
GET /
, GET /v2.0
, and GET /v3
operations. The format of this response is a JSON document which is
Keystone-specific (it's defined in the Identity API spec). Keystone
should support JSON Home, since this is a more standard way to do REST
API discovery. This will help to standardize version discovery across
the OpenStack ecosystem.
This was discussed on the openstack-dev mailing list.
Problem Description
An application writer has a need to interact with different OpenStack services, so she starts by writing some code to talk to the servers to discover the version of the APIs supported by each server. She finds that all the servers provide a different response and so has to write custom code for each service. This is harder than it should be, since all the services should use the same format for their version document. The format chosen for the version document should provide a link-driven approach, such as JSON Home.
With this change, Keystone will provide a JSON Home document so that it's consistent with other services that use JSON Home.
Proposed Change
The V3 Identity API spec will be changed to document that the server
can respond to a GET /v3
request with a JSON Home document
if the Accept
header is application/json-home
,
and also provide an example of what the response will look like. The
WADLs for the Identity
API v2 will be updated similarly.
The Keystone server will be changed to check the Accept
header on GET /
, GET /v2.0
, and
GET /v3
request, and if the header indicates that
application/json-home
is the preferred format over
application/json
, then the server will generate a JSON Home
document rather than the normal JSON response.
Here's an example of a minimal document that only has
/v3/users
and /v3/users/{user_id}
:
{"resources": {
"http://docs.openstack.org/api/openstack-identity/3/rel/users": {
"href": "/v3/users"
,
}"http://docs.openstack.org/api/openstack-identity/3/rel/user": {
"href-template": "/v3/users/{user_id}",
"href-vars": {
"user_id": "http://docs.openstack.org/api/openstack-identity/3/param/user_id"
,
},
}// ...
} }
The keys of the resources
property are link relation
types. A relationship type needs to be chosen for the key. There are
several relationship types registered
with IANA, but there's none designated for Identity API resources.
If a group doesn't want to register a relation with IANA (see section
4.2 "Extension Relation Types" in RFC 5988), they can use
some unique URL instead. An application could potentially fetch this URL
to get information about the relationship, so we should pick one that
could potentially be used to serve up some info about what the
relationship is and describe the resource. The Nova project publishes
their XSD files at
http://docs.openstack.org/api/openstack-compute/2/xsd/
so
Keystone should publish its files in a similar location for consistency.
For v3 resources, the relation type link will be like
http://docs.openstack.org/api/openstack-identity/3/rel/<type>
,
where <type>
is like users
,
user
, projects
, etc.
A relationship URL also has to be chosen for the parameters. For v3
parameters, these will be like
http://docs.openstack.org/api/openstack-identity/3/param/<parameter-type>
,
where <parameter-type>
is like user_id
,
project_id
, etc.
The JSON Home document that the server returns will change depending
on which extensions are enabled. The enabled extensions (that are in the
pipeline) will intercept the GET
request and update the
response.
There will be a resource in resources
for every resource
template in the v3 API (for V3), V3 extensions that are enabled, the
public and admin v2 APIs and v2 extensions that are enabled.
Here's an example of a resource for an extension, OS-EP-FILTER:
{"resources": {
"http://docs.openstack.org/api/openstack-identity/3/ext/OS-EP-FILTER/1.0/rel/project_endpoint": {
"href": "/v3/OS-EP-FILTER/projects/{project_id}/endpoints/{endpoint_id}",
"href-vars": {
"project_id": "http://docs.openstack.org/api/openstack-identity/3/param/project_id",
"endpoint_id": "http://docs.openstack.org/api/openstack-identity/3/param/endpoint_id"
}
}
} }
The relationship type for extensions will be like
http://docs.openstack.org/api/openstack-identity/<api-version>/ext/<extension-name>/<extension-version>/rel/<resource>
.
The relationship type for a parameter used by an extension will be
like
http://docs.openstack.org/api/openstack-identity/<api-version>/ext/<extension-name>/<extension-version>/param/<param-id>
.
The extensions provided by Keystone have routers that implement the
keystone.common.wsgi.ExtensionRouter
class. A new
V3ExtensionRouter
will be created from
ExtensionRouter
that has code to intercept the
GET /v3
request and update the response with the info for
the extension. The info for the extension will be a property that's
overridden by the extension implementation.
Alternatives
None.
Data Model Impact
None. This will not require database changes.
REST API Impact
GET /
If the Accept
header is
application/json-home
, the server will respond with a
200 OK
and the JSON Home document describing the REST API,
as described in the "Proposed Change" section above.
Note that if the client is making the request with
Accept: application/json-home
, an old server will return
the old JSON response with Content-Type: application/json
,
so clients will have to verify that the Content-Type
in the
response is actually application/json-home
as expected
before using the result. A server that conforms to the HTTP 1.1
specification would respond with a 406 Not Acceptable
error
in the case where it doesn't support the provided Accept
header, so a client should also be able to handle that response.
A client will be able to set the Accept
header to a
value like application/json; q=0.2, application/json-home
and the server will return JSON if it doesn't support JSON Home. Note
that the Keystone server doesn't support this today. The WebOb library
that Keystone uses has support for Accept
header handling, but Keystone doesn't use it for the
Accept
header (it's used for Accept-Language
handling).
GET /v2.0
Similar to GET /
, but returns the JSON Home document for
only the V2 API and extensions.
GET /v3
Similar to GET /
, but returns the JSON Home document for
only the V3 API and extensions.
Security Impact
None. The API is public info.
Notifications Impact
None.
Other End User Impact
python-keystoneclient should be changed to support fetching and using the JSON Home document for discovery.
Performance Impact
None.
Other Deployer Impact
None.
Developer Impact
When adding a new resource, or changing a resource with new arguments, the JSON Home document will have to be updated. Extensions will have to update the JSON Home document.
Implementation
Assignee(s)
- Primary assignee:
-
blk-u <Brant Knudson>
- Other contributors:
-
<None>
Work Items
- Update the Identity V3 spec and other specs with the new
Accept
header and sample response. - Enhance the Keystone server so that it can process the
Accept
header, in thatapplication/json; q=0.2, application/json-home
could result in a JSON Home response by passing on the requestedAccept
header to the controller. - Change Keystone server to respond with JSON Home for
/
,/v2.0
,/v3
when the accept header isapplication/json-home
. - Change the v2 and v3 extensions to update the JSON Home response.
- Write a Tempest test to verify requests for
/
,/v2.0
, and/v3
withAccept
set toapplication/json-home
. - Update python-keystoneclient to be able to use JSON Home for
/
,/v2.0
, and/v3
.
Dependencies
None.
Testing
Tempest will be changed to validate the response for
GET /
, GET /v2.0
, and GET /v3
with Accept: application/json-home
.
Documentation Impact
The documentation will need to be changed to say that Keystone supports JSON Home.
References
[0] JSON Home
[1] Nottingham, M. "Web Linking", RFC 5988, October 2010
[2] Discoverable home document for APIs discusson on the openstack-dev mailing list.