nested injector on provider `multi: true` doesn't continue searching parents when injector returns something

This issue has been tracked since 2022-09-16.

Which @angular/* package(s) are the source of the bug?

core

Is this a regression?

I don't know, but version 14.0.0, 14.1.0 and 14.2.2 all have the same issue.

Description

version: @angular/[email protected]

Code:

const injector1 = Injector.create([{provide: 'foo', useValue: 'bar 1', multi: true}]);
const injector2 = Injector.create([{provide: 'foo', useValue: 'bar 2', multi: true}], injector1);

// actual:   [ 'bar 2' ]
// expected: [ 'bar 2', 'bar 1' ]
console.log('injector2', injector2.get('foo'));

Reproduction: https://stackblitz.com/edit/angular-ivy-vdqqgr?file=src%2Fapp%2Fapp.component.ts

--

I stumbled on this bug as I couldn't provide an BEFORE_APP_SERIALIZED provider on ssr anymore when upgrading from angular 14.1.0 to angular 14.2.2:

platformServer([{
    provide: BEFORE_APP_SERIALIZED,
    useFactory: () => { /* ... do something ... */ },
    multi: true,
});

Because the ServerModule also provides a BEFORE_APP_SERIALIZED, and the dependency injector stops searching for my custom root level provider after it found the one in the ServerModule. Maybe this behavior of Injector was always there. But this commit a0b2d36 made it a problem for me specifically.

JoostK wrote this answer on 2022-09-16

This is expected behavior and working as designed. Multi providers are not merged across injectors, and there are certainly cases where the current behavior is desired.

There was a feature request in #43304 to support this, but it is already possible to achieve merging behavior if needed using the current DI system.

JoostK wrote this answer on 2022-09-16

About the BEFORE_APP_SERIALIZED scenario: it's unclear to me what the exact setup is in that case, so I can't judge what is going on there (and how it was affected from 14.1 to 14.2.2)

sod wrote this answer on 2022-09-16

@JoostK my uneducated guess is that the refactor in a0b2d36 caused the issue for me.

sod wrote this answer on 2022-09-16

I workaround this issue, so a fix is not urgent. But having this as expected behavior wants me to never use multi: true ever again and purge it from our code to not have this potential footgun.

More Details About Repo
Owner Name angular
Repo Name angular
Full Name angular/angular
Language TypeScript
Created Date 2014-09-18
Updated Date 2022-10-05
Star Count 84147
Watcher Count 3063
Fork Count 22247
Issue Count 1201

YOU MAY BE INTERESTED

Issue Title Created Date Updated Date