raml-spec
raml-spec copied to clipboard
RAML 1.0 Arrays: inside an object or plain array?
Here's what RAML 1.0 says about arrays: https://github.com/raml-org/raml-spec/blob/master/versions/raml-10/raml-10.md#array-type
However the specifications isn't exactly clear whether to use a Array... Assuming I have a of body: Pokemon[]
, where each Pokemon is:
type: object
description: Pokemon
properties:
name:
type: string
description: Pokemon name
description:
type: string
description: Description of Pokemon
Which is the correct JSON, A or B?
A)
{
"pokemons": [{
"name": "Pikachu",
"description": "Electric"
}, {
"name": "Bulbasaur",
"description": "Dual-type Grass/Poison"
}]
}
or B)
[{
"name": "Pikachu",
"description": "Electric"
}, {
"name": "Bulbasaur",
"description": "Dual-type Grass/Poison"
}]
Both are valid json according to: http://jsonlint.com/
Really depends. I would say its mostly A) since you always use a key-value pair for properties in RAML data types. In your example you would have:
types:
Pokemon:
PokemonGo:
properties:
pokemons: Pokemon[]
The only place where B) can be relevant is if you have something like:
types:
Pokemon:
Pokemons: Pokemon[]
Hmm, shouldn't the specification be unambiguous? Say there's two companies implementing equivalents on each side and if the spec isn't unambiguous, both sides can implement it differently?
Its unambiguous as far as you can get with plain English. The actual output just depends if you say a type is an array or a property. Same in JSON schema.
For body: Pokemon[]
, I'd expect B only.
jsonlint.com is irrelevant here; both examples are JSON, but only B conforms with body: Pokemon[]
.
@freddrake so you think we have to clarify anything in the specification? if yes, there are multiple places but maybe we should provide an additional reference document that explains how RAML data types do map into JSON schema?
@sichvoge I think the specification is clear. If more examples are required (indicated by questions like this coming up), an informative document can be added. My interpretation is based on interpreting what's in the spec, without bringing in outside expectations based on what I'd like to see in an actual API.
(I think it's clear that my expectation of RAML is that I can use it to describe an API accurately and unambiguously, even if that API doesn't conform to best practices. Because humans have a hard time agreeing on the later. Best practices considerations are best left to linters.)
OK. I think an informative document makes some sense especially around mapping into JSON schema. If one would like to start with that, go for it :) Otherwise, it would take me some time to consolidate something
I think this is cleared out, and can be closed.
If anyone has a spare minute, quick question: is it possible to define arrays of objects inline without creating a global type? Something like
[...]
application/json:
type: object[]
properties:
name: string
age: integer
example: |
[
{
"name": "harry",
"age": 18
}
]
Hi, you should be able to do this without using type expressions ([]
). In your case, the following works:
[...]
application/json:
type: array
items:
type: object
properties:
name: string
age: integer
example: |
[
{
"name": "harry",
"age": 18
}
]
@sichvoge I found out, but thanks a lot for the swift response! (The example
key in your snippet needs to be indented one level lower, though :)
Ups, you are right :D
In Anypoint Studio Design center, the following seems like it would work; the API console renders nicely with no errors.
application/json:
properties:
Customer:
type: object
properties:
firstName:
lastName:
titleCode:
password:
carrier:
MId:
description: ******ID
email:
order:
type: object
properties:
cart:
type: object
properties:
txnId:
accountNumber:
storeFrontId:
shipMethod:
sendToFulfillment:
byodErrorEmail:
orderCompletionEmail:
cartItems:
type: array
items:
type: object
properties:
coverageZip: string
teamId:
referringMDN:
securityPIN:
email:
userName:
language:
example: |
{
"Customer": {
"firstName": "Jack",
"lastName": "Ophaltrades",
"titleCode": "Mr.",
"password": "somepassword",
"carrier": "Verizon",
"MId": "1234567",
"email": "[email protected]"
},
"order": {
"cart": {
"txnId": "3234234",
"accountNumber": "stri123456ng",
"storeFrontId": "1234",
"shipMethod": "UPS Ground",
"sendToFulfillment": "Yes",
"byodErrorEmail": "[email protected]",
"orderCompletionEmail": "true",
"cartItems":
[
{
"coverageZip": "90210"
},
{
"coverageZip": "23423"
}
],
"teamId": "1234",
"referringMDN": "16",
"securityPIN": "1561",
"email": "[email protected]",
"userName": "username",
"language": "ENG"
}
}
}
However, when I "try it", the HTTP response from the mocking service yields this error.
{ "error": "body: order: cart: cartItems: Cannot read property '#<Object>' of undefined" }
Thoughts as to what is wrong?