Using TypeScript will result in errors when attempting to use the Promise object and the Awaited keyword

In this example, I am trying to ensure that the function foo does not accept a Promise as an argument, but any other type should be acceptable.

export {}

function foo<T>(arg: T extends Promise<unknown> ? never : T) {
  console.log(arg);
}

async function bar<T>(arg: Promise<T>) {
  foo(await arg); // Why is this causing an error?
}

async function baz(arg: Promise<number>) {
  foo(await arg); // This works fine!
}

foo(await Promise.resolve(1)); // No issues here

foo(1); // All good

foo(Promise.resolve(1)); // This should give an error, as expected

When looking at the error in the bar function:

Argument of type 'Awaited<T>' is not assignable
to parameter of type 'T extends Promise<unknown> ? never : T'.

What exactly sets apart T from Awaited<T>?

Is there a solution to make this work correctly, especially when utilizing await with generics?

Answer №1

When the type T extends Promise<unknown>, it implies that the argument must be of type never. However, if we are unaware of the actual type of T within the function bar, ensuring the correctness of the type passed to foo becomes uncertain.

In essence, it is plausible to provide a parameter of type

Promise<Promise<any>>
to bar, wherein technically T would represent a Promise.

Nonetheless, since await handles resolving nested promises, post-await operation confirms that the resolved value cannot be a Promise. Regrettably, the Typescript compiler fails to recognize this fact.

Hence, it is feasible to establish a generic type for this argument and securely cast it after await.

type NotPromise<T> = T extends Promise<unknown> ? never: T;

function foo<T>(arg: NotPromise<T>) {
  console.log(arg);
}

async function bar<T>(arg: Promise<T>) {
  foo((await arg) as NotPromise<T>);
}

For a functional demonstration, visit: https://stackblitz.com/edit/typescript-h2izuv?file=index.ts

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

What is the best way to insert CSS code into a custom Vue directive file?

I need a solution that applies a gradient background to the parent div in case an image fails to load. I've attempted to create a directive for this purpose: export default { bind(el: any, binding: any) { try { ..... ...

Encountering issues with React Nextjs - unable to utilize useState hook or

Hi everyone, I'm new to React and I think I might have overlooked something. I've been trying to create a simple registration form, but it seems like I'm having trouble changing the state. ` import {useState} from 'react' export ...

The never-ending scroll feature in Vue.js

For the component of cards in my project, I am trying to implement infinite scrolling with 3 cards per row. Upon reaching the end of the page, I intend to make an API call for the next page and display the subsequent set of cards. Below is my implementatio ...

Encountering a Typescript error with Next-Auth providers

I've been struggling to integrate Next-Auth with Typescript and an OAuth provider like Auth0. Despite following the documentation, I encountered a problem that persists even after watching numerous tutorials and mimicking their steps verbatim. Below i ...

How can I display JSON values without revealing the parent in Angular 5 and Ionic 3?

I am trying to extract values from JSON without the parent keys. Here is the JSON structure I have: [ { "companies": [{ "id": 1, "name": "Prueba", "company_number": "23423423A", "latitude": 241241.12, "lo ...

Who is the intended audience for the "engines" field in an npm package - consumers or developers?

As the creator of an npm library, I have included the current LTS versions of Node.js and npm in the package manifest under the engines field. This ensures that all contributors use the same versions I utilized for development: Node.js <a href="/cdn-cgi ...

How to delete an item from an object in TypeScript

Can you help with filtering an object in Angular or TypeScript to eliminate objects with empty values, such as removing objects where annualRent === null? Additionally, what method can we use to round a number like 2.833333333333335 to 2.83 and remove the ...

Handlebar files are not compatible with Typescript loading capabilities

I am encountering an issue with my directory structure as follows : src |- server |- myServer.ts |- views |- myView.hbs dist |- server |- myServer.js The problem lies in the fact that the dist folder does not have a views subfolder, where the J ...

Incorporate a JavaScript array into a TypeScript document

Having a file named array.js with a large collection of strings, structured like this: module.exports = ["word1","word2",...] I attempted to utilize this array in my validation.ts file by adding the following line: let wiki = require('./array.js&a ...

Difficulty encountered when trying to apply a decorator within a permission guard

I'm a newcomer to Nestjs and I am currently working on implementing Authorization using Casl. To achieve this, I have created a custom decorator as shown below: import { SetMetadata } from '@nestjs/common'; export const Permission = (acti ...

The test.ts file does not contain any type definitions

While I am able to successfully utilize my types in .ts files, I am facing difficulties in understanding why it's failing in .test.ts files, even though both files are located in the same folder. Check out the code in the .ts file below: https://i.s ...

Tips on utilizing index and eliminating React Warning: Ensure every child within a list has a distinct "key" prop

Hello, I am encountering an issue where I need to properly pass the index in this component. Can you help me figure out how to do that? Error: react-jsx-dev-runtime.development.js:117 Warning: Each child in a list should have a unique "key" prop ...

What is causing the Typescript compiler to interpret an element in a string array as the type 'never'?

My Typescript function compiled without issue in version 3.5.3, but after updating to 3.8.3, it now throws a confusing error during compilation. import { isNumber, toInteger, padNumber } from './math'; parse(value: string): NgbDateStruct { if ...

Stop redux useSelector from causing unnecessary re-renders

I'm working on a component in React-Redux that utilizes the useSelector hook to retrieve a dictionary from the Redux store. This dictionary maps UUIDs to objects containing data that I need to display. interface IComponentProps { id: string } const ...

Creating a Higher Order Component (HOC) for your Next.js page

Upon running the following code, I encountered an error message Error: The default export is not a React Component in page: "/" pages/index.tsx import React, { useState, useRef } from "react"; import type { NextPage } from "next&q ...

Developing a TypeScript NodeJS module

I've been working on creating a Node module using TypeScript, and here is my progress so far: MysqlMapper.ts export class MysqlMapper{ private _config: Mysql.IConnectionConfig; private openConnection(): Mysql.IConnection{ ... } ...

Sticky header in React data grid

Is there a way to implement a sticky header for a data grid in react? I have tried various methods but haven't been able to figure it out. Any suggestions would be appreciated. You can find my code sandbox example here. #react code export const Styl ...

Having difficulty implementing dynamic contentEditable for inline editing in Angular 2+

Here I am facing an issue. Below is my JSON data: data = [{ 'id':1,'name': 'mr.x', },{ 'id':2,'name': 'mr.y', },{ 'id':3,'name': 'mr.z', },{ & ...

What is the best way to verify that all elements within an object are 'false' except for one that is 'true'?

I am working with an object that has multiple boolean fields: type SomeObject = { A: boolean B: boolean C: boolean .... } Is there a simple and efficient method to determine if all other fields (except for a specified one) are set to false? We co ...

Is there something I'm missing? The action buttons cannot be displayed on a preview of the event

Currently in the process of developing an angular application featuring a calendar component to showcase events, I opted to utilize angular-calendar for the visual representation. While exploring the month view functionality, I encountered an issue where t ...