Please provide us with the following information:
Mac OSX (El Capitan)
>
@angular/cli: 1.0.0-beta.30
node: 7.5.0
os: darwin x64
@angular/common: 2.4.6
@angular/compiler: 2.4.6
@angular/core: 2.4.6
@angular/forms: 2.4.6
@angular/http: 2.4.6
@angular/platform-browser: 2.4.6
@angular/platform-browser-dynamic: 2.4.6
@angular/router: 3.4.6
@angular/compiler-cli: 2.4.6
The issue occurred when I tried to retrieve the current url scheme/protocol and hostname dynamically using "window.location object".
let url = location.protocol +'//api.' + location.hostname + '/';
console.log(url);
When ng build is called in development mode, code works as expected, however, while compiling for production (ng build --prod --aot; which safely compiles) I receive an unexpected "[Object Object]" in console while attempting to retrieve the url. Why does this happen and how do i resolve this problem.
I had set this up as part of a config file. Please see below
import { OpaqueToken } from "@angular/core";
export let APP_CONFIG = new OpaqueToken("app.config");
export interface IAPPCONFIG{
apiUrl: string,...}
export const config: IAPPCONFIG = {
apiUrl: window.location.protocol +'//api.' + window.location.hostname + '/',
...
}
import { APP_CONFIG, IAPPCONFIG } from './common/config';
export class AuthorizationService {
constructor(private authHttp: AuthHttp, @Inject( APP_CONFIG ) private config: IAPPCONFIG) {
}
getAuth(loginDetail: Login): Observable<Response> {
let url = this.config.apiUrl + 'oauth';
...........
let response = this.http.post(url, body, {headers: contentHeader});
return response;
}
POST http://www.example.com/[object%20Object]//api.[object%20Object]/oauth 404 (Not Found) polyfills.db0a652….bundle.js:30
e @ polyfills.db0a652….bundle.js:30
t.scheduleTask @ polyfills.db0a652….bundle.js:37
n.scheduleMacroTask @ polyfills.db0a652….bundle.js:37
(anonymous) @ polyfills.db0a652….bundle.js:30
send @ VM959:3
(anonymous) @ vendor.f3f572f….bundle.js:782
t._trySubscribe @ vendor.f3f572f….bundle.js:1
t.subscribe @ vendor.f3f572f….bundle.js:1
t.call @ vendor.f3f572f….bundle.js:346
t.subscribe @ vendor.f3f572f….bundle.js:1
e.submitForm @ main.1a773e9….bundle.js:1
t.handleEvent_24 @ main.1a773e9….bundle.js:8
e.object.i @ vendor.f3f572f….bundle.js:388
e.__tryOrUnsub @ vendor.f3f572f….bundle.js:2
e.next @ vendor.f3f572f….bundle.js:2
e._next @ vendor.f3f572f….bundle.js:2
e.next @ vendor.f3f572f….bundle.js:2
e.next @ vendor.f3f572f….bundle.js:52
e.emit @ vendor.f3f572f….bundle.js:388
e.onSubmit @ vendor.f3f572f….bundle.js:171
e.handleEvent @ main.1a773e9….bundle.js:1
t.handleEvent_24 @ main.1a773e9….bundle.js:8
(anonymous) @ vendor.f3f572f….bundle.js:614
t.invokeTask @ polyfills.db0a652….bundle.js:37
onInvokeTask @ vendor.f3f572f….bundle.js:451
t.invokeTask @ polyfills.db0a652….bundle.js:37
n.runTask @ polyfills.db0a652….bundle.js:37
invoke @ polyfills.db0a652….bundle.js:37
using window.location object directly (without importing value from config file) in the component/class works as expected in both production and development builds:
import { APP_CONFIG, IAPPCONFIG } from './common/config';
export class AuthorizationService {
constructor(private authHttp: AuthHttp, @Inject( APP_CONFIG ) private config: IAPPCONFIG) {
}
getAuth(loginDetail: Login): Observable {
// used window.location directly
let url = location.protocol +'//api.' + location.hostname + '/' + 'oauth';
console.log(url);
...........
let response = this.http.post(url, body, {headers: contentHeader});
return response;
}
however it means i'd have to lose the benefits defining the url once and using it where needed via the config file definition.
Thanks! We'll be in touch soon.
Hi @byteworksng ,
A better approach would be to import your environments file like:
import { environment } from '../environments/environment';
Where environment.prod.ts looks like:
export const environment = {
production: true,
productionApi: "https://"+ window.location.hostname +"/api/"
};
This returns a string rather than an object with just location.hostname
I understand that this is happening to you, but I'm not too sure it's a CLI bug... it looks like it's an AOT thing even. Something about how providers work, I'd wager. Try to use a factory instead of an object, I remember some similar problems with window were solved that way.
This approach returns null on production builds as the AOT compilation cannot access the window.location.host value. Any better fix?
I am facing the same issue in Aug 2018 .. did not find any fix for a while. does anyone have a solution for this ?
We made a getter function to retrieve it at runtime. Something like this:
export function getHostLocation() {
return window.location.protocol + '//' + window.location.host + '/' ;
}
This issue has been automatically locked due to inactivity.
Please file a new issue if you are encountering a similar or related problem.
Read more about our automatic conversation locking policy.
_This action has been performed automatically by a bot._
Most helpful comment
This approach returns null on production builds as the AOT compilation cannot access the window.location.host value. Any better fix?