util.js
3.79 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
'use strict';
const ApiError = require('./ApiError.js')
, HueError = require('./HueError') //TODO consider remove the use of this here now
;
const suppressDeprecationWarnings = process.env.NODE_HUE_API_SUPPRESS_DEPRICATION_WARNINGS || false;
module.exports = {
parseErrors: parseErrors,
wasSuccessful: wasSuccessful,
extractUpdatedAttributes: extractUpdatedAttributes,
toStringArray: asStringArray,
flatten: mergeArrays,
// getValueForKey: getValueforKey,
deprecatedFunction: deprecatedFunction,
};
/**
* Parses a JSON response looking for the errors in the result(s) returned.
* @param results The results to look for errors in.
* @returns {Array} Of errors found.
*/
function parseErrors(results) {
let errors = [];
if (Array.isArray(results)) {
results.forEach(result => {
if (!result.success) {
errors = errors.concat(this.parseErrors(result));
}
});
} else {
if (results.error) {
// Due to the handling of remote and local errors, we need to differentiate description and message in the errors,
// as the remote API uses both, whilst local uses only description. -- TODO need to review this
if (results.error.description && !results.error.message) {
const payload = Object.assign({message: results.error.description}, results.error);
errors.push(new HueError(payload));
} else {
errors.push(new HueError(results.error));
}
}
}
return errors.length > 0 ? errors : null;
}
/**
* Parses a JSON response checking for success on all changes.
* @param result The JSON object to parse for success messages.
* @returns {boolean} true if all changes were successful.
*/
function wasSuccessful(result) {
let success = true,
idx,
len;
if (Array.isArray(result)) {
for (idx = 0, len = result.length; idx < len; idx++) {
success = success && wasSuccessful(result[idx]);
}
} else {
success = result.success !== undefined;
}
return success;
}
function extractUpdatedAttributes(result) {
if (wasSuccessful(result)) {
const values = {};
result.forEach(update => {
const success = update.success;
Object.keys(success).forEach(key => {
const attribute = /.*\/(.*)$/.exec(key)[1];
values[attribute] = true; //success[key];
});
});
return values;
} else {
throw new ApiError('Error in response'); //TODO extract the error
}
}
//TODO the type system could replace this function now
function asStringArray(value) {
if (!value) {
return null;
}
if (Array.isArray(value)) {
const result = [];
value.forEach(val => {
result.push(`${val}`);
});
return result;
} else {
return [`${value}`];
}
}
// function getValueforKey(key, data) {
// //Use dot notation to get nested values
// const path = key.split('.');
//
// let target = data
// , value = null
// ;
//
// path.forEach(part => {
// if (target != null) {
// value = target[part];
// target = value;
// } else {
// target = null;
// }
// });
//
// return value;
// }
function mergeArrays() {
// TODO this can be replaced with [[], [], ...].flat under Node.js 12+
let result = [];
Array.from(arguments).forEach(arg => {
if (arg) {
result = result.concat(arg);
}
});
return result;
}
function deprecatedFunction(version, func, message) {
if (suppressDeprecationWarnings) {
return;
}
console.log(`**************************************************************************************************`);
console.log(`Deprecated Function Usage: ${func}\n`);
console.log(` ${message}\n`);
console.log(` Function will be removed from node-hue-api in version ${version}`);
console.log(`**************************************************************************************************`);
}