UNPKG

11.1 kBMarkdownView Raw
1# JSON API Serializer
2
3<p align="center">
4 <img src="https://github.com/SeyZ/jsonapi-serializer/blob/master/logo.jpg?raw=true" alt="JSONAPI Serializer Logo">
5</p>
6
7[![Build Status](https://travis-ci.org/SeyZ/jsonapi-serializer.svg?branch=master)](https://travis-ci.org/SeyZ/jsonapi-serializer)
8[![npm version](https://img.shields.io/npm/v/jsonapi-serializer.svg)](https://yarnpkg.com/en/package/jsonapi-serializer)
9[![download](https://img.shields.io/npm/dm/jsonapi-serializer.svg)](https://yarnpkg.com/en/package/jsonapi-serializer)
10
11A Node.js framework agnostic library for (de)serializing your data to [JSON
12API](http://jsonapi.org) (1.0 compliant).
13
14- [Migrate from 2.0 to 3.0](https://github.com/SeyZ/jsonapi-serializer/wiki/Migrate-from-2.0-to-3.0)
15- [Migrate from 1.x to 2.0](https://github.com/SeyZ/jsonapi-serializer/wiki/Migrate-from-1.x-to-2.0)
16
17## Installation
18`$ npm install jsonapi-serializer`
19
20## Documentation
21
22### Serialization
23
24 var JSONAPISerializer = require('jsonapi-serializer').Serializer;
25 new JSONAPISerializer(type, opts).serialize(data);
26
27The function `JSONAPISerializer` takes two arguments:
28
29- `type`: The resource type.
30- `opts`: The serialization options.
31
32Calling the `serialize` method on the returned object will serialize your `data` (object or array) to a compliant JSONAPI document.
33
34
35#### Available serialization option (`opts` argument)
36
37- **attributes**: An array of attributes to show. You can define an attribute as an option if you want to define some relationships (included or not).
38 - **ref**: If present, it's considered as a relationships.
39 - **included**: Consider the relationships as [compound document](http://jsonapi.org/format/#document-compound-documents). Default: true.
40 - **id**: Configurable identifier field for the resource. Default: `id`.
41 - **attributes**: An array of attributes to show.
42 - **topLevelLinks**: An object that describes the top-level links. Values can be *string* or a *function*
43 - **dataLinks**: An object that describes the links inside data. Values can be *string* or a *function* (see examples below)
44 - **dataMeta**: An object that describes the meta inside data. Values can be a plain value or a *function* (see examples below)
45 - **relationshipLinks**: An object that describes the links inside relationships. Values can be *string* or a *function*
46 - **relationshipMeta**: An object that describes the meta inside relationships. Values can be a plain value or a *function*
47 - **ignoreRelationshipData**: Do not include the `data` key inside the relationship. Default: false.
48 - **keyForAttribute**: A function or string to customize attributes. Functions are passed the attribute as a single argument and expect a string to be returned. Strings are aliases for inbuilt functions for common case conversions. Options include: `dash-case` (default), `lisp-case`, `spinal-case`, `kebab-case`, `underscore_case`, `snake_case`, `camelCase`, `CamelCase`.
49 - **nullIfMissing**: Set the attribute to null if missing from your data input. Default: false.
50 - **pluralizeType**: A boolean to indicate if the type must be pluralized or not. Default: true.
51 - **typeForAttribute**: A function that maps the attribute (passed as an argument) to the type you want to override. If it returns `undefined`, ignores the flag for that attribute. Option *pluralizeType* ignored if set.
52 - **meta**: An object to include non-standard meta-information. Values can be a plain value or a *function*
53 - **transform**: A function to transform each record before the serialization.
54
55**Examples**
56
57- [Express example](https://github.com/SeyZ/jsonapi-serializer/tree/master/examples/express)
58- [Simple usage](#simple-usage-serializer)
59- [More examples in tests](https://github.com/SeyZ/jsonapi-serializer/blob/master/test/serializer.js)
60
61<a name="simple-usage-serializer"></a>
62Simple usage:
63
64```javascript
65var data = [
66 { id: 1, firstName: 'Sandro', lastName: 'Munda' },
67 { id: 2, firstName: 'John', lastName: 'Doe' }
68];
69```
70
71```javascript
72var JSONAPISerializer = require('jsonapi-serializer').Serializer;
73
74var UserSerializer = new JSONAPISerializer('users', {
75 attributes: ['firstName', 'lastName']
76});
77
78var users = UserSerializer.serialize(data);
79
80// `users` here are JSON API compliant.
81```
82
83The result will be something like:
84
85```javascript
86{
87 "data": [{
88 "type": "users",
89 "id": "1",
90 "attributes": {
91 "first-name": "Sandro",
92 "last-name": "Munda"
93 }
94 }, {
95 "type": "users",
96 "id": "2",
97 "attributes": {
98 "first-name": "John",
99 "last-name": "Doe"
100 }
101 }]
102}
103```
104
105### Deserialization
106
107 var JSONAPIDeserializer = require('jsonapi-serializer').Deserializer;
108 new JSONAPIDeserializer(opts).deserialize(data);
109
110The function `JSONAPIDeserializer` takes one argument:
111
112- `opts`: The deserializer options.
113
114Calling the `deserialize` method on the returned object will deserialize your `data` (JSONAPI document) to a plain javascript object.
115
116#### Available deserialization option (`opts` argument)
117
118- **keyForAttribute**: A function or string to customize attributes. Functions are passed the attribute as a single argument and expect a string to be returned. Strings are aliases for inbuilt functions for common case conversions. Options include: `dash-case` (default), `lisp-case`, `spinal-case`, `kebab-case`, `underscore_case`, `snake_case`, `camelCase`, `CamelCase`.
119- **AN\_ATTRIBUTE\_TYPE**: this option name corresponds to the type of a relationship from your JSONAPI document.
120 - **valueForRelationship**: A function that returns whatever you want for a relationship (see examples below) ***can return a Promise (see tests)***
121 - **transform**: A function to transform each record after the deserialization.
122
123**Examples**
124
125- [Simple usage](#simple-usage-deserializer)
126- [Relationship](#relationship-deserializer)
127- [More examples in tests](https://github.com/SeyZ/jsonapi-serializer/blob/master/test/deserializer.js)
128
129<a name="simple-usage-deserializer"></a>
130Simple usage:
131
132```
133{
134 data: [{
135 type: 'users',
136 id: '1',
137 attributes: {
138 'first-name': Sandro,
139 'last-name': Munda
140 }
141 }, {
142 type: 'users',
143 id: '2',
144 attributes: {
145 'first-name': 'John',
146 'last-name': 'Doe'
147 }
148 }]
149}
150```
151
152```javascript
153var JSONAPIDeserializer = require('jsonapi-serializer').Deserializer;
154
155new JSONAPIDeserializer().deserialize(jsonapi, function (err, users) {
156 // `users` is...
157});
158```
159
160```javascript
161[
162 { id: 1, firstName: 'Sandro', lastName: 'Munda' },
163 { id: 2, firstName: 'John', lastName: 'Doe' }
164];
165```
166<a name="relationship-deserializer"></a>
167Relationship:
168
169```
170{
171 data: [{
172 type: 'users',
173 id: '54735750e16638ba1eee59cb',
174 attributes: {
175 'first-name': 'Sandro',
176 'last-name': 'Munda'
177 },
178 relationships: {
179 address: {
180 data: { type: 'addresses', id: '54735722e16620ba1eee36af' }
181 }
182 }
183 }, {
184 type: 'users',
185 id: '5490143e69e49d0c8f9fc6bc',
186 attributes: {
187 'first-name': 'Lawrence',
188 'last-name': 'Bennett'
189 },
190 relationships: {
191 address: {
192 data: { type: 'addresses', id: '54735697e16624ba1eee36bf' }
193 }
194 }
195 }]
196}
197```
198
199```javascript
200var JSONAPIDeserializer = require('jsonapi-serializer').Deserializer;
201
202new JSONAPIDeserializer({
203 addresses: {
204 valueForRelationship: function (relationship) {
205 return {
206 id: relationship.id,
207 'address-line1': '406 Madison Court',
208 'zip-code': '49426',
209 country: 'USA'
210 };
211 }
212 }
213}).deserialize(jsonapi, function (err, users) {
214 // `users` is...
215});
216```
217
218```
219[{
220 id: '54735750e16638ba1eee59cb',
221 'first-name': 'Sandro',
222 'last-name': 'Munda',
223 address: {
224 id: '54735722e16620ba1eee36af',
225 'address-line1': '406 Madison Court',
226 'zip-code': '49426',
227 country: 'USA'
228 }
229}, {
230 id: '5490143e69e49d0c8f9fc6bc',
231 'first-name': 'Lawrence',
232 'last-name': 'Bennett',
233 address: {
234 id: '54735697e16624ba1eee36bf',
235 'address-line1': '406 Madison Court',
236 'zip-code': '49426',
237 country: 'USA'
238 }
239}]
240```
241
242#### Notes on Promises
243The deserialization option `valueForRelationship` supports returning a `Promise` and so this library uses `Promises` under the hood. `bluebird` was previously used as a dependency, but due to bundle size concerns on both node and the web it was replaced with native promises.
244
245`bluebird` is definitely [more performant](http://bluebirdjs.com/docs/benchmarks.html) than native Promises. If performance is a major concern `Promise` can be globally polyfilled
246- node - via `global.Promise = require('bluebird')`
247- web - global `Promise` automatically gets assigned when using the [script tag](http://bluebirdjs.com/docs/getting-started.html) to load `bluebird`
248
249## Error serialization
250
251 var JSONAPIError = require('jsonapi-serializer').Error;
252 var error = new JSONAPIError(opts);
253
254The function JSONAPIError takes one argument:
255
256- `opts`: The error options. All options are optional.
257
258#### Available error option (`opts` argument)
259
260- **id**: a unique identifier for this particular occurrence of the problem.
261- **status**: the HTTP status code applicable to this problem, expressed as a string value.
262- **code**: an application-specific error code, expressed as a string value.
263- **title**: a short, human-readable summary of the problem that SHOULD NOT change from occurrence to occurrence of the problem, except for purposes of localization.
264- **detail**: a human-readable explanation specific to this occurrence of the problem. Like title, this field’s value can be localized.
265- **source**: an object containing references to the source of the error, optionally including any of the following members:
266 - **pointer**: a JSON Pointer [RFC6901] to the associated entity in the request document [e.g. "/data" for a primary data object, or "/data/attributes/title" for a specific attribute].
267 - **parameter**: a string indicating which URI query parameter caused the error.
268- **links**: a links object containing the following members:
269 - **about**: a link that leads to further details about this particular occurrence of the problem.
270- **meta**: a meta object containing non-standard meta-information about the error.
271
272**Examples**
273
274- [Simple usage](#simple-usage-error)
275- [More example](https://github.com/SeyZ/jsonapi-serializer/blob/master/test/error.js)
276
277<a name="simple-usage-error"></a>
278Simple usage:
279
280```javascript
281var JSONAPIError = require('jsonapi-serializer').Error;
282
283var errors = new JSONAPIError({
284 code: '123',
285 source: { 'pointer': '/data/attributes/first-name' },
286 title: 'Value is too short',
287 detail: 'First name must contain at least three characters.'
288});
289
290// `errors` here are JSON API compliant.
291```
292
293The result will be something like:
294
295```javascript
296{
297 "errors": [
298 {
299 "code": "123",
300 "source": { "pointer": "/data/attributes/first-name" },
301 "title": "Value is too short",
302 "detail": "First name must contain at least three characters."
303 }
304 ]
305}
306```
307
308# License
309
310[MIT](https://github.com/SeyZ/jsonapi-serializer/blob/master/LICENSE)