angular HTTP requests: Use square brackets in HttpParams as parameter key/name

Today I stumbled upon passing parameters with brackets to an REST API. In my case it was used for filtering by multiple values.

By passing the parameter as filter[x] to angulars’ HttpParams caused the following:

filter%5Bx%5D=param1

I searched the web for solutions but no one really satisfied myself. By getting through angulars’ sources of the HttpParams I found HttpUrlEncodingCodec which encodes the key with JS-built-in function encodeURIComponent() plus replacing some more characters:

// s. https://github.com/angular/angular/blob/master/packages/common/http/src/params.ts
 
export class HttpUrlEncodingCodec implements HttpParameterCodec {
    encodeKey(k: string): string { return standardEncoding(k); }
    // ...
}
 
function standardEncoding(v: string): string {
    return encodeURIComponent(v)
        .replace(/%40/gi, '@')
        .replace(/%3A/gi, ':')
        .replace(/%24/gi, '$')
        .replace(/%2C/gi, ',')
        .replace(/%3B/gi, ';')
        .replace(/%2B/gi, '+')
        .replace(/%3D/gi, '=')
        .replace(/%3F/gi, '?')
        .replace(/%2F/gi, '/');
}

So my solution was overriding angulars’ function. I am using angulars’ built in function to avoid side effects, prevent changing angulars’ default functionality and re-replace the square brackets afterwards:

export class MyCustomHttpUrlEncodingCodec extends HttpUrlEncodingCodec {
    encodeKey(k: string): string {
        return super.encodeKey(k)
            .replace(new RegExp("%5B", "g"), "[")
            .replace(new RegExp("%5D", "g"), "]");
    }
}

Using it when adding the parameters to request:

let params: HttpParams = new HttpParams({
    encoder: new MyCustomHttpUrlEncodingCodec()
});
params = params.append("filter[x]", "param1");
params = params.append("filter[y]", "param2");
params = params.append("q", "param3");
this.http.get(endpoint, {
    params: params
}).subscribe();

Before: http://my-url.com?filter%5Bx%5D=param1&filter%5By%5D=param2&q=param3

After: http://my-url.com?filter[x]=param1&filter[y]=param2&q=param3

This strategy can be used in the same way for encoding the value or decoding key and value. For usage take a look at the API documentation here.

References