Создание строки запроса из объекта в JavaScript

0

Создание строки запроса из объекта в JavaScript

Доброго времени суток! При создании веб-сайтов часто, если не всегда, приходится иметь дело с фильтрацией и сортировкой результатов запроса к базе данных. Эти операции осуществляются на основе данных пришедших в запросе на сервер из браузера, например.

А данные для фильтрации, это как правило, некоторый объект JavaScript, который описывает, какие данные нужны и как их сортировать.

Далле мы рассмотрим с Вами пример, того как можно преобразовать JavaScript объект в строку запроса (query string), которую потом можно будет передать на сервер в виде GET параметра.

Итак, для начала определим некоторые вспомогательные функции, необходимые для работы функции buildQueryString.

// Функция для проверки, является ли объект пустым
function isEmpty(obj) {
    // Проверяем, если длина массива ключей объекта равна 0, то объект пуст
    if (Object.keys(obj).length === 0) {
        return true;
    }

    // Проверяем каждое свойство объекта на пустоту
    for (const key in obj) {
        const value = obj[key];
        // Если значение не является пустым, объект не пуст
        if (
            value !== null &&
            value !== '' &&
            !(Array.isArray(value) && value.length === 0) &&
            !(typeof value === 'object' && isEmpty(value))
        ) {
            return false;
        }
    }

    // Если не найдены непустые свойства, объект пуст
    return true;
}

// Функция для удаления пустых полей из объекта
function removeEmptyFields(obj) {
    return Object.keys(obj).reduce((acc, key) => {
        const value = obj[key];
        // Если значение не пусто, добавляем его в аккумулятор
        if (value !== null && value !== '' && !(Array.isArray(value) && value.length === 0)) {
            acc[key] = value;
        }
        return acc;
    }, {});
}

// Функция для построения строки запроса из объекта параметров
function buildQueryString(params = {}, parentKey = null) {
    const queryString = [];

    // Проверяем, если объект параметров пуст, возвращаем undefined
    if (isEmpty(params)) return;

    // Обходим каждое свойство объекта параметров
    for (const key in params) {
        if (params.hasOwnProperty(key)) {
            const value = params[key];

            // Строим ключ с учетом вложенности
            const constructedKey = parentKey ? `${parentKey}[${key}]` : key;

            // Если значение является объектом и не пусто, обрабатываем его
            if (typeof value === 'object' && Object.entries(value).length !== 0) {
                // Удаляем пустые поля из объекта и рекурсивно строим строку запроса для вложенных объектов
                const _value = removeEmptyFields(value);
                queryString.push(buildQueryString(_value, constructedKey));
            } else {
                // Если значение существует, добавляем его в строку запроса с кодированием URI
                if (value) {
                    queryString.push(`${constructedKey}=${encodeURIComponent(value)}`);
                }
            }
        }
    }

    // Фильтруем undefined элементы и пустые строки, объединяем элементы в строку запроса с символом &
    return queryString.filter(v => v !== undefined).filter(s => s?.trim().length !== 0).join('&');
}

Тестируем на следующих данных:

const testData = 
{
    "filters": {
        "customer_id": null,
        "couriers": [],
        "order_statuses": [
            6,
            5,
            3,
            1,
            7,
            8,
            4
        ],
        "addresses_from": [],
        "addresses_to": [],
        "start_datetime": "",
        "end_datetime": "",
        "customer_cities": [
            1,
            2,
            8
        ]     },
    "sort": {
        "customer": "asc"
    }
}

const query_string = buildQueryString(testData);

// Получем следующую строку, которую можно отправлять на сервер

// filters[order_statuses][0]=6&filters[order_statuses][1]=5&filters[order_statuses][2]=3&filters[order_statuses][3]=1&filters[order_statuses][4]=7&filters[order_statuses][5]=8&filters[order_statuses][6]=4&filters[customer_cities][0]=1&filters[customer_cities][1]=2&filters[customer_cities][2]=8&sort[customer]=asc

const url = 'https://srs.myruakov.ru' + '?' + query_string;
console.log(url);

Таким образом, объект, который мы передаем в функция buildQueryString может состоять из необходимых для фильтрации и сортировки параметров. Однако, имейте ввиду, что не стоит делать строку запроса (query_string) слишком длинной (можно сделать имена свойств короче в объекте testData), а также, все данные, пришедшие на сервер необходимо обязательно проверять, на соответствие правилам безопасности.

Источник

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Этот сайт использует Akismet для борьбы со спамом. Узнайте, как обрабатываются ваши данные комментариев.