Подтвердить что ты не робот

Как получить доменное имя для службы в Angular2

Мне нужно сделать запрос на один и тот же сервер, отдохнуть api на другом порту.

Как я могу сделать это без полного имени hardcoding в служебных URL-адресах?

4b9b3361

Ответ 1

Нет необходимости в угловом2-специфичном решении. Вы можете использовать window.location.hostname для получения текущего имени хоста.

Обратите внимание, однако, что если вы не хотите использовать глобальные переменные, такие как window -object напрямую, вы можете предоставить свой собственный объект Window, который затем можно внедрить.

См. Этот полный рабочий образец углового Stackblitz для деталей.

Обновленный ответ для Angular 6+

Как уже говорили другие, оригинальный ответ больше не работает. Для Angular 6+ необходимо предоставить токен впрыска, чтобы window -object можно было разрешить и в AOT -build.

Я рекомендую создать массив WINDOW_PROVIDERS в отдельном файле, например:

import { InjectionToken, FactoryProvider } from '@angular/core';

export const WINDOW = new InjectionToken<Window>('window');

const windowProvider: FactoryProvider = {
  provide: WINDOW,
  useFactory: () => window
};

export const WINDOW_PROVIDERS = [
    windowProvider
]

Константу WINDOW_PROVIDERS можно добавить в массив providers в AppModule следующим образом:

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule
  ],
  providers: [
    WINDOW_PROVIDERS, // <- add WINDOW_PROVIDERS here
    SampleService,
  ],
  bootstrap: [AppComponent]
})
export class AppModule { }

В SampleService window объект может быть внедрен с использованием определенного токена инъекции следующим образом:

import { Injectable, Inject } from '@angular/core';
import { WINDOW } from '../window.provider';

@Injectable()
export class SampleService {

    constructor(@Inject(WINDOW) private window: Window) {
    }

    getHostname() : string {
        return this.window.location.hostname;
    }
}

Оригинальный ответ для Angular 2

Поэтому вам нужно установить провайдера для Window -object при загрузке вашего приложения.

import {provide} from 'angular2/core';
bootstrap(..., [provide(Window, {useValue: window})]);

После этого вы можете использовать объект окна и получить доступ к имени хоста следующим образом:

constructor(private window: Window) {
   var hostname = this.window.location.hostname;
}

Ответ 2

Другой вариант - использовать DOCUMENT из @angular/platform-browser.

import {DOCUMENT} from '@angular/platform-browser';

constructor(@Inject(DOCUMENT) private document: Document) {
    let url = document.location.protocol +'//'+ document.location.hostname + ':my_port' );
}

Ответ 3

Angular 2 последнее рабочее решение:

app.module.ts

providers: [
    {provide: Window, useValue: window},
    ...
]

youclass.ts

constructor(
    @Inject(Window) private _window: Window
) {
    this._baseUrl = `http://${this._window.location.hostname}:3333`;
};

Ответ 4

Вы можете использовать window, как заявили другие, и чтобы сделать его инъекционным, начиная с ng6 и выше, вам нужен токен инъекции.

Объявите токен так:

export const WINDOW = new InjectionToken('window',
    { providedIn: 'root', factory: () => window }
);

Затем используйте его в конструкторе класса:

class Foo {
  constructor(@Inject(WINDOW) private window: Window) { }
}

Поскольку Window - это интерфейс в TypeScript, если вы не сделаете инъекцию подобным образом, при создании проекта для производства вы получите ошибку: Can't resolve all parameters for <ClassName> удается Can't resolve all parameters for <ClassName>. А потом еще: ERROR in: Error: Internal error: unknown identifier undefined.

Чтобы лучше понять инъекцию, прочитайте угловые документы для DI: https://angular.io/guide/dependency-injection

Ответ 5

Я достиг этого с помощью следующего кода в app.component.ts:

import { Component, OnInit, Inject, Injectable } from '@angular/core';
import { DOCUMENT } from '@angular/platform-browser';

@Component({
    selector: 'app-root',
    templateUrl: './app.component.html',
    styleUrls: ['./app.component.scss']
})
export class AppComponent implements OnInit {

    constructor(@Inject(DOCUMENT) private document: any) { }

    ngOnInit() {
        this.domain = this.document.location.hostname;
        console.log(this.domain);
    }
}

Это должно печатать имя домена в консоли.

Ответ 6

Я рекомендую использовать window.location, как прокомментировали другие.

Однако вы также можете сделать это, импортировав библиотеку Angular common 'Location' и используя ее для инъекции следующим образом:

import { Injectable } from '@angular/core';
import { Location }   from '@angular/common';
const otherPort = 8000;

@Injectable()
export class ServiceOrComponentName {
  constructor(location: Location) {
    this.baseUrl = location._platformStrategy._platformLocation._location.protocol +
      '//' + location._platformStrategy._platformLocation._location.hostname +
      ':' + otherPort;
  }
}

Ответ 7

Я проверяю это на Angular 7, и он работал правильно

declare var window: any;

console.log (window.location.host); //result lrlucas.github.io > domain github pages

с window.location.host я получаю полный домен

Примечание. @Component переменную окна перед @Component

Ответ 8

Это должно помочь вам:

import {LocationStrategy} from '@angular/common';

constructor(private locationStrategy:LocationStrategy) {
  console.log(locationStrategy.prepareExternalUrl('xxx'));
}

Ответ 9

Я использую простой JavaScript и URL нативного API для анализа URL:

const parsedUrl = new URL(window.location.href);
const baseUrl = parsedUrl.origin;
console.log(baseUrl); // this will print http://example.com or http://localhost:4200