Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Constructor parameters of BigInt which is lost BigInt, String, Boolean, Number type #57283

Closed
NWYLZW opened this issue Feb 4, 2024 · 2 comments
Labels
Working as Intended The behavior described is the intended behavior; this is not a bug

Comments

@NWYLZW
Copy link

NWYLZW commented Feb 4, 2024

⚙ Compilation target

ES2020

⚙ Library

TypeScript

Missing / Incorrect Definition

interface BigIntConstructor {
    // wrong
    (value: bigint | boolean | number | string): bigint;
    // right
    (value: bigint | BigInt | boolean | Boolean | number | Number | string | String): bigint;
}

Sample Code

declare const n: unknown

if (n instanceof BigInt) {
  BigInt(n)
  //     ^? TS2345: Argument of type BigInt is not assignable to parameter of type string | number | bigint | boolean
}

// ----

function foo(a: BigInt) {
  BigInt(a)
  //     ^? TS2345: Argument of type BigInt is not assignable to parameter of type string | number | bigint | boolean
}
foo(Object(BigInt(1)))

Documentation Link

We can see in 21.2.1.1 BigInt ( value ) that 2. Let prim be ? ToPrimitive(value, NUMBER). corresponds to our situation and triggers ToPrimitive.
ToPrimitive attempts to retrieve the valueOf method of the Object. For BigInt, Number, String, and Boolean, this method exists, allowing us to obtain a corresponding primitive value. Then, based on the preferredType of NUMBER, it is further converted to a number.
Our problem is essentially answered here, indicating that we should support Boxed Types as input.

image

about

@MartinJohns
Copy link
Contributor

MartinJohns commented Feb 4, 2024

This is intentional. The usage of these wrapper objects is discouraged. This is the same as #54059.

Also see the handbook: https://www.typescriptlang.org/docs/handbook/declaration-files/do-s-and-don-ts.html#number-string-boolean-symbol-and-object

Don’t ever use the types Number, String, Boolean, Symbol, or Object These types refer to non-primitive boxed objects that are almost never used appropriately in JavaScript code.

You also shouldn't use instanceof BigInt, as this check will actually fail with primitive bigints: 5n instanceof BigInt // false.

It seems you actually want #2361.

@NWYLZW
Copy link
Author

NWYLZW commented Feb 4, 2024

  1. I understand that TypeScript does not encourage the use of boxed types. However, as a runtime data validation module, I cannot guarantee whether the data received by the user at runtime has been boxed or not.

  2. I am aware that instanceof cannot handle checks for primitive, so I have implemented an unboxing process.

https://github.com/typp-js/typp/blob/cd94af21d2c0bb9a73026df0e634e845841719e4/packages/validator/src/index.ts#L349-L353

@RyanCavanaugh RyanCavanaugh added the Working as Intended The behavior described is the intended behavior; this is not a bug label Feb 5, 2024
@NWYLZW NWYLZW closed this as not planned Won't fix, can't repro, duplicate, stale Feb 7, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Working as Intended The behavior described is the intended behavior; this is not a bug
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants