@novo-learning/novo-sdk
Version:
SDK for the Novolanguage Speech Analysis API
49 lines (42 loc) • 1.29 kB
text/typescript
export const isObject = <T>(item: T): item is NonNullable<T> => {
return item != null && typeof item === 'object' && !Array.isArray(item);
};
const forbiddenProperties: string[] = ['__proto__', 'constructor', 'prototype'];
const isSafeKey = (obj: object, key: string): boolean =>
Object.prototype.hasOwnProperty.call(obj, key) && !forbiddenProperties.includes(key);
const mergeValue = <T extends Record<PropertyKey, unknown>, K extends keyof T>(
target: T,
key: K,
value?: T[K],
): void => {
if (isObject(value)) {
if (!target[key]) {
target[key] = {} as T[K];
}
mergeDeep(target[key], value);
} else if (value !== undefined) {
target[key] = value;
}
};
/**
* Merges partial objects into the target object.
* This modifies the target object and returns it.
*
* @param target The object into which the changes are merged
* @param sources A list of patches to apply
* @returns the target
*/
export const mergeDeep = <T>(target: T, ...sources: Partial<T>[]): T => {
for (const source of sources) {
if (!isObject(target) || !isObject(source)) {
continue;
}
for (const key in source) {
if (!isSafeKey(source, key)) {
continue;
}
mergeValue(target, key, source[key]);
}
}
return target;
};