개발자를 향해...
[ReactJS로 영화 웹 서비스 만들기] #4 MAKING THE MOVIE APP 본문
[ReactJS로 영화 웹 서비스 만들기] #4 MAKING THE MOVIE APP
eugeneHwang1124 2021. 2. 8. 16:10본 내용은 노마드코더 - ReactJS로 영화 웹 서비스 만들기 를 수강하며 작성되었습니다.
yts라는 불법 영화 사이트에서 api를 참고한다.현재 우리가 사용하려는 api의 주소는 https://yts.lt/api/v2/list_movies.json 이다. 하지만 yts는 항상 그 주소가 바뀐다. 따라서 강의에서 제공하는 api를 사용한다.https://yts-proxy.now.sh/list_movies.json
visual code에서 axios를 설치하고 import 하자. ( npm i axios ) 이제 componentDidMount에 axios를 넣어준다.
componentDidMount() {
const movies= axios.get("https://yts-proxy.now.sh/list_movies.json");
}
이 코드를 통해 axios는 사이트의 데이터를 가져온다.
axios는 속도가 느리기 때문에 javascript에게 componentDidMount가 끝날 때까지 시간이 걸린다고 말해야한다.
getMovies=async()=>{
const movies =await axios.get("https://yts-proxy.now.sh/list_movies.json");
}
componentDidMount() {
this.getMovies();
}
await을 통해 기다리라는 의미를 주었다. await은 async가 있어야 동작한다. 이제 영화 데이터를 가져와서 state의 렌더 함수에 보여주자.
console.log(movies);로 출력해보면 데이터를 잘 가져오는 것을 알 수 있다. 여기의 data 부분을 가져와야한다.
console.log(movies.data.data.movies);
이 코드를 다음과 같이 단축할 수 있다.
getMovies=async()=>{
const {data: {data :{movies}}} =await axios.get("https://yts-proxy.now.sh/list_movies.json");
console.log(movies);
}
이 movies를 state안에 넣자.
getMovies=async()=>{
const {data: {data :{movies}}} =await axios.get("https://yts-proxy.now.sh/list_movies.json");
this.setState({movies});
}
this.setState({movies});는 this.setState({movies : movies});와 같은 코드이다.
이제 Movie.js라는 파일을 생성한다. 그리고 movies 에서 id, year, title, summary, poster을 가져오도록 코드를 작성한다.
<Movie.js>
import React from 'react';
import PropTypes from 'prop-types';
import axios from 'axios';
function Movie({id, year,title, summary,poster}){
return<h1>{title}</h1>;
}
Movie.propTypes = {
id:PropTypes.number.isRequired,
year:PropTypes.number.isRequired,
title:PropTypes.string.isRequired,
summary:PropTypes.string.isRequired,
poster:PropTypes.string.isRequired
}
export default Movie;
App.js에서 map으로 데이터를 Movie.js에 보내준다.
import React from 'react';
import PropTypes from 'prop-types';
import axios from 'axios';
import Movie from './Movie';
class App extends React.Component {
state = {
isLoading: true,
movies:[]
}
getMovies=async()=>{
const {data: {data :{movies}}} =await axios.get("https://yts-proxy.now.sh/list_movies.json");
this.setState({movies,isLoading:false});
}
componentDidMount() {
this.getMovies();
}
render() {
const { isLoading,movies}=this.state;
return (
<div>
{ isLoading ? "Loading..." : movies.map(movie =>{
console.log(movie);
return <Movie id={movie.id} year={movie.year} title={movie.title} summary={movie.summary} poster={movie.medium_cover_image} />
})}
</div>
);
}
}
export default App;
실행을 시키니 다음과 같은 에러가 떴다. 즉 <Movie/>에서 고유한 key가 필요하다는 것이다. 따라서 key={movie.id}를 추가해준다.
이제 Movie.js의 HTML을 꾸며주자.
먼저 App.js의 render을 다음과 같이 바꾼다.
render() {
const { isLoading,movies}=this.state;
return (
<section class="container">
{ isLoading ? (<div class="loader">
<span class="loader__text">Loading...</span>
</div>
) : (
<div class="movies">
{movies.map(movie =>{
console.log(movie);
return <Movie key={movie.id} id={movie.id} year={movie.year} title={movie.title} summary={movie.summary} poster={movie.medium_cover_image} />
})
}
</div>
)}
</section>
);
}
Movie.js와 App.js에 각각 Movie.css와 App.css 파일을 만들고 import한다.
그리고 Movie.js에 genres 데이터를 추가로 가져온다.
//<App.js>
return <Movie key={movie.id} id={movie.id} year={movie.year} title={movie.title} summary={movie.summary} poster={movie.medium_cover_image} genres={movie.genres} />
//<Movie.js>
Movie.propTypes = {
id:PropTypes.number.isRequired,
year:PropTypes.number.isRequired,
title:PropTypes.string.isRequired,
summary:PropTypes.string.isRequired,
poster:PropTypes.string.isRequired,
genres:PropTypes.arrayOf(PropTypes.string).isRequired
}
function Movie({id, year,title, summary,poster, genres}){...
실행을 시키니 class가 아니라 className을 써야한다는 에러가 떴다. 자바스크립트 class안에서는 className을 써야한다. 따라서 해당 부분을 바꾸어준다.
장르를 가져와서 Movie에서 화면에 출력하도록 한다.
import React from 'react';
import PropTypes from 'prop-types';
import axios from 'axios';
import './Movie.css';
function Movie({id, year,title, summary,poster, genres}){
return(
<div className="movie">
<img src={poster} alt={title} title={title}/>
<div className="movie__data">
<h3 className="movie_title">{title}</h3>
<h5 className="movie_year">{year}</h5>
<ul className="genres">{genres.map((genre,index)=><li key={index} className="genres__genre">{genre}</li> )}</ul>
<p className="movie_summary">{summary}</p>
</div>
</div>
);
}
Movie.propTypes = {
id:PropTypes.number.isRequired,
year:PropTypes.number.isRequired,
title:PropTypes.string.isRequired,
summary:PropTypes.string.isRequired,
poster:PropTypes.string.isRequired,
genres:PropTypes.arrayOf(PropTypes.string).isRequired
}
export default Movie;
App.css 파일도 코드를 넣어 꾸며주었다.
코드 참고 : github.com/nomadcoders/movie_app_2019/commit/c0a3270f5824c2555e2621190c6307cbaefe0704
여기서 텍스트를 다듬고 이미지를 조금 키워보자
.movie img {
position: relative;
top: -50px;
max-width: 180px;
width:100%;
margin-right: 30px;
box-shadow: 0 30px 60px -12px rgba(50, 50, 93, 0.25),
0 18px 36px -18px rgba(0, 0, 0, 0.3), 0 -12px 36px -8px rgba(0, 0, 0, 0.025);
}
그리고 summary의 크기를 일정하게 잘라서 표시해준다.
//Movie.js
<p className="movie_summary">{summary.slice(0,180)}</p>
이렇게 바꾸어주자.
App.css에서 이 부분을 Movie.css로 옮기자.
.movies .movie {
width: 45%;
background-color: white;
margin-bottom: 70px;
display: flex;
align-items: flex-start;
justify-content: space-between;
font-weight: 300;
padding: 20px;
border-radius: 5px;
color: #adaeb9;
box-shadow: 0 13px 27px -5px rgba(50, 50, 93, 0.25),
0 8px 16px -8px rgba(0, 0, 0, 0.3), 0 -6px 16px -6px rgba(0, 0, 0, 0.025);
}
.movie img {
position: relative;
top: -50px;
max-width: 180px;
width:100%;
margin-right: 30px;
box-shadow: 0 30px 60px -12px rgba(50, 50, 93, 0.25),
0 18px 36px -18px rgba(0, 0, 0, 0.3), 0 -12px 36px -8px rgba(0, 0, 0, 0.025);
}
.movie .movie__title,
.movie .movie__year {
margin: 0;
font-weight: 300;
}
.movie .movie__title {
margin-bottom: 5px;
font-size: 24px;
color: #2c2c2c;
}
.movie .movie__genres {
list-style: none;
padding: 0;
margin: 0;
display: flex;
margin: 5px 0px;
}
.movie__genres li,
.movie .movie__year {
margin-right: 10px;
font-size: 14px;
}
'웹 자바스크립트 공부 > ReactJS + node.js' 카테고리의 다른 글
[ReactJS로 영화 웹 서비스 만들기] #6 ROUTING BONUS (0) | 2021.02.10 |
---|---|
[ReactJS로 영화 웹 서비스 만들기] #5 CONCLUSIONS (0) | 2021.02.08 |
[ReactJS로 영화 웹 서비스 만들기] #3 STATE (0) | 2021.02.06 |
[ReactJS로 영화 웹 서비스 만들기] #2 JSX & PROPS (0) | 2021.02.05 |
[ReactJS로 영화 웹 서비스 만들기] #0 INTRODUCTION ~ #1 SETUP (0) | 2021.02.04 |