1
0
mirror of https://github.com/dzeiocom/libs.git synced 2025-04-22 10:52:11 +00:00

fix(object-util): Typing not being sent back to user

Signed-off-by: Avior <f.bouillon@aptatio.com>
This commit is contained in:
Florian Bouillon 2022-12-08 12:15:08 +01:00
parent c0da88ff2b
commit 6be80cb2e1
Signed by: Florian Bouillon
GPG Key ID: E05B3A94178D3A7C
5 changed files with 5040 additions and 211 deletions

4704
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -1,5 +1,7 @@
module.exports = { module.exports = {
extends: "../config/eslint/typescript.json",
root: true,
"parserOptions": { "parserOptions": {
"project": __dirname + "/tsconfig.json" "project": `${dirname}/tsconfig.json`
} }
} }

412
packages/object-util/package-lock.json generated Normal file
View File

@ -0,0 +1,412 @@
{
"name": "@dzeio/object-util",
"version": "1.4.2",
"lockfileVersion": 2,
"requires": true,
"packages": {
"": {
"name": "@dzeio/object-util",
"version": "1.4.2",
"license": "MIT",
"devDependencies": {
"esbuild": "^0.13.2"
}
},
"node_modules/esbuild": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.13.15.tgz",
"integrity": "sha512-raCxt02HBKv8RJxE8vkTSCXGIyKHdEdGfUmiYb8wnabnaEmHzyW7DCHb5tEN0xU8ryqg5xw54mcwnYkC4x3AIw==",
"dev": true,
"hasInstallScript": true,
"bin": {
"esbuild": "bin/esbuild"
},
"optionalDependencies": {
"esbuild-android-arm64": "0.13.15",
"esbuild-darwin-64": "0.13.15",
"esbuild-darwin-arm64": "0.13.15",
"esbuild-freebsd-64": "0.13.15",
"esbuild-freebsd-arm64": "0.13.15",
"esbuild-linux-32": "0.13.15",
"esbuild-linux-64": "0.13.15",
"esbuild-linux-arm": "0.13.15",
"esbuild-linux-arm64": "0.13.15",
"esbuild-linux-mips64le": "0.13.15",
"esbuild-linux-ppc64le": "0.13.15",
"esbuild-netbsd-64": "0.13.15",
"esbuild-openbsd-64": "0.13.15",
"esbuild-sunos-64": "0.13.15",
"esbuild-windows-32": "0.13.15",
"esbuild-windows-64": "0.13.15",
"esbuild-windows-arm64": "0.13.15"
}
},
"node_modules/esbuild-android-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-android-arm64/-/esbuild-android-arm64-0.13.15.tgz",
"integrity": "sha512-m602nft/XXeO8YQPUDVoHfjyRVPdPgjyyXOxZ44MK/agewFFkPa8tUo6lAzSWh5Ui5PB4KR9UIFTSBKh/RrCmg==",
"cpu": [
"arm64"
],
"dev": true,
"optional": true,
"os": [
"android"
]
},
"node_modules/esbuild-darwin-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-darwin-64/-/esbuild-darwin-64-0.13.15.tgz",
"integrity": "sha512-ihOQRGs2yyp7t5bArCwnvn2Atr6X4axqPpEdCFPVp7iUj4cVSdisgvEKdNR7yH3JDjW6aQDw40iQFoTqejqxvQ==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"darwin"
]
},
"node_modules/esbuild-darwin-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-darwin-arm64/-/esbuild-darwin-arm64-0.13.15.tgz",
"integrity": "sha512-i1FZssTVxUqNlJ6cBTj5YQj4imWy3m49RZRnHhLpefFIh0To05ow9DTrXROTE1urGTQCloFUXTX8QfGJy1P8dQ==",
"cpu": [
"arm64"
],
"dev": true,
"optional": true,
"os": [
"darwin"
]
},
"node_modules/esbuild-freebsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-freebsd-64/-/esbuild-freebsd-64-0.13.15.tgz",
"integrity": "sha512-G3dLBXUI6lC6Z09/x+WtXBXbOYQZ0E8TDBqvn7aMaOCzryJs8LyVXKY4CPnHFXZAbSwkCbqiPuSQ1+HhrNk7EA==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"freebsd"
]
},
"node_modules/esbuild-freebsd-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-freebsd-arm64/-/esbuild-freebsd-arm64-0.13.15.tgz",
"integrity": "sha512-KJx0fzEDf1uhNOZQStV4ujg30WlnwqUASaGSFPhznLM/bbheu9HhqZ6mJJZM32lkyfGJikw0jg7v3S0oAvtvQQ==",
"cpu": [
"arm64"
],
"dev": true,
"optional": true,
"os": [
"freebsd"
]
},
"node_modules/esbuild-linux-32": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-32/-/esbuild-linux-32-0.13.15.tgz",
"integrity": "sha512-ZvTBPk0YWCLMCXiFmD5EUtB30zIPvC5Itxz0mdTu/xZBbbHJftQgLWY49wEPSn2T/TxahYCRDWun5smRa0Tu+g==",
"cpu": [
"ia32"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-linux-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-64/-/esbuild-linux-64-0.13.15.tgz",
"integrity": "sha512-eCKzkNSLywNeQTRBxJRQ0jxRCl2YWdMB3+PkWFo2BBQYC5mISLIVIjThNtn6HUNqua1pnvgP5xX0nHbZbPj5oA==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-linux-arm": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-arm/-/esbuild-linux-arm-0.13.15.tgz",
"integrity": "sha512-wUHttDi/ol0tD8ZgUMDH8Ef7IbDX+/UsWJOXaAyTdkT7Yy9ZBqPg8bgB/Dn3CZ9SBpNieozrPRHm0BGww7W/jA==",
"cpu": [
"arm"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-linux-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-arm64/-/esbuild-linux-arm64-0.13.15.tgz",
"integrity": "sha512-bYpuUlN6qYU9slzr/ltyLTR9YTBS7qUDymO8SV7kjeNext61OdmqFAzuVZom+OLW1HPHseBfJ/JfdSlx8oTUoA==",
"cpu": [
"arm64"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-linux-mips64le": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-mips64le/-/esbuild-linux-mips64le-0.13.15.tgz",
"integrity": "sha512-KlVjIG828uFPyJkO/8gKwy9RbXhCEUeFsCGOJBepUlpa7G8/SeZgncUEz/tOOUJTcWMTmFMtdd3GElGyAtbSWg==",
"cpu": [
"mips64el"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-linux-ppc64le": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-ppc64le/-/esbuild-linux-ppc64le-0.13.15.tgz",
"integrity": "sha512-h6gYF+OsaqEuBjeesTBtUPw0bmiDu7eAeuc2OEH9S6mV9/jPhPdhOWzdeshb0BskRZxPhxPOjqZ+/OqLcxQwEQ==",
"cpu": [
"ppc64"
],
"dev": true,
"optional": true,
"os": [
"linux"
]
},
"node_modules/esbuild-netbsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-netbsd-64/-/esbuild-netbsd-64-0.13.15.tgz",
"integrity": "sha512-3+yE9emwoevLMyvu+iR3rsa+Xwhie7ZEHMGDQ6dkqP/ndFzRHkobHUKTe+NCApSqG5ce2z4rFu+NX/UHnxlh3w==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"netbsd"
]
},
"node_modules/esbuild-openbsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-openbsd-64/-/esbuild-openbsd-64-0.13.15.tgz",
"integrity": "sha512-wTfvtwYJYAFL1fSs8yHIdf5GEE4NkbtbXtjLWjM3Cw8mmQKqsg8kTiqJ9NJQe5NX/5Qlo7Xd9r1yKMMkHllp5g==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"openbsd"
]
},
"node_modules/esbuild-sunos-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-sunos-64/-/esbuild-sunos-64-0.13.15.tgz",
"integrity": "sha512-lbivT9Bx3t1iWWrSnGyBP9ODriEvWDRiweAs69vI+miJoeKwHWOComSRukttbuzjZ8r1q0mQJ8Z7yUsDJ3hKdw==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"sunos"
]
},
"node_modules/esbuild-windows-32": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-32/-/esbuild-windows-32-0.13.15.tgz",
"integrity": "sha512-fDMEf2g3SsJ599MBr50cY5ve5lP1wyVwTe6aLJsM01KtxyKkB4UT+fc5MXQFn3RLrAIAZOG+tHC+yXObpSn7Nw==",
"cpu": [
"ia32"
],
"dev": true,
"optional": true,
"os": [
"win32"
]
},
"node_modules/esbuild-windows-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-64/-/esbuild-windows-64-0.13.15.tgz",
"integrity": "sha512-9aMsPRGDWCd3bGjUIKG/ZOJPKsiztlxl/Q3C1XDswO6eNX/Jtwu4M+jb6YDH9hRSUflQWX0XKAfWzgy5Wk54JQ==",
"cpu": [
"x64"
],
"dev": true,
"optional": true,
"os": [
"win32"
]
},
"node_modules/esbuild-windows-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-arm64/-/esbuild-windows-arm64-0.13.15.tgz",
"integrity": "sha512-zzvyCVVpbwQQATaf3IG8mu1IwGEiDxKkYUdA4FpoCHi1KtPa13jeScYDjlW0Qh+ebWzpKfR2ZwvqAQkSWNcKjA==",
"cpu": [
"arm64"
],
"dev": true,
"optional": true,
"os": [
"win32"
]
}
},
"dependencies": {
"esbuild": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.13.15.tgz",
"integrity": "sha512-raCxt02HBKv8RJxE8vkTSCXGIyKHdEdGfUmiYb8wnabnaEmHzyW7DCHb5tEN0xU8ryqg5xw54mcwnYkC4x3AIw==",
"dev": true,
"requires": {
"esbuild-android-arm64": "0.13.15",
"esbuild-darwin-64": "0.13.15",
"esbuild-darwin-arm64": "0.13.15",
"esbuild-freebsd-64": "0.13.15",
"esbuild-freebsd-arm64": "0.13.15",
"esbuild-linux-32": "0.13.15",
"esbuild-linux-64": "0.13.15",
"esbuild-linux-arm": "0.13.15",
"esbuild-linux-arm64": "0.13.15",
"esbuild-linux-mips64le": "0.13.15",
"esbuild-linux-ppc64le": "0.13.15",
"esbuild-netbsd-64": "0.13.15",
"esbuild-openbsd-64": "0.13.15",
"esbuild-sunos-64": "0.13.15",
"esbuild-windows-32": "0.13.15",
"esbuild-windows-64": "0.13.15",
"esbuild-windows-arm64": "0.13.15"
}
},
"esbuild-android-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-android-arm64/-/esbuild-android-arm64-0.13.15.tgz",
"integrity": "sha512-m602nft/XXeO8YQPUDVoHfjyRVPdPgjyyXOxZ44MK/agewFFkPa8tUo6lAzSWh5Ui5PB4KR9UIFTSBKh/RrCmg==",
"dev": true,
"optional": true
},
"esbuild-darwin-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-darwin-64/-/esbuild-darwin-64-0.13.15.tgz",
"integrity": "sha512-ihOQRGs2yyp7t5bArCwnvn2Atr6X4axqPpEdCFPVp7iUj4cVSdisgvEKdNR7yH3JDjW6aQDw40iQFoTqejqxvQ==",
"dev": true,
"optional": true
},
"esbuild-darwin-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-darwin-arm64/-/esbuild-darwin-arm64-0.13.15.tgz",
"integrity": "sha512-i1FZssTVxUqNlJ6cBTj5YQj4imWy3m49RZRnHhLpefFIh0To05ow9DTrXROTE1urGTQCloFUXTX8QfGJy1P8dQ==",
"dev": true,
"optional": true
},
"esbuild-freebsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-freebsd-64/-/esbuild-freebsd-64-0.13.15.tgz",
"integrity": "sha512-G3dLBXUI6lC6Z09/x+WtXBXbOYQZ0E8TDBqvn7aMaOCzryJs8LyVXKY4CPnHFXZAbSwkCbqiPuSQ1+HhrNk7EA==",
"dev": true,
"optional": true
},
"esbuild-freebsd-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-freebsd-arm64/-/esbuild-freebsd-arm64-0.13.15.tgz",
"integrity": "sha512-KJx0fzEDf1uhNOZQStV4ujg30WlnwqUASaGSFPhznLM/bbheu9HhqZ6mJJZM32lkyfGJikw0jg7v3S0oAvtvQQ==",
"dev": true,
"optional": true
},
"esbuild-linux-32": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-32/-/esbuild-linux-32-0.13.15.tgz",
"integrity": "sha512-ZvTBPk0YWCLMCXiFmD5EUtB30zIPvC5Itxz0mdTu/xZBbbHJftQgLWY49wEPSn2T/TxahYCRDWun5smRa0Tu+g==",
"dev": true,
"optional": true
},
"esbuild-linux-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-64/-/esbuild-linux-64-0.13.15.tgz",
"integrity": "sha512-eCKzkNSLywNeQTRBxJRQ0jxRCl2YWdMB3+PkWFo2BBQYC5mISLIVIjThNtn6HUNqua1pnvgP5xX0nHbZbPj5oA==",
"dev": true,
"optional": true
},
"esbuild-linux-arm": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-arm/-/esbuild-linux-arm-0.13.15.tgz",
"integrity": "sha512-wUHttDi/ol0tD8ZgUMDH8Ef7IbDX+/UsWJOXaAyTdkT7Yy9ZBqPg8bgB/Dn3CZ9SBpNieozrPRHm0BGww7W/jA==",
"dev": true,
"optional": true
},
"esbuild-linux-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-arm64/-/esbuild-linux-arm64-0.13.15.tgz",
"integrity": "sha512-bYpuUlN6qYU9slzr/ltyLTR9YTBS7qUDymO8SV7kjeNext61OdmqFAzuVZom+OLW1HPHseBfJ/JfdSlx8oTUoA==",
"dev": true,
"optional": true
},
"esbuild-linux-mips64le": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-mips64le/-/esbuild-linux-mips64le-0.13.15.tgz",
"integrity": "sha512-KlVjIG828uFPyJkO/8gKwy9RbXhCEUeFsCGOJBepUlpa7G8/SeZgncUEz/tOOUJTcWMTmFMtdd3GElGyAtbSWg==",
"dev": true,
"optional": true
},
"esbuild-linux-ppc64le": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-linux-ppc64le/-/esbuild-linux-ppc64le-0.13.15.tgz",
"integrity": "sha512-h6gYF+OsaqEuBjeesTBtUPw0bmiDu7eAeuc2OEH9S6mV9/jPhPdhOWzdeshb0BskRZxPhxPOjqZ+/OqLcxQwEQ==",
"dev": true,
"optional": true
},
"esbuild-netbsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-netbsd-64/-/esbuild-netbsd-64-0.13.15.tgz",
"integrity": "sha512-3+yE9emwoevLMyvu+iR3rsa+Xwhie7ZEHMGDQ6dkqP/ndFzRHkobHUKTe+NCApSqG5ce2z4rFu+NX/UHnxlh3w==",
"dev": true,
"optional": true
},
"esbuild-openbsd-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-openbsd-64/-/esbuild-openbsd-64-0.13.15.tgz",
"integrity": "sha512-wTfvtwYJYAFL1fSs8yHIdf5GEE4NkbtbXtjLWjM3Cw8mmQKqsg8kTiqJ9NJQe5NX/5Qlo7Xd9r1yKMMkHllp5g==",
"dev": true,
"optional": true
},
"esbuild-sunos-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-sunos-64/-/esbuild-sunos-64-0.13.15.tgz",
"integrity": "sha512-lbivT9Bx3t1iWWrSnGyBP9ODriEvWDRiweAs69vI+miJoeKwHWOComSRukttbuzjZ8r1q0mQJ8Z7yUsDJ3hKdw==",
"dev": true,
"optional": true
},
"esbuild-windows-32": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-32/-/esbuild-windows-32-0.13.15.tgz",
"integrity": "sha512-fDMEf2g3SsJ599MBr50cY5ve5lP1wyVwTe6aLJsM01KtxyKkB4UT+fc5MXQFn3RLrAIAZOG+tHC+yXObpSn7Nw==",
"dev": true,
"optional": true
},
"esbuild-windows-64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-64/-/esbuild-windows-64-0.13.15.tgz",
"integrity": "sha512-9aMsPRGDWCd3bGjUIKG/ZOJPKsiztlxl/Q3C1XDswO6eNX/Jtwu4M+jb6YDH9hRSUflQWX0XKAfWzgy5Wk54JQ==",
"dev": true,
"optional": true
},
"esbuild-windows-arm64": {
"version": "0.13.15",
"resolved": "https://registry.npmjs.org/esbuild-windows-arm64/-/esbuild-windows-arm64-0.13.15.tgz",
"integrity": "sha512-zzvyCVVpbwQQATaf3IG8mu1IwGEiDxKkYUdA4FpoCHi1KtPa13jeScYDjlW0Qh+ebWzpKfR2ZwvqAQkSWNcKjA==",
"dev": true,
"optional": true
}
}
}

View File

@ -1,6 +1,6 @@
{ {
"name": "@dzeio/object-util", "name": "@dzeio/object-util",
"version": "1.4.2", "version": "1.4.3",
"description": "Utility functions to manipulate an object", "description": "Utility functions to manipulate an object",
"repository": { "repository": {
"type": "git", "type": "git",
@ -15,11 +15,21 @@
"types": "./dist/types/ObjectUtil.d.ts", "types": "./dist/types/ObjectUtil.d.ts",
"sideEffects": false, "sideEffects": false,
"devDependencies": { "devDependencies": {
"esbuild": "^0.13.2" "@types/jest": "^29",
"@typescript-eslint/eslint-plugin": "^5",
"@typescript-eslint/parser": "^5",
"esbuild": "^0.16.2",
"eslint": "^8",
"jest": "^29",
"jest-sonar-reporter": "^2",
"ts-jest": "^29",
"ts-node": "^10",
"typescript": "^4"
}, },
"scripts": { "scripts": {
"prepublishOnly": "npm run build", "prepublishOnly": "npm run build",
"build": "esbuild src/index.ts --outfile=dist/browser.js --minify --bundle --target=es6 && tsc && tsc --project tsconfig.esm.json", "build": "esbuild src/index.ts --outfile=dist/browser.js --minify --bundle --target=es6 && tsc && tsc --project tsconfig.esm.json",
"test": "jest --coverage" "test": "jest --coverage",
"lint": "eslint src"
} }
} }

View File

@ -1,13 +1,17 @@
type BasicObjectKeys = string | number | symbol
type BasicObject<K extends BasicObjectKeys = BasicObjectKeys, V = any> = Record<K, V>
/** /**
* Remap an object to an array through a function * Remap an object to an array through a function
* *
* (Same as Array.map) * (Same as Array.map but for objects)
*
* @param obj the object to remap * @param obj the object to remap
* @param fn the function to run for each key: value pairs * @param fn the function to run for each key: value pairs
*/ */
export function objectMap<T = any, J = any>( export function objectMap<T = any, J = any, K extends BasicObjectKeys = BasicObjectKeys>(
obj: Record<string, T>, obj: BasicObject<K, T>,
fn: (value: T, key: string, index: number) => J fn: (value: T, key: K, index: number) => J
): Array<J> { ): Array<J> {
mustBeObject(obj) mustBeObject(obj)
const list: Array<J> = [] const list: Array<J> = []
@ -19,18 +23,19 @@ export function objectMap<T = any, J = any>(
/** /**
* Loop through the object * Loop through the object
*
* @param obj the object to loop through * @param obj the object to loop through
* @param fn the function to run for each childs if the function return `false` it will stop * @param fn the function to run for each childs if the function return `false` it will stop
*/ */
export function objectLoop<T = any>( export function objectLoop<T = any, K extends BasicObjectKeys = BasicObjectKeys>(
obj: Record<string, T>, obj: BasicObject<K, T>,
fn: (value: T, key: string, index: number) => boolean | void fn: (value: T, key: K, index: number) => boolean | void
): boolean { ): boolean {
mustBeObject(obj) mustBeObject(obj)
const keys = objectKeys(obj) const keys = objectKeys(obj)
for (let index = 0; index < keys.length; index++) { for (let index = 0; index < keys.length; index++) {
const key = keys[index] const key = keys[index]
const stop = fn(obj[key], key, index) const stop = fn(obj[key] as T, key as K, index)
if (stop === false) { if (stop === false) {
return false return false
} }
@ -40,9 +45,10 @@ export function objectLoop<T = any>(
/** /**
* Transform an object to an array of its values * Transform an object to an array of its values
*
* @param obj the object to transform * @param obj the object to transform
*/ */
export function objectValues<T = any>(obj: Record<string, T>): Array<T> { export function objectValues<T = any>(obj: BasicObject<BasicObjectKeys, T>): Array<T> {
mustBeObject(obj) mustBeObject(obj)
return Object.values(obj) return Object.values(obj)
} }
@ -50,36 +56,44 @@ export function objectValues<T = any>(obj: Record<string, T>): Array<T> {
/** /**
* @deprecated use `objectValues` * @deprecated use `objectValues`
*/ */
export function objectToArray<T = any>(obj: Record<string, T>): Array<T> { export function objectToArray<T = any>(obj: BasicObject<BasicObjectKeys, T>): Array<T> {
mustBeObject(obj) mustBeObject(obj)
return objectValues(obj) return objectValues(obj)
} }
/** /**
* return the keys of the object * return the keys of the object
*
* @param obj the object * @param obj the object
*/ */
export function objectKeys(obj: Record<string, any>): Array<string> { export function objectKeys<K extends BasicObjectKeys = BasicObjectKeys>(obj: BasicObject<K>): Array<K> {
mustBeObject(obj) mustBeObject(obj)
return Object.keys(obj)
// Handle arrays
if (Array.isArray(obj)) {
return Array.from(obj.keys()) as Array<K>
}
return Object.keys(obj) as Array<K>
} }
/** /**
* return the length of an object * return the length of an object
*
* @param obj the object * @param obj the object
*/ */
export function objectSize(obj: Record<string, any>): number { export function objectSize(obj: BasicObject): number {
return objectKeys(obj).length return objectKeys(obj).length
} }
/** /**
* Sort an object by its keys * Sort an object by its keys
* *
* Same as Array.sort * Same as Array.sort but for objects
*
* @param obj the object to sort * @param obj the object to sort
* @param fn (Optionnal) the function to run to sort * @param fn (Optionnal) the function to run to sort
*/ */
export function objectSort<T extends Record<string, any> = Record<string, any>>( export function objectSort<T extends BasicObject>(
obj: T, obj: T,
fn?: Array<keyof T> | ((a: keyof T, b: keyof T) => number) fn?: Array<keyof T> | ((a: keyof T, b: keyof T) => number)
): T { ): T {
@ -87,7 +101,7 @@ export function objectSort<T extends Record<string, any> = Record<string, any>>(
const ordered: any = {} const ordered: any = {}
let sortedKeys: Array<keyof T> = [] let sortedKeys: Array<keyof T> = []
if (Array.isArray(fn)) { if (Array.isArray(fn)) {
sortedKeys = fn.concat(objectKeys(obj).filter((k) => !fn.includes(k))) sortedKeys = fn.concat(objectKeys(obj).filter((key) => !fn.includes(key)))
} else { } else {
sortedKeys = objectKeys(obj).sort(fn) sortedKeys = objectKeys(obj).sort(fn)
} }
@ -100,25 +114,26 @@ export function objectSort<T extends Record<string, any> = Record<string, any>>(
/** /**
* @deprecated use `objectClone` * @deprecated use `objectClone`
*/ */
export function cloneObject<T = Record<string, any>>(obj: T): T { export function cloneObject<T extends BasicObject>(obj: T): T {
return objectClone(obj) return objectClone(obj)
} }
/** /**
* Deeply clone an object * Deeply clone an object
*
* @param obj the object to clone * @param obj the object to clone
* @param options Cloning options
* @param options.deep (Default: true) deeply clone the object
* @returns the clone of the object * @returns the clone of the object
*/ */
export function objectClone<T = Record<string, any>>(obj: T, options?: {deep?: boolean}): T { export function objectClone<T extends BasicObject>(obj: T, options?: {deep?: boolean}): T {
mustBeObject(obj) mustBeObject(obj)
if (Array.isArray(obj)) { if (Array.isArray(obj)) {
const arr: Array<any> = [] const arr: Array<any> = []
for (const item of obj) { for (const item of obj) {
if (isObject(item)) { arr.push(
arr.push(objectClone(item)) isObject(item) ? objectClone(item) : item
} else { )
arr.push(item)
}
} }
return arr as unknown as T return arr as unknown as T
} }
@ -136,20 +151,22 @@ export function objectClone<T = Record<string, any>>(obj: T, options?: {deep?: b
/** /**
* deeply set the value at the path given * deeply set the value at the path given
* *
* (Create sub object/array if not made) * (Create sub object/array if not made depending on path type (number = Array, string = Object))
*
* _NOTE: it is way quicker to use `obj[path][path]... = value` when possible_
* *
* _NOTE: it is way quicker to use obj[path][path]... = value_
* @param obj the object to set the value * @param obj the object to set the value
* @param path the path * @param path the path
* @param value the value * @param value the value
*/ */
export function objectSet(obj: Record<string, any>, path: Array<string | number>, value: any): void { export function objectSet(obj: BasicObject, path: Array<BasicObjectKeys>, value: any): void {
mustBeObject(obj) mustBeObject(obj)
let pointer = obj let pointer = obj
for (let index = 0; index < path.length; index++) { for (let index = 0; index < path.length; index++) {
const key = path[index] const key = path[index]
if ((!Object.prototype.hasOwnProperty.call(pointer, key)) && (index+1) < path.length) { const nextIndex = index + 1
const key1 = path[index + 1] if (!Object.prototype.hasOwnProperty.call(pointer, key) && nextIndex < path.length) {
const key1 = path[nextIndex]
if (typeof key1 === 'number') { if (typeof key1 === 'number') {
pointer[key] = [] pointer[key] = []
} else { } else {
@ -158,7 +175,7 @@ export function objectSet(obj: Record<string, any>, path: Array<string | number>
} }
// if last index // if last index
if ((index+1) === path.length) { if (nextIndex === path.length) {
pointer[key] = value pointer[key] = value
if (value === undefined) { if (value === undefined) {
delete pointer[key] delete pointer[key]
@ -172,20 +189,21 @@ export function objectSet(obj: Record<string, any>, path: Array<string | number>
/** /**
* deeply compare objects and return if they are equal or not * deeply compare objects and return if they are equal or not
* @param x the first object *
* @param y the second object * @param first the first object
* @param second the second object
*/ */
export function objectEqual(x: Record<string, any>, y: Record<string, any>): boolean { export function objectEqual(first: BasicObject, second: BasicObject): boolean {
mustBeObject(x) mustBeObject(first)
mustBeObject(y) mustBeObject(second)
if (objectSize(x) !== objectSize(y)) { if (objectSize(first) !== objectSize(second)) {
return false return false
} }
const res = objectLoop(x, (item, key) => { const res = objectLoop(first, (item, key) => {
if (!(key in y)) { if (!(key in second)) {
return false return false
} }
const item2 = y[key] const item2 = second[key]
if (item === null && item2 === null) { if (item === null && item2 === null) {
return true return true
} }
@ -199,12 +217,13 @@ export function objectEqual(x: Record<string, any>, y: Record<string, any>): boo
/** /**
* deeply clean an object from having {key: undefined} * deeply clean an object from having {key: undefined}
*
* @param obj the object to clean * @param obj the object to clean
* @param {boolean?} options.cleanUndefined (default: true) clean undefined from the object * @param {boolean?} options.cleanUndefined (default: true) clean undefined from the object
* @param {boolean?} options.cleanNull clean null frrom the object * @param {boolean?} options.cleanNull clean null from the object
* @param {boolean?} options.deep (default: true) deeply clean the object * @param {boolean?} options.deep (default: true) deeply clean the object
*/ */
export function objectClean(obj: Record<string, any>, options?: {cleanUndefined?: boolean, cleanNull?: boolean, deep?: boolean}): void { export function objectClean(obj: BasicObject, options?: {cleanUndefined?: boolean, cleanNull?: boolean, deep?: boolean}): void {
mustBeObject(obj) mustBeObject(obj)
objectLoop(obj, (item, key) => { objectLoop(obj, (item, key) => {
if ((typeof options?.cleanUndefined === 'undefined' || options?.cleanUndefined) && item === undefined) { if ((typeof options?.cleanUndefined === 'undefined' || options?.cleanUndefined) && item === undefined) {
@ -223,11 +242,12 @@ export function objectClean(obj: Record<string, any>, options?: {cleanUndefined?
/** /**
* clone the object (not deeply) and emit some keys from cloning * clone the object (not deeply) and emit some keys from cloning
*
* @param obj the object to clone * @param obj the object to clone
* @param keys the keys to emit * @param keys the keys to emit
* @returns the cloned object * @returns the cloned object
*/ */
export function objectOmit<T extends Record<string, any> = Record<string, any>>(obj: T, ...keys: Array<string>): T { export function objectOmit<T extends BasicObject>(obj: T, ...keys: Array<string>): T {
const cloned = objectClone(obj, {deep: false}) const cloned = objectClone(obj, {deep: false})
for (const key of keys) { for (const key of keys) {
if (key in cloned) { if (key in cloned) {
@ -239,25 +259,25 @@ export function objectOmit<T extends Record<string, any> = Record<string, any>>(
/** /**
* return if an item is an object * return if an item is an object
*
* @param item the item to check * @param item the item to check
* @returns {boolean} the item is an object * @returns {boolean} the item is an object
*/ */
export function isObject(item: any): item is Record<any, any> { export function isObject(item: any): item is BasicObject {
return typeof item === 'object' && item !== null return typeof item === 'object' && item !== null
} }
/** /**
* Strict check for an object * Strict check for an object
* *
* @internal
* @param item the item to check * @param item the item to check
* @returns {boolean} throw an error is the item is not an item * @returns {boolean} throw an error is the item is not an item
*/ */
function mustBeObject(item: any): item is Record<any, any> { export function mustBeObject(item: any): item is BasicObject {
if (isObject(item)) { if (isObject(item)) {
return true return true
} else { } else {
throw new Error("Input is not an object!") throw new Error('Input is not an object!')
} }
} }
@ -274,5 +294,6 @@ export default {
objectEqual, objectEqual,
objectClean, objectClean,
objectOmit, objectOmit,
isObject isObject,
mustBeObject
} }