Как установить baseUrl для углового HttpClient?
Я не нашел способ в документации, чтобы установить URL базы API для HTTP - запросов. Возможно ли это сделать с помощью Angular HttpClient?
Ответы
Ответ 1
Используйте новый HttpClient Interceptor.
Создайте правильную инъекцию, которая реализует HttpInterceptor
:
import {Injectable} from '@angular/core';
import {HttpEvent, HttpInterceptor, HttpHandler, HttpRequest} from '@angular/common/http';
import {Observable} from 'rxjs/Observable';
@Injectable()
export class APIInterceptor implements HttpInterceptor {
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const apiReq = req.clone({ url: `your-api-url/${req.url}` });
return next.handle(apiReq);
}
}
HttpInterceptor может клонировать запрос и изменять его по своему усмотрению, в этом случае я определил путь по умолчанию для всех HTTP-запросов.
Предоставить HttpClientModule следующие конфигурации:
providers: [{
provide: HTTP_INTERCEPTORS,
useClass: APIInterceptor,
multi: true,
}
]
Теперь все ваши запросы начинаются с your-api-url/
Ответ 2
Основываясь на очень полезном ответе TheUnreal
, можно написать перехватчик, чтобы получить базовый URL через DI:
@Injectable()
export class BaseUrlInterceptor implements HttpInterceptor {
constructor(
@Inject('BASE_API_URL') private baseUrl: string) {
}
intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
const apiReq = request.clone({ url: '${this.baseUrl}/${request.url}' });
return next.handle(apiReq);
}
}
BASE_API_URL
может быть предоставлен модулем приложения:
providers: [
{ provide: "BASE_API_URL", useValue: environment.apiUrl }
]
где environment
- это объект, автоматически создаваемый CLI при создании проекта:
export const environment = {
production: false,
apiUrl: "..."
};
Ответ 3
вам необязательно нужен базовый URL с HttpClient, документы говорят, что вам просто нужно указать часть api запроса, если вы делаете вызовы на тот же сервер, это просто, как это:
this.http.get('/api/items').subscribe(data => {
...
Однако, если вы хотите или хотите, укажите базовый URL.
У меня есть 2 предложения для этого:
1. Вспомогательный класс со статическим классом.
export class HttpClientHelper{
static baseURL: string = 'http://localhost:8080/myApp';
}
this.http.get(`${HttpClientHelper.baseURL}/api/items`);//in your service class
2. Базовый класс с классом, поэтому любая новая служба должна его расширять:
export class BackendBaseService {
baseURL: string = 'http://localhost:8080/myApp';
constructor(){}
}
@Injectable()
export class ItemsService extends BackendBaseService{
constructor(private http: HttpClient){
super();
}
public listAll(): Observable<any>{
return this.http.get(`${this.baseURL}/api/items`);
}
}
Ответ 4
Выдержки из Visual Studio 2017 asp.net.
включить ниже строки в Main.ts
export function getBaseUrl() {
return document.getElementsByTagName('base')[0].href;
}
const providers = [
{ provide: 'BASE_URL', useFactory: getBaseUrl, deps: [] }
];
в вашем компоненте
constructor(http: HttpClient, @Inject('BASE_URL') baseUrl: string) {
http.get<WeatherForecast[]>(baseUrl + 'api/SampleData/WeatherForecasts').subscribe(result => {
this.forecasts = result;
}, error => console.error(error));
}
мой полный код main.ts выглядит ниже
import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module';
import { environment } from './environments/environment';
export function getBaseUrl() {
return document.getElementsByTagName('base')[0].href;
}
const providers = [
{ provide: 'BASE_URL', useFactory: getBaseUrl, deps: [] }
];
if (environment.production) {
enableProdMode();
}
platformBrowserDynamic()
.bootstrapModule(AppModule)
.catch(err => console.error(err));
мой код компонента выглядит ниже
import { Component, Inject } from '@angular/core';
import { HttpClient } from '@angular/common/http';
@Component({
selector: 'fetch-weather',
templateUrl: './weather.component.html',
styleUrls: ['./weather.component.scss']
})
export class WeatherComponent {
public forecasts: WeatherForecast[];
constructor(http: HttpClient, @Inject('BASE_URL') baseUrl: string) {
http.get<WeatherForecast[]>(baseUrl + 'api/SampleData/WeatherForecasts').subscribe(result => {
this.forecasts = result;
}, error => console.error(error));
}
}
interface WeatherForecast {
dateFormatted: string;
temperatureC: number;
temperatureF: number;
summary: string;
}
Ответ 5
Я думаю, что для этого нет способа по умолчанию. У HttpService и внутри вы можете определить свойство вашего URL-адреса по умолчанию и сделать методы для вызова http.get и других с вашим URL-адресом свойств. Затем введите HttpService вместо HttpClient
Ответ 6
Почему бы не создать подкласс HttpClient с настраиваемым baseUrl? Таким образом, если вашему приложению необходимо взаимодействовать с несколькими службами, вы можете использовать разные подклассы для каждого или создать несколько экземпляров одного подкласса, каждый из которых имеет свою конфигурацию.
@Injectable()
export class ApiHttpClient extends HttpClient {
public baseUrl: string;
public constructor(handler: HttpHandler) {
super(handler);
// Get base url from wherever you like, or provision ApiHttpClient in your AppComponent or some other high level
// component and set the baseUrl there.
this.baseUrl = '/api/';
}
public get(url: string, options?: Object): Observable<any> {
url = this.baseUrl + url;
return super.get(url, options);
}
}