Skip to content

Commit 660fbf5

Browse files
cexbrayatalxhub
authored andcommitted
fix(migrations): migrate HttpClientModule to provideHttpClient() (#48949)
The `standalone-bootstrap` migration now migrates `HttpClientModule` imports to `provideHttpClient(withInterceptorsFromDi())` instead of `importProvidersFrom(HttpClientModule)`. The `withInterceptorsFromDi()` feature is added to make sure class-based interceptors still works if there are any in the application. Fixes #48948 PR Close #48949
1 parent 323ffc9 commit 660fbf5

File tree

2 files changed

+63
-0
lines changed

2 files changed

+63
-0
lines changed

packages/core/schematics/ng-generate/standalone-migration/standalone-bootstrap.ts

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -308,6 +308,22 @@ function migrateImportsForBootstrapCall(
308308
tracker.addImport(sourceFile, 'provideNoopAnimations', animationsImport), [], []));
309309
continue;
310310
}
311+
312+
// `HttpClientModule` can be replaced with `provideHttpClient()`.
313+
const httpClientModule = 'common/http';
314+
const httpClientImport = `@angular/${httpClientModule}`;
315+
if (isClassReferenceInAngularModule(
316+
element, 'HttpClientModule', httpClientModule, typeChecker)) {
317+
const callArgs = [
318+
// we add `withInterceptorsFromDi()` to the call to ensure that class-based interceptors
319+
// still work
320+
ts.factory.createCallExpression(
321+
tracker.addImport(sourceFile, 'withInterceptorsFromDi', httpClientImport), [], [])
322+
];
323+
providersInNewCall.push(ts.factory.createCallExpression(
324+
tracker.addImport(sourceFile, 'provideHttpClient', httpClientImport), [], callArgs));
325+
continue;
326+
}
311327
}
312328

313329
const target =

packages/core/schematics/test/standalone_migration_spec.ts

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,16 @@ describe('standalone migration', () => {
124124
}
125125
`);
126126

127+
writeFile('/node_modules/@angular/common/http/index.d.ts', `
128+
import {ModuleWithProviders} from '@angular/core';
129+
130+
export declare class HttpClientModule {
131+
static ɵfac: i0.ɵɵFactoryDeclaration<HttpClientModule, never>;
132+
static ɵmod: i0.ɵɵNgModuleDeclaration<HttpClientModule, never, never, never>;
133+
static ɵinj: i0.ɵɵInjectorDeclaration<HttpClientModule>;
134+
}
135+
`);
136+
127137
writeFile('/node_modules/@angular/core/testing/index.d.ts', `
128138
export declare class TestBed {
129139
static configureTestingModule(config: any): any;
@@ -3393,6 +3403,43 @@ describe('standalone migration', () => {
33933403
`));
33943404
});
33953405

3406+
it('should convert HttpClientModule references to provideHttpClient(withInterceptorsFromDi())',
3407+
async () => {
3408+
writeFile('main.ts', `
3409+
import {AppModule} from './app/app.module';
3410+
import {platformBrowser} from '@angular/platform-browser';
3411+
3412+
platformBrowser().bootstrapModule(AppModule).catch(e => console.error(e));
3413+
`);
3414+
3415+
writeFile('./app/app.module.ts', `
3416+
import {NgModule, Component} from '@angular/core';
3417+
import {HttpClientModule} from '@angular/common/http';
3418+
3419+
@Component({template: 'hello'})
3420+
export class AppComponent {}
3421+
3422+
@NgModule({
3423+
declarations: [AppComponent],
3424+
bootstrap: [AppComponent],
3425+
imports: [HttpClientModule]
3426+
})
3427+
export class AppModule {}
3428+
`);
3429+
3430+
await runMigration('standalone-bootstrap');
3431+
3432+
expect(stripWhitespace(tree.readContent('main.ts'))).toBe(stripWhitespace(`
3433+
import {AppComponent} from './app/app.module';
3434+
import {platformBrowser, bootstrapApplication} from '@angular/platform-browser';
3435+
import {withInterceptorsFromDi, provideHttpClient} from '@angular/common/http';
3436+
3437+
bootstrapApplication(AppComponent, {
3438+
providers: [provideHttpClient(withInterceptorsFromDi())]
3439+
}).catch(e => console.error(e));
3440+
`));
3441+
});
3442+
33963443
it('should omit standalone directives from the imports array from the importProvidersFrom call',
33973444
async () => {
33983445
writeFile('main.ts', `

0 commit comments

Comments
 (0)