Socket
Socket
Sign inDemoInstall

@js-bits/typedef-utils

Package Overview
Dependencies
0
Maintainers
1
Versions
18
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

Comparing version 0.0.10 to 1.0.0

dist/math.d.ts

97

docs/modules/math.md

@@ -5,4 +5,97 @@ # Module: math

### Namespaces
### Type Aliases
- [MathUtils](math.MathUtils.md)
- [Add](math.md#add)
- [Multiply](math.md#multiply)
- [Parse](math.md#parse)
## Type Aliases
### Add
**Add**<`A`, `B`\>: `_Add_`<`A`, `B`\>
Addition of two positive integer values represented by either a number or a string format
**`Requires`**
TypeScript 4.8+
**`Remarks`**
The operation doesn't have any noticeable limitations
**`Example`**
```ts
const smallValue: MathUtils.Add<3, 4> = 7;
const bigValue: MathUtils.Add<9999999, 9999999> = 19999998;
const stringArgs: MathUtils.Add<'1234567890', '987654321'> = 2222222211;
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `string` \| `number` | any positive integer number |
| `B` | extends `string` \| `number` | any positive integer number |
___
### Multiply
**Multiply**<`A`, `B`\>: `_Multiply_`<`A`, `B`\>
Multiplies two positive integer values represented by either a number or a string format
**`Requires`**
TypeScript 4.8+
**`Remarks`**
The first argument can be 999 max because of a [hardcoded limit in TypeScript compiler](https://github.com/microsoft/TypeScript/pull/45711)
**`Example`**
```ts
const numberArgs: MathUtils.Multiply<78, 63> = 4914;
const stringArgs: MathUtils.Multiply<'999', '999'> = 998001;
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `string` \| `number` | any positive integer number from 0 to 999 |
| `B` | extends `string` \| `number` | any positive integer number |
___
### Parse
**Parse**<`T`\>: `T` extends `number` ? `T` : `T` extends \`${infer N extends number}\` ? `N` : `never`
Returns number by the given string representation
**`Requires`**
TypeScript 4.8+
**`Remarks`**
[Related TypeScript issue](https://github.com/microsoft/TypeScript/pull/48094)
**`Example`**
```ts
const intValue: MathUtils.Parse<'123'> = 123;
const floatValue: MathUtils.Parse<'-56.78'> = -56.78;
const stringArg: MathUtils.Parse<123> = 123;
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `T` | extends `string` \| `number` | any number |

@@ -5,4 +5,117 @@ # Module: string

### Namespaces
### Type Aliases
- [StringUtils](string.StringUtils.md)
- [Split](string.md#split)
- [Trim](string.md#trim)
- [TrimLeft](string.md#trimleft)
- [TrimRight](string.md#trimright)
- [Unique](string.md#unique)
## Type Aliases
### Split
**Split**<`Str`, `Separator`, `NoEmpty`\>: `_Split_`<`Str`, `Separator`, `NoEmpty`\>
Returns a tuple of substrings by splitting the string pattern by the given separator.
Additionally you can filter out empty string from the resulting list by specifying the third argument as `true`
**`Example`**
```ts
const arr: StringUtils.Split<'a b c', ' '> = ['a', 'b', 'c'];
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `Str` | extends `string` | any string |
| `Separator` | extends `string` | any string character |
| `NoEmpty` | extends `boolean` = ``false`` | optional flag |
___
### Trim
**Trim**<`Str`, `Spacer`\>: [`TrimLeft`](string.md#trimleft)<[`TrimRight`](string.md#trimright)<`Str`, `Spacer`\>, `Spacer`\>
Removes leading and trailing white spaces (or the specified characters) from the given string
**`Example`**
```ts
const str1: StringUtils.Trim<' abc '> = 'abc';
const str2: StringUtils.Trim<'*******abc*******', '*'> = 'abc';
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `Str` | extends `string` | any string |
| `Spacer` | extends `string` = ``" "`` | optional string character |
___
### TrimLeft
**TrimLeft**<`Str`, `Spacer`\>: `Str` extends \`${Spacer}${infer Part}\` ? [`TrimLeft`](string.md#trimleft)<`Part`, `Spacer`\> : `Str`
Removes leading white spaces (or the specified characters) from the given string
**`Example`**
```ts
const str1: StringUtils.TrimLeft<' abc'> = 'abc';
const str2: StringUtils.TrimLeft<'*******abc', '*'> = 'abc';
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `Str` | extends `string` | any string |
| `Spacer` | extends `string` = ``" "`` | any string |
___
### TrimRight
**TrimRight**<`Str`, `Spacer`\>: `Str` extends \`${infer Part}${Spacer}\` ? [`TrimRight`](string.md#trimright)<`Part`, `Spacer`\> : `Str`
Removes trailing white spaces (or the specified characters) from the given string
**`Example`**
```ts
const str1: StringUtils.TrimRight<'abc '> = 'abc';
const str2: StringUtils.TrimRight<'abc*******', '*'> = 'abc';
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `Str` | extends `string` | any string |
| `Spacer` | extends `string` = ``" "`` | optional string character |
___
### Unique
**Unique**<`A`\>: `NotEmptyString`<`A`[`number`]\>
Transforms a tuple of strings into a union of string values
**`Example`**
```ts
type StringUnion = StringUtils.Unique<['a', 'a', 'b', 'c', 'c']>; // "a" | "b" | "c"
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `string`[] | any string tuple |

@@ -5,4 +5,75 @@ # Module: tuple

### Namespaces
### Type Aliases
- [TupleUtils](tuple.TupleUtils.md)
- [Append](tuple.md#append)
- [Length](tuple.md#length)
- [Longest](tuple.md#longest)
## Type Aliases
### Append
**Append**<`A`, `Item`, `NoEmpty`\>: `NoEmpty` extends ``true`` ? `Item` extends ``""`` ? `A` : [...A, `Item`] : [...A, `Item`]
Appends new item to the given tuple.
Optionally you can ignore empty strings by specifying the third argument as `true`
**`Example`**
```ts
const arr: TupleUtils.Append<[1, 2, 3, 4], 5> = [1, 2, 3, 4, 5];
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `unknown`[] | any tuple |
| `Item` | `Item` | any value |
| `NoEmpty` | extends `boolean` = ``false`` | optional flag |
___
### Length
**Length**<`A`\>: `A` extends { `length`: infer L } ? `L` : `never`
Returns length of the given tuple
**`Example`**
```ts
const length: TupleUtils.Length<[1, 2, 3, 4, 5]> = 5;
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `unknown`[] | any tuple |
___
### Longest
**Longest**<`A`, `B`\>: `B`[[`Length`](tuple.md#length)<`A`\>] extends `undefined` ? `A` : `B`
Compares two tuples by their length and returns either the longest one of them
or the first one if they are the same length
**`Remarks`**
All items of both tuples must be defined in order for the operation to work properly
**`Example`**
```ts
const longest: TupleUtils.Longest<[1], [1, 2, 3]> = [1, 2, 3];
```
#### Type parameters
| Name | Type | Description |
| :------ | :------ | :------ |
| `A` | extends `unknown`[] | any tuple without undefined items |
| `B` | extends `unknown`[] | any tuple without undefined items |
{
"name": "@js-bits/typedef-utils",
"version": "0.0.10",
"version": "1.0.0",
"description": "Utility types for TypeScript",

@@ -20,7 +20,18 @@ "keywords": [

"type": "module",
"types": "dist/index.d.ts",
"exports": {
"./math": "./types/math.ts",
"./string": "./types/string.ts",
"./tuple": "./types/tuple.ts"
},
"typesVersions": {
"*": {
"*": [
"./dist/*"
]
}
},
"scripts": {
"lint": "tsc --noEmit && eslint '**/*.{js,jsx,ts,tsx}'",
"test": "yarn lint",
"build": "rimraf ./dist && tsc types/*.ts --emitDeclarationOnly --declaration --outFile dist/index.d.ts",
"build": "rimraf ./dist && tsc types/*.ts --emitDeclarationOnly --declaration --outDir dist",
"docs": "rimraf ./docs && typedoc types/*.ts --plugin typedoc-plugin-markdown --disableSources --readme none --hideMembersSymbol --hideBreadcrumbs",

@@ -27,0 +38,0 @@ "prepare": "husky install"

55

test/math.test.ts
/* eslint-disable import/extensions, @typescript-eslint/no-unused-vars, camelcase */
import { Add, AddString, Multiply, Normalize, Parse, SplitDigits, SumDigits, ToNumber } from '../types/math';
const test_ParseInt: MathUtils.Parse<'123'> = 123;
const test_ParseInt2: MathUtils.Parse<123> = 123;
const test_ParseFloat: MathUtils.Parse<'56.78'> = 56.78;
const test_ParseNegative: MathUtils.Parse<'-56.78'> = -56.78;
const test_ParseInt: Parse<'123'> = 123;
const test_ParseInt2: Parse<123> = 123;
const test_ParseFloat: Parse<'56.78'> = 56.78;
const test_ParseNegative: Parse<'-56.78'> = -56.78;
const test_SplitDigits1: MathUtils.SplitDigits<'1234'> = ['4', '3', '2', '1', '0'];
const test_SplitDigits1: SplitDigits<'1234'> = ['4', '3', '2', '1', '0'];
const test_SumDigits1: MathUtils.SumDigits<'9', '9'> = 18;
const test_SumDigits2: MathUtils.SumDigits<'1', '2'> = 3;
const test_SumDigits1: SumDigits<'9', '9'> = 18;
const test_SumDigits2: SumDigits<'1', '2'> = 3;
const test_AddString1: MathUtils.AddString<'3', '85'> = [8, 8, 0];
const test_AddString2: MathUtils.AddString<'99', '1'> = [10, 9, 0];
const test_AddString1: AddString<'3', '85'> = [8, 8, 0];
const test_AddString2: AddString<'99', '1'> = [10, 9, 0];
const test_ToNumber1: MathUtils.ToNumber<[1, 2, 3, 0]> = '0321';
const test_ToNumber2: MathUtils.ToNumber<[10, 12, 0]> = '130';
const test_ToNumber1: ToNumber<[1, 2, 3, 0]> = '0321';
const test_ToNumber2: ToNumber<[10, 12, 0]> = '130';
const test_Normalize1: MathUtils.Normalize<'0000000123'> = '123';
const test_Normalize2: MathUtils.Normalize<'123000000'> = '123000000';
const test_Normalize1: Normalize<'0000000123'> = '123';
const test_Normalize2: Normalize<'123000000'> = '123000000';
const test_Add0: MathUtils.Add<3, 4> = 7;
const test_Add1: MathUtils.Add<1999, 1> = 2000;
const test_Add2: MathUtils.Add<9, 1> = 10;
const test_Add3: MathUtils.Add<99, 1> = 100;
const test_Add4: MathUtils.Add<999, 1> = 1000;
const test_Add5: MathUtils.Add<999, 999> = 1998;
const test_Add6: MathUtils.Add<9, 99999999999> = 100000000008;
const test_Add7: MathUtils.Add<99999999999, 9> = 100000000008;
const test_Add8: MathUtils.Add<9999999, 9999999> = 19999998;
const test_Add9: MathUtils.Add<'1234567890', '987654321'> = 2222222211;
const test_Add0: Add<3, 4> = 7;
const test_Add1: Add<1999, 1> = 2000;
const test_Add2: Add<9, 1> = 10;
const test_Add3: Add<99, 1> = 100;
const test_Add4: Add<999, 1> = 1000;
const test_Add5: Add<999, 999> = 1998;
const test_Add6: Add<9, 99999999999> = 100000000008;
const test_Add7: Add<99999999999, 9> = 100000000008;
const test_Add8: Add<9999999, 9999999> = 19999998;
const test_Add9: Add<'1234567890', '987654321'> = 2222222211;
// A is limited to 999, B is "limitless"
const test_Multiply1: MathUtils.Multiply<999, 99999999> = 99899999001;
const test_Multiply2: MathUtils.Multiply<199, 3> = 597;
const test_Multiply3: MathUtils.Multiply<78, 63> = 4914;
const test_Multiply4: MathUtils.Multiply<'999', '999'> = 998001;
const test_Multiply1: Multiply<999, 99999999> = 99899999001;
const test_Multiply2: Multiply<199, 3> = 597;
const test_Multiply3: Multiply<78, 63> = 4914;
const test_Multiply4: Multiply<'999', '999'> = 998001;
/* eslint-disable @typescript-eslint/no-unused-vars, camelcase, import/extensions */
import { Split, Trim, Unique } from '../types/string';
import { MULTI_LINE_LIST, SINGLE_LINE_LIST, SINGLE_LINE_LONG_STRING } from './string.data';
let test_trimEmpty: StringUtils.Trim<' '> = '';
let test_trimEmpty: Trim<' '> = '';
// @ts-expect-error Type '"abc"' is not assignable to type '""'
test_trimEmpty = 'abc';
const test_trimNone: StringUtils.Trim<'option_l0'> = 'option_l0';
const test_trimNone: Trim<'option_l0'> = 'option_l0';
const test_trimLeftSingle: StringUtils.Trim<' option_l1'> = 'option_l1';
let test_trimLeftMultiple: StringUtils.Trim<' option_l2'> = 'option_l2';
const test_trimLeftSingle: Trim<' option_l1'> = 'option_l1';
let test_trimLeftMultiple: Trim<' option_l2'> = 'option_l2';
// @ts-expect-error Type '"option_l3"' is not assignable to type '"option_l2"'
test_trimLeftMultiple = 'option_l3';
const test_trimRightSingle: StringUtils.Trim<'option_r1 '> = 'option_r1';
let test_trimRightMutliple: StringUtils.Trim<'option_r2 '> = 'option_r2';
const test_trimRightSingle: Trim<'option_r1 '> = 'option_r1';
let test_trimRightMutliple: Trim<'option_r2 '> = 'option_r2';
// @ts-expect-error Type '"option_r3"' is not assignable to type '"option_r2"'
test_trimRightMutliple = 'option_r3';
const test_trimCenterSingle: StringUtils.Trim<' option_c1 '> = 'option_c1';
const test_trimCenterMultiple: StringUtils.Trim<' option_c2 '> = 'option_c2';
const test_trimCenterDashes: StringUtils.Trim<'-------option_c3---------', '-'> = 'option_c3';
const test_trimCenterSingle: Trim<' option_c1 '> = 'option_c1';
const test_trimCenterMultiple: Trim<' option_c2 '> = 'option_c2';
const test_trimCenterDashes: Trim<'-------option_c3---------', '-'> = 'option_c3';
let test_trimSingleLineLimits: StringUtils.Trim<SINGLE_LINE_LONG_STRING> = 'string';
let test_trimSingleLineLimits: Trim<SINGLE_LINE_LONG_STRING> = 'string';
// @ts-expect-error Type '"abc"' is not assignable to type '"string"'
test_trimSingleLineLimits = 'abc';
const test_splitNoneSpace: StringUtils.Split<'a b c', '\n'> = ['a b c'];
const test_splitNoneNewLine: StringUtils.Split<'a\nb\nc', ' '> = ['a\nb\nc'];
const test_splitNoneSpace: Split<'a b c', '\n'> = ['a b c'];
const test_splitNoneNewLine: Split<'a\nb\nc', ' '> = ['a\nb\nc'];
const test_splitNewLine1: StringUtils.Split<'a\nb\nc', '\n'> = ['a', 'b', 'c'];
const test_splitNewLine2: StringUtils.Split<'a\nb\nc\n', '\n'> = ['a', 'b', 'c', ''];
const test_splitNewLine3: StringUtils.Split<
const test_splitNewLine1: Split<'a\nb\nc', '\n'> = ['a', 'b', 'c'];
const test_splitNewLine2: Split<'a\nb\nc\n', '\n'> = ['a', 'b', 'c', ''];
const test_splitNewLine3: Split<
`

@@ -42,31 +43,31 @@ a

const test_splitSpace1: StringUtils.Split<'a b c', ' '> = ['a', 'b', 'c'];
const test_splitSpace2: StringUtils.Split<' a b c ', ' '> = ['', 'a', 'b', 'c'];
const test_splitSpace1: Split<'a b c', ' '> = ['a', 'b', 'c'];
const test_splitSpace2: Split<' a b c ', ' '> = ['', 'a', 'b', 'c'];
const test_splitNoEmpty1: StringUtils.Split<'\na\nb\nc\n', '\n', true> = ['a', 'b', 'c'];
const test_splitNoEmpty2: StringUtils.Split<' a b c ', ' ', true> = ['a', 'b', 'c'];
const test_splitNoEmpty1: Split<'\na\nb\nc\n', '\n', true> = ['a', 'b', 'c'];
const test_splitNoEmpty2: Split<' a b c ', ' ', true> = ['a', 'b', 'c'];
const test_SplitSingleLineLimits21: StringUtils.Split<SINGLE_LINE_LIST, ' '>[10] = 'OPTION011';
const test_SplitSingleLineLimits21: Split<SINGLE_LINE_LIST, ' '>[10] = 'OPTION011';
// @ts-expect-error Type '"OPTION010"' is not assignable to type '"OPTION011"'
const test_SplitSingleLineLimits22: StringUtils.Split<SINGLE_LINE_LIST, ' '>[10] = 'OPTION010';
const test_SplitSingleLineLimits3: StringUtils.Split<SINGLE_LINE_LIST, ' '>[99] = 'OPTION100';
const test_SplitSingleLineLimits4: StringUtils.Split<SINGLE_LINE_LIST, ' '>[998] = 'OPTION999';
const test_SplitSingleLineLimits22: Split<SINGLE_LINE_LIST, ' '>[10] = 'OPTION010';
const test_SplitSingleLineLimits3: Split<SINGLE_LINE_LIST, ' '>[99] = 'OPTION100';
const test_SplitSingleLineLimits4: Split<SINGLE_LINE_LIST, ' '>[998] = 'OPTION999';
const test_SplitMultiLineLimits1: StringUtils.Split<MULTI_LINE_LIST, '\n'>[0] = '';
const test_SplitMultiLineLimits21: StringUtils.Split<MULTI_LINE_LIST, '\n'>[10] = 'OPTION010';
const test_SplitMultiLineLimits1: Split<MULTI_LINE_LIST, '\n'>[0] = '';
const test_SplitMultiLineLimits21: Split<MULTI_LINE_LIST, '\n'>[10] = 'OPTION010';
// @ts-expect-error Type '"OPTION011"' is not assignable to type '"OPTION010"'
const test_SplitMultiLineLimits22: StringUtils.Split<MULTI_LINE_LIST, '\n'>[10] = 'OPTION011';
const test_SplitMultiLineLimits3: StringUtils.Split<MULTI_LINE_LIST, '\n'>[100] = 'OPTION100';
const test_SplitMultiLineLimits4: StringUtils.Split<MULTI_LINE_LIST, '\n'>[997] = 'OPTION997';
const test_SplitMultiLineLimits5: StringUtils.Split<MULTI_LINE_LIST, '\n'>[998] = '';
const test_SplitMultiLineLimits22: Split<MULTI_LINE_LIST, '\n'>[10] = 'OPTION011';
const test_SplitMultiLineLimits3: Split<MULTI_LINE_LIST, '\n'>[100] = 'OPTION100';
const test_SplitMultiLineLimits4: Split<MULTI_LINE_LIST, '\n'>[997] = 'OPTION997';
const test_SplitMultiLineLimits5: Split<MULTI_LINE_LIST, '\n'>[998] = '';
const test_SplitUnionLimits1: StringUtils.Unique<StringUtils.Split<MULTI_LINE_LIST, '\n'>> = 'OPTION010';
const test_SplitUnionLimits2: StringUtils.Unique<StringUtils.Split<MULTI_LINE_LIST, '\n'>> = 'OPTION997';
const test_SplitUnionLimits1: Unique<Split<MULTI_LINE_LIST, '\n'>> = 'OPTION010';
const test_SplitUnionLimits2: Unique<Split<MULTI_LINE_LIST, '\n'>> = 'OPTION997';
// @ts-expect-error Type '"OPTION999"' is not assignable to type 'Unique<["", "OPTION001", "OPTION002", ...
const test_SplitUnionLimits3: StringUtils.Unique<StringUtils.Split<MULTI_LINE_LIST>> = 'OPTION999';
const test_SplitUnionLimits3: Unique<Split<MULTI_LINE_LIST>> = 'OPTION999';
// @ts-expect-error Type '""' is not assignable to type 'Unique<["", "OPTION001", "OPTION002", ...
const test_SplitUnionLimits4: StringUtils.Unique<StringUtils.Split<MULTI_LINE_LIST>> = '';
const test_SplitUnionLimits4: Unique<Split<MULTI_LINE_LIST>> = '';
// @ts-expect-error Type '""' is not assignable to type 'Unique<["OPTION001", "OPTION002",
const test_SplitUnionLimits5: StringUtils.Unique<StringUtils.Split<SINGLE_LINE_LIST, ' '>> = '';
const test_SplitUnionLimits5: Unique<Split<SINGLE_LINE_LIST, ' '>> = '';
// @ts-expect-error Type '"OPTION000"' is not assignable to type 'Unique<["OPTION001", "OPTION002", ...
const test_SplitUnionLimits6: StringUtils.Unique<StringUtils.Split<SINGLE_LINE_LIST, ' '>> = 'OPTION000';
const test_SplitUnionLimits6: Unique<Split<SINGLE_LINE_LIST, ' '>> = 'OPTION000';
/* eslint-disable @typescript-eslint/no-unused-vars, import/extensions, camelcase */
const test_Length1: TupleUtils.Length<[1, 2, 3, 4, 5]> = 5;
const test_Length2: TupleUtils.Length<[]> = 0;
const test_Length3: TupleUtils.Length<['a', 'b', 'c']> = 3;
import { Append, Length, Longest } from '../types/tuple';
const lest_Longest1: TupleUtils.Longest<[1, 1, 1], [2, 2, 2]> = [1, 1, 1];
const lest_Longest2: TupleUtils.Longest<[1, 1], [2, 2, 2]> = [2, 2, 2];
const lest_Longest3: TupleUtils.Longest<[1, 1, 1, 1, 1], [2]> = [1, 1, 1, 1, 1];
const test_Length1: Length<[1, 2, 3, 4, 5]> = 5;
const test_Length2: Length<[]> = 0;
const test_Length3: Length<['a', 'b', 'c']> = 3;
const test_Append1: TupleUtils.Append<[1, 2, 3, 4], 5> = [1, 2, 3, 4, 5];
const test_Append2: TupleUtils.Append<['a', true, undefined], 6> = ['a', true, undefined, 6];
const lest_Longest1: Longest<[1, 1, 1], [2, 2, 2]> = [1, 1, 1];
const lest_Longest2: Longest<[1, 1], [2, 2, 2]> = [2, 2, 2];
const lest_Longest3: Longest<[1, 1, 1, 1, 1], [2]> = [1, 1, 1, 1, 1];
const test_Append1: Append<[1, 2, 3, 4], 5> = [1, 2, 3, 4, 5];
const test_Append2: Append<['a', true, undefined], 6> = ['a', true, undefined, 6];

@@ -6,2 +6,3 @@ {

"strictNullChecks": true,
"isolatedModules": true,
"forceConsistentCasingInFileNames": true,

@@ -8,0 +9,0 @@ "lib": ["es5", "es6", "es2015", "es7", "es2016", "es2017", "es2018", "es2019", "es2020", "es2021", "es2022", "DOM"]

/* eslint-disable @typescript-eslint/no-unused-vars, import/extensions, @typescript-eslint/no-namespace */
// INSPIRATION: https://itnext.io/implementing-arithmetic-within-typescripts-type-system-a1ef140a6f6f
import { Longest } from './tuple';
/**

@@ -9,109 +11,107 @@ * Type-level math operations

declare namespace MathUtils {
/**
* Returns number by the given string representation
* @typeParam T - any number
* @requires TypeScript 4.8+
* @remarks
* {@link https://github.com/microsoft/TypeScript/pull/48094 | Related TypeScript issue}
* @example
* const intValue: MathUtils.Parse<'123'> = 123;
* const floatValue: MathUtils.Parse<'-56.78'> = -56.78;
* const stringArg: MathUtils.Parse<123> = 123;
*/
type Parse<T extends string | number> = T extends number ? T : T extends `${infer N extends number}` ? N : never;
/**
* Returns number by the given string representation
* @typeParam T - any number
* @requires TypeScript 4.8+
* @remarks
* {@link https://github.com/microsoft/TypeScript/pull/48094 | Related TypeScript issue}
* @example
* const intValue: MathUtils.Parse<'123'> = 123;
* const floatValue: MathUtils.Parse<'-56.78'> = -56.78;
* const stringArg: MathUtils.Parse<123> = 123;
*/
export type Parse<T extends string | number> = T extends number ? T : T extends `${infer N extends number}` ? N : never;
/** @ignore */
type Digits = '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9';
/** @ignore */
type Digits = '0' | '1' | '2' | '3' | '4' | '5' | '6' | '7' | '8' | '9';
/** @ignore */
type Carryings = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1];
/** @ignore */
type Carryings = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1];
/** @ignore */
type Units = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
/** @ignore */
type Units = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9];
/** @ignore */
type DigitSums = [
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
[2, 3, 4, 5, 6, 7, 8, 9, 10, 11],
[3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
[4, 5, 6, 7, 8, 9, 10, 11, 12, 13],
[5, 6, 7, 8, 9, 10, 11, 12, 13, 14],
[6, 7, 8, 9, 10, 11, 12, 13, 14, 15],
[7, 8, 9, 10, 11, 12, 13, 14, 15, 16],
[8, 9, 10, 11, 12, 13, 14, 15, 16, 17],
[9, 10, 11, 12, 13, 14, 15, 16, 17, 18]
];
/** @ignore */
type DigitSums = [
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
[2, 3, 4, 5, 6, 7, 8, 9, 10, 11],
[3, 4, 5, 6, 7, 8, 9, 10, 11, 12],
[4, 5, 6, 7, 8, 9, 10, 11, 12, 13],
[5, 6, 7, 8, 9, 10, 11, 12, 13, 14],
[6, 7, 8, 9, 10, 11, 12, 13, 14, 15],
[7, 8, 9, 10, 11, 12, 13, 14, 15, 16],
[8, 9, 10, 11, 12, 13, 14, 15, 16, 17],
[9, 10, 11, 12, 13, 14, 15, 16, 17, 18]
];
/** @ignore */
type SplitDigits<
Num extends string | number,
A extends Digits[] = []
> = `${Num}` extends `${infer D extends Digits}${infer X}` ? SplitDigits<X, [D, ...A]> : [...A, '0'];
/** @ignore */
export type SplitDigits<
Num extends string | number,
A extends Digits[] = []
> = `${Num}` extends `${infer D extends Digits}${infer X}` ? SplitDigits<X, [D, ...A]> : [...A, '0'];
/** @ignore */
type SumDigits<A extends Digits = '0', B extends Digits = '0'> = DigitSums[A extends undefined
? '0'
: A][B extends undefined ? '0' : B];
/** @ignore */
export type SumDigits<A extends Digits = '0', B extends Digits = '0'> = DigitSums[A extends undefined
? '0'
: A][B extends undefined ? '0' : B];
/** @ignore */
type AddString<
A extends string | number,
B extends string | number,
NumA extends Digits[] = SplitDigits<A>,
NumB extends Digits[] = SplitDigits<B>,
L extends Digits[] = TupleUtils.Longest<NumA, NumB>
> = {
[Index in keyof L]: SumDigits<NumA[Parse<Index>], NumB[Parse<Index>]>;
};
/** @ignore */
export type AddString<
A extends string | number,
B extends string | number,
NumA extends Digits[] = SplitDigits<A>,
NumB extends Digits[] = SplitDigits<B>,
L extends Digits[] = Longest<NumA, NumB>
> = {
[Index in keyof L]: SumDigits<NumA[Parse<Index>], NumB[Parse<Index>]>;
};
/** @ignore */
type ToNumber<A, Result extends string = '', Carrying extends number = 0> = A extends [
infer D extends number,
...infer Rest extends number[]
]
? ToNumber<Rest, `${Units[DigitSums[Units[D]][Carrying]]}${Result}`, D extends 9 ? Carrying : Carryings[D]>
: Result;
/** @ignore */
export type ToNumber<A, Result extends string = '', Carrying extends number = 0> = A extends [
infer D extends number,
...infer Rest extends number[]
]
? ToNumber<Rest, `${Units[DigitSums[Units[D]][Carrying]]}${Result}`, D extends 9 ? Carrying : Carryings[D]>
: Result;
/** @ignore */
type Normalize<Str extends string> = Str extends `0${infer Num}` ? Normalize<Num> : Str;
/** @ignore */
export type Normalize<Str extends string> = Str extends `0${infer Num}` ? Normalize<Num> : Str;
/** @ignore */
type _Add_<A extends string | number, B extends string | number> = Parse<Normalize<ToNumber<AddString<A, B>>>>;
/** @ignore */
type _Add_<A extends string | number, B extends string | number> = Parse<Normalize<ToNumber<AddString<A, B>>>>;
/** @ignore */
type _Multiply_<
A extends string | number,
B extends string | number,
Result extends number = 0,
I extends number = 0
> = I extends Parse<A> ? Result : _Multiply_<Parse<A>, B, _Add_<Result, B>, _Add_<I, 1>>;
/** @ignore */
type _Multiply_<
A extends string | number,
B extends string | number,
Result extends number = 0,
I extends number = 0
> = I extends Parse<A> ? Result : _Multiply_<Parse<A>, B, _Add_<Result, B>, _Add_<I, 1>>;
/**
* Addition of two positive integer values represented by either a number or a string format
* @typeParam A - any positive integer number
* @typeParam B - any positive integer number
* @requires TypeScript 4.8+
* @remarks
* The operation doesn't have any noticeable limitations
* @example
* const smallValue: MathUtils.Add<3, 4> = 7;
* const bigValue: MathUtils.Add<9999999, 9999999> = 19999998;
* const stringArgs: MathUtils.Add<'1234567890', '987654321'> = 2222222211;
*/
type Add<A extends string | number, B extends string | number> = _Add_<A, B>;
/**
* Addition of two positive integer values represented by either a number or a string format
* @typeParam A - any positive integer number
* @typeParam B - any positive integer number
* @requires TypeScript 4.8+
* @remarks
* The operation doesn't have any noticeable limitations
* @example
* const smallValue: MathUtils.Add<3, 4> = 7;
* const bigValue: MathUtils.Add<9999999, 9999999> = 19999998;
* const stringArgs: MathUtils.Add<'1234567890', '987654321'> = 2222222211;
*/
export type Add<A extends string | number, B extends string | number> = _Add_<A, B>;
/**
* Multiplies two positive integer values represented by either a number or a string format
* @typeParam A - any positive integer number from 0 to 999
* @typeParam B - any positive integer number
* @requires TypeScript 4.8+
* @remarks
* The first argument can be 999 max because of a [hardcoded limit in TypeScript compiler](https://github.com/microsoft/TypeScript/pull/45711)
* @example
* const numberArgs: MathUtils.Multiply<78, 63> = 4914;
* const stringArgs: MathUtils.Multiply<'999', '999'> = 998001;
*/
type Multiply<A extends string | number, B extends string | number> = _Multiply_<A, B>;
}
/**
* Multiplies two positive integer values represented by either a number or a string format
* @typeParam A - any positive integer number from 0 to 999
* @typeParam B - any positive integer number
* @requires TypeScript 4.8+
* @remarks
* The first argument can be 999 max because of a [hardcoded limit in TypeScript compiler](https://github.com/microsoft/TypeScript/pull/45711)
* @example
* const numberArgs: MathUtils.Multiply<78, 63> = 4914;
* const stringArgs: MathUtils.Multiply<'999', '999'> = 998001;
*/
export type Multiply<A extends string | number, B extends string | number> = _Multiply_<A, B>;

@@ -1,4 +0,6 @@

/* eslint-disable @typescript-eslint/no-namespace, @typescript-eslint/no-unused-vars */
/* eslint-disable @typescript-eslint/no-namespace, import/extensions, @typescript-eslint/no-unused-vars */
// INSPIRATION: https://lihautan.com/extract-parameters-type-from-string-literal-types-with-typescript/
import { Append } from './tuple';
/**

@@ -8,72 +10,70 @@ * @requires Typescript: 4.5+

declare namespace StringUtils {
/** @ignore */
type NotEmptyString<Str> = Str extends '' ? never : Str;
/** @ignore */
type NotEmptyString<Str> = Str extends '' ? never : Str;
/**
* Removes leading white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam Spacer - any string
* @example
* const str1: StringUtils.TrimLeft<' abc'> = 'abc';
* const str2: StringUtils.TrimLeft<'*******abc', '*'> = 'abc';
*/
type TrimLeft<Str extends string, Spacer extends string = ' '> = Str extends `${Spacer}${infer Part}`
? TrimLeft<Part, Spacer>
: Str;
/**
* Removes leading white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam Spacer - any string
* @example
* const str1: StringUtils.TrimLeft<' abc'> = 'abc';
* const str2: StringUtils.TrimLeft<'*******abc', '*'> = 'abc';
*/
export type TrimLeft<Str extends string, Spacer extends string = ' '> = Str extends `${Spacer}${infer Part}`
? TrimLeft<Part, Spacer>
: Str;
/**
* Removes trailing white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam Spacer - optional string character
* @example
* const str1: StringUtils.TrimRight<'abc '> = 'abc';
* const str2: StringUtils.TrimRight<'abc*******', '*'> = 'abc';
*/
type TrimRight<Str extends string, Spacer extends string = ' '> = Str extends `${infer Part}${Spacer}`
? TrimRight<Part, Spacer>
: Str;
/**
* Removes trailing white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam Spacer - optional string character
* @example
* const str1: StringUtils.TrimRight<'abc '> = 'abc';
* const str2: StringUtils.TrimRight<'abc*******', '*'> = 'abc';
*/
export type TrimRight<Str extends string, Spacer extends string = ' '> = Str extends `${infer Part}${Spacer}`
? TrimRight<Part, Spacer>
: Str;
/**
* Removes leading and trailing white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam [Spacer] - optional string character
* @example
* const str1: StringUtils.Trim<' abc '> = 'abc';
* const str2: StringUtils.Trim<'*******abc*******', '*'> = 'abc';
*/
type Trim<Str extends string, Spacer extends string = ' '> = TrimLeft<TrimRight<Str, Spacer>, Spacer>;
/**
* Removes leading and trailing white spaces (or the specified characters) from the given string
* @typeParam Str - any string
* @typeParam [Spacer] - optional string character
* @example
* const str1: StringUtils.Trim<' abc '> = 'abc';
* const str2: StringUtils.Trim<'*******abc*******', '*'> = 'abc';
*/
export type Trim<Str extends string, Spacer extends string = ' '> = TrimLeft<TrimRight<Str, Spacer>, Spacer>;
/** @ignore */
type _Split_<
Str extends string,
Spacer extends string = '\n',
NoEmpty extends boolean = false,
A extends string[] = []
> = Str extends `${infer PartA}${Spacer}${infer PartB}`
? _Split_<Trim<PartB>, Spacer, NoEmpty, TupleUtils.Append<A, Trim<PartA>, NoEmpty>>
: TupleUtils.Append<A, Trim<Str>, NoEmpty>;
/** @ignore */
type _Split_<
Str extends string,
Spacer extends string = '\n',
NoEmpty extends boolean = false,
A extends string[] = []
> = Str extends `${infer PartA}${Spacer}${infer PartB}`
? _Split_<Trim<PartB>, Spacer, NoEmpty, Append<A, Trim<PartA>, NoEmpty>>
: Append<A, Trim<Str>, NoEmpty>;
/**
* Returns a tuple of substrings by splitting the string pattern by the given separator.
* Additionally you can filter out empty string from the resulting list by specifying the third argument as `true`
* @typeParam Str - any string
* @typeParam Separator - any string character
* @typeParam [NoEmpty] - optional flag
* @example
* const arr: StringUtils.Split<'a b c', ' '> = ['a', 'b', 'c'];
*/
type Split<Str extends string, Separator extends string, NoEmpty extends boolean = false> = _Split_<
Str,
Separator,
NoEmpty
>;
/**
* Returns a tuple of substrings by splitting the string pattern by the given separator.
* Additionally you can filter out empty string from the resulting list by specifying the third argument as `true`
* @typeParam Str - any string
* @typeParam Separator - any string character
* @typeParam [NoEmpty] - optional flag
* @example
* const arr: StringUtils.Split<'a b c', ' '> = ['a', 'b', 'c'];
*/
export type Split<Str extends string, Separator extends string, NoEmpty extends boolean = false> = _Split_<
Str,
Separator,
NoEmpty
>;
/**
* Transforms a tuple of strings into a union of string values
* @typeParam A - any string tuple
* @example
* type StringUnion = StringUtils.Unique<['a', 'a', 'b', 'c', 'c']>; // "a" | "b" | "c"
*/
type Unique<A extends string[]> = NotEmptyString<A[number]>;
}
/**
* Transforms a tuple of strings into a union of string values
* @typeParam A - any string tuple
* @example
* type StringUnion = StringUtils.Unique<['a', 'a', 'b', 'c', 'c']>; // "a" | "b" | "c"
*/
export type Unique<A extends string[]> = NotEmptyString<A[number]>;

@@ -6,37 +6,36 @@ /* eslint-disable @typescript-eslint/no-namespace, @typescript-eslint/no-unused-vars */

*/
declare namespace TupleUtils {
/**
* Returns length of the given tuple
* @typeParam A - any tuple
* @example
* const length: TupleUtils.Length<[1, 2, 3, 4, 5]> = 5;
*/
type Length<A extends unknown[]> = A extends { length: infer L } ? L : never;
/**
* Compares two tuples by their length and returns either the longest one of them
* or the first one if they are the same length
* @remarks
* All items of both tuples must be defined in order for the operation to work properly
* @typeParam A - any tuple without undefined items
* @typeParam B - any tuple without undefined items
* @example
* const longest: TupleUtils.Longest<[1], [1, 2, 3]> = [1, 2, 3];
*/
type Longest<A extends unknown[], B extends unknown[]> = B[Length<A>] extends undefined ? A : B;
/**
* Returns length of the given tuple
* @typeParam A - any tuple
* @example
* const length: TupleUtils.Length<[1, 2, 3, 4, 5]> = 5;
*/
export type Length<A extends unknown[]> = A extends { length: infer L } ? L : never;
/**
* Appends new item to the given tuple.
* Optionally you can ignore empty strings by specifying the third argument as `true`
* @typeParam A - any tuple
* @typeParam Item - any value
* @typeParam [NoEmpty] - optional flag
* @example
* const arr: TupleUtils.Append<[1, 2, 3, 4], 5> = [1, 2, 3, 4, 5];
*/
type Append<A extends unknown[], Item, NoEmpty extends boolean = false> = NoEmpty extends true
? Item extends ''
? A
: [...A, Item]
: [...A, Item];
}
/**
* Compares two tuples by their length and returns either the longest one of them
* or the first one if they are the same length
* @remarks
* All items of both tuples must be defined in order for the operation to work properly
* @typeParam A - any tuple without undefined items
* @typeParam B - any tuple without undefined items
* @example
* const longest: TupleUtils.Longest<[1], [1, 2, 3]> = [1, 2, 3];
*/
export type Longest<A extends unknown[], B extends unknown[]> = B[Length<A>] extends undefined ? A : B;
/**
* Appends new item to the given tuple.
* Optionally you can ignore empty strings by specifying the third argument as `true`
* @typeParam A - any tuple
* @typeParam Item - any value
* @typeParam [NoEmpty] - optional flag
* @example
* const arr: TupleUtils.Append<[1, 2, 3, 4], 5> = [1, 2, 3, 4, 5];
*/
export type Append<A extends unknown[], Item, NoEmpty extends boolean = false> = NoEmpty extends true
? Item extends ''
? A
: [...A, Item]
: [...A, Item];
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc