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

Huge performance regression with tsc #28231

Closed
Pauan opened this issue Oct 30, 2018 · 5 comments
Closed

Huge performance regression with tsc #28231

Pauan opened this issue Oct 30, 2018 · 5 comments
Assignees
Labels
Domain: Performance Reports of unusually slow behavior Needs Investigation This issue needs a team member to investigate its status.

Comments

@Pauan
Copy link

Pauan commented Oct 30, 2018

TypeScript Version: 3.2.0-dev.20181030

Search Terms: slow performance

Code

I am speaking on behalf of AmCharts.

We have a large TypeScript library (which we sell to our customers). We tried to add in TypeScript 3.0 support to our library, but doing so caused massive slowdown issues. This is preventing our customers from using our library with TypeScript 3.0.

I have created two self-contained repos:

https://github.com/Pauan/amcharts4-typescript-example-fast
https://github.com/Pauan/amcharts4-typescript-example-slow

You can build them by using yarn install and then yarn build.

The fast repo is using typescript@2.8.1, the slow repo is using typescript@next.

The fast repo builds in ~11 seconds. The slow repo builds in ~81 seconds!

Here is a diff between the two repos:

diff -r '--exclude=node_modules' '--exclude=.git' '--exclude=dist' amcharts4-typescript-example-fast/package.json amcharts4-typescript-example-slow/package.json
6c6
<     "typescript": "2.8.1",
---
>     "typescript": "next",
diff -r '--exclude=node_modules' '--exclude=.git' '--exclude=dist' amcharts4-typescript-example-fast/src/.internal/charts/types/TreeMap.ts amcharts4-typescript-example-slow/src/.internal/charts/types/TreeMap.ts
610c610
<               let xAxis = this.xAxes.push(new ValueAxis());
---
>               let xAxis = this.xAxes.push(new ValueAxis<this["_xAxisRendererType"]>());
625c625
<               let yAxis = this.yAxes.push(new ValueAxis());
---
>               let yAxis = this.yAxes.push(new ValueAxis<this["_yAxisRendererType"]>());
diff -r '--exclude=node_modules' '--exclude=.git' '--exclude=dist' amcharts4-typescript-example-fast/yarn.lock amcharts4-typescript-example-slow/yarn.lock
846,848c846,848
< typescript@2.8.1:
<   version "2.8.1"
<   resolved "http://registry.npmjs.org/typescript/-/typescript-2.8.1.tgz#6160e4f8f195d5ba81d4876f9c0cc1fbc0820624"
---
> typescript@next:
>   version "3.2.0-dev.20181030"
>   resolved "https://registry.yarnpkg.com/typescript/-/typescript-3.2.0-dev.20181030.tgz#a80e3377101224aad5e1e3a341f320b5a9b9b1ef"

As you can see, aside from the tsc version change, only one very small code change was made (because it was required by typescript@next).

Expected behavior:

Compilation should be the same speed or faster.

Actual behavior:

Compilation is much slower.

Playground Link:
N/A

Related Issues:
#28025

@weswigham weswigham added Needs Investigation This issue needs a team member to investigate its status. Domain: Performance Reports of unusually slow behavior labels Oct 30, 2018
@weswigham
Copy link
Member

For content: In 2.8.1, we manufacture 61910 types (246955 symbols). In master, we manufacture 322305 types (1050759 symbols). That's 5.2x the types, and 4.2x the symbols; so we're certainly making more work for ourselves, given the same code. I'm still working out why, though

@weswigham
Copy link
Member

Something to do with how we're resolving the getX or getY calls in RadarColumnSeries, it seems like. Definitely triggered by the body of the validateDataElementReal method in some way (if you delete it, compile time goes all the way back down).

@weswigham
Copy link
Member

weswigham commented Oct 30, 2018

Yeah, the indexed this type in the parameter is causing us to perform an explosion of work when comparing signatures for some reason. If you make the signature

	public validateDataElementReal(dataItem: RadarColumnSeriesDataItem): void

instead of

	public validateDataElementReal(dataItem: this["_dataItem"]): void;

compile time also goes all the way back down. Still looking into why, but there's a workaround.

@weswigham
Copy link
Member

Looks like during comparison checking we don't appropriately share work when comparing type references instantiated with different this types. this["_dataItem"] becomes RadarColumnSeriesDataItem with a this of this["_dataItem"], which we then compare structurally against XYSeriesDataItem. We get a field _component of each, which on the this-instantiated source apparently becomes this["_dataItem"]["_component"] and of the second, a real type... we then against instantiate this and proceed like this to the fringes of the entire structure of types in the program, effectively instantiating every type on the source side of the relation with every path through which it could be reached (and checking that, yes, they are in fact still structurally assignable)! In effect, this types are disabling all cacheing.

@Pauan
Copy link
Author

Pauan commented Nov 2, 2018

I have confirmed that 3.2.0-dev.20181102 fixes the performance issue. Thanks a lot!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Domain: Performance Reports of unusually slow behavior Needs Investigation This issue needs a team member to investigate its status.
Projects
None yet
Development

No branches or pull requests

2 participants