IslomDevIslomDev
Booster
Imtihon
Booster
Imtihon
  • Angular Intervyu Tayyorgarlik
  • JavaScript / TypeScript

    • JavaScript / TypeScript
    • Asoslar (JavaScript)
    • Asinxronlik
    • Prototip va OOP
    • TypeScript
    • Performance
  • Algoritmlash

    • Algoritmlash
    • Murakkablik tahlili
    • Ma'lumot tuzilmalari
    • Qidiruv va Saralash
    • Algoritmik paradigmalar
    • Amaliy masalalar
  • Angular — Boshlang'ich

    • Angular — Boshlang'ich
    • Component
    • Template
    • Change Detection
    • Advanced Component
  • Angular — Service va DI

    • Angular — Service va DI
    • Service asoslari
    • HTTP
    • Hierarchical DI
    • Advanced DI
    • State management (service)
  • Angular — Versiyalar

    • Angular — Versiyalar
    • Angular 12–13
    • Angular 14
    • Angular 15
    • Angular 16
    • Angular 17
    • Angular 18+
  • Angular — Directive

    • Angular — Directive
    • Built-in Directives
    • Custom Attribute Directive
    • Custom Structural Directive
    • Advanced
  • Angular — RxJS

    • Angular — RxJS
    • Observable asoslari
    • Asosiy operatorlar
    • Higher-order operatorlar
    • Combination operatorlar
    • Subject turlari
    • Xato va xotira
    • Advanced
  • Angular — Pipe

    • Angular — Pipe
    • Built-in Pipes
    • Custom Pipe
    • Performance
  • Angular — Forms

    • Angular — Forms
    • Template-driven Forms
    • Reactive Forms
    • Validators
    • Advanced
  • Angular — NgModule

    • Angular — NgModule
    • NgModule asoslari
    • Module arxitekturasi
    • Lazy Loading
    • Standalone vs NgModule
  • Angular — Sintaksis va Clean Code

    • Angular — Sintaksis va Clean Code
    • Template sintaksisi
    • Angular 17+ yangi sintaksis
    • Komponent arxitekturasi
    • Performance pattern'lar
    • SOLID va Clean Code
    • Testing

HTTP

Daraja:

Angular HttpClient — REST API bilan ishlash uchun RxJS Observable qaytaradigan HTTP client. Interceptor'lar esa har bir so'rov/javobni markaziy tarzda o'zgartirish imkonini beradi.

HttpClient — get, post, put, patch, delete

Junior

Nima bu?

HttpClient — @angular/common/http modulidan keladigan service. Barcha HTTP metodlari Observable qaytaradi (Promise emas). subscribe yoki async pipe orqali natija olinadi. Standalone ilovada provideHttpClient() bilan ro'yxatdan o'tkaziladi.

Kod misoli

// main.ts
import { bootstrapApplication } from '@angular/platform-browser';
import { provideHttpClient } from '@angular/common/http';

bootstrapApplication(AppComponent, {
  providers: [provideHttpClient()],
});
interface Product {
  id: number;
  name: string;
  price: number;
}

@Injectable({ providedIn: 'root' })
export class ProductApiService {
  private http = inject(HttpClient);
  private baseUrl = '/api/products';

  getAll(): Observable<Product[]> {
    return this.http.get<Product[]>(this.baseUrl);
  }

  getById(id: number): Observable<Product> {
    return this.http.get<Product>(`${this.baseUrl}/${id}`);
  }

  create(product: Omit<Product, 'id'>): Observable<Product> {
    return this.http.post<Product>(this.baseUrl, product);
  }

  update(id: number, product: Partial<Product>): Observable<Product> {
    return this.http.put<Product>(`${this.baseUrl}/${id}`, product);
  }

  patchPrice(id: number, price: number): Observable<Product> {
    return this.http.patch<Product>(`${this.baseUrl}/${id}`, { price });
  }

  delete(id: number): Observable<void> {
    return this.http.delete<void>(`${this.baseUrl}/${id}`);
  }
}

Imtihonda

Savol: HttpClient nima qaytaradi — Promise yoki Observable?

Javob: Observable. Bu cancel qilish, retry, operatorlar zanjiri va bir nechta subscriber uchun qulay.

Yodlash uchun

CRUD: get, post, put (to'liq almashtirish), patch (qisman), delete. Generic tip ``T`` javob tipini belgilaydi.

HTTP options — params, headers, responseType

JuniorMiddle

Nima bu?

Har bir HTTP so'rov uchun HttpParams, HttpHeaders va responseType orqali qo'shimcha sozlash mumkin. Query parametrlar, auth header, blob/arraybuffer javob turlari shu yerda beriladi.

Kod misoli

import { HttpClient, HttpParams, HttpHeaders } from '@angular/common/http';

@Injectable({ providedIn: 'root' })
export class SearchService {
  private http = inject(HttpClient);

  searchProducts(query: string, page = 1, limit = 10): Observable<Product[]> {
    const params = new HttpParams()
      .set('q', query)
      .set('page', page.toString())
      .set('limit', limit.toString());

    const headers = new HttpHeaders({
      'X-Request-Id': crypto.randomUUID(),
    });

    return this.http.get<Product[]>('/api/products', { params, headers });
  }

  downloadPdf(id: number): Observable<Blob> {
    return this.http.get(`/api/reports/${id}`, {
      responseType: 'blob',
    });
  }

  getRawText(): Observable<string> {
    return this.http.get('/api/readme', { responseType: 'text' });
  }
}

Imtihonda

Savol: HttpParams immutable — yangi param qo'shish qanday?

Javob: .set() va .append() yangi HttpParams instance qaytaradi. Eski ob'ekt o'zgarmaydi — zanjirlab yozish kerak.

Yodlash uchun

JSON default. Fayl yuklash: `responseType: 'blob'`. Matn: `'text'`. Header immutable — `setHeaders` clone orqali.

HTTP Interceptor — request/response transform

Middle

Nima bu?

Interceptor — HTTP so'rov ketishidan oldin yoki javob kelganda aralashuvchi. Auth token qo'shish, loading spinner, logging — bularning hammasi markaziy joyda bajariladi. Class-based interceptor HttpInterceptor interfeysini implement qiladi.

Kod misoli

import { Injectable } from '@angular/core';
import {
  HttpInterceptor,
  HttpRequest,
  HttpHandler,
  HttpEvent,
} from '@angular/common/http';
import { Observable } from 'rxjs';
import { finalize } from 'rxjs/operators';

@Injectable()
export class LoadingInterceptor implements HttpInterceptor {
  private loading = inject(LoadingService);

  intercept(req: HttpRequest<unknown>, next: HttpHandler): Observable<HttpEvent<unknown>> {
    this.loading.show();
    return next.handle(req).pipe(finalize(() => this.loading.hide()));
  }
}

// main.ts (class interceptor)
providers: [
  provideHttpClient(withInterceptorsFromDi()),
  { provide: HTTP_INTERCEPTORS, useClass: LoadingInterceptor, multi: true },
]

Imtihonda

Savol: Interceptor zanjiri qanday ishlaydi?

Javob: So'rov birinchi ro'yxatdagi interceptordan o'tadi, next.handle(req) keyingisiga uzatadi. Javob esa teskari tartibda qaytadi — oxirgi interceptor birinchi javobni ko'radi.

Yodlash uchun

So'rov o'zgartirish: `req.clone({ setHeaders: {...} })`. Asl `HttpRequest` immutable.

Functional interceptor (v15+)

MiddleSenior

Nima bu?

Angular 15+ da HttpInterceptorFn — oddiy funksiya ko'rinishidagi interceptor. Class o'rniga inject() ishlatiladi. provideHttpClient(withInterceptors([...])) bilan ro'yxatdan o'tkaziladi. Zamonaviy standalone ilovalar uchun tavsiya etiladi.

Kod misoli

import { HttpInterceptorFn } from '@angular/common/http';
import { inject } from '@angular/core';

export const authInterceptor: HttpInterceptorFn = (req, next) => {
  const auth = inject(AuthService);
  const token = auth.getToken();

  if (!token) {
    return next(req);
  }

  return next(
    req.clone({
      setHeaders: { Authorization: `Bearer ${token}` },
    })
  );
};

export const apiBaseInterceptor: HttpInterceptorFn = (req, next) => {
  if (req.url.startsWith('/api/')) {
    return next(req.clone({ url: `https://api.example.com${req.url}` }));
  }
  return next(req);
};

// main.ts
bootstrapApplication(AppComponent, {
  providers: [
    provideHttpClient(withInterceptors([apiBaseInterceptor, authInterceptor])),
  ],
});

Imtihonda

Savol: Functional va class interceptor bir vaqtda ishlatilsa tartib qanday?

Javob: withInterceptors ro'yxati birinchi, keyin withInterceptorsFromDi() (class-based). Functional interceptor'lar DI'siz yengilroq va tree-shake qilinadi.

Yodlash uchun

Yangi loyihada: functional interceptor + `withInterceptors`. Eski kod: `HTTP_INTERCEPTORS` + class.

Error handling interceptor — global

Middle

Nima bu?

Global error interceptor barcha HTTP xatolarini bir joyda ushlaydi: 401 — login'ga yo'naltirish, 500 — toast xabar, network error — qayta urinish taklifi. catchError operatori bilan HttpErrorResponse tahlil qilinadi.

Kod misoli

import { HttpInterceptorFn, HttpErrorResponse } from '@angular/common/http';
import { inject } from '@angular/core';
import { Router } from '@angular/router';
import { catchError, throwError } from 'rxjs';

export const errorInterceptor: HttpInterceptorFn = (req, next) => {
  const router = inject(Router);
  const toast = inject(ToastService);

  return next(req).pipe(
    catchError((error: HttpErrorResponse) => {
      if (error.status === 401) {
        router.navigate(['/login']);
        return throwError(() => error);
      }

      if (error.status === 0) {
        toast.error('Internet aloqasi yo\'q');
      } else if (error.status >= 500) {
        toast.error('Server xatosi. Keyinroq urinib ko\'ring.');
      } else {
        toast.error(error.error?.message ?? 'Noma\'lum xato');
      }

      return throwError(() => error);
    })
  );
};

Imtihonda

Savol: Interceptor'da xatoni "yutib" yuborish to'g'rimi?

Javob: Yo'q, agar component ham xatoni bilishi kerak bo'lsa. catchError ichida UI ko'rsatgandan keyin throwError(() => error) bilan qayta tashlash kerak — aks holda subscriber xato olmaydi.

Yodlash uchun

Global UI (toast, redirect) — interceptor'da. Form-specific xato — component/service'da alohida `catchError`.

Retry va exponential backoff

Senior

Nima bu?

Tarmoq yoki server vaqtincha ishlamaganda so'rovni qayta yuborish. retry(n) — oddiy qayta urinish. Exponential backoff — har urinish orasidagi kutish vaqti ikki barobar oshadi (1s, 2s, 4s...) — serverga bosim kamayadi.

Kod misoli

import { HttpClient } from '@angular/common/http';
import { retry, timer } from 'rxjs';
import { retryWhen, mergeMap, finalize } from 'rxjs/operators';

@Injectable({ providedIn: 'root' })
export class ResilientApiService {
  private http = inject(HttpClient);

  // Oddiy retry — 3 marta, darhol
  getWithRetry<T>(url: string): Observable<T> {
    return this.http.get<T>(url).pipe(retry(3));
  }

  // Exponential backoff — RxJS 7+ retry with delay config
  getWithBackoff<T>(url: string): Observable<T> {
    return this.http.get<T>(url).pipe(
      retry({
        count: 3,
        delay: (error, retryCount) => {
          if (error.status === 429 || error.status >= 500) {
            return timer(Math.pow(2, retryCount) * 1000); // 2s, 4s, 8s
          }
          throw error; // 4xx — qayta urinma
        },
      })
    );
  }
}
// Interceptor darajasida
export const retryInterceptor: HttpInterceptorFn = (req, next) => {
  if (req.method !== 'GET') {
    return next(req); // faqat GET uchun retry
  }
  return next(req).pipe(retry({ count: 2, delay: 1000 }));
};

Imtihonda

Savol: POST so'rovni avtomatik retry qilish xavflimi?

Javob: Ha. POST ikki marta bajarilsa duplicate ma'lumot yaratilishi mumkin (to'lov, buyurtma). Retry faqat idempotent so'rovlar uchun: GET, HEAD, ba'zi PUT.

Yodlash uchun

GET — retry xavfsiz. POST/DELETE — ehtiyotkorlik. 429/503 — backoff. 400/404 — retry foydasiz.
Prev
Service asoslari
Next
Hierarchical DI