I am using the following dependencies:
package.json:
{
"name": "myApp",
"version": "0.0.0",
"license": "MIT",
"scripts": {
"ng": "ng",
"start": "ng serve --base-href /myapp/",
"build": "ng build",
"build-stage": "ng build --environment=stage --aot --prod --vendor-chunk=false --common-chunk=false",
"build-prod": "ng build --environment=prod --aot --prod --vendor-chunk=false --common-chunk=false",
"test": "ng test",
"lint": "ng lint",
"e2e": "ng e2e"
},
"private": true,
"dependencies": {
"@angular/animations": "^4.2.4",
"@angular/common": "^4.2.4",
"@angular/compiler": "^4.2.4",
"@angular/core": "^4.2.4",
"@angular/forms": "^4.2.4",
"@angular/http": "^4.2.4",
"@angular/platform-browser": "^4.2.4",
"@angular/platform-browser-dynamic": "^4.2.4",
"@angular/router": "^4.2.4",
"@ngx-translate/core": "^7.2.2",
"@ngx-translate/http-loader": "^1.1.0",
"bootstrap": "^3.3.7",
"core-js": "^2.4.1",
"jquery": "^3.2.1",
"qrcode": "^1.0.0",
"rxjs": "^5.4.2",
"zone.js": "^0.8.14"
},
"devDependencies": {
"@angular/cli": "1.4.2",
"@angular/compiler-cli": "^4.2.4",
"@angular/language-service": "^4.2.4",
"@types/jasmine": "~2.5.53",
"@types/jasminewd2": "~2.0.2",
"@types/node": "~6.0.60",
"codelyzer": "~3.1.1",
"jasmine-core": "~2.6.2",
"jasmine-spec-reporter": "~4.1.0",
"karma": "~1.7.0",
"karma-chrome-launcher": "~2.1.1",
"karma-cli": "~1.0.1",
"karma-coverage-istanbul-reporter": "^1.2.1",
"karma-jasmine": "~1.1.0",
"karma-jasmine-html-reporter": "^0.2.2",
"protractor": "~5.1.2",
"ts-node": "~3.2.0",
"tslint": "~5.3.2",
"typescript": "~2.3.3"
}
}
cross-domain.service.ts:
import { Injectable, NgZone } from '@angular/core';
import { Subject } from 'rxjs/Subject';
import { BehaviorSubject } from 'rxjs/BehaviorSubject';
import { environment } from '../../environments/environment';
import { ArticlePreview } from './article.model';
import { TranslateService } from '@ngx-translate/core';
@Injectable()
export class CrossDomainService {
globalSelectors = new Subject<GlobalSelectors>();
globalLanguage = new BehaviorSubject<string>('en');
initialArticlePath: string;
initialGlobalSelectors: GlobalSelectors;
private socket;
constructor(private zone: NgZone,private translateService: TranslateService) {
translateService.setDefaultLang('en');
}
public init() {
if (this.inIframe) {
const self = this;
this.socket = new window['easyXDM'].Socket({
onMessage(_response) {
try {
const response = JSON.parse(_response);
self.zone.run(() => {
switch (response.type) {
case 'tileActionQuery': {
if (response.data.action && response.data.action === 'goToArticle') {
self.initialArticlePath = response.data.path;
}
break;
}
case 'setGlobalSelectors': {
self.initialGlobalSelectors = response.data;
self.globalSelectors.next(response.data);
break;
}
case 'tileInfo': {
self.globalLanguage.next(response.data.tileLanguage);
self.translateService.use(response.data.tileLanguage);
break;
}
}
});
} catch (e) {}
},
remote: environment.dashboardSiteUrl
});
}
}
private get inIframe () {
try {
return window.self !== window.top;
} catch (e) {
return true;
}
}
}
export interface GlobalSelectors {
client?: any[];
jurisdiction?: any[];
process?: any[];
year?: any[];
}
app.module.ts:
import { BrowserModule } from '@angular/platform-browser';
import { NgModule, APP_INITIALIZER } from '@angular/core';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { AnalyticsService, CoreModule, CrossDomainService } from './core';
import { TileModule } from './tile/tile.module';
@NgModule({
declarations: [AppComponent],
imports: [
BrowserModule,
AppRoutingModule,
TileModule,
CoreModule
],
providers: [
{
provide: APP_INITIALIZER,
useFactory: onModuleInit,
multi: true,
deps: [CrossDomainService, AnalyticsService]
}
],
bootstrap: [AppComponent]
})
export class AppModule {}
export function onModuleInit(crossDomainService: CrossDomainService, analyticsService: AnalyticsService) {
return () => {
crossDomainService.init();
analyticsService.init();
return new Promise((resolve) => resolve(true));
};
}
core.module.ts:
import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';
import { HTTP_INTERCEPTORS, HttpClientModule ,HttpClient } from '@angular/common/http';
import { HttpRequestInterceptor } from './http-request.interceptor';
import { ArticleService } from './article.service';
import { CrossDomainService } from './cross-domain.service';
import { AnalyticsService } from './analytics.service';
import { TranslateModule, TranslateLoader } from '@ngx-translate/core';
import { TranslateHttpLoader } from '@ngx-translate/http-loader';
export function translateHttpLoaderFactory(http: HttpClient) {
return new TranslateHttpLoader(http);
}
@NgModule({
imports: [
CommonModule,
HttpClientModule,
TranslateModule.forRoot({
loader: {
provide: TranslateLoader,
useFactory: translateHttpLoaderFactory,
deps: [HttpClient]
}
})
],
providers: [
ArticleService,
CrossDomainService,
AnalyticsService,
{
provide: HTTP_INTERCEPTORS,
useClass: HttpRequestInterceptor,
multi: true
}
]
})
export class CoreModule {}
http-request.interceptor.ts:
import { Injectable } from '@angular/core';
import { HttpEvent, HttpInterceptor, HttpHandler, HttpRequest } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';
import { CrossDomainService } from './cross-domain.service';
@Injectable()
export class HttpRequestInterceptor implements HttpInterceptor {
language: string = 'en';
constructor(private crossDomainService: CrossDomainService) {
crossDomainService.globalLanguage.subscribe((language) => {
this.language = language;
});
}
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const request = req.headers.has('Accept-Language') ?
req :
req.clone({ setHeaders: { 'Accept-Language': this.language } });
return next.handle(request);
}
}
on compiling the project I am getting an error:
ERROR in Error: Provider parse errors:
Cannot instantiate cyclic dependency! HTTP_INTERCEPTORS ("[ERROR ->]"): in NgModule CoreModule in C:/temp/myApp/src/app/core/core.module.ts@-1:-1
at NgModuleProviderAnalyzer.parse (C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:11699:19) at NgModuleCompiler.compile (C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:18548:36)
at AotCompiler._compileModule (C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:24004:32)
at C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:23916:66 at Array.forEach (<anonymous>)
at AotCompiler._compileImplFile (C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:23916:19)
at C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:23829:87
at Array.map (<anonymous>)
at AotCompiler.emitAllImpls (C:\temp\myApp\node_modules\@angular\compiler\bundles\compiler.umd.js:23829:52)
at CodeGenerator.emit (C:\temp\myApp\node_modules\@angular\compiler-cli\src\codegen.js:42:46)
at C:\temp\myApp\node_modules\@angular\compiler-cli\src\codegen.js:33:61
at <anonymous>
at process._tickCallback (internal/process/next_tick.js:188:7)
Can anyone help me to fix this issue?
A cyclic dependency exists when a dependency of a service directly or indirectly depends on the service itself. For example, if UserService depends on EmployeeService, which also depends on UserService. Angular will have to instantiate EmployeeService to create UserService, which depends on UserService, itself. Debugging the error link
Previously, an interceptor attempting to inject HttpClient directly would receive a circular dependency error, as HttpClient was constructed via a factory which injected the interceptor instances. Users want to inject HttpClient into interceptors to make supporting requests (ex: to retrieve an authentication token).
What Are Http Interceptors And How to Use Them In Angular? Use cases where we can make use of Interceptors in Angular. We have faced multiple scenarios where we might want to globally capture or change every request or response, like append a user’s token or handle errors from the response and we can achieve this using Http Interceptor.
The error may come in either the client-side (browser) or it may be an error from the server-side when the request fails due to any reason. You can learn more about the internal implementation of interceptors in Insider’s guide into interceptors and HttpClient mechanics in Angular.
Try not setting CrossDomainService in constructor but getting in the intercept function
@Injectable()
export class HttpRequestInterceptor implements HttpInterceptor {
constructor(private injector: Injector) {
}
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
// try to call the service here.
language: string = 'en';
const lanaguageInj= this.injector.get(CrossDomainService);
const globalLanguage= auth.globalLanguage.subscribe((language) => {
this.language = language;
});
const request = req.headers.has('Accept-Language') ?
req :
req.clone({ setHeaders: { 'Accept-Language': this.language } });
return next.handle(request);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With