-
Notifications
You must be signed in to change notification settings - Fork 0
Strawman2
hoegertn edited this page Apr 20, 2012
·
22 revisions
(also - apologies to @hoegertn, did not mean to clobber your changes on strawman1 yesterday!) [hoegertn] no problem
I've made the following changes from the first example:
- Renamed 'body' to 'accepts' to make it's purpose more clear.
- Changed the 'representations' array items to objects as in alternative #1, with the exception of the 'body' element.
- Changed example request bodies to strings.
- Added an optional "headers" element to example requests.
- [hoegertn] how are headers described? You may want to use custom headers
- [grncdr] Headers are always a flat key-value object. Mapping header names to header strings.
- [hoegertn] Sure, but how can I specify which headers I can use? I think we need a definition section for request and response headers per method with doc and pattern info.
- Added a query param to the request template as an alternative to alternative #1's 'style' member.
- The above is also an example of using an enum for parameter descriptions.
- Removed redundant
type: "string"elements from parameter descriptions. - Added more comments.
{
// Keeping the top level open in the schema means we could allow other metadata such as API versions,
// authors, and so on. (Idea lifted from https://github.com/SPORE/specifications)
// [hoegertn] I really like this idea
resources: [
{
id: "LocalizedMessage",
doc: "A localized message",
path: "/{language}/{messageId}{?seasonal}", // representing query params with L3 URI templates
params: { // Request parameters only, JSON schemas with type: 'string' implied
locale: {
description: "A standard locale string, e.g. \"en_US.utf-8\"",
pattern: "[a-z]+(_[A-Z]+)?(\\.[a-z-]+)?"
},
messageId: {
description: "A free-form message string",
pattern: "[a-z_]+"
},
seasonal: {
description: "Whether the message is seasonal.",
enum: ['true', 'false', 'yes', 'no'],
}
},
methods: {
PUT: {
doc: "Update or create a message",
statusCodes: [ 201 ],
accepts: [ // Representations accepted by the method on this resource.
{ type: "text/plain" },
{ type: "application/json", schema: "http://some.json/schema" }
],
examples: [
{
path: "/en_US/greeting",
body: "Hello, world!"
},
{
path: "/en_US/greeting",
headers: {"content-type": "application/json"},
body: "{\"message\":\"Hello, world!\"}", // Should bodies *always* be strings?
},
{
path: "/en_US/greeting",
headers: {"content-type": "application/xml"},
body: "<message>Hello, world</message>",
}
]
},
GET: {
doc: "Retrieve a message",
statusCodes: [ 200, 302 ],
accepts: null, // Possible to explicitly indicate that this method takes no request body.
}
},
representations: [ // Response representations this resource provides
{ type: 'application/json', schema: 'http://my.json/schema' },
{ type: 'application/xml', schema: 'http://my.xml/dtd' }, // Externally referenced schema
{ type: 'text/plain' },
]
},
{
// This resource has no human-readable documentation, but still provides some info on how to use it.
id: "FallbackLocale",
methods: {
GET: { statusCodes: [ 200 ] },
PUT: { statusCodes: [ 201 ] }
},
parameters: {
locale: { pattern: "[a-z]+(_[A-Z]+)?(\\.[a-z-]+)?" }
}
}
]
}(Perceived) Improvements:
- This version handles multiple representation formats for requests and responses independently of each other.
- It is independent of JSON, (could just as easily be represented in XML, Avro, MessagePack, etc). While this may not be of immediate necessity, it seems prudent to try not to bind ourselves to strongly to one serialization format.
[hoegertn] Ideas:
- Add an object array with the schema URI to URL mapping
- Rename and split the doc element to name (a short name) and description (a longer description of the element)
- Do we want to move the representation block into the method or is it only possible to have one format for every method of a resource?
[saary] Ideas:
- In some places we can support both a string value or a more descriptive json value.
for example the accepts field can be a string in simple cases and an object with type and schema in others.
- [hoegertn] there I see a problem with language with types. If I want to use Java I would have a List<AcceptTypes> object, but strings in this list will break the runtime.
-
[grncdr] Agree with hoegertn here. Even in dynamic languages, the need to check whether you're dealing with string or object/hash/dict isn't worth the trade-off. Of course, the application API's by which this metadata is defined could accept the simple string and turn it into
{ type: <string type> }before serving it to clients.
- Using doc/description across the board. We should stick to one term as it means the same all around.
- [grncdr] Agreed, I'll open a "decision" issue for it. (I really like that approach btw!)
- Having both a pattern and enum fields makes for a bit of inconsistency (you could have both).
I think I would start with only one of them as enum could be represented as "option1|option2|option3" which is pretty self explanatory.
- [hoegertn] Check!
- [grncdr] - I agree. I was using things that were "built-in" to JSON schemas, but now that schema definitions for requests/responses are no longer inline, requiring a JSON schema implementation to validate some strings is overkill.