DEV Community

Cover image for HttpParams Builder for Angular
Felipe Belluco
Felipe Belluco

Posted on

HttpParams Builder for Angular

Greetings,

Today I was revisiting the code of an Angular project I'm working on, and I went through the following piece of code in a service class:

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

  buildParams(filter: any) {
    let params = new HttpParams();

    if (filter.uf) {
        params = params.append('uf', filter.uf);
    }

    if (filter.cidade) {
        params = params.append('cidade', filter.cidade);
    }

    if (filter.pagination) {
        const pagination = filter.pagination;

        params = params.append('sort', 'cidade,asc');

        if (pagination.pageNumber) {
            params = params.append('page', pagination.pageNumber);
        }

        if (pagination.pageSize) {
            params = params.append('size', pagination.pageSize);
        }
    }

    return params;
  }
Enter fullscreen mode Exit fullscreen mode

As you may know, the HttpParams is an immutable class used to declare the query params passed on a http request using HttpClient.

And because of the HttpParams immutability aspect, its instance doesn't change, instead, every time I call .append() a new instance is created. So I have to reassign the params variable with the new instance.

params = params.append('uf', filter.uf);

Although necessary, it doesn't look very nice. So I came up with a builder to keep things cleaner, and turn the code above in to the this:

import { HttpParams } from '@angular/common/http';
import { HttpParamsBuilder } from 'http-params.builder';

buildParams(filter: any) {
    const builder = new HttpParamsBuilder();

    builder
      .append('uf', filter.uf)
      .append('cidade', filter.cidade);

    if (filter.pagination) {
        const pagination = filter.pagination;
        builder
            .append('sort', 'cidade,asc')
            .append('page', pagination.pageNumber)
            .append('size', pagination.pageSize);  
    }

    return builder.build();
  }
Enter fullscreen mode Exit fullscreen mode

In my opinion, it looks more concise. Here's the implementation of the HttpParamsBuilder:

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

export class HttpParamsBuilder implements IHttpParamsBuilder {
  private params: HttpParams;

  constructor() {
    this.params = new HttpParams();
  }

  append(param: string, value: any): this {
    if (value) {
      this.params = this.params.append(param, value);
    }
    return this;
  }

  build(): HttpParams {
    return this.params;
  }
}

interface IHttpParamsBuilder {
  append(key: string, value: any): this;
  build(): HttpParams;
}
Enter fullscreen mode Exit fullscreen mode

Let me know your thoughts!

Top comments (0)