@react-native/js-polyfills 0.72.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Object.es8.js +58 -0
- package/console.js +631 -0
- package/error-guard.js +123 -0
- package/index.js +16 -0
- package/package.json +11 -0
package/Object.es8.js
ADDED
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
* @format
|
|
8
|
+
* @polyfill
|
|
9
|
+
* @nolint
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
(function () {
|
|
13
|
+
'use strict';
|
|
14
|
+
|
|
15
|
+
const hasOwnProperty = Object.prototype.hasOwnProperty;
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* Returns an array of the given object's own enumerable entries.
|
|
19
|
+
* https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/entries
|
|
20
|
+
*/
|
|
21
|
+
if (typeof Object.entries !== 'function') {
|
|
22
|
+
Object.entries = function (object) {
|
|
23
|
+
// `null` and `undefined` values are not allowed.
|
|
24
|
+
if (object == null) {
|
|
25
|
+
throw new TypeError('Object.entries called on non-object');
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
const entries = [];
|
|
29
|
+
for (const key in object) {
|
|
30
|
+
if (hasOwnProperty.call(object, key)) {
|
|
31
|
+
entries.push([key, object[key]]);
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
return entries;
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* Returns an array of the given object's own enumerable entries.
|
|
40
|
+
* https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/values
|
|
41
|
+
*/
|
|
42
|
+
if (typeof Object.values !== 'function') {
|
|
43
|
+
Object.values = function (object) {
|
|
44
|
+
// `null` and `undefined` values are not allowed.
|
|
45
|
+
if (object == null) {
|
|
46
|
+
throw new TypeError('Object.values called on non-object');
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
const values = [];
|
|
50
|
+
for (const key in object) {
|
|
51
|
+
if (hasOwnProperty.call(object, key)) {
|
|
52
|
+
values.push(object[key]);
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
return values;
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
})();
|
package/console.js
ADDED
|
@@ -0,0 +1,631 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
* @polyfill
|
|
8
|
+
* @nolint
|
|
9
|
+
* @format
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
/* eslint-disable no-shadow, eqeqeq, curly, no-unused-vars, no-void, no-control-regex */
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* This pipes all of our console logging functions to native logging so that
|
|
16
|
+
* JavaScript errors in required modules show up in Xcode via NSLog.
|
|
17
|
+
*/
|
|
18
|
+
const inspect = (function () {
|
|
19
|
+
// Copyright Joyent, Inc. and other Node contributors.
|
|
20
|
+
//
|
|
21
|
+
// Permission is hereby granted, free of charge, to any person obtaining a
|
|
22
|
+
// copy of this software and associated documentation files (the
|
|
23
|
+
// "Software"), to deal in the Software without restriction, including
|
|
24
|
+
// without limitation the rights to use, copy, modify, merge, publish,
|
|
25
|
+
// distribute, sublicense, and/or sell copies of the Software, and to permit
|
|
26
|
+
// persons to whom the Software is furnished to do so, subject to the
|
|
27
|
+
// following conditions:
|
|
28
|
+
//
|
|
29
|
+
// The above copyright notice and this permission notice shall be included
|
|
30
|
+
// in all copies or substantial portions of the Software.
|
|
31
|
+
//
|
|
32
|
+
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
33
|
+
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
34
|
+
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN
|
|
35
|
+
// NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
|
|
36
|
+
// DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
|
37
|
+
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
|
|
38
|
+
// USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
39
|
+
//
|
|
40
|
+
// https://github.com/joyent/node/blob/master/lib/util.js
|
|
41
|
+
|
|
42
|
+
function inspect(obj, opts) {
|
|
43
|
+
var ctx = {
|
|
44
|
+
seen: [],
|
|
45
|
+
formatValueCalls: 0,
|
|
46
|
+
stylize: stylizeNoColor,
|
|
47
|
+
};
|
|
48
|
+
return formatValue(ctx, obj, opts.depth);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
function stylizeNoColor(str, styleType) {
|
|
52
|
+
return str;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
function arrayToHash(array) {
|
|
56
|
+
var hash = {};
|
|
57
|
+
|
|
58
|
+
array.forEach(function (val, idx) {
|
|
59
|
+
hash[val] = true;
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
return hash;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
function formatValue(ctx, value, recurseTimes) {
|
|
66
|
+
ctx.formatValueCalls++;
|
|
67
|
+
if (ctx.formatValueCalls > 200) {
|
|
68
|
+
return `[TOO BIG formatValueCalls ${ctx.formatValueCalls} exceeded limit of 200]`;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
// Primitive types cannot have properties
|
|
72
|
+
var primitive = formatPrimitive(ctx, value);
|
|
73
|
+
if (primitive) {
|
|
74
|
+
return primitive;
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
// Look up the keys of the object.
|
|
78
|
+
var keys = Object.keys(value);
|
|
79
|
+
var visibleKeys = arrayToHash(keys);
|
|
80
|
+
|
|
81
|
+
// IE doesn't make error fields non-enumerable
|
|
82
|
+
// http://msdn.microsoft.com/en-us/library/ie/dww52sbt(v=vs.94).aspx
|
|
83
|
+
if (
|
|
84
|
+
isError(value) &&
|
|
85
|
+
(keys.indexOf('message') >= 0 || keys.indexOf('description') >= 0)
|
|
86
|
+
) {
|
|
87
|
+
return formatError(value);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
// Some type of object without properties can be shortcutted.
|
|
91
|
+
if (keys.length === 0) {
|
|
92
|
+
if (isFunction(value)) {
|
|
93
|
+
var name = value.name ? ': ' + value.name : '';
|
|
94
|
+
return ctx.stylize('[Function' + name + ']', 'special');
|
|
95
|
+
}
|
|
96
|
+
if (isRegExp(value)) {
|
|
97
|
+
return ctx.stylize(RegExp.prototype.toString.call(value), 'regexp');
|
|
98
|
+
}
|
|
99
|
+
if (isDate(value)) {
|
|
100
|
+
return ctx.stylize(Date.prototype.toString.call(value), 'date');
|
|
101
|
+
}
|
|
102
|
+
if (isError(value)) {
|
|
103
|
+
return formatError(value);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
var base = '',
|
|
108
|
+
array = false,
|
|
109
|
+
braces = ['{', '}'];
|
|
110
|
+
|
|
111
|
+
// Make Array say that they are Array
|
|
112
|
+
if (isArray(value)) {
|
|
113
|
+
array = true;
|
|
114
|
+
braces = ['[', ']'];
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// Make functions say that they are functions
|
|
118
|
+
if (isFunction(value)) {
|
|
119
|
+
var n = value.name ? ': ' + value.name : '';
|
|
120
|
+
base = ' [Function' + n + ']';
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
// Make RegExps say that they are RegExps
|
|
124
|
+
if (isRegExp(value)) {
|
|
125
|
+
base = ' ' + RegExp.prototype.toString.call(value);
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
// Make dates with properties first say the date
|
|
129
|
+
if (isDate(value)) {
|
|
130
|
+
base = ' ' + Date.prototype.toUTCString.call(value);
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
// Make error with message first say the error
|
|
134
|
+
if (isError(value)) {
|
|
135
|
+
base = ' ' + formatError(value);
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
if (keys.length === 0 && (!array || value.length == 0)) {
|
|
139
|
+
return braces[0] + base + braces[1];
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
if (recurseTimes < 0) {
|
|
143
|
+
if (isRegExp(value)) {
|
|
144
|
+
return ctx.stylize(RegExp.prototype.toString.call(value), 'regexp');
|
|
145
|
+
} else {
|
|
146
|
+
return ctx.stylize('[Object]', 'special');
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
ctx.seen.push(value);
|
|
151
|
+
|
|
152
|
+
var output;
|
|
153
|
+
if (array) {
|
|
154
|
+
output = formatArray(ctx, value, recurseTimes, visibleKeys, keys);
|
|
155
|
+
} else {
|
|
156
|
+
output = keys.map(function (key) {
|
|
157
|
+
return formatProperty(
|
|
158
|
+
ctx,
|
|
159
|
+
value,
|
|
160
|
+
recurseTimes,
|
|
161
|
+
visibleKeys,
|
|
162
|
+
key,
|
|
163
|
+
array,
|
|
164
|
+
);
|
|
165
|
+
});
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
ctx.seen.pop();
|
|
169
|
+
|
|
170
|
+
return reduceToSingleString(output, base, braces);
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
function formatPrimitive(ctx, value) {
|
|
174
|
+
if (isUndefined(value)) return ctx.stylize('undefined', 'undefined');
|
|
175
|
+
if (isString(value)) {
|
|
176
|
+
var simple =
|
|
177
|
+
"'" +
|
|
178
|
+
JSON.stringify(value)
|
|
179
|
+
.replace(/^"|"$/g, '')
|
|
180
|
+
.replace(/'/g, "\\'")
|
|
181
|
+
.replace(/\\"/g, '"') +
|
|
182
|
+
"'";
|
|
183
|
+
return ctx.stylize(simple, 'string');
|
|
184
|
+
}
|
|
185
|
+
if (isNumber(value)) return ctx.stylize('' + value, 'number');
|
|
186
|
+
if (isBoolean(value)) return ctx.stylize('' + value, 'boolean');
|
|
187
|
+
// For some reason typeof null is "object", so special case here.
|
|
188
|
+
if (isNull(value)) return ctx.stylize('null', 'null');
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
function formatError(value) {
|
|
192
|
+
return '[' + Error.prototype.toString.call(value) + ']';
|
|
193
|
+
}
|
|
194
|
+
|
|
195
|
+
function formatArray(ctx, value, recurseTimes, visibleKeys, keys) {
|
|
196
|
+
var output = [];
|
|
197
|
+
for (var i = 0, l = value.length; i < l; ++i) {
|
|
198
|
+
if (hasOwnProperty(value, String(i))) {
|
|
199
|
+
output.push(
|
|
200
|
+
formatProperty(
|
|
201
|
+
ctx,
|
|
202
|
+
value,
|
|
203
|
+
recurseTimes,
|
|
204
|
+
visibleKeys,
|
|
205
|
+
String(i),
|
|
206
|
+
true,
|
|
207
|
+
),
|
|
208
|
+
);
|
|
209
|
+
} else {
|
|
210
|
+
output.push('');
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
keys.forEach(function (key) {
|
|
214
|
+
if (!key.match(/^\d+$/)) {
|
|
215
|
+
output.push(
|
|
216
|
+
formatProperty(ctx, value, recurseTimes, visibleKeys, key, true),
|
|
217
|
+
);
|
|
218
|
+
}
|
|
219
|
+
});
|
|
220
|
+
return output;
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
function formatProperty(ctx, value, recurseTimes, visibleKeys, key, array) {
|
|
224
|
+
var name, str, desc;
|
|
225
|
+
desc = Object.getOwnPropertyDescriptor(value, key) || {value: value[key]};
|
|
226
|
+
if (desc.get) {
|
|
227
|
+
if (desc.set) {
|
|
228
|
+
str = ctx.stylize('[Getter/Setter]', 'special');
|
|
229
|
+
} else {
|
|
230
|
+
str = ctx.stylize('[Getter]', 'special');
|
|
231
|
+
}
|
|
232
|
+
} else {
|
|
233
|
+
if (desc.set) {
|
|
234
|
+
str = ctx.stylize('[Setter]', 'special');
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
if (!hasOwnProperty(visibleKeys, key)) {
|
|
238
|
+
name = '[' + key + ']';
|
|
239
|
+
}
|
|
240
|
+
if (!str) {
|
|
241
|
+
if (ctx.seen.indexOf(desc.value) < 0) {
|
|
242
|
+
if (isNull(recurseTimes)) {
|
|
243
|
+
str = formatValue(ctx, desc.value, null);
|
|
244
|
+
} else {
|
|
245
|
+
str = formatValue(ctx, desc.value, recurseTimes - 1);
|
|
246
|
+
}
|
|
247
|
+
if (str.indexOf('\n') > -1) {
|
|
248
|
+
if (array) {
|
|
249
|
+
str = str
|
|
250
|
+
.split('\n')
|
|
251
|
+
.map(function (line) {
|
|
252
|
+
return ' ' + line;
|
|
253
|
+
})
|
|
254
|
+
.join('\n')
|
|
255
|
+
.substr(2);
|
|
256
|
+
} else {
|
|
257
|
+
str =
|
|
258
|
+
'\n' +
|
|
259
|
+
str
|
|
260
|
+
.split('\n')
|
|
261
|
+
.map(function (line) {
|
|
262
|
+
return ' ' + line;
|
|
263
|
+
})
|
|
264
|
+
.join('\n');
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
} else {
|
|
268
|
+
str = ctx.stylize('[Circular]', 'special');
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
if (isUndefined(name)) {
|
|
272
|
+
if (array && key.match(/^\d+$/)) {
|
|
273
|
+
return str;
|
|
274
|
+
}
|
|
275
|
+
name = JSON.stringify('' + key);
|
|
276
|
+
if (name.match(/^"([a-zA-Z_][a-zA-Z_0-9]*)"$/)) {
|
|
277
|
+
name = name.substr(1, name.length - 2);
|
|
278
|
+
name = ctx.stylize(name, 'name');
|
|
279
|
+
} else {
|
|
280
|
+
name = name
|
|
281
|
+
.replace(/'/g, "\\'")
|
|
282
|
+
.replace(/\\"/g, '"')
|
|
283
|
+
.replace(/(^"|"$)/g, "'");
|
|
284
|
+
name = ctx.stylize(name, 'string');
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
|
|
288
|
+
return name + ': ' + str;
|
|
289
|
+
}
|
|
290
|
+
|
|
291
|
+
function reduceToSingleString(output, base, braces) {
|
|
292
|
+
var numLinesEst = 0;
|
|
293
|
+
var length = output.reduce(function (prev, cur) {
|
|
294
|
+
numLinesEst++;
|
|
295
|
+
if (cur.indexOf('\n') >= 0) numLinesEst++;
|
|
296
|
+
return prev + cur.replace(/\u001b\[\d\d?m/g, '').length + 1;
|
|
297
|
+
}, 0);
|
|
298
|
+
|
|
299
|
+
if (length > 60) {
|
|
300
|
+
return (
|
|
301
|
+
braces[0] +
|
|
302
|
+
(base === '' ? '' : base + '\n ') +
|
|
303
|
+
' ' +
|
|
304
|
+
output.join(',\n ') +
|
|
305
|
+
' ' +
|
|
306
|
+
braces[1]
|
|
307
|
+
);
|
|
308
|
+
}
|
|
309
|
+
|
|
310
|
+
return braces[0] + base + ' ' + output.join(', ') + ' ' + braces[1];
|
|
311
|
+
}
|
|
312
|
+
|
|
313
|
+
// NOTE: These type checking functions intentionally don't use `instanceof`
|
|
314
|
+
// because it is fragile and can be easily faked with `Object.create()`.
|
|
315
|
+
function isArray(ar) {
|
|
316
|
+
return Array.isArray(ar);
|
|
317
|
+
}
|
|
318
|
+
|
|
319
|
+
function isBoolean(arg) {
|
|
320
|
+
return typeof arg === 'boolean';
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
function isNull(arg) {
|
|
324
|
+
return arg === null;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
function isNullOrUndefined(arg) {
|
|
328
|
+
return arg == null;
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
function isNumber(arg) {
|
|
332
|
+
return typeof arg === 'number';
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
function isString(arg) {
|
|
336
|
+
return typeof arg === 'string';
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
function isSymbol(arg) {
|
|
340
|
+
return typeof arg === 'symbol';
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
function isUndefined(arg) {
|
|
344
|
+
return arg === void 0;
|
|
345
|
+
}
|
|
346
|
+
|
|
347
|
+
function isRegExp(re) {
|
|
348
|
+
return isObject(re) && objectToString(re) === '[object RegExp]';
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
function isObject(arg) {
|
|
352
|
+
return typeof arg === 'object' && arg !== null;
|
|
353
|
+
}
|
|
354
|
+
|
|
355
|
+
function isDate(d) {
|
|
356
|
+
return isObject(d) && objectToString(d) === '[object Date]';
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
function isError(e) {
|
|
360
|
+
return (
|
|
361
|
+
isObject(e) &&
|
|
362
|
+
(objectToString(e) === '[object Error]' || e instanceof Error)
|
|
363
|
+
);
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
function isFunction(arg) {
|
|
367
|
+
return typeof arg === 'function';
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
function objectToString(o) {
|
|
371
|
+
return Object.prototype.toString.call(o);
|
|
372
|
+
}
|
|
373
|
+
|
|
374
|
+
function hasOwnProperty(obj, prop) {
|
|
375
|
+
return Object.prototype.hasOwnProperty.call(obj, prop);
|
|
376
|
+
}
|
|
377
|
+
|
|
378
|
+
return inspect;
|
|
379
|
+
})();
|
|
380
|
+
|
|
381
|
+
const OBJECT_COLUMN_NAME = '(index)';
|
|
382
|
+
const LOG_LEVELS = {
|
|
383
|
+
trace: 0,
|
|
384
|
+
info: 1,
|
|
385
|
+
warn: 2,
|
|
386
|
+
error: 3,
|
|
387
|
+
};
|
|
388
|
+
const INSPECTOR_LEVELS = [];
|
|
389
|
+
INSPECTOR_LEVELS[LOG_LEVELS.trace] = 'debug';
|
|
390
|
+
INSPECTOR_LEVELS[LOG_LEVELS.info] = 'log';
|
|
391
|
+
INSPECTOR_LEVELS[LOG_LEVELS.warn] = 'warning';
|
|
392
|
+
INSPECTOR_LEVELS[LOG_LEVELS.error] = 'error';
|
|
393
|
+
|
|
394
|
+
// Strip the inner function in getNativeLogFunction(), if in dev also
|
|
395
|
+
// strip method printing to originalConsole.
|
|
396
|
+
const INSPECTOR_FRAMES_TO_SKIP = __DEV__ ? 2 : 1;
|
|
397
|
+
|
|
398
|
+
function getNativeLogFunction(level) {
|
|
399
|
+
return function () {
|
|
400
|
+
let str;
|
|
401
|
+
if (arguments.length === 1 && typeof arguments[0] === 'string') {
|
|
402
|
+
str = arguments[0];
|
|
403
|
+
} else {
|
|
404
|
+
str = Array.prototype.map
|
|
405
|
+
.call(arguments, function (arg) {
|
|
406
|
+
return inspect(arg, {depth: 10});
|
|
407
|
+
})
|
|
408
|
+
.join(', ');
|
|
409
|
+
}
|
|
410
|
+
|
|
411
|
+
// TRICKY
|
|
412
|
+
// If more than one argument is provided, the code above collapses them all
|
|
413
|
+
// into a single formatted string. This transform wraps string arguments in
|
|
414
|
+
// single quotes (e.g. "foo" -> "'foo'") which then breaks the "Warning:"
|
|
415
|
+
// check below. So it's important that we look at the first argument, rather
|
|
416
|
+
// than the formatted argument string.
|
|
417
|
+
const firstArg = arguments[0];
|
|
418
|
+
|
|
419
|
+
let logLevel = level;
|
|
420
|
+
if (
|
|
421
|
+
typeof firstArg === 'string' &&
|
|
422
|
+
firstArg.slice(0, 9) === 'Warning: ' &&
|
|
423
|
+
logLevel >= LOG_LEVELS.error
|
|
424
|
+
) {
|
|
425
|
+
// React warnings use console.error so that a stack trace is shown,
|
|
426
|
+
// but we don't (currently) want these to show a redbox
|
|
427
|
+
// (Note: Logic duplicated in ExceptionsManager.js.)
|
|
428
|
+
logLevel = LOG_LEVELS.warn;
|
|
429
|
+
}
|
|
430
|
+
if (global.__inspectorLog) {
|
|
431
|
+
global.__inspectorLog(
|
|
432
|
+
INSPECTOR_LEVELS[logLevel],
|
|
433
|
+
str,
|
|
434
|
+
[].slice.call(arguments),
|
|
435
|
+
INSPECTOR_FRAMES_TO_SKIP,
|
|
436
|
+
);
|
|
437
|
+
}
|
|
438
|
+
if (groupStack.length) {
|
|
439
|
+
str = groupFormat('', str);
|
|
440
|
+
}
|
|
441
|
+
global.nativeLoggingHook(str, logLevel);
|
|
442
|
+
};
|
|
443
|
+
}
|
|
444
|
+
|
|
445
|
+
function repeat(element, n) {
|
|
446
|
+
return Array.apply(null, Array(n)).map(function () {
|
|
447
|
+
return element;
|
|
448
|
+
});
|
|
449
|
+
}
|
|
450
|
+
|
|
451
|
+
function consoleTablePolyfill(rows) {
|
|
452
|
+
// convert object -> array
|
|
453
|
+
if (!Array.isArray(rows)) {
|
|
454
|
+
var data = rows;
|
|
455
|
+
rows = [];
|
|
456
|
+
for (var key in data) {
|
|
457
|
+
if (data.hasOwnProperty(key)) {
|
|
458
|
+
var row = data[key];
|
|
459
|
+
row[OBJECT_COLUMN_NAME] = key;
|
|
460
|
+
rows.push(row);
|
|
461
|
+
}
|
|
462
|
+
}
|
|
463
|
+
}
|
|
464
|
+
if (rows.length === 0) {
|
|
465
|
+
global.nativeLoggingHook('', LOG_LEVELS.info);
|
|
466
|
+
return;
|
|
467
|
+
}
|
|
468
|
+
|
|
469
|
+
var columns = Object.keys(rows[0]).sort();
|
|
470
|
+
var stringRows = [];
|
|
471
|
+
var columnWidths = [];
|
|
472
|
+
|
|
473
|
+
// Convert each cell to a string. Also
|
|
474
|
+
// figure out max cell width for each column
|
|
475
|
+
columns.forEach(function (k, i) {
|
|
476
|
+
columnWidths[i] = k.length;
|
|
477
|
+
for (var j = 0; j < rows.length; j++) {
|
|
478
|
+
var cellStr = (rows[j][k] || '?').toString();
|
|
479
|
+
stringRows[j] = stringRows[j] || [];
|
|
480
|
+
stringRows[j][i] = cellStr;
|
|
481
|
+
columnWidths[i] = Math.max(columnWidths[i], cellStr.length);
|
|
482
|
+
}
|
|
483
|
+
});
|
|
484
|
+
|
|
485
|
+
// Join all elements in the row into a single string with | separators
|
|
486
|
+
// (appends extra spaces to each cell to make separators | aligned)
|
|
487
|
+
function joinRow(row, space) {
|
|
488
|
+
var cells = row.map(function (cell, i) {
|
|
489
|
+
var extraSpaces = repeat(' ', columnWidths[i] - cell.length).join('');
|
|
490
|
+
return cell + extraSpaces;
|
|
491
|
+
});
|
|
492
|
+
space = space || ' ';
|
|
493
|
+
return cells.join(space + '|' + space);
|
|
494
|
+
}
|
|
495
|
+
|
|
496
|
+
var separators = columnWidths.map(function (columnWidth) {
|
|
497
|
+
return repeat('-', columnWidth).join('');
|
|
498
|
+
});
|
|
499
|
+
var separatorRow = joinRow(separators, '-');
|
|
500
|
+
var header = joinRow(columns);
|
|
501
|
+
var table = [header, separatorRow];
|
|
502
|
+
|
|
503
|
+
for (var i = 0; i < rows.length; i++) {
|
|
504
|
+
table.push(joinRow(stringRows[i]));
|
|
505
|
+
}
|
|
506
|
+
|
|
507
|
+
// Notice extra empty line at the beginning.
|
|
508
|
+
// Native logging hook adds "RCTLog >" at the front of every
|
|
509
|
+
// logged string, which would shift the header and screw up
|
|
510
|
+
// the table
|
|
511
|
+
global.nativeLoggingHook('\n' + table.join('\n'), LOG_LEVELS.info);
|
|
512
|
+
}
|
|
513
|
+
|
|
514
|
+
const GROUP_PAD = '\u2502'; // Box light vertical
|
|
515
|
+
const GROUP_OPEN = '\u2510'; // Box light down+left
|
|
516
|
+
const GROUP_CLOSE = '\u2518'; // Box light up+left
|
|
517
|
+
|
|
518
|
+
const groupStack = [];
|
|
519
|
+
|
|
520
|
+
function groupFormat(prefix, msg) {
|
|
521
|
+
// Insert group formatting before the console message
|
|
522
|
+
return groupStack.join('') + prefix + ' ' + (msg || '');
|
|
523
|
+
}
|
|
524
|
+
|
|
525
|
+
function consoleGroupPolyfill(label) {
|
|
526
|
+
global.nativeLoggingHook(groupFormat(GROUP_OPEN, label), LOG_LEVELS.info);
|
|
527
|
+
groupStack.push(GROUP_PAD);
|
|
528
|
+
}
|
|
529
|
+
|
|
530
|
+
function consoleGroupCollapsedPolyfill(label) {
|
|
531
|
+
global.nativeLoggingHook(groupFormat(GROUP_CLOSE, label), LOG_LEVELS.info);
|
|
532
|
+
groupStack.push(GROUP_PAD);
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
function consoleGroupEndPolyfill() {
|
|
536
|
+
groupStack.pop();
|
|
537
|
+
global.nativeLoggingHook(groupFormat(GROUP_CLOSE), LOG_LEVELS.info);
|
|
538
|
+
}
|
|
539
|
+
|
|
540
|
+
function consoleAssertPolyfill(expression, label) {
|
|
541
|
+
if (!expression) {
|
|
542
|
+
global.nativeLoggingHook('Assertion failed: ' + label, LOG_LEVELS.error);
|
|
543
|
+
}
|
|
544
|
+
}
|
|
545
|
+
|
|
546
|
+
if (global.nativeLoggingHook) {
|
|
547
|
+
const originalConsole = global.console;
|
|
548
|
+
// Preserve the original `console` as `originalConsole`
|
|
549
|
+
if (__DEV__ && originalConsole) {
|
|
550
|
+
const descriptor = Object.getOwnPropertyDescriptor(global, 'console');
|
|
551
|
+
if (descriptor) {
|
|
552
|
+
Object.defineProperty(global, 'originalConsole', descriptor);
|
|
553
|
+
}
|
|
554
|
+
}
|
|
555
|
+
|
|
556
|
+
global.console = {
|
|
557
|
+
error: getNativeLogFunction(LOG_LEVELS.error),
|
|
558
|
+
info: getNativeLogFunction(LOG_LEVELS.info),
|
|
559
|
+
log: getNativeLogFunction(LOG_LEVELS.info),
|
|
560
|
+
warn: getNativeLogFunction(LOG_LEVELS.warn),
|
|
561
|
+
trace: getNativeLogFunction(LOG_LEVELS.trace),
|
|
562
|
+
debug: getNativeLogFunction(LOG_LEVELS.trace),
|
|
563
|
+
table: consoleTablePolyfill,
|
|
564
|
+
group: consoleGroupPolyfill,
|
|
565
|
+
groupEnd: consoleGroupEndPolyfill,
|
|
566
|
+
groupCollapsed: consoleGroupCollapsedPolyfill,
|
|
567
|
+
assert: consoleAssertPolyfill,
|
|
568
|
+
};
|
|
569
|
+
|
|
570
|
+
Object.defineProperty(console, '_isPolyfilled', {
|
|
571
|
+
value: true,
|
|
572
|
+
enumerable: false,
|
|
573
|
+
});
|
|
574
|
+
|
|
575
|
+
// If available, also call the original `console` method since that is
|
|
576
|
+
// sometimes useful. Ex: on OS X, this will let you see rich output in
|
|
577
|
+
// the Safari Web Inspector console.
|
|
578
|
+
if (__DEV__ && originalConsole) {
|
|
579
|
+
Object.keys(console).forEach(methodName => {
|
|
580
|
+
const reactNativeMethod = console[methodName];
|
|
581
|
+
if (originalConsole[methodName]) {
|
|
582
|
+
console[methodName] = function () {
|
|
583
|
+
originalConsole[methodName](...arguments);
|
|
584
|
+
reactNativeMethod.apply(console, arguments);
|
|
585
|
+
};
|
|
586
|
+
}
|
|
587
|
+
});
|
|
588
|
+
|
|
589
|
+
// The following methods are not supported by this polyfill but
|
|
590
|
+
// we still should pass them to original console if they are
|
|
591
|
+
// supported by it.
|
|
592
|
+
['clear', 'dir', 'dirxml', 'profile', 'profileEnd'].forEach(methodName => {
|
|
593
|
+
if (typeof originalConsole[methodName] === 'function') {
|
|
594
|
+
console[methodName] = function () {
|
|
595
|
+
originalConsole[methodName](...arguments);
|
|
596
|
+
};
|
|
597
|
+
}
|
|
598
|
+
});
|
|
599
|
+
}
|
|
600
|
+
} else if (!global.console) {
|
|
601
|
+
function stub() {}
|
|
602
|
+
const log = global.print || stub;
|
|
603
|
+
|
|
604
|
+
global.console = {
|
|
605
|
+
debug: log,
|
|
606
|
+
error: log,
|
|
607
|
+
info: log,
|
|
608
|
+
log: log,
|
|
609
|
+
trace: log,
|
|
610
|
+
warn: log,
|
|
611
|
+
assert(expression, label) {
|
|
612
|
+
if (!expression) {
|
|
613
|
+
log('Assertion failed: ' + label);
|
|
614
|
+
}
|
|
615
|
+
},
|
|
616
|
+
clear: stub,
|
|
617
|
+
dir: stub,
|
|
618
|
+
dirxml: stub,
|
|
619
|
+
group: stub,
|
|
620
|
+
groupCollapsed: stub,
|
|
621
|
+
groupEnd: stub,
|
|
622
|
+
profile: stub,
|
|
623
|
+
profileEnd: stub,
|
|
624
|
+
table: stub,
|
|
625
|
+
};
|
|
626
|
+
|
|
627
|
+
Object.defineProperty(console, '_isPolyfilled', {
|
|
628
|
+
value: true,
|
|
629
|
+
enumerable: false,
|
|
630
|
+
});
|
|
631
|
+
}
|
package/error-guard.js
ADDED
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
* @format
|
|
8
|
+
* @flow strict
|
|
9
|
+
* @polyfill
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
let _inGuard = 0;
|
|
13
|
+
|
|
14
|
+
type ErrorHandler = (error: mixed, isFatal: boolean) => void;
|
|
15
|
+
type Fn<Args, Return> = (...Args) => Return;
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* This is the error handler that is called when we encounter an exception
|
|
19
|
+
* when loading a module. This will report any errors encountered before
|
|
20
|
+
* ExceptionsManager is configured.
|
|
21
|
+
*/
|
|
22
|
+
let _globalHandler: ErrorHandler = function onError(
|
|
23
|
+
e: mixed,
|
|
24
|
+
isFatal: boolean,
|
|
25
|
+
) {
|
|
26
|
+
throw e;
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* The particular require runtime that we are using looks for a global
|
|
31
|
+
* `ErrorUtils` object and if it exists, then it requires modules with the
|
|
32
|
+
* error handler specified via ErrorUtils.setGlobalHandler by calling the
|
|
33
|
+
* require function with applyWithGuard. Since the require module is loaded
|
|
34
|
+
* before any of the modules, this ErrorUtils must be defined (and the handler
|
|
35
|
+
* set) globally before requiring anything.
|
|
36
|
+
*/
|
|
37
|
+
const ErrorUtils = {
|
|
38
|
+
setGlobalHandler(fun: ErrorHandler): void {
|
|
39
|
+
_globalHandler = fun;
|
|
40
|
+
},
|
|
41
|
+
getGlobalHandler(): ErrorHandler {
|
|
42
|
+
return _globalHandler;
|
|
43
|
+
},
|
|
44
|
+
reportError(error: mixed): void {
|
|
45
|
+
_globalHandler && _globalHandler(error, false);
|
|
46
|
+
},
|
|
47
|
+
reportFatalError(error: mixed): void {
|
|
48
|
+
// NOTE: This has an untyped call site in Metro.
|
|
49
|
+
_globalHandler && _globalHandler(error, true);
|
|
50
|
+
},
|
|
51
|
+
applyWithGuard<TArgs: $ReadOnlyArray<mixed>, TOut>(
|
|
52
|
+
fun: Fn<TArgs, TOut>,
|
|
53
|
+
context?: ?mixed,
|
|
54
|
+
args?: ?TArgs,
|
|
55
|
+
// Unused, but some code synced from www sets it to null.
|
|
56
|
+
unused_onError?: null,
|
|
57
|
+
// Some callers pass a name here, which we ignore.
|
|
58
|
+
unused_name?: ?string,
|
|
59
|
+
): ?TOut {
|
|
60
|
+
try {
|
|
61
|
+
_inGuard++;
|
|
62
|
+
/* $FlowFixMe[incompatible-call] : TODO T48204745 (1) apply(context,
|
|
63
|
+
* null) is fine. (2) array -> rest array should work */
|
|
64
|
+
/* $FlowFixMe[incompatible-type] : TODO T48204745 (1) apply(context,
|
|
65
|
+
* null) is fine. (2) array -> rest array should work */
|
|
66
|
+
return fun.apply(context, args);
|
|
67
|
+
} catch (e) {
|
|
68
|
+
ErrorUtils.reportError(e);
|
|
69
|
+
} finally {
|
|
70
|
+
_inGuard--;
|
|
71
|
+
}
|
|
72
|
+
return null;
|
|
73
|
+
},
|
|
74
|
+
applyWithGuardIfNeeded<TArgs: $ReadOnlyArray<mixed>, TOut>(
|
|
75
|
+
fun: Fn<TArgs, TOut>,
|
|
76
|
+
context?: ?mixed,
|
|
77
|
+
args?: ?TArgs,
|
|
78
|
+
): ?TOut {
|
|
79
|
+
if (ErrorUtils.inGuard()) {
|
|
80
|
+
/* $FlowFixMe[incompatible-call] : TODO T48204745 (1) apply(context,
|
|
81
|
+
* null) is fine. (2) array -> rest array should work */
|
|
82
|
+
/* $FlowFixMe[incompatible-type] : TODO T48204745 (1) apply(context,
|
|
83
|
+
* null) is fine. (2) array -> rest array should work */
|
|
84
|
+
return fun.apply(context, args);
|
|
85
|
+
} else {
|
|
86
|
+
ErrorUtils.applyWithGuard(fun, context, args);
|
|
87
|
+
}
|
|
88
|
+
return null;
|
|
89
|
+
},
|
|
90
|
+
inGuard(): boolean {
|
|
91
|
+
return !!_inGuard;
|
|
92
|
+
},
|
|
93
|
+
guard<TArgs: $ReadOnlyArray<mixed>, TOut>(
|
|
94
|
+
fun: Fn<TArgs, TOut>,
|
|
95
|
+
name?: ?string,
|
|
96
|
+
context?: ?mixed,
|
|
97
|
+
): ?(...TArgs) => ?TOut {
|
|
98
|
+
// TODO: (moti) T48204753 Make sure this warning is never hit and remove it - types
|
|
99
|
+
// should be sufficient.
|
|
100
|
+
if (typeof fun !== 'function') {
|
|
101
|
+
console.warn('A function must be passed to ErrorUtils.guard, got ', fun);
|
|
102
|
+
return null;
|
|
103
|
+
}
|
|
104
|
+
const guardName = name ?? fun.name ?? '<generated guard>';
|
|
105
|
+
/* $FlowFixMe[missing-this-annot] The 'this' type annotation(s) required by
|
|
106
|
+
* Flow's LTI update could not be added via codemod */
|
|
107
|
+
function guarded(...args: TArgs): ?TOut {
|
|
108
|
+
return ErrorUtils.applyWithGuard(
|
|
109
|
+
fun,
|
|
110
|
+
context ?? this,
|
|
111
|
+
args,
|
|
112
|
+
null,
|
|
113
|
+
guardName,
|
|
114
|
+
);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
return guarded;
|
|
118
|
+
},
|
|
119
|
+
};
|
|
120
|
+
|
|
121
|
+
global.ErrorUtils = ErrorUtils;
|
|
122
|
+
|
|
123
|
+
export type ErrorUtilsT = typeof ErrorUtils;
|
package/index.js
ADDED
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Copyright (c) Meta Platforms, Inc. and affiliates.
|
|
3
|
+
*
|
|
4
|
+
* This source code is licensed under the MIT license found in the
|
|
5
|
+
* LICENSE file in the root directory of this source tree.
|
|
6
|
+
*
|
|
7
|
+
* @format
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
'use strict';
|
|
11
|
+
|
|
12
|
+
module.exports = () => [
|
|
13
|
+
require.resolve('./console.js'),
|
|
14
|
+
require.resolve('./error-guard.js'),
|
|
15
|
+
require.resolve('./Object.es8.js'),
|
|
16
|
+
];
|
package/package.json
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@react-native/js-polyfills",
|
|
3
|
+
"version": "0.72.0",
|
|
4
|
+
"description": "Polyfills for React Native.",
|
|
5
|
+
"repository": {
|
|
6
|
+
"type": "git",
|
|
7
|
+
"url": "git@github.com:facebook/react-native.git",
|
|
8
|
+
"directory": "packages/polyfills"
|
|
9
|
+
},
|
|
10
|
+
"license": "MIT"
|
|
11
|
+
}
|