12

I'm pretty sure I'll be able to solve this issue by myself but if it can help somebody else I want to share and save somebody else time.

I had to add the es6-promise library to get rid of this error

Promise only result to a type, but is only used as a value here.

when I was trying to use Promise.all (see this discussion ). It worked fine until now, I get an error when I'm trying to use a Promise from MongoDB.

Promise<whatever> is not assignable to Promise<any>
    Property 'finally' is missing in type Promise<whatever>

According to this issue on es6-promise (if I got that right), the new finally property is breaking compatibility. It's there on the Promise Mongo return but not on the one I imported from es6-promise.

Any idea?

Loic Coenen
  • 773
  • 3
  • 8
  • 19

2 Answers2

7

I'm the one who noted that the finally shim was breaking Promise compatibility on that linked issue. Nice to see this getting some attention. Here are some options:

1. Rely purely on the TypeScript core library's typings

tsconfig.json

{
    "compilerOptions": {
        "lib": ["DOM","ES5","ScriptHost", "es2018.promise"]
    }
}

Install the shim, run the polyfill once at the start of your app, and from then on use the global Promise object rather than continuing to import the Promise class from es6-promise. I've found this to be the most inter-operable way.

npm install --save es6-promise@latest

Note that es6-promise has, for the last few releases, been bundling its own typings that conflict with the typings of TypeScript's built-in Promise libs.

2. Use an older version of es6-promise that doesn't include the finally shim

Note: Of course this means that you can't use finally

{
    "compilerOptions": {
        "lib": ["DOM","ES5","ScriptHost"]
    }
}

Install the last version of es6-promise before they introduced finally, and use those typings:

npm install --save es6-promise@4.2.2 && npm install --save-dev @types/es6-promise@0.0.32

(Or otherwise omit those typings and add es2015.promise to your compilerOptions.lib array in tsconfig.json.)

Jamie Birch
  • 5,839
  • 1
  • 46
  • 60
  • Note for other people coming here: you can encounter a very similar error when you're treating a resolved promise value as a promise. This can trip people up when you're dealing with nested promises. – Barbarrosa Nov 16 '19 at 00:00
  • @Barbarrosa I think I might be encountering the problem you describe...any pointers on how to fix it? – Max Waterman Jul 14 '20 at 06:41
  • @MaxWaterman I'm not sure about your particular situation, but generally you'd need to update the typings to reflect the non-promise value and correct accessors to avoid using properties that don't exist on the non-promise type. – Barbarrosa Apr 24 '21 at 07:36
1

If all you need is a correct type definition for a Promise then you can just use the built-in definitions that come with typescript (I say this because you note that the promise you are actually working with has the finally method as expected).

To do this, remove es6-promise form you project and in tsconfig change your lib to:

{
    ....
    "lib": ["es5","es2015.promise","dom", "scripthost"] 
    ....
} 
Titian Cernicova-Dragomir
  • 230,986
  • 31
  • 415
  • 357
  • I am using typescript 2.7.2 and want to use finally in my promises. this solved it.. but what are you setting in target and module? and is there any way to update this to 2018 with my version? – Fraga Nov 02 '20 at 18:32