-
Notifications
You must be signed in to change notification settings - Fork 0
/
deserializer.ts
74 lines (59 loc) · 2 KB
/
deserializer.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
import { AxiosResponse } from 'axios';
import isArray from 'lodash/isArray';
import isEmpty from 'lodash/isEmpty';
import { Resource } from 'types/resource';
import { JSONObject } from './json';
export interface DeserializableResponse extends AxiosResponse<Deserializer> {
included?: Deserializer[];
}
export interface DeserializableListResponse extends AxiosResponse<Deserializer[]> {
included?: Deserializer[];
}
export interface Deserializer {
type: string;
id: string;
attributes: JSONObject;
relationships?: Relationship;
}
export interface Relationship {
[key: string]: {
data: RelationshipResource | RelationshipResource[];
};
}
interface RelationshipResource {
type: string;
id: string;
}
export const deserialize = <T extends Resource>(data: Deserializer, included?: Deserializer[]): T => {
const relationships = data.relationships;
const resource = {
id: data.id,
resourceType: data.type,
...data.attributes,
};
if (relationships && included) {
const relationshipResource = (resourceId: string) => {
const matchingItem = included.find((item) => item.id === resourceId);
if (matchingItem) {
return deserialize(matchingItem, included);
}
};
Object.keys(relationships).forEach((resourceType: string) => {
const relationshipData = relationships[resourceType].data;
if (isArray(relationshipData) && !isEmpty(relationshipData)) {
const relationshipResources = relationshipData.map((item) => relationshipResource(item.id));
Object.assign(resource, {
[resourceType]: relationshipResources,
});
} else if (!isEmpty(relationshipData)) {
Object.assign(resource, {
[resourceType]: relationshipResource((relationshipData as RelationshipResource).id),
});
}
});
}
return resource as T;
};
export const deserializeList = <T extends Resource>(data: Deserializer[], included?: Deserializer[]): T[] => {
return data.map((item) => deserialize<T>(item, included));
};