Каким образом мы получаем переменную вне функции?

170
29 сентября 2021, 05:40

В данном коде, по клику на кнопку мы вытягиваем массив объектов из сервера. Затем добавляем эти объекты в разметку.

Вопрос: каким образом мы получаем значение переменной response вне функции getPosts, что является её аргументом (cb) и что вызывает cb(response)?

const btn = document.getElementById("get-posts");
const container = document.getElementById("container");
function getPosts(cb) {
  let xhr = new XMLHttpRequest();
  xhr.open("GET", "https://jsonplaceholder.typicode.com/posts");
  xhr.send();
  xhr.addEventListener("load", () => {
    const response = JSON.parse(xhr.responseText);
    cb(response);
  });
}
function renderPosts(response) {
  const fragment = document.createDocumentFragment();
  response.forEach(post => {
    const card = document.createElement("div");
    card.classList.add("card");
    const title = document.createElement("h5");
    title.classList.add("card-title");
    title.textContent = post.title;
    const article = document.createElement("p");
    article.classList.add("card-text");
    article.textContent = post.body;
    card.appendChild(title);
    card.appendChild(article);
    fragment.appendChild(card);
  });
  container.appendChild(fragment);
}
btn.addEventListener("click", e => {
  getPosts(renderPosts);
});
Answer 1

У вас есть функция renderPosts(response) response - её аргумент, и есть функция getPosts(cb) cb - её аргумент.

Смотрим по коду:

btn.addEventListener("click", e => {
    getPosts(renderPosts);
});

Добавляется ивент клика на кнопку, который вызывает функцию getPosts и ей уже в качестве аргумента передаётся функция renderPosts (только название функции без скобок это "передача" функции, со скобками, аля renderPosts() это уже вызов функции).

То есть, вот этот код: cb(response); аналогичен вот этому: renderPosts(response).

В итоге, мы можем по-другому показать наш код так:

const btn = document.getElementById("get-posts"); 
    const container = document.getElementById("container"); 
 
     function getPosts() { 
      let xhr = new XMLHttpRequest(); 
      xhr.open("GET", "https://jsonplaceholder.typicode.com/posts"); 
      xhr.send(); 
      xhr.addEventListener("load", () => { 
        const response = JSON.parse(xhr.responseText); 
        renderPosts(response); 
      }); 
    } 
 
    function renderPosts(response) { 
      const fragment = document.createDocumentFragment(); 
      response.forEach(post => { 
        const card = document.createElement("div"); 
        card.classList.add("card"); 
 
        const title = document.createElement("h5"); 
        title.classList.add("card-title"); 
        title.textContent = post.title; 
 
        const article = document.createElement("p"); 
        article.classList.add("card-text"); 
        article.textContent = post.body; 
 
        card.appendChild(title); 
        card.appendChild(article); 
        fragment.appendChild(card); 
      }); 
      container.appendChild(fragment); 
    } 
 
    btn.addEventListener("click", e => { 
      getPosts(); 
    });

Или даже так:

        const btn = document.getElementById("get-posts"); 
        const container = document.getElementById("container"); 
 
         function getPosts() { 
          let xhr = new XMLHttpRequest(); 
          xhr.open("GET", "https://jsonplaceholder.typicode.com/posts"); 
          xhr.send(); 
          xhr.addEventListener("load", () => { 
            const response = JSON.parse(xhr.responseText); 
            const fragment = document.createDocumentFragment(); 
          response.forEach(post => { 
            const card = document.createElement("div"); 
            card.classList.add("card"); 
 
            const title = document.createElement("h5"); 
            title.classList.add("card-title"); 
            title.textContent = post.title; 
 
            const article = document.createElement("p"); 
            article.classList.add("card-text"); 
            article.textContent = post.body; 
 
            card.appendChild(title); 
            card.appendChild(article); 
            fragment.appendChild(card); 
          }); 
          container.appendChild(fragment); 
          }); 
        } 
 
        btn.addEventListener("click", e => { 
          getPosts(); 
        });

То есть, выходит что мы не получаем значение переменной response вне функции getPosts. Потому что всё структурировано - создаётся видимость того что данные используются вне функции, но по сути всё происходит внутри getPosts.

Answer 2

var param;  
 
function renderPosts(response) { 
    param = respons; 
}

если я вас правильно понял

READ ALSO
Symfony: глобальный импорт bootstrap

Symfony: глобальный импорт bootstrap

Мне необходимо подключить bootstrap 4 таким образом, чтобы он был виден во всех подключаемых javascript файлахСобственно, есть файл app

101
Код не возвращает данные из JSON файла

Код не возвращает данные из JSON файла

Проходя курс по JS столкнулся с проблемой во время использования Promise вместо обычных callback функций

84
event.target.value - взять одно значение из двух

event.target.value - взять одно значение из двух

Возникла необходимость добавить выпадающий список с двумя значениями - условно контактом и его ID, одной строкойВыбранное значение обрабатывается...

99
Проблема с памятью

Проблема с памятью

Практика «Частотность N-грамм»

112