Skip to content

Upgraded Typescript to 3.7.x #720

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

Merged
merged 3 commits into from
Dec 10, 2019
Merged

Upgraded Typescript to 3.7.x #720

merged 3 commits into from
Dec 10, 2019

Conversation

hiranya911
Copy link
Contributor

New TS compiler flagged a semantic error in api-request.ts which I have fixed here.

@@ -933,7 +933,7 @@ export class ExponentialBackoffPoller extends EventEmitter {
* callback when polling is complete.
*/
public poll(callback: () => Promise<object>): Promise<object> {
if (this.pollCallback) {
if (typeof this.pollCallback !== 'undefined') {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What was the ts error?
Can you just do if(this.pollCallback !== undefined)? typeof isn't necessary here.

Copy link
Contributor Author

@hiranya911 hiranya911 Dec 10, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The error was:

src/utils/api-request.ts(936,9): error TS2774: This condition will always return true since the function is always defined. Did you mean to call it instead?
TypeScript: 1 semantic error

And made the suggested change.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it true that the function is always defined? Does the error get fixed if line 915 is changed to private pollCallback: () => Promise<object> = null;?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That requires more code changes. We need to declare the type as (() => Promise<object>) | null to be able to assign null. When we do that we get another compiler error from the repoll() method saying Cannot invoke an object which is possibly 'null'.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think using if(this.pollCallback !== undefined) while keeping the type the same is just avoiding the compiler error without fixing the underlying issue. We should probably either make that (() => Promise<object>) | null type change, or introduce a separate boolean like this:

private started = false;

public poll(callback: () => Promise<object>): Promise<object> {
  if (this.started) {
    throw ...
  }
  this.started = true;
  ...
}

Copy link
Member

@Feiyang1 Feiyang1 Dec 10, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I see. How about we type it (() => Promise<object>) | null to reflect the accurate typing, so no change here. But in repoll(), we do

// we only call repoll() in poll() after this.pollCallback is assigned.
this.pollCallback!().then(...)

Copy link
Contributor Author

@hiranya911 hiranya911 Dec 10, 2019

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But is there an underlying issue (if so what?), or is it just a false positive from the new TS version?

EDIT: As far as I can see TS incorrectly thinks pollCallback is a statically-defined function because it has a function type, whereas it is really just a variable.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Was going through the test cases in microsoft/TypeScript@006a327#diff-27ba0012946727ed197bf4c5dc9f9194

Looks like the correct solution is to declare this variable as pollCallback?.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The underlying issue is that pollCallback's type is telling TS that it can't be null. I'm somewhat surprised that we're not getting an error for giving it that type and not setting it when it's defined or in the constructor. Does TS assume that any variable can be undefined even if it's not specified in its type?

+1 to @Feiyang1's suggestion. I think that's more correct than using a separate bool. And using ? instead of | null is slightly better IMO.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@hiranya911 yep, sounds good.

@nbegley nbegley assigned hiranya911 and unassigned nbegley Dec 10, 2019
@hiranya911 hiranya911 assigned nbegley and unassigned hiranya911 Dec 10, 2019
@nbegley nbegley assigned hiranya911 and unassigned nbegley Dec 10, 2019
@hiranya911 hiranya911 assigned nbegley and unassigned hiranya911 Dec 10, 2019
@nbegley nbegley assigned hiranya911 and unassigned nbegley Dec 10, 2019
@hiranya911 hiranya911 merged commit bba61e1 into master Dec 10, 2019
@hiranya911 hiranya911 deleted the hkj-ts-37 branch December 10, 2019 19:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants