mirror of
https://github.com/gravitational/teleport
synced 2024-10-19 00:33:50 +00:00
Remove usage of lodash methods (#21567)
* Create new local util lib to replace lodash. * Replace usage of isInteger and debounce from lodash with highbar. * Create isObject and runOnce utility methods. * remove use of at, isObject, and once lodash method usage. * remove map and transform lodash calls. * Add memoize function to highbar. * remove memoize lodash usage. * remove merge and isEqual lodash methods and update other missing refs to highbar. * convert the throttle to debounce. * add throttle method to highbar. * use the new throttle method instead of debounce where necessary. * Add mergeDeep function for init config merge. * remove lodash from the build process. * Fix introduced bug in workspacesService. * Added tests for highbar mergeDeep and expanded its functionality to support arrays. * review updates. * Added types to mergeDeep function. * Add missing MapCache prototype methods. * Add license notices, types and missing hash code. * First pass at compare an array objects function. * use new compareArrayObjs fn * Add missing not * Added types to arrayObjectIsEqual * Add tests for arrayObjectIsEqual and fix some edge case bugs. * update util fn name
This commit is contained in:
parent
2f0c97d276
commit
5eafe86fa4
|
@ -57,7 +57,6 @@ module.exports = {
|
|||
plugins: [
|
||||
...plugins,
|
||||
['babel-plugin-styled-components', { displayName: false, ssr: false }],
|
||||
'babel-plugin-lodash',
|
||||
],
|
||||
},
|
||||
},
|
||||
|
|
|
@ -45,7 +45,6 @@
|
|||
"@testing-library/react-hooks": "^8.0.1",
|
||||
"@testing-library/user-event": "^14.4.3",
|
||||
"@types/jest": "^27.3.1",
|
||||
"@types/lodash": "4.14.149",
|
||||
"@types/node": "^16.11.10",
|
||||
"@types/react": "^16.8.19",
|
||||
"@types/react-router-dom": "^4.3.3",
|
||||
|
@ -55,7 +54,6 @@
|
|||
"@typescript-eslint/eslint-plugin": "^5.4.0",
|
||||
"@typescript-eslint/parser": "^5.4.0",
|
||||
"babel-loader": "^8.2.5",
|
||||
"babel-plugin-lodash": "^3.3.4",
|
||||
"clean-webpack-plugin": "4.0.0",
|
||||
"core-js": "^3",
|
||||
"cross-env": "5.0.5",
|
||||
|
@ -76,7 +74,6 @@
|
|||
"html-webpack-plugin": "^5.5.0",
|
||||
"jest": "^27.3.1",
|
||||
"jest-styled-components": "^7.0.8",
|
||||
"lodash-webpack-plugin": "^0.11.6",
|
||||
"msw": "^0.47.4",
|
||||
"optimist": "^0.6.1",
|
||||
"prettier": "^2.5.0",
|
||||
|
|
|
@ -18,7 +18,6 @@ const path = require('path');
|
|||
|
||||
const { BundleAnalyzerPlugin } = require('webpack-bundle-analyzer');
|
||||
const HtmlWebPackPlugin = require('html-webpack-plugin');
|
||||
const LodashModuleReplacementPlugin = require('lodash-webpack-plugin');
|
||||
const ForkTsCheckerWebpackPlugin = require('fork-ts-checker-webpack-plugin');
|
||||
const ReactRefreshPlugin = require('@pmmmwh/react-refresh-webpack-plugin');
|
||||
|
||||
|
@ -51,9 +50,6 @@ const configFactory = {
|
|||
...options,
|
||||
});
|
||||
},
|
||||
lodash() {
|
||||
return new LodashModuleReplacementPlugin();
|
||||
},
|
||||
bundleAnalyzer(options) {
|
||||
return new BundleAnalyzerPlugin({ analyzerHost: '0.0.0.0', ...options });
|
||||
},
|
||||
|
|
|
@ -19,7 +19,7 @@ const configFactory = require('./webpack.base');
|
|||
process.env.BABEL_ENV = 'production';
|
||||
process.env.NODE_ENV = 'production';
|
||||
|
||||
const plugins = [configFactory.plugins.lodash()];
|
||||
const plugins = [];
|
||||
|
||||
if (process.env.WEBPACK_ANALYZE_BUNDLE === 'true') {
|
||||
plugins.push(configFactory.plugins.bundleAnalyzer());
|
||||
|
|
|
@ -16,7 +16,7 @@ limitations under the License.
|
|||
|
||||
import React from 'react';
|
||||
|
||||
import { isObject } from 'lodash';
|
||||
import { isObject } from 'shared/utils/highbar';
|
||||
|
||||
import Logger from '../../libs/logger';
|
||||
|
||||
|
|
|
@ -13,7 +13,6 @@
|
|||
"ace-builds": "1.4.6",
|
||||
"create-react-class": "^15.6.3",
|
||||
"cross-env": "5.0.5",
|
||||
"lodash": "^4.17.21",
|
||||
"date-fns": "^2.28.0",
|
||||
"react": "^16.8.4",
|
||||
"react-day-picker": "7.3.2",
|
||||
|
|
221
web/packages/shared/utils/highbar.test.ts
Normal file
221
web/packages/shared/utils/highbar.test.ts
Normal file
|
@ -0,0 +1,221 @@
|
|||
/**
|
||||
* Copyright 2023 Gravitational, Inc
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { arrayObjectIsEqual, mergeDeep } from './highbar';
|
||||
|
||||
describe('mergeDeep can merge two', () => {
|
||||
it('objects together', () => {
|
||||
const a = { a: 1, b: 2, c: 3, e: 5 };
|
||||
const b = { a: 3, b: 2, c: 1, d: 4 };
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: 3,
|
||||
b: 2,
|
||||
c: 1,
|
||||
d: 4,
|
||||
e: 5,
|
||||
});
|
||||
});
|
||||
|
||||
it('nested objects together', () => {
|
||||
const a = { a: 1, b: 2, c: { d: 3, e: 6, g: 8 } };
|
||||
const b = { a: 1, b: 2, c: { d: 4, e: 6, f: 7 } };
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: 1,
|
||||
b: 2,
|
||||
c: { d: 4, e: 6, f: 7, g: 8 },
|
||||
});
|
||||
});
|
||||
|
||||
it('objects together that contain arrays', () => {
|
||||
const a = { a: 1, b: ['a', 'b', 'd'] };
|
||||
const b = { a: 2, b: ['b', 'c'] };
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: 2,
|
||||
b: ['b', 'c', 'd'],
|
||||
});
|
||||
|
||||
const c = { a: 1, b: ['b', 'c'] };
|
||||
const d = { a: 2, b: ['a', 'b', 'd'] };
|
||||
expect(mergeDeep(c, d)).toStrictEqual({
|
||||
a: 2,
|
||||
b: ['a', 'b', 'd'],
|
||||
});
|
||||
});
|
||||
|
||||
it('objects together that contain arrays of arrays', () => {
|
||||
const a = { a: [['b', 'c', 'f']] };
|
||||
const b = { a: [['d', 'e']] };
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: [['d', 'e', 'f']],
|
||||
});
|
||||
|
||||
const c = { a: [['d', 'e']] };
|
||||
const d = { a: [['b', 'c', 'f']] };
|
||||
expect(mergeDeep(c, d)).toStrictEqual({
|
||||
a: [['b', 'c', 'f']],
|
||||
});
|
||||
});
|
||||
|
||||
it('objects together that contain arrays that contain objects', () => {
|
||||
const a = { a: 1, b: [{ c: 3, d: 4, e: 5 }, 'b'] };
|
||||
const b = { a: 2, b: [{ c: 3, d: 4, f: 6 }, 'c'] };
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: 2,
|
||||
b: [{ c: 3, d: 4, e: 5, f: 6 }, 'c'],
|
||||
});
|
||||
});
|
||||
|
||||
it('objects with arrays with undefined indexes', () => {
|
||||
const a = {
|
||||
a: false,
|
||||
b: {
|
||||
c: 'foo',
|
||||
d: 'bar',
|
||||
},
|
||||
c: {
|
||||
a: 'no',
|
||||
b: [],
|
||||
},
|
||||
};
|
||||
|
||||
const b = {
|
||||
a: true,
|
||||
b: {
|
||||
d: 'baz',
|
||||
e: 'bax',
|
||||
},
|
||||
c: {
|
||||
a: 'ok',
|
||||
b: [
|
||||
{
|
||||
a: 'foo',
|
||||
b: 'bar',
|
||||
},
|
||||
],
|
||||
},
|
||||
};
|
||||
expect(mergeDeep(a, b)).toStrictEqual({
|
||||
a: true,
|
||||
b: {
|
||||
c: 'foo',
|
||||
d: 'baz',
|
||||
e: 'bax',
|
||||
},
|
||||
c: {
|
||||
a: 'ok',
|
||||
b: [
|
||||
{
|
||||
a: 'foo',
|
||||
b: 'bar',
|
||||
},
|
||||
],
|
||||
},
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('arrayObjectIsEqual correctly compares', () => {
|
||||
it('simple arrays', () => {
|
||||
const a = [{ foo: 'bar' }];
|
||||
const b = [{ foo: 'bar' }];
|
||||
|
||||
expect(arrayObjectIsEqual(a, b)).toBe(true);
|
||||
|
||||
const c = [{ foo: 'bar' }];
|
||||
const d = [{ foo: 'baz' }];
|
||||
expect(arrayObjectIsEqual(c, d)).toBe(false);
|
||||
});
|
||||
|
||||
it('arrays with complex objects', () => {
|
||||
const a = [
|
||||
{
|
||||
'/clusters/test-uri': {
|
||||
accessRequests: {
|
||||
pending: {
|
||||
app: {},
|
||||
db: {},
|
||||
kube_cluster: {},
|
||||
node: {},
|
||||
role: {},
|
||||
windows_desktop: {},
|
||||
},
|
||||
isBarCollapsed: false,
|
||||
},
|
||||
localClusterUri: '/clusters/test-uri',
|
||||
documents: [
|
||||
{
|
||||
kind: 'doc.cluster',
|
||||
title: 'Cluster Test',
|
||||
clusterUri: '/clusters/test-uri',
|
||||
uri: '/docs/test-cluster-uri',
|
||||
},
|
||||
],
|
||||
location: '/docs/test-cluster-uri',
|
||||
previous: {
|
||||
documents: [
|
||||
{
|
||||
kind: 'doc.terminal_shell',
|
||||
uri: '/docs/some_uri',
|
||||
title: '/Users/alice/Documents',
|
||||
},
|
||||
],
|
||||
location: '/docs/some_uri',
|
||||
},
|
||||
},
|
||||
},
|
||||
];
|
||||
|
||||
const b = [
|
||||
{
|
||||
'/clusters/test-uri': {
|
||||
accessRequests: {
|
||||
pending: {
|
||||
app: {},
|
||||
db: {},
|
||||
kube_cluster: {},
|
||||
node: {},
|
||||
role: {},
|
||||
windows_desktop: {},
|
||||
},
|
||||
isBarCollapsed: false,
|
||||
},
|
||||
localClusterUri: '/clusters/test-uri',
|
||||
documents: [
|
||||
{
|
||||
kind: 'doc.cluster',
|
||||
title: 'Cluster Test',
|
||||
clusterUri: '/clusters/test-uri',
|
||||
uri: '/docs/test-cluster-uri',
|
||||
},
|
||||
],
|
||||
location: '/docs/test-cluster-uri',
|
||||
previous: {
|
||||
documents: [
|
||||
{
|
||||
kind: 'doc.terminal_shell',
|
||||
uri: '/docs/some_uri',
|
||||
title: '/Users/alice/Documents',
|
||||
},
|
||||
],
|
||||
location: '/docs/some_uri',
|
||||
},
|
||||
},
|
||||
},
|
||||
];
|
||||
|
||||
expect(arrayObjectIsEqual(a, b)).toBe(true);
|
||||
});
|
||||
});
|
459
web/packages/shared/utils/highbar.ts
Normal file
459
web/packages/shared/utils/highbar.ts
Normal file
|
@ -0,0 +1,459 @@
|
|||
/**
|
||||
* Copyright 2023 Gravitational, Inc
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
type SupportedMergeTypes = string | number | Record<string, unknown>;
|
||||
type MergeTarget = Record<string, unknown> | Array<SupportedMergeTypes>;
|
||||
|
||||
export function mergeDeep(target: MergeTarget, ...sources: Array<MergeTarget>) {
|
||||
const isObject = obj => obj && typeof obj === 'object' && !Array.isArray(obj);
|
||||
|
||||
const mergeArray = (target, source) => {
|
||||
source.forEach((value, index) => {
|
||||
if (
|
||||
Array.isArray(value) ||
|
||||
(isObject(value) && isObject(source[index]))
|
||||
) {
|
||||
if (target[index] === undefined) {
|
||||
target[index] = source[index];
|
||||
} else {
|
||||
mergeDeep(target[index], source[index]);
|
||||
}
|
||||
} else {
|
||||
target[index] = source[index];
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
if (!sources.length) return target;
|
||||
const source = sources.shift();
|
||||
|
||||
if (isObject(target) && isObject(source)) {
|
||||
for (const key in source) {
|
||||
if (isObject(source[key])) {
|
||||
if (!target[key]) Object.assign(target, { [key]: {} });
|
||||
mergeDeep(target[key], source[key]);
|
||||
} else if (Array.isArray(source[key])) {
|
||||
mergeArray(target[key], source[key]);
|
||||
} else {
|
||||
Object.assign(target, { [key]: source[key] });
|
||||
}
|
||||
}
|
||||
} else if (Array.isArray(target) && Array.isArray(source)) {
|
||||
mergeArray(target, source);
|
||||
}
|
||||
|
||||
return mergeDeep(target, ...sources);
|
||||
}
|
||||
|
||||
type CompareArray = Array<Record<string, unknown>>;
|
||||
|
||||
export function arrayObjectIsEqual(
|
||||
arr1: CompareArray,
|
||||
arr2: CompareArray
|
||||
): boolean {
|
||||
const compareArrays = (arr1, arr2) =>
|
||||
arr1.length === arr2.length &&
|
||||
arr1.every((obj, idx) => compareObjects(obj, arr2[idx]));
|
||||
|
||||
const compareObjects = (obj1, obj2) => {
|
||||
if (!isObject(obj1)) {
|
||||
return obj1 === obj2;
|
||||
}
|
||||
|
||||
if (Object.keys(obj1).length) {
|
||||
if (Object.keys(obj1).length !== Object.keys(obj2).length) {
|
||||
return false;
|
||||
}
|
||||
return Object.keys(obj1).every(key => {
|
||||
return compareObjects(obj1[key], obj2[key]);
|
||||
});
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
};
|
||||
return compareArrays(arr1, arr2);
|
||||
}
|
||||
|
||||
export function isInteger(checkVal: any): boolean {
|
||||
return Number.isInteger(checkVal) || checkVal == parseInt(checkVal);
|
||||
}
|
||||
|
||||
export function isObject(checkVal: unknown): boolean {
|
||||
const type = typeof checkVal;
|
||||
return checkVal != null && (type == 'object' || type == 'function');
|
||||
}
|
||||
|
||||
/**
|
||||
* Lodash <https://lodash.com/>
|
||||
* Copyright JS Foundation and other contributors <https://js.foundation/>
|
||||
* Released under MIT license <https://lodash.com/license>
|
||||
* Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
|
||||
* Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
|
||||
*/
|
||||
export function runOnce<T extends (...args) => any>(func: T) {
|
||||
let n = 2;
|
||||
let result;
|
||||
return function () {
|
||||
if (--n > 0) {
|
||||
result = func.apply(this, arguments);
|
||||
}
|
||||
if (n <= 1) {
|
||||
func = undefined;
|
||||
}
|
||||
return result;
|
||||
};
|
||||
}
|
||||
|
||||
interface ThrottleSettings {
|
||||
leading?: boolean | undefined;
|
||||
trailing?: boolean | undefined;
|
||||
}
|
||||
|
||||
/**
|
||||
* Lodash <https://lodash.com/>
|
||||
* Copyright JS Foundation and other contributors <https://js.foundation/>
|
||||
* Released under MIT license <https://lodash.com/license>
|
||||
* Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
|
||||
* Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
|
||||
*/
|
||||
export function throttle<T extends (...args: any) => any>(
|
||||
func: T,
|
||||
wait = 0,
|
||||
options?: ThrottleSettings
|
||||
): DebouncedFunc<T> {
|
||||
var leading = true,
|
||||
trailing = true;
|
||||
|
||||
if (isObject(options)) {
|
||||
leading = 'leading' in options ? !!options.leading : leading;
|
||||
trailing = 'trailing' in options ? !!options.trailing : trailing;
|
||||
}
|
||||
return debounce(func, wait, {
|
||||
leading: leading,
|
||||
maxWait: wait,
|
||||
trailing: trailing,
|
||||
});
|
||||
}
|
||||
|
||||
export type DebouncedFunc<T extends (...args: any[]) => any> = {
|
||||
(...args: Parameters<T>): ReturnType<T> | undefined;
|
||||
cancel(): void;
|
||||
flush(): ReturnType<T> | undefined;
|
||||
};
|
||||
|
||||
type DebounceSettings = {
|
||||
leading?: boolean | undefined;
|
||||
maxWait?: number | undefined;
|
||||
trailing?: boolean | undefined;
|
||||
};
|
||||
|
||||
/**
|
||||
* Lodash <https://lodash.com/>
|
||||
* Copyright JS Foundation and other contributors <https://js.foundation/>
|
||||
* Released under MIT license <https://lodash.com/license>
|
||||
* Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
|
||||
* Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
|
||||
*/
|
||||
export function debounce<T extends (...args: any) => any>(
|
||||
func: T,
|
||||
wait = 0,
|
||||
options?: DebounceSettings
|
||||
): DebouncedFunc<T> {
|
||||
var lastArgs,
|
||||
lastThis,
|
||||
maxWait,
|
||||
result,
|
||||
timerId,
|
||||
lastCallTime,
|
||||
lastInvokeTime = 0,
|
||||
leading = false,
|
||||
maxing = false,
|
||||
trailing = true;
|
||||
|
||||
if (isObject(options)) {
|
||||
leading = !!options.leading;
|
||||
maxing = 'maxWait' in options;
|
||||
maxWait = maxing ? Math.max(options.maxWait || 0, wait) : maxWait;
|
||||
trailing = 'trailing' in options ? !!options.trailing : trailing;
|
||||
}
|
||||
|
||||
function invokeFunc(time) {
|
||||
var args = lastArgs,
|
||||
thisArg = lastThis;
|
||||
|
||||
lastArgs = lastThis = undefined;
|
||||
lastInvokeTime = time;
|
||||
result = func.apply(thisArg, args);
|
||||
return result;
|
||||
}
|
||||
|
||||
function leadingEdge(time) {
|
||||
// Reset any `maxWait` timer.
|
||||
lastInvokeTime = time;
|
||||
// Start the timer for the trailing edge.
|
||||
timerId = setTimeout(timerExpired, wait);
|
||||
// Invoke the leading edge.
|
||||
return leading ? invokeFunc(time) : result;
|
||||
}
|
||||
|
||||
function remainingWait(time) {
|
||||
var timeSinceLastCall = time - lastCallTime,
|
||||
timeSinceLastInvoke = time - lastInvokeTime,
|
||||
timeWaiting = wait - timeSinceLastCall;
|
||||
|
||||
return maxing
|
||||
? Math.min(timeWaiting, maxWait - timeSinceLastInvoke)
|
||||
: timeWaiting;
|
||||
}
|
||||
|
||||
function shouldInvoke(time) {
|
||||
var timeSinceLastCall = time - lastCallTime,
|
||||
timeSinceLastInvoke = time - lastInvokeTime;
|
||||
|
||||
// Either this is the first call, activity has stopped and we're at the
|
||||
// trailing edge, the system time has gone backwards and we're treating
|
||||
// it as the trailing edge, or we've hit the `maxWait` limit.
|
||||
return (
|
||||
lastCallTime === undefined ||
|
||||
timeSinceLastCall >= wait ||
|
||||
timeSinceLastCall < 0 ||
|
||||
(maxing && timeSinceLastInvoke >= maxWait)
|
||||
);
|
||||
}
|
||||
|
||||
function timerExpired() {
|
||||
var time = Date.now();
|
||||
if (shouldInvoke(time)) {
|
||||
return trailingEdge(time);
|
||||
}
|
||||
// Restart the timer.
|
||||
timerId = setTimeout(timerExpired, remainingWait(time));
|
||||
}
|
||||
|
||||
function trailingEdge(time) {
|
||||
timerId = undefined;
|
||||
|
||||
// Only invoke if we have `lastArgs` which means `func` has been
|
||||
// debounced at least once.
|
||||
if (trailing && lastArgs) {
|
||||
return invokeFunc(time);
|
||||
}
|
||||
lastArgs = lastThis = undefined;
|
||||
return result;
|
||||
}
|
||||
|
||||
function cancel() {
|
||||
if (timerId !== undefined) {
|
||||
clearTimeout(timerId);
|
||||
}
|
||||
lastInvokeTime = 0;
|
||||
lastArgs = lastCallTime = lastThis = timerId = undefined;
|
||||
}
|
||||
|
||||
function flush() {
|
||||
return timerId === undefined ? result : trailingEdge(Date.now());
|
||||
}
|
||||
|
||||
function debounced() {
|
||||
var time = Date.now(),
|
||||
isInvoking = shouldInvoke(time);
|
||||
|
||||
lastArgs = arguments;
|
||||
lastThis = this;
|
||||
lastCallTime = time;
|
||||
|
||||
if (isInvoking) {
|
||||
if (timerId === undefined) {
|
||||
return leadingEdge(lastCallTime);
|
||||
}
|
||||
if (maxing) {
|
||||
// Handle invocations in a tight loop.
|
||||
timerId = setTimeout(timerExpired, wait);
|
||||
return invokeFunc(lastCallTime);
|
||||
}
|
||||
}
|
||||
if (timerId === undefined) {
|
||||
timerId = setTimeout(timerExpired, wait);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
debounced.cancel = cancel;
|
||||
debounced.flush = flush;
|
||||
return debounced;
|
||||
}
|
||||
|
||||
interface MapCacheType {
|
||||
delete(key: any): boolean;
|
||||
get(key: any): any;
|
||||
has(key: any): boolean;
|
||||
set(key: any, value: any): this;
|
||||
clear?: (() => void) | undefined;
|
||||
}
|
||||
|
||||
type MemoizedFunction = {
|
||||
cache: MapCacheType;
|
||||
};
|
||||
|
||||
/**
|
||||
* Lodash <https://lodash.com/>
|
||||
* Copyright JS Foundation and other contributors <https://js.foundation/>
|
||||
* Released under MIT license <https://lodash.com/license>
|
||||
* Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
|
||||
* Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
|
||||
*/
|
||||
export function memoize<T extends (...args: any) => any>(
|
||||
func: T
|
||||
): T & MemoizedFunction {
|
||||
const memoized = function () {
|
||||
const args = arguments;
|
||||
const key = args[0];
|
||||
const cache = memoized.cache;
|
||||
|
||||
if (cache.has(key)) {
|
||||
return cache.get(key);
|
||||
}
|
||||
const result = func.apply(this, args);
|
||||
memoized.cache = cache.set(key, result) || cache;
|
||||
return result;
|
||||
};
|
||||
memoized.cache = new (memoize.Cache || MapCache)();
|
||||
/* eslint-disable @typescript-eslint/ban-ts-comment*/
|
||||
// @ts-ignore
|
||||
return memoized;
|
||||
}
|
||||
|
||||
// Expose `MapCache`.
|
||||
memoize.Cache = MapCache;
|
||||
|
||||
function MapCache(entries?: any) {
|
||||
let index = -1;
|
||||
const length = entries == null ? 0 : entries.length;
|
||||
|
||||
this.clear();
|
||||
while (++index < length) {
|
||||
const entry = entries[index];
|
||||
this.set(entry[0], entry[1]);
|
||||
}
|
||||
}
|
||||
|
||||
function mapCacheClear() {
|
||||
this.size = 0;
|
||||
this.__data__ = {
|
||||
hash: new Hash(),
|
||||
map: new Map(),
|
||||
string: new Hash(),
|
||||
};
|
||||
}
|
||||
|
||||
function mapCacheDelete(key) {
|
||||
var result = getMapData(this, key)['delete'](key);
|
||||
this.size -= result ? 1 : 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
function mapCacheGet(key) {
|
||||
return getMapData(this, key).get(key);
|
||||
}
|
||||
|
||||
function mapCacheHas(key) {
|
||||
return getMapData(this, key).has(key);
|
||||
}
|
||||
|
||||
function mapCacheSet(key, value) {
|
||||
var data = getMapData(this, key),
|
||||
size = data.size;
|
||||
|
||||
data.set(key, value);
|
||||
this.size += data.size == size ? 0 : 1;
|
||||
return this;
|
||||
}
|
||||
|
||||
MapCache.prototype.clear = mapCacheClear;
|
||||
MapCache.prototype['delete'] = mapCacheDelete;
|
||||
MapCache.prototype.get = mapCacheGet;
|
||||
MapCache.prototype.has = mapCacheHas;
|
||||
MapCache.prototype.set = mapCacheSet;
|
||||
|
||||
function Hash(entries?) {
|
||||
var index = -1,
|
||||
length = entries == null ? 0 : entries.length;
|
||||
|
||||
this.clear();
|
||||
while (++index < length) {
|
||||
var entry = entries[index];
|
||||
this.set(entry[0], entry[1]);
|
||||
}
|
||||
}
|
||||
|
||||
const HASH_UNDEFINED = '__lodash_hash_undefined__';
|
||||
|
||||
function hashClear() {
|
||||
this.__data__ = Object.create ? Object.create(null) : {};
|
||||
this.size = 0;
|
||||
}
|
||||
|
||||
function hashDelete(key) {
|
||||
var result = this.has(key) && delete this.__data__[key];
|
||||
this.size -= result ? 1 : 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
function hashGet(key) {
|
||||
var data = this.__data__;
|
||||
if (Object.create) {
|
||||
var result = data[key];
|
||||
return result === HASH_UNDEFINED ? undefined : result;
|
||||
}
|
||||
return Object.hasOwnProperty.call(data, key) ? data[key] : undefined;
|
||||
}
|
||||
|
||||
function hashHas(key) {
|
||||
var data = this.__data__;
|
||||
return Object.create
|
||||
? data[key] !== undefined
|
||||
: Object.hasOwnProperty.call(data, key);
|
||||
}
|
||||
|
||||
function hashSet(key, value) {
|
||||
var data = this.__data__;
|
||||
this.size += this.has(key) ? 0 : 1;
|
||||
data[key] = Object.create && value === undefined ? HASH_UNDEFINED : value;
|
||||
return this;
|
||||
}
|
||||
|
||||
// Add methods to `Hash`.
|
||||
Hash.prototype.clear = hashClear;
|
||||
Hash.prototype['delete'] = hashDelete;
|
||||
Hash.prototype.get = hashGet;
|
||||
Hash.prototype.has = hashHas;
|
||||
Hash.prototype.set = hashSet;
|
||||
|
||||
function getMapData(map, key) {
|
||||
var data = map.__data__;
|
||||
return isKeyable(key)
|
||||
? data[typeof key == 'string' ? 'string' : 'hash']
|
||||
: data.map;
|
||||
}
|
||||
|
||||
function isKeyable(value) {
|
||||
var type = typeof value;
|
||||
return type == 'string' ||
|
||||
type == 'number' ||
|
||||
type == 'symbol' ||
|
||||
type == 'boolean'
|
||||
? value !== '__proto__'
|
||||
: value === null;
|
||||
}
|
|
@ -19,7 +19,7 @@ import styled from 'styled-components';
|
|||
import Popover from 'design/Popover';
|
||||
import theme from 'design/theme';
|
||||
import { Box } from 'design';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
|
||||
export default function JoinedUsers(props) {
|
||||
const { active, users, open = false, ml, mr } = props;
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
|
||||
import React, { useState, useEffect, useRef } from 'react';
|
||||
|
||||
import { throttle } from 'lodash';
|
||||
import { throttle } from 'shared/utils/highbar';
|
||||
import { dateToUtc } from 'shared/services/loc';
|
||||
import { format } from 'date-fns';
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { throttle } from 'lodash';
|
||||
import { throttle } from 'shared/utils/highbar';
|
||||
|
||||
import TtyPlayer from 'teleport/lib/term/ttyPlayer';
|
||||
|
||||
|
|
|
@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
|
|||
limitations under the License.
|
||||
*/
|
||||
import React from 'react';
|
||||
import { throttle } from 'lodash';
|
||||
import { throttle } from 'shared/utils/highbar';
|
||||
|
||||
export default function useTtyBpfMapper(tty, events) {
|
||||
// create a map [time][index] for quick lookups
|
||||
|
|
|
@ -15,7 +15,7 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { throttle } from 'lodash';
|
||||
import { throttle } from 'shared/utils/highbar';
|
||||
import Logger from 'shared/libs/logger';
|
||||
|
||||
import session from 'teleport/services/websession';
|
||||
|
|
|
@ -15,7 +15,7 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
import styled from 'styled-components';
|
||||
import { height, space, color } from 'design/system';
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import { generatePath } from 'react-router';
|
||||
import { merge } from 'lodash';
|
||||
import { mergeDeep } from 'shared/utils/highbar';
|
||||
|
||||
import generateResourcePath from './generateResourcePath';
|
||||
|
||||
|
@ -554,7 +554,7 @@ const cfg = {
|
|||
},
|
||||
|
||||
init(backendConfig = {}) {
|
||||
merge(this, backendConfig);
|
||||
mergeDeep(this, backendConfig);
|
||||
},
|
||||
};
|
||||
|
||||
|
|
|
@ -16,12 +16,14 @@ limitations under the License.
|
|||
import 'xterm/css/xterm.css';
|
||||
import { Terminal } from 'xterm';
|
||||
import { FitAddon } from 'xterm-addon-fit';
|
||||
import { debounce, Cancelable, isInteger } from 'lodash';
|
||||
import { debounce, isInteger } from 'shared/utils/highbar';
|
||||
import Logger from 'shared/libs/logger';
|
||||
|
||||
import { TermEvent } from './enums';
|
||||
import Tty from './tty';
|
||||
|
||||
import type { DebouncedFunc } from 'shared/utils/highbar';
|
||||
|
||||
const logger = Logger.create('lib/term/terminal');
|
||||
const DISCONNECT_TXT = 'disconnected';
|
||||
const WINDOW_RESIZE_DEBOUNCE_DELAY = 200;
|
||||
|
@ -37,7 +39,7 @@ export default class TtyTerminal {
|
|||
_scrollBack: number;
|
||||
_fontFamily: string;
|
||||
_fontSize: number;
|
||||
_debouncedResize: (() => void) & Cancelable;
|
||||
_debouncedResize: DebouncedFunc<() => void>;
|
||||
_fitAddon = new FitAddon();
|
||||
|
||||
constructor(tty: Tty, options: Options) {
|
||||
|
|
|
@ -14,8 +14,6 @@ See the License for the specific language governing permissions and
|
|||
limitations under the License.
|
||||
*/
|
||||
|
||||
import { map } from 'lodash';
|
||||
|
||||
import api from 'teleport/services/api';
|
||||
import cfg from 'teleport/config';
|
||||
|
||||
|
@ -26,7 +24,7 @@ const service = {
|
|||
fetchSessions(clusterId) {
|
||||
return api.get(cfg.getTerminalSessionUrl({ clusterId })).then(response => {
|
||||
if (response && response.sessions) {
|
||||
return map(response.sessions, makeSession);
|
||||
return response.sessions.map(makeSession);
|
||||
}
|
||||
|
||||
return [];
|
||||
|
@ -44,7 +42,7 @@ const service = {
|
|||
|
||||
const parties: ParticipantList = {};
|
||||
json.sessions.forEach(s => {
|
||||
parties[s.id] = map(s.parties, makeParticipant);
|
||||
parties[s.id] = s.parties.map(makeParticipant);
|
||||
});
|
||||
|
||||
return parties;
|
||||
|
|
|
@ -14,12 +14,10 @@
|
|||
* limitations under the License.
|
||||
*/
|
||||
|
||||
import { at } from 'lodash';
|
||||
|
||||
import { ResetToken } from './types';
|
||||
|
||||
export default function makeResetToken(json): ResetToken {
|
||||
const [expires, username, value] = at(json, ['expiry', 'user', 'tokenId']);
|
||||
const { expires, username, value } = json;
|
||||
return {
|
||||
username,
|
||||
expires: new Date(expires),
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
|
||||
import fs, { existsSync, readFileSync, writeFileSync } from 'fs';
|
||||
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
|
||||
import Logger from 'teleterm/logger';
|
||||
|
||||
|
|
|
@ -19,7 +19,7 @@ import winston, {
|
|||
format,
|
||||
transports,
|
||||
} from 'winston';
|
||||
import { isObject } from 'lodash';
|
||||
import { isObject } from 'shared/utils/highbar';
|
||||
|
||||
import split2 from 'split2';
|
||||
|
||||
|
|
|
@ -42,7 +42,7 @@
|
|||
|
||||
import { spawn } from 'child_process';
|
||||
|
||||
import { memoize } from 'lodash';
|
||||
import { memoize } from 'shared/utils/highbar';
|
||||
|
||||
import Logger from 'teleterm/logger';
|
||||
import { unique } from 'teleterm/ui/utils/uid';
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
*/
|
||||
|
||||
import * as grpc from '@grpc/grpc-js';
|
||||
import { isObject, transform } from 'lodash';
|
||||
import { isObject } from 'shared/utils/highbar';
|
||||
|
||||
import Logger from 'teleterm/logger';
|
||||
|
||||
|
@ -127,24 +127,24 @@ export const withLogging = (logger: Logger): UnaryInterceptor => {
|
|||
};
|
||||
|
||||
function filterSensitiveProperties(toFilter: object): object {
|
||||
return transform(
|
||||
toFilter,
|
||||
(result: object, value: any, key: any) => {
|
||||
if (
|
||||
SENSITIVE_PROPERTIES.some(
|
||||
sensitiveProp =>
|
||||
typeof key === 'string' && key.includes(sensitiveProp)
|
||||
)
|
||||
) {
|
||||
result[key] = '~FILTERED~';
|
||||
return;
|
||||
}
|
||||
if (isObject(value)) {
|
||||
result[key] = filterSensitiveProperties(value);
|
||||
return;
|
||||
}
|
||||
result[key] = value;
|
||||
},
|
||||
{}
|
||||
);
|
||||
const acc = {};
|
||||
const transformer = (result: object, value: any, key: any) => {
|
||||
if (
|
||||
SENSITIVE_PROPERTIES.some(
|
||||
sensitiveProp => typeof key === 'string' && key.includes(sensitiveProp)
|
||||
)
|
||||
) {
|
||||
result[key] = '~FILTERED~';
|
||||
return;
|
||||
}
|
||||
if (isObject(value)) {
|
||||
result[key] = filterSensitiveProperties(value);
|
||||
return;
|
||||
}
|
||||
result[key] = value;
|
||||
};
|
||||
|
||||
Object.keys(toFilter).forEach(key => transformer(acc, toFilter[key], key));
|
||||
|
||||
return acc;
|
||||
}
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
|
||||
import React from 'react';
|
||||
import styled from 'styled-components';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
import { space, width, color, height } from 'styled-system';
|
||||
|
||||
export default function ClusterSearch(props: Props) {
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
*/
|
||||
|
||||
import React, { useMemo, useRef } from 'react';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
import { Box, ButtonSecondary, Flex, Link, Text } from 'design';
|
||||
import Validation from 'shared/components/Validation';
|
||||
import * as Alerts from 'design/Alert';
|
||||
|
|
|
@ -14,10 +14,10 @@ See the License for the specific language governing permissions and
|
|||
limitations under the License.
|
||||
*/
|
||||
|
||||
import { debounce } from 'lodash';
|
||||
import React, { useEffect, useRef } from 'react';
|
||||
import styled, { useTheme } from 'styled-components';
|
||||
import { Box, Flex } from 'design';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
|
||||
import { IPtyProcess } from 'teleterm/sharedProcess/ptyHost';
|
||||
|
||||
|
|
|
@ -17,7 +17,7 @@ limitations under the License.
|
|||
import 'xterm/css/xterm.css';
|
||||
import { IDisposable, Terminal } from 'xterm';
|
||||
import { FitAddon } from 'xterm-addon-fit';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
|
||||
import { IPtyProcess } from 'teleterm/sharedProcess/ptyHost';
|
||||
import Logger from 'teleterm/logger';
|
||||
|
|
|
@ -18,7 +18,7 @@ import { useEffect } from 'react';
|
|||
|
||||
import { useAsync } from 'shared/hooks/useAsync';
|
||||
|
||||
import { once } from 'lodash';
|
||||
import { runOnce } from 'shared/utils/highbar';
|
||||
|
||||
import { useAppContext } from 'teleterm/ui/appContextProvider';
|
||||
import { IAppContext } from 'teleterm/ui/types';
|
||||
|
@ -131,7 +131,7 @@ async function initState(
|
|||
removeInitCommand();
|
||||
});
|
||||
|
||||
const markDocumentAsConnectedOnce = once(() => {
|
||||
const markDocumentAsConnectedOnce = runOnce(() => {
|
||||
docsService.update(doc.uri, { status: 'connected' });
|
||||
});
|
||||
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
|
||||
import React, { useEffect, useMemo, useRef, useState } from 'react';
|
||||
import styled from 'styled-components';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
import { Box, Flex } from 'design';
|
||||
import { color, height, space, width } from 'styled-system';
|
||||
import { Spinner } from 'design/Icon';
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
*/
|
||||
|
||||
import React, { Fragment, useMemo, useState } from 'react';
|
||||
import { debounce } from 'lodash';
|
||||
import { debounce } from 'shared/utils/highbar';
|
||||
import styled from 'styled-components';
|
||||
|
||||
import { prepareVirtualScrollItems } from './prepareVirtualScrollItems';
|
||||
|
|
|
@ -85,7 +85,7 @@ describe('restoring workspace', () => {
|
|||
return { workspacesService, clusterDocument };
|
||||
}
|
||||
|
||||
it('restores the workspace if it there is a persisted state for given clusterUri', () => {
|
||||
it('restores the workspace if there is a persisted state for given clusterUri', () => {
|
||||
const testClusterUri = '/clusters/test-uri';
|
||||
const testWorkspace: Workspace = {
|
||||
accessRequests: {
|
||||
|
|
|
@ -15,8 +15,8 @@
|
|||
*/
|
||||
|
||||
import { useStore } from 'shared/libs/stores';
|
||||
import { arrayObjectIsEqual } from 'shared/utils/highbar';
|
||||
|
||||
import { isEqual } from 'lodash';
|
||||
/* eslint-disable @typescript-eslint/ban-ts-comment*/
|
||||
// @ts-ignore
|
||||
import { ResourceKind } from 'e-teleport/Workflow/NewRequest/useNewRequest';
|
||||
|
@ -344,7 +344,7 @@ export class WorkspacesService extends ImmutableStore<WorkspacesState> {
|
|||
|
||||
return (
|
||||
previousDocuments?.length &&
|
||||
!isEqual(
|
||||
!arrayObjectIsEqual(
|
||||
omitUriAndTitle(previousDocuments),
|
||||
omitUriAndTitle(currentDocuments)
|
||||
)
|
||||
|
|
56
yarn.lock
56
yarn.lock
|
@ -202,13 +202,6 @@
|
|||
dependencies:
|
||||
"@babel/types" "^7.16.0"
|
||||
|
||||
"@babel/helper-module-imports@^7.0.0-beta.49":
|
||||
version "7.18.6"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-module-imports/-/helper-module-imports-7.18.6.tgz#1e3ebdbbd08aad1437b428c50204db13c5a3ca6e"
|
||||
integrity sha512-0NFvs3VkuSYbFi1x2Vd6tKrywq+z/cLeYC/RJNFrIX/30Bf5aiGYbtvGXolEktzJH8o5E5KJ3tT+nkxuuZFVlA==
|
||||
dependencies:
|
||||
"@babel/types" "^7.18.6"
|
||||
|
||||
"@babel/helper-module-transforms@^7.12.1", "@babel/helper-module-transforms@^7.16.0":
|
||||
version "7.16.0"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-module-transforms/-/helper-module-transforms-7.16.0.tgz#1c82a8dd4cb34577502ebd2909699b194c3e9bb5"
|
||||
|
@ -280,11 +273,6 @@
|
|||
dependencies:
|
||||
"@babel/types" "^7.16.0"
|
||||
|
||||
"@babel/helper-string-parser@^7.19.4":
|
||||
version "7.19.4"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-string-parser/-/helper-string-parser-7.19.4.tgz#38d3acb654b4701a9b77fb0615a96f775c3a9e63"
|
||||
integrity sha512-nHtDoQcuqFmwYNYPz3Rah5ph2p8PFeFCsZk9A/48dPc/rGocJ5J3hAAZ7pb76VWX3fZKu+uEr/FhH5jLx7umrw==
|
||||
|
||||
"@babel/helper-validator-identifier@^7.15.7":
|
||||
version "7.15.7"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.15.7.tgz#220df993bfe904a4a6b02ab4f3385a5ebf6e2389"
|
||||
|
@ -295,11 +283,6 @@
|
|||
resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.18.6.tgz#9c97e30d31b2b8c72a1d08984f2ca9b574d7a076"
|
||||
integrity sha512-MmetCkz9ej86nJQV+sFCxoGGrUbU3q02kgLciwkrt9QqEB7cP39oKEY0PakknEO0Gu20SskMRi+AYZ3b1TpN9g==
|
||||
|
||||
"@babel/helper-validator-identifier@^7.19.1":
|
||||
version "7.19.1"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-validator-identifier/-/helper-validator-identifier-7.19.1.tgz#7eea834cf32901ffdc1a7ee555e2f9c27e249ca2"
|
||||
integrity sha512-awrNfaMtnHUr653GgGEs++LlAvW6w+DcPrOliSMXWCKo597CwL5Acf/wWdNkf/tfEQE3mjkeD1YOVZOUV/od1w==
|
||||
|
||||
"@babel/helper-validator-option@^7.14.5":
|
||||
version "7.14.5"
|
||||
resolved "https://registry.yarnpkg.com/@babel/helper-validator-option/-/helper-validator-option-7.14.5.tgz#6e72a1fff18d5dfcb878e1e62f1a021c4b72d5a3"
|
||||
|
@ -1155,15 +1138,6 @@
|
|||
"@babel/helper-validator-identifier" "^7.15.7"
|
||||
to-fast-properties "^2.0.0"
|
||||
|
||||
"@babel/types@^7.0.0-beta.49", "@babel/types@^7.18.6":
|
||||
version "7.19.4"
|
||||
resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.19.4.tgz#0dd5c91c573a202d600490a35b33246fed8a41c7"
|
||||
integrity sha512-M5LK7nAeS6+9j7hAq+b3fQs+pNfUtTGq+yFFfHnauFA8zQtLRfmuipmsKDKKLuyG+wC8ABW43A153YNawNTEtw==
|
||||
dependencies:
|
||||
"@babel/helper-string-parser" "^7.19.4"
|
||||
"@babel/helper-validator-identifier" "^7.19.1"
|
||||
to-fast-properties "^2.0.0"
|
||||
|
||||
"@bcoe/v8-coverage@^0.2.3":
|
||||
version "0.2.3"
|
||||
resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39"
|
||||
|
@ -3118,11 +3092,6 @@
|
|||
dependencies:
|
||||
keyv "*"
|
||||
|
||||
"@types/lodash@4.14.149":
|
||||
version "4.14.149"
|
||||
resolved "https://registry.yarnpkg.com/@types/lodash/-/lodash-4.14.149.tgz#1342d63d948c6062838fbf961012f74d4e638440"
|
||||
integrity sha512-ijGqzZt/b7BfzcK9vTrS6MFljQRPn5BFWOx8oE0GYxribu6uV+aA9zZuXI1zc/etK9E8nrgdoF2+LgUw7+9tJQ==
|
||||
|
||||
"@types/long@^4.0.1":
|
||||
version "4.0.2"
|
||||
resolved "https://registry.yarnpkg.com/@types/long/-/long-4.0.2.tgz#b74129719fc8d11c01868010082d483b7545591a"
|
||||
|
@ -4532,17 +4501,6 @@ babel-plugin-jest-hoist@^27.4.0:
|
|||
"@types/babel__core" "^7.0.0"
|
||||
"@types/babel__traverse" "^7.0.6"
|
||||
|
||||
babel-plugin-lodash@^3.3.4:
|
||||
version "3.3.4"
|
||||
resolved "https://registry.yarnpkg.com/babel-plugin-lodash/-/babel-plugin-lodash-3.3.4.tgz#4f6844358a1340baed182adbeffa8df9967bc196"
|
||||
integrity sha512-yDZLjK7TCkWl1gpBeBGmuaDIFhZKmkoL+Cu2MUUjv5VxUZx/z7tBGBCBcQs5RI1Bkz5LLmNdjx7paOyQtMovyg==
|
||||
dependencies:
|
||||
"@babel/helper-module-imports" "^7.0.0-beta.49"
|
||||
"@babel/types" "^7.0.0-beta.49"
|
||||
glob "^7.1.1"
|
||||
lodash "^4.17.10"
|
||||
require-package-name "^2.0.1"
|
||||
|
||||
babel-plugin-macros@^2.0.0, babel-plugin-macros@^2.8.0:
|
||||
version "2.8.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-plugin-macros/-/babel-plugin-macros-2.8.0.tgz#0f958a7cc6556b1e65344465d99111a1e5e10138"
|
||||
|
@ -10424,13 +10382,6 @@ locate-path@^6.0.0:
|
|||
dependencies:
|
||||
p-locate "^5.0.0"
|
||||
|
||||
lodash-webpack-plugin@^0.11.6:
|
||||
version "0.11.6"
|
||||
resolved "https://registry.yarnpkg.com/lodash-webpack-plugin/-/lodash-webpack-plugin-0.11.6.tgz#8204c6b78beb62ce5211217dfe783c21557ecd33"
|
||||
integrity sha512-nsHN/+IxZK/C425vGC8pAxkKJ8KQH2+NJnhDul14zYNWr6HJcA95w+oRR7Cp0oZpOdMplDZXmjVROp8prPk7ig==
|
||||
dependencies:
|
||||
lodash "^4.17.20"
|
||||
|
||||
lodash.camelcase@^4.3.0:
|
||||
version "4.3.0"
|
||||
resolved "https://registry.yarnpkg.com/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz#b28aa6288a2b9fc651035c7711f65ab6190331a6"
|
||||
|
@ -10451,7 +10402,7 @@ lodash.uniq@4.5.0:
|
|||
resolved "https://registry.yarnpkg.com/lodash.uniq/-/lodash.uniq-4.5.0.tgz#d0225373aeb652adc1bc82e4945339a842754773"
|
||||
integrity sha1-0CJTc662Uq3BvILklFM5qEJ1R3M=
|
||||
|
||||
lodash@^4.17.10, lodash@^4.17.11, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.20, lodash@^4.17.21, lodash@^4.7.0:
|
||||
lodash@^4.17.11, lodash@^4.17.15, lodash@^4.17.19, lodash@^4.17.20, lodash@^4.17.21, lodash@^4.7.0:
|
||||
version "4.17.21"
|
||||
resolved "https://registry.yarnpkg.com/lodash/-/lodash-4.17.21.tgz#679591c564c3bffaae8454cf0b3df370c3d6911c"
|
||||
integrity sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==
|
||||
|
@ -13113,11 +13064,6 @@ require-in-the-middle@^5.0.3:
|
|||
module-details-from-path "^1.0.3"
|
||||
resolve "^1.22.1"
|
||||
|
||||
require-package-name@^2.0.1:
|
||||
version "2.0.1"
|
||||
resolved "https://registry.yarnpkg.com/require-package-name/-/require-package-name-2.0.1.tgz#c11e97276b65b8e2923f75dabf5fb2ef0c3841b9"
|
||||
integrity sha512-uuoJ1hU/k6M0779t3VMVIYpb2VMJk05cehCaABFhXaibcbvfgR8wKiozLjVFSzJPmQMRqIcO0HMyTFqfV09V6Q==
|
||||
|
||||
requireindex@^1.2.0:
|
||||
version "1.2.0"
|
||||
resolved "https://registry.yarnpkg.com/requireindex/-/requireindex-1.2.0.tgz#3463cdb22ee151902635aa6c9535d4de9c2ef1ef"
|
||||
|
|
Loading…
Reference in a new issue