Почему метод «добавить» в javaScript не возвращает массив?

avatar
Abdulrahman sabah
1 июля 2021 в 18:12
51
1
1

Вот вызов API, которому нужны некоторые значения для возврата определенного набора продуктов,

выпуск

  • "category_slug" должен быть массивом, но по какой-то причине API говорит, что это не так. в чем здесь проблема?

const url = new URL(
            "https://someApi/products"
        );
        
        let params = {
            "limit": "10",
            "page": "1",
            "category_slug": ["shoes"]
        };

        // "limit" is "how many products in on one page".
        // "page" is the fetched page with the specific "limited" products.

        //issue
        // "category_slug" is a specific products category, this has to be an array but for 
        //  some reason, the API says it's not. what is the problem here?
        
        Object.keys(params)
            .forEach(key => url.searchParams.append(key, params[key]));

        //here I'm appending the specific value in {params} to the URL.


        let headers = {
        "Accept": "application/json",
        "Content-Type": "application/json",
    };
        

        
        fetch(url, {
            method: "GET",
            headers: headers,
        })
            .then(response => response.json())
            .then(json => console.log(json));
Источник

Ответы (1)

avatar
raina77ow
1 июля 2021 в 18:41
2

Понимаете, вы одновременно ожидаете слишком мало и слишком много от такой прекрасной вещи, как URLSearchParams.

Слишком мало, потому что обычно можно просто передать весь объект params в его конструктор, не тратя время на keys, forEach и т.д...

const url = new URL('https://example.com/');
const params = {
  limit: 10,
  page: 1
};
url.search = new URLSearchParams(params); // yes, that easy

console.log(url.toString()); 
// https://example.com/?limit=10&page=1

Слишком много, потому что URLSearchParams не предназначен для работы с массивами. Когда добавленный элемент является массивом, он просто преобразуется в строку:

const url = new URL('https://example.com/');
const params = {
  slug: [1, 2, 3]
};
url.search = new URLSearchParams(params);
console.log(url); // https://example.com/?slug=1%2C2%2C3

В этом случае параметр slug получил присвоенный ему 1,2,3 (результат [1, 2, 3].toString()) (и все запятые были закодированы urlencoded - заменены последовательностью %2C).

Ваш API может на самом деле работать с этим, но велика вероятность того, что он ожидает передачи аргументов массива в следующем формате:

https://example.com/?slug=1&slug=2&slug=3

... но даже это может не сработать, если API ожидает передачи аргументов массива с добавлением [] к каждому ключу, например:

https://example.com/?slug[]=1&slug[]=2&slug[]=3

Поэтому вам придется проверить свой API (трудно отладить такие вещи, просто заглянув в хрустальный шар, знаете ли...), принять во внимание его вкус и обрабатывать ваши элементы отдельно . Например,

const url = new URL('https://example.com/');
const params = {
  limit: 10,
  page: 1
};
url.search = new URLSearchParams(params);

const slugs = [1, 2, 3];
url.search += ['', ...slugs.map(
  slug => `category_slug[]=${encodeURIComponent(slug)}`)].join('&');

console.log(url.toString());
0xLogN
1 июля 2021 в 18:46
1

или разделить на , и соединить с помощью &slug=