Copyright 2000 - 2026 the Confederation of European Paper Industries AISBL ("papiNet") the "Copyright Owner". All rights reserved by the Copyright Owner under the laws of the United States, Belgium, the European Economic Community, and all states, domestic and foreign. For support, more information, or to report implementation bugs, please contact papiNet at https://github.com/papinet.
This style guide documents guidelines and recommendations for designing JSON structures for the papiNet API. It clarifies and standardizes specific cases so that all JSON structures used by the papiNet API have a standard look and feel. These guidelines are applicable to JSON requests and responses.
For the purposes of this style guide, papiNet defines the following terms:
- property - a name/value pair inside a JSON object.
- property name - the name portion of the property, also called key.
- property value - the value portion of the property, sometimes simply called value.
So, within the following example:
{
"propertyName": "propertyValue",
"anotherPropertyName": "anotherPropertyValue"
}It's the "propertyName": "propertyValue" part, that papiNet calls a property.
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC2119.
If the context is clearly given by the parent, DO NOT repeat the context in the property name; If the context is NOT adequately given by the parent, then DO give the context in the property name up to what is necessary.
Let's give an example of each case:
-
within
supplierOrders[],supplierOrderNumbershould becomenumberbecause its parentsupplierOrders[]is giving the context. -
within
supplierOrders[],purchaseOrderNumbershould NOT becomenumberbecause its parentsupplierOrders[]is NOT giving the right context, it is not thenumber(identifier) of thesupplierOrders[], but of thenumber(identifier) ofpurchaseOrders[].
papiNet restrict enumerated values to the minimum list that applies within the context. As a consequence, objects will be usually be defined locally! However, if a structure can be reuse whatever the context is, it could be defined globally.
An empty collection MUST be communicated via the HTTP status code 204 No Content and the response MUST NOT contain a response's body. This rule will be enforced by not allowing empty array in the non-empty response's body using minItems: 1.
When papiNet defines a property with type string required, papiNet ALWAYS means that this property MUST communicate a non-empty information, therefore the constraint minLength: 1 will always be added.
When a property with type string is not required and there is no information to be communicated, the property MUST NOT appear in the response's body. That rule will be enforced by always add the constraint minLength: 1 to all properties with type string.
This minLength: 1 constraint will not be added to the property with type string that already has such a constraint via enum or format. Of course, more restrictive constraint with more than 1 character minimum can be defined, but not less!
papiNet does not set a maxLength to all properties with type string driven by system technical constraints. papiNet only sets a maxLength to a property with type string when it is driven by a business constraint!
The response body always contains the full representation of the resource, including the id even if it is already part of the request (usually conveyed by the URL).
When a response contains the reference to something (e.g. a seller-product), it MUST only contain the identifier of that thing and any additional information MUST be retrieved via a subsequent lookup. There should not be any lookup optimization combining the identifier with additional information.
When papiNet defines a property of type array, papiNet ALWAYS means that this array MUST have at least one element; therefore the constraint minItems: 1 will always be added.
... (with the execption of the id)
We MUST use UUID (only) for resource ID defined by the id property of every resource/entity/object.
When referring to another resource/entity/object we MUST also use this UUID only, therefore, to be able to know which type of resource/entity/object this UUID refers to, we MUST name of property or one of its ancestors including the type of resource/entity/object.
We have two types of properties capturing date and time:
- The properties ending with the suffix
...Timestamp: the MUST contain a date and time expressed in UTC, ending with the letter "Z", e.g.2024-04-23T13:24:26.000Z. - The properties ending with the suffix
...DateTime: they MUST contain a local date and time, in accordance with the ISO 8601 standard (preferably without explicit time-zone) for which the location is defined by the business context, excluding duration alone, but including intervals such as the following:2023-08-16T13:00/2023-08-18T13:002023-08-16/2023-08-182023-08-16T13:00/P2DP2D/2023-08-18T13:00
JSON properties MUST be written in lowerCamelCase names capitalize the first letter of each word, except the first which is always lowercase, even if it's an acronym. For instance, we have the property coordinatesWgs84: where Wgs stands for "World Geodetic System".
All names specified in path and query parameters, resource names, and JSON input and output fields and pre-defined values SHOULD NOT use abbreviations or acronyms.
However, we have decided, during papiNet CWG meeting 2024-06-19 (Wed), to make an exception with "unit of measure" that we will write uom or (...)Uom, instead of unitOfMeasure or (...)UnitOfMeasure.