2017-02-22 1 views
1

작은 프로젝트를위한 단일 페이지 응용 프로그램을 만들고 있습니다. API 호출의 데이터를 객체의 동영상 데이터베이스에 저장하려고했습니다. 내가 console.log 개체, 나는 모든 속성과 값을 볼 수 있습니다. object.property를 console.log에 저장하면 'undefined'가 반환됩니다. 내가 4 개 속성을 보려면 내가 console.log(allData)를 사용하는 경우 모든 API의 결과로 가득개체 속성이 정의되어 있지 않습니다. 개체 자체가 모든 데이터를 표시합니다.

(() => { 
"use strict" 

    /* Saving sections to variables 
    --------------------------------------------------------------*/ 
    const movieList = document.getElementsByClassName('movie_list')[0]; 
    const movieSingle = document.getElementsByClassName('movie_single')[0]; 

    /* All standard filters for displaying movies 
    --------------------------------------------------------------*/ 
    const allFilters = { 
    trending: 'movie/popular', 
    toplist: 'movie/top_rated', 
    latest: 'movie/now_playing', 
    upcoming: 'movie/upcoming' 
    }; 

    const allData = {}; 

    /* Initialize app - Get al standard data and save it in object 
    --------------------------------------------------------------*/ 
    const app = { 
    init() { 
     getData(allFilters.trending, 'popular'); 
     getData(allFilters.toplist, 'toplist'); 
     getData(allFilters.latest, 'latest'); 
     getData(allFilters.upcoming, 'upcoming'); 

     this.startPage(); 
    }, 
    startPage() { 
     window.location.hash = "trending"; 
    } 
    } 

    /* Function for getting data from the API 
    --------------------------------------------------------------*/ 
    const getData = (filter, key) => { 
    const request = new XMLHttpRequest(); 
    const apiKey = '?api_key=xxx'; 
    const getUrl = `https://api.themoviedb.org/3/${filter}${apiKey}`; 

    request.open('GET', getUrl, true); 
    request.onload =() => { 
     if (request.status >= 200 && request.status < 400) { 
     let data = JSON.parse(request.responseText); 
     data.filter = key; 
     cleanData.init(data); 
     } else { 
     window.location.hash = 'random'; 
     } 
    }; 
    request.onerror =() => { 
     console.error('Error'); 
    }; 
    request.send(); 
    }; 

    /* Check if the data is list or single, and clean up 
    --------------------------------------------------------------*/ 
    const cleanData = { 
    init(originalData) { 
     if (!originalData.results) { 
     this.single(originalData); 
     } else { 
     allData[originalData.filter] = originalData; 
     } 
    }, 

    list(data) { 
     data.results.map(function(el) { 
     el.backdrop_path = `https://image.tmdb.org/t/p/w500/${el.backdrop_path}`; 
     }); 
     let attributes = { 
     movie_image: { 
      src: function() { 
      return this.backdrop_path; 
      }, 
      alt: function() { 
      return this.title; 
      } 
     }, 
     title_url: { 
      href: function() { 
      return `#movie/${this.id}/${this.title}`; 
      } 
     } 
     } 
     showList(data.results, attributes); 
    }, 

    single(data) { 
     data.poster_path = `https://image.tmdb.org/t/p/w500/${data.poster_path}`; 
     data.budget = formatCurrency(data.budget); 
     data.revenue = formatCurrency(data.revenue); 
     data.runtime = `${(data.runtime/60).toFixed(1)} uur`; 
     data.imdb_id = `http://www.imdb.com/title/${data.imdb_id}`; 
     let attributes = { 
     movie_image: { 
      src: function() { 
      return this.poster_path; 
      }, 
      alt: function() { 
      return this.title; 
      } 
     }, 
     imdb_url: { 
      href: function() { 
      return this.imdb_id 
      } 
     }, 
     similar_url: { 
      href: function() { 
      return `#movie/${this.id}/${this.title}/similar` 
      } 
     } 
     }; 
     showSingle(data, attributes); 
    } 
    }; 

    const showList = (cleanedData, attributes) => { 
    movieList.classList.remove('hidden'); 
    movieSingle.classList.add('hidden'); 
    Transparency.render(movieList, cleanedData, attributes); 
    }; 

    const showSingle = (cleanedData, attributes) => { 
    movieSingle.classList.remove('hidden'); 
    movieList.classList.add('hidden'); 
    Transparency.render(movieSingle, cleanedData, attributes); 
    } 

const formatCurrency = amount => { 
    amount = amount.toFixed(0).replace(/./g, function(c, i, a) { 
     return i && c !== "." && ((a.length - i) % 3 === 0) ? '.' + c : c; 
    }); 
    return `€${amount},-`; 
    }; 

    app.init(); 

console.log(allData); // Returns object with 4 properties: trending, toplist, latest & upcoming. Each property is filled with 20 results (movies with data) from the API. 

console.log(allData.trending) // Returns 'undefined' (each property I've tried). 

console.log(allData['trending']) // Returns 'undefined' 

Object.keys(allData); // Returns an empty Array [] 

})(); 

:이 코드입니다. 하지만 console.log(allData.trending) 또는 console.log(allData['trending']) 일 때 콘솔에서 '정의되지 않음'을 반환합니다. 이 문제를 해결하는 방법에 대한 아이디어가 있습니까?

+0

'Object.keys (allData) '의 출력은 무엇입니까? –

+0

@AmreshVenugopal 빈 배열 –

+2

을 반환합니다. 속성이 객체가 아닌 것처럼 보입니다. 내 말은, 콘솔에서 볼 수있는 속성은 프로토 타입에서 나온 것입니다. –

답변

1

app.init()을 호출하면 init이 발생하고 API 호출이 데이터를 가져 오도록 보냅니다.

데이터 가져 오기 호출은 비동기식입니다. 즉, 응답을 계속 실행하기를 기다리지 않습니다. 따라서 다음 코드 행을 실행합니다 (console.logs). 현재 API 호출이 데이터로 응답하지 않았으므로 data.property에 액세스하려고하면 데이터가 아직 없으므로 실패합니다.

log(data)을 수행하면 데이터에 대한 참조 로그가 생성되며,이 참조는 나중에 값으로 채워질 때 로그에서 업데이트됩니다. 해당 인스턴스에서 data의 값을 얻고 나중에 업데이트하지 못하게하려면 log(JSON.stringify(data))을 시도하십시오. 그렇게하면 일관된 결과를 얻을 수 있으며 로그가 작동하지 않습니다. 이는 실제 동작입니다.

로그를 얻으려면 A (동기식) JAX 요청의 성공 /로드 콜백을 살펴보고 거기에서 기록하십시오. 또는 allData을 나중에 cleanData에 작성한 경우 cleanData 기능 후 로그를 호출하십시오.

질문에 대답하기 위해 비동기 호출이므로 아무 로그도 작동하지 않아야합니다. allData은 나중에 업데이트되는 참조와 함께 작동하므로 console.logconsole.log(JSON.stringify(allData))을 사용하여 객체의 실제 스냅 샷을 얻습니다.

+0

답변 해 주셔서 감사합니다. :) –

관련 문제