.gitignore added
[dotfiles/.git] / .config / coc / extensions / node_modules / coc-prettier / node_modules / class-utils / index.js
1 'use strict';
2
3 var util = require('util');
4 var union = require('arr-union');
5 var define = require('define-property');
6 var staticExtend = require('static-extend');
7 var isObj = require('isobject');
8
9 /**
10  * Expose class utils
11  */
12
13 var cu = module.exports;
14
15 /**
16  * Expose class utils: `cu`
17  */
18
19 cu.isObject = function isObject(val) {
20   return isObj(val) || typeof val === 'function';
21 };
22
23 /**
24  * Returns true if an array has any of the given elements, or an
25  * object has any of the give keys.
26  *
27  * ```js
28  * cu.has(['a', 'b', 'c'], 'c');
29  * //=> true
30  *
31  * cu.has(['a', 'b', 'c'], ['c', 'z']);
32  * //=> true
33  *
34  * cu.has({a: 'b', c: 'd'}, ['c', 'z']);
35  * //=> true
36  * ```
37  * @param {Object} `obj`
38  * @param {String|Array} `val`
39  * @return {Boolean}
40  * @api public
41  */
42
43 cu.has = function has(obj, val) {
44   val = cu.arrayify(val);
45   var len = val.length;
46
47   if (cu.isObject(obj)) {
48     for (var key in obj) {
49       if (val.indexOf(key) > -1) {
50         return true;
51       }
52     }
53
54     var keys = cu.nativeKeys(obj);
55     return cu.has(keys, val);
56   }
57
58   if (Array.isArray(obj)) {
59     var arr = obj;
60     while (len--) {
61       if (arr.indexOf(val[len]) > -1) {
62         return true;
63       }
64     }
65     return false;
66   }
67
68   throw new TypeError('expected an array or object.');
69 };
70
71 /**
72  * Returns true if an array or object has all of the given values.
73  *
74  * ```js
75  * cu.hasAll(['a', 'b', 'c'], 'c');
76  * //=> true
77  *
78  * cu.hasAll(['a', 'b', 'c'], ['c', 'z']);
79  * //=> false
80  *
81  * cu.hasAll({a: 'b', c: 'd'}, ['c', 'z']);
82  * //=> false
83  * ```
84  * @param {Object|Array} `val`
85  * @param {String|Array} `values`
86  * @return {Boolean}
87  * @api public
88  */
89
90 cu.hasAll = function hasAll(val, values) {
91   values = cu.arrayify(values);
92   var len = values.length;
93   while (len--) {
94     if (!cu.has(val, values[len])) {
95       return false;
96     }
97   }
98   return true;
99 };
100
101 /**
102  * Cast the given value to an array.
103  *
104  * ```js
105  * cu.arrayify('foo');
106  * //=> ['foo']
107  *
108  * cu.arrayify(['foo']);
109  * //=> ['foo']
110  * ```
111  *
112  * @param {String|Array} `val`
113  * @return {Array}
114  * @api public
115  */
116
117 cu.arrayify = function arrayify(val) {
118   return val ? (Array.isArray(val) ? val : [val]) : [];
119 };
120
121 /**
122  * Noop
123  */
124
125 cu.noop = function noop() {
126   return;
127 };
128
129 /**
130  * Returns the first argument passed to the function.
131  */
132
133 cu.identity = function identity(val) {
134   return val;
135 };
136
137 /**
138  * Returns true if a value has a `contructor`
139  *
140  * ```js
141  * cu.hasConstructor({});
142  * //=> true
143  *
144  * cu.hasConstructor(Object.create(null));
145  * //=> false
146  * ```
147  * @param  {Object} `value`
148  * @return {Boolean}
149  * @api public
150  */
151
152 cu.hasConstructor = function hasConstructor(val) {
153   return cu.isObject(val) && typeof val.constructor !== 'undefined';
154 };
155
156 /**
157  * Get the native `ownPropertyNames` from the constructor of the
158  * given `object`. An empty array is returned if the object does
159  * not have a constructor.
160  *
161  * ```js
162  * cu.nativeKeys({a: 'b', b: 'c', c: 'd'})
163  * //=> ['a', 'b', 'c']
164  *
165  * cu.nativeKeys(function(){})
166  * //=> ['length', 'caller']
167  * ```
168  *
169  * @param  {Object} `obj` Object that has a `constructor`.
170  * @return {Array} Array of keys.
171  * @api public
172  */
173
174 cu.nativeKeys = function nativeKeys(val) {
175   if (!cu.hasConstructor(val)) return [];
176   var keys = Object.getOwnPropertyNames(val);
177   if ('caller' in val) keys.push('caller');
178   return keys;
179 };
180
181 /**
182  * Returns property descriptor `key` if it's an "own" property
183  * of the given object.
184  *
185  * ```js
186  * function App() {}
187  * Object.defineProperty(App.prototype, 'count', {
188  *   get: function() {
189  *     return Object.keys(this).length;
190  *   }
191  * });
192  * cu.getDescriptor(App.prototype, 'count');
193  * // returns:
194  * // {
195  * //   get: [Function],
196  * //   set: undefined,
197  * //   enumerable: false,
198  * //   configurable: false
199  * // }
200  * ```
201  *
202  * @param {Object} `obj`
203  * @param {String} `key`
204  * @return {Object} Returns descriptor `key`
205  * @api public
206  */
207
208 cu.getDescriptor = function getDescriptor(obj, key) {
209   if (!cu.isObject(obj)) {
210     throw new TypeError('expected an object.');
211   }
212   if (typeof key !== 'string') {
213     throw new TypeError('expected key to be a string.');
214   }
215   return Object.getOwnPropertyDescriptor(obj, key);
216 };
217
218 /**
219  * Copy a descriptor from one object to another.
220  *
221  * ```js
222  * function App() {}
223  * Object.defineProperty(App.prototype, 'count', {
224  *   get: function() {
225  *     return Object.keys(this).length;
226  *   }
227  * });
228  * var obj = {};
229  * cu.copyDescriptor(obj, App.prototype, 'count');
230  * ```
231  * @param {Object} `receiver`
232  * @param {Object} `provider`
233  * @param {String} `name`
234  * @return {Object}
235  * @api public
236  */
237
238 cu.copyDescriptor = function copyDescriptor(receiver, provider, name) {
239   if (!cu.isObject(receiver)) {
240     throw new TypeError('expected receiving object to be an object.');
241   }
242   if (!cu.isObject(provider)) {
243     throw new TypeError('expected providing object to be an object.');
244   }
245   if (typeof name !== 'string') {
246     throw new TypeError('expected name to be a string.');
247   }
248
249   var val = cu.getDescriptor(provider, name);
250   if (val) Object.defineProperty(receiver, name, val);
251 };
252
253 /**
254  * Copy static properties, prototype properties, and descriptors
255  * from one object to another.
256  *
257  * @param {Object} `receiver`
258  * @param {Object} `provider`
259  * @param {String|Array} `omit` One or more properties to omit
260  * @return {Object}
261  * @api public
262  */
263
264 cu.copy = function copy(receiver, provider, omit) {
265   if (!cu.isObject(receiver)) {
266     throw new TypeError('expected receiving object to be an object.');
267   }
268   if (!cu.isObject(provider)) {
269     throw new TypeError('expected providing object to be an object.');
270   }
271   var props = Object.getOwnPropertyNames(provider);
272   var keys = Object.keys(provider);
273   var len = props.length,
274     key;
275   omit = cu.arrayify(omit);
276
277   while (len--) {
278     key = props[len];
279
280     if (cu.has(keys, key)) {
281       define(receiver, key, provider[key]);
282     } else if (!(key in receiver) && !cu.has(omit, key)) {
283       cu.copyDescriptor(receiver, provider, key);
284     }
285   }
286 };
287
288 /**
289  * Inherit the static properties, prototype properties, and descriptors
290  * from of an object.
291  *
292  * @param {Object} `receiver`
293  * @param {Object} `provider`
294  * @param {String|Array} `omit` One or more properties to omit
295  * @return {Object}
296  * @api public
297  */
298
299 cu.inherit = function inherit(receiver, provider, omit) {
300   if (!cu.isObject(receiver)) {
301     throw new TypeError('expected receiving object to be an object.');
302   }
303   if (!cu.isObject(provider)) {
304     throw new TypeError('expected providing object to be an object.');
305   }
306
307   var keys = [];
308   for (var key in provider) {
309     keys.push(key);
310     receiver[key] = provider[key];
311   }
312
313   keys = keys.concat(cu.arrayify(omit));
314
315   var a = provider.prototype || provider;
316   var b = receiver.prototype || receiver;
317   cu.copy(b, a, keys);
318 };
319
320 /**
321  * Returns a function for extending the static properties,
322  * prototype properties, and descriptors from the `Parent`
323  * constructor onto `Child` constructors.
324  *
325  * ```js
326  * var extend = cu.extend(Parent);
327  * Parent.extend(Child);
328  *
329  * // optional methods
330  * Parent.extend(Child, {
331  *   foo: function() {},
332  *   bar: function() {}
333  * });
334  * ```
335  * @param {Function} `Parent` Parent ctor
336  * @param {Function} `extend` Optional extend function to handle custom extensions. Useful when updating methods that require a specific prototype.
337  *   @param {Function} `Child` Child ctor
338  *   @param {Object} `proto` Optionally pass additional prototype properties to inherit.
339  *   @return {Object}
340  * @api public
341  */
342
343 cu.extend = function() {
344   // keep it lazy, instead of assigning to `cu.extend`
345   return staticExtend.apply(null, arguments);
346 };
347
348 /**
349  * Bubble up events emitted from static methods on the Parent ctor.
350  *
351  * @param {Object} `Parent`
352  * @param {Array} `events` Event names to bubble up
353  * @api public
354  */
355
356 cu.bubble = function(Parent, events) {
357   events = events || [];
358   Parent.bubble = function(Child, arr) {
359     if (Array.isArray(arr)) {
360       events = union([], events, arr);
361     }
362     var len = events.length;
363     var idx = -1;
364     while (++idx < len) {
365       var name = events[idx];
366       Parent.on(name, Child.emit.bind(Child, name));
367     }
368     cu.bubble(Child, events);
369   };
370 };