-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathrest-mapper.js
More file actions
161 lines (128 loc) · 4 KB
/
rest-mapper.js
File metadata and controls
161 lines (128 loc) · 4 KB
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
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
import axios from 'axios';
import merge from 'object-merge';
class RestMapper {
constructor(config) {
const defaultConfig = {
host: '',
resources: {},
cruds: {},
intercept: false
};
const c = merge({}, defaultConfig, config);
this.host = c.host;
this.resources = c.resources;
this.cruds = c.cruds;
// Defaults
const defaults = {
method: 'get'
};
this.defaults = merge({}, defaults, c.defaults || {});
// Create an axios instance
this.axios = axios.create(merge({}, this.defaults, {
baseURL: this.host
}));
// Intercept
this.buildIntercept(c);
return this.build(c);
}
build(config) {
let obj = {};
// Loop the cruds
for (let prop in this.cruds) {
obj[prop] = {};
// If the current crud has the property baseURL
const crud = this.cruds[prop];
if (crud.hasOwnProperty('baseURL')) {
let baseURL = crud.baseURL;
let methods = [
{ name: 'all', type: 'get', url: baseURL },
{ name: 'get', type: 'get', url: `${baseURL}/{id}` },
{ name: 'create', type: 'post', url: baseURL },
{ name: 'update', type: 'patch', url: `${baseURL}/{id}` },
{ name: 'delete', type: 'delete', url: `${baseURL}/{id}` }
];
// Runs inside methods
for (let i = 0, t = methods.length; i < t; i++) {
let method = methods[i];
let resource = merge({}, crud.defaults, {
url: method.url,
method: method.type
});
obj[prop][method.name] = this.call.bind(this, resource);
}
}
else {
return Promise.reject('Please, set a baseURL property to create your cruds methods.')
}
}
// Percorre os resources
for (let prop in this.resources) {
// Check if obj has the crud resource
obj[prop] = obj.hasOwnProperty(prop) ? obj[prop] : {};
// Percorre os filhos do resource
for (let method in this.resources[prop]) {
let resources = this.resources[prop][method];
obj[prop][method] = this.call.bind(this, resources);
}
}
return obj;
}
call(resources, params = {}) {
let options = merge({}, resources, params);
options.url = resources.hasOwnProperty('url') ? resources.url : '';
if (options.hasOwnProperty('supplant')) {
options.url = this._supplant(options.url, options.supplant);
}
return this.axios.request(options);
}
buildIntercept(c) {
// Create Interceptors
if (c.hasOwnProperty('intercept') && this._type(c) === 'object') {
let { intercept } = c;
// request
if (intercept.hasOwnProperty('request')) {
this.axios.interceptors.request.use(
// before send
function (config) {
if (intercept.request.hasOwnProperty('before')) intercept.request.before(config);
return config;
},
// request error
function (error) {
if (intercept.request.hasOwnProperty('error')) intercept.request.error(error);
return Promise.reject(error);
}
);
}
// response
if (intercept.hasOwnProperty('response')) {
this.axios.interceptors.response.use(
// response success
function (response) {
if (intercept.response.hasOwnProperty('success')) intercept.response.success(response);
return response;
},
// response error
function (error) {
if (intercept.response.hasOwnProperty('error')) intercept.response.error(error);
return Promise.reject(error);
}
);
}
}
}
_supplant(str, o) {
return str.replace(/{([^{}]*)}/g, function (a, b) {
var r = o[b];
return typeof r === 'string' || typeof r === 'number' ? r : a;
});
}
_type(obj) {
return Object.prototype.toString.call(obj)
.trim()
.toLowerCase()
.split(' ')[1]
.replace(/\]$/, '');
}
}
export default RestMapper;