import { Injectable } from '@angular/core';
import { HttpClient, HttpParams } from '@angular/common/http';
import { map, Observable } from 'rxjs';

import { environment } from '../../environments/environment';
import { ApiCollectionResponse } from '../models/api-response.model';
import { ReceivablePayment } from '../models/receivable-payment.model';
import { ReceivableSummary } from '../models/receivable-summary.model';
import { Receivable } from '../models/receivable.model';
import { extractCollectionData } from '../utils/api-response.util';

export interface ReceivableFilters {
  clientId?: string;
  branchId?: string;
  ticketId?: string;
  status?: string;
  from?: string;
  to?: string;
}

@Injectable({
  providedIn: 'root'
})
export class ReceivableService {
  private apiUrl = `${environment.apiBaseUrl}/receivables`;

  constructor(private http: HttpClient) {}

  getAll(filters?: ReceivableFilters): Observable<Receivable[]> {
    return this.http
      .get<Receivable[] | ApiCollectionResponse<Receivable>>(this.apiUrl, {
        params: this.buildParams(filters)
      })
      .pipe(map(response => extractCollectionData(response)));
  }

  getSummary(filters?: ReceivableFilters): Observable<ReceivableSummary> {
    return this.http.get<ReceivableSummary>(`${this.apiUrl}/summary`, {
      params: this.buildParams(filters)
    });
  }

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

  create(receivable: Receivable): Observable<Receivable> {
    return this.http.post<Receivable>(this.apiUrl, receivable);
  }

  update(id: number, receivable: Receivable): Observable<Receivable> {
    return this.http.put<Receivable>(`${this.apiUrl}/${id}`, receivable);
  }

  registerPayment(id: number, payment: ReceivablePayment): Observable<ReceivablePayment> {
    return this.http.post<ReceivablePayment>(`${this.apiUrl}/${id}/payments`, payment);
  }

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

  private buildParams(filters?: ReceivableFilters): HttpParams {
    let params = new HttpParams();

    if (!filters) {
      return params;
    }

    Object.entries(filters).forEach(([key, value]) => {
      if (value !== null && value !== undefined && value !== '') {
        params = params.set(key, String(value));
      }
    });

    return params;
  }
}
