In TypeScript, values other than numbers or strings can be accepted as parameters, even when the expected type is a

The issue I am encountering with TypeScript is quite perplexing, especially since I am new to this language and framework. Coming from a Java background, I have never faced such a problem before and it's presenting challenges in my bug-fixing efforts with TypeScript / NestJS.

It appears that there may be a lack of type safety in TypeScript, which raises questions about whether it functions as intended or if there is a specific reason for this behavior. Below is a simplified example to demonstrate the issue:

  async findAll(@Query() query, @Res() res: Response) {
      ... lines omitted ...
      this.cache.getProxyCache(query.page, query.page_size);
      ... lines omitted ...
  }

The query object obtained from the @Query decorator in a NestJS controller is causing confusion.

  async getProxyCache(page: number = 0, pageSize: number): Promise<AxwayProxy[]> {
    console.log(`page: ${page} typeof: ${typeof page}`);
    console.log(`pageSize: ${pageSize} typeof: ${typeof pageSize}`);

    let pageSizeAdded = pageSize + 3;
    console.log(`pageSizeAdded: ${pageSizeAdded} typeof: ${typeof pageSizeAdded}`);

    let pageSizeAdded2 = Number(pageSize) + 3;
    console.log(`pageSizeAdded2: ${pageSizeAdded2} typeof: ${typeof pageSizeAdded2}`);
    ... lines omitted ...

The output reveals a discrepancy, particularly in the value of pageSizeAdded, which is incorrect. On the other hand, pageSizeAdded2 is calculated accurately after converting the data type from string to number:

page: 1 typeof: string
pageSize: 4 typeof: string
pageSizeAdded: 43 typeof: string
pageSizeAdded2: 7 typeof: number

I find it puzzling that both page and pageSize are being treated as strings even though they are declared as numbers in the function parameters.

While TypeScript displays an error message when attempting to directly call the function with string values (e.g.,

this.cache.getProxyCache('1', '2');
), it seems to accept non-number values when passed from another object.

Has anyone else encountered this issue? Is it a known limitation or a bug? Why is this behavior permitted?

Thank you, Christoph

Answer №1

It is important to note that TypeScript will be converted into JavaScript before it is executed. This means that all the typing information will be removed. When you define a function like

async getProxyCache(page: number = 0, pageSize: number): Promise<AxwayProxy[]>

You are essentially asking TypeScript to verify that the parameters and return type are correct. However, this verification only happens during transpilation (and in development with a good IDE). At runtime, the types are no longer enforced, allowing you to pass any value without any checks or casting. The resulting code in pure JavaScript will look like this:

async getProxyCache(page = 0, pageSize)

If you are wondering why TypeScript allows you to call the function with values that are not numbers, consider checking the type of page where the function is being called. If it is declared as any, then it is compatible with any type. In this scenario, it might be better to declare it as unknown instead, which would require explicit type-checking before usage.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Angular template driven forms fail to bind to model data

In an attempt to connect the model in angular template-driven forms, I have created a model class and utilized it to fill the input field. HTML: <div class="form-group col-md-2 col-12" [class.text-danger]="nameCode.invalid && nameCode.touched ...

Accessing the currently operating WS server instance with NodeJS

After successfully setting up a basic REST API using NodeJS, ExpressJS, and routing-controllers, I also managed to configure a WebSocket server alongside the REST API by implementing WS. const app = express(); app.use(bodyParser.json({limit: "50mb"})); a ...

Guide to loading a minified file in Angular 2 with Gulp Uglify for TypeScript Bundled File minimization

In my Angular 2 application, I have set the TypeScript compiler options to generate a single outFile named Scripts1.js along with Scripts1.js.map. Within my index.html file: <script src="Scripts/Script1.js"></script> <script> ...

`How can we efficiently transfer style props to child components?`

Is there a way to pass Props in the Style so that each component has a unique background image? Take a look at this component: countries.astro --- import type { Props } from 'astro'; const { country, description } = Astro.props as Props; --- & ...

How can we update a boolean value in an Angular service using a set function?

Hey there! I'm currently working on updating a boolean value in my service when a button is clicked within my component. My goal is to trigger the setfunction and toggle the boolean value from true to false, and vice versa when the button is clicked a ...

Tips for utilizing jest.mock following the removal of @types/jest (^jest@24)

After upgrading from version 7 to version 8 of @angular-builders/jest, I followed the instructions provided in the migration guide which advised removing @types/jest since it now comes bundled with Jest v24. Additionally, changes were made to my tsconfig a ...

What is the best way to implement persistStore in Redux-Toolkit?

Here is my setup: import AsyncStorage from '@react-native-async-storage/async-storage' import { persistStore, persistReducer } from 'redux-persist'; import { configureStore } from "@reduxjs/toolkit"; import { searchReducer } f ...

Child component in Angular2 makes an observer call to its parent object

Let me try to explain this in the best way possible. I have a service that includes an observable class responsible for updating itself. This observable class needs to be pushed out to the app using the observer within the service. How can I trigger that ...

Tips on enlarging the header size in ion-action-sheet within the VueJS framework of Ionic

Recently I started using Vue along with the ionic framework. This is a snippet of code from my application: <ion-action-sheet :is-open="isActionSheetOpen" header="Choose Payment" mode="ios" :buttons="buttons&qu ...

Leveraging Global Variables for Validation in Angular (Angular 10)

I am currently creating a form in Angular 10 which involves the use of validators. Specifically, I have been utilizing the Validators.min() method within my form... Instead of manually inputting the value '100' in the Validators.min('100&ap ...

Share a callback function with child components via props

My child container defines Ownprops like this: export interface OwnProps { prop1: string; prop2: "callback function" } I want to pass a callback function from the parent to this child in order to trigger a parent function from the child. However ...

"Error encountered: Array is undefined when using the map and subscribe functions in Ionic

I have developed a service that is supposed to retrieve data from a JSON file and assign it to an array called 'countries', which will be used throughout the application on multiple pages. However, when I call the method getCountries, the countri ...

In TypeScript, what specific term denotes a type of data?

Given the following code snippet: class Foo { } interface TypeProvider() { type(): ?; } class Bar implements TypeProvider { type(): ? { return (Foo); } } class Baz implements TypeProvider { type(): ? { return (Bar); ...

How can I customize a Vue component slot in Storybook 8.0.6 using Vue 3.4 and Typescript to display various subcomponents within a story?

Incorporating a variety of sub-components into my Vue 3 component based on context is proving to be a challenge. Utilizing slots seems to be the solution in Vue 3, but I'm struggling to make it work within Storybook 8, which I'm using to showcase ...

Using Mongoose $addToSet to add items to an array only if they are unique

Currently, my code is set up to add new flagDtos using $addToSet without consideration for the uniqueness of item.name. However, I want to change this behavior so that: If item.name is unique, add the new flagDtos object. Otherwise, update the existing fl ...

Validator in Angular FormControl ensures that two fields have the same value or both are empty

When filling out a form with four fields, I have encountered a specific requirement. Two of the fields are mandatory, which is straightforward. However, the other two must either both be empty or both have a value - essentially resembling an XNOR logic sta ...

Create a custom definition for the useSelector function within a separate TypeScript file in a React

Question: Is it possible to define a type like <TRootState, string> in an external file and use it directly inside multiple Component files? External file: export type TUser = <TRootState, string> // This method does not work Component's ...

Tips on preventing the copying of .txt and .xml files with the fs-extra.copySync function

Currently, I am working on a small TypeScript assignment and facing an issue that I can't seem to solve. Any guidance or advice on the problem mentioned below would be greatly appreciated. The task at hand involves copying a directory from one locati ...

Unable to locate module, encountered a webpack alias issue while using typescript and react

I'm currently in the process of setting up aliases in webpack. My goal is to make importing components in App.js easier by replacing: ./components/layout/Header/Header with: @components/layout/Header/Header This way, I can avoid potential issues w ...

I'm currently working on building a fresh window with Tauri 1.2, combining the powers of Rust, React, and Typescript. However, I've encountered a few

Utilizing Tauri's WindowBuilder in Rust, I attempted to create a new window. Despite successfully generating a blank window, I encountered challenges: The inability to display any content on the window The failure to close the window Being relativel ...