-
Notifications
You must be signed in to change notification settings - Fork 27k
Description
Variables are generated in the pipeline by inserting references to all the symbols within the scope and then later cleaning up the unused ones in an optimization pass. When generating the scope for listener instructions, we expose all the @let declarations in the same view (see) which leads us to generate ɵɵrestoreView and ɵɵresetView calls, however if the @let reference isn't used within the listener, the variable optimization phase only removes the variable that reads it and not the ɵɵrestoreView/ɵɵresetView calls.
For example, if we take the following template:
@let unused = 1;
<button (click)="noop()"></button>It produces the following code before optimization:
if (rf & 1) {
const _r1 = ɵɵgetCurrentView();
ɵɵdeclareLet(0);
ɵɵdomElementStart(1, "button", 0);
ɵɵdomListener(
"click",
function TestComp_Template_button_click_1_listener() {
const ctx_r1 = ɵɵrestoreView(_r1);
const unused_r3 = ɵɵreadContextLet(0);
return ɵɵresetView(ctx.noop());
}
);
ɵɵdomElementEnd();
}
if (rf & 2) {
const unused_r4 = ɵɵstoreLet(1);
}Which becomes the following after optimization:
if (rf & 1) {
const _r1 = ɵɵgetCurrentView();
ɵɵdomElementStart(0, "button", 0);
ɵɵdomListener(
"click",
function TestComp_Template_button_click_0_listener() {
ɵɵrestoreView(_r1);
return ɵɵresetView(ctx.noop());
}
);
ɵɵdomElementEnd();
}
if (rf & 2) {
1;
}The ɵɵrestoreView and ɵɵresetView calls aren't necessary and should be removed, because there aren't any reads of the unused @let.