import React from 'react';
import ReactDOM from 'react-dom/client';
import './index.css';
import App from './App';
import reportWebVitals from './reportWebVitals';
import {BrowserRouter} from 'react-router-dom';
import {Provider} from 'react-redux';
import store from "./util/store";
const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<Provider store={store}>
<BrowserRouter>
<App/>
</BrowserRouter>
</Provider>
);
reportWebVitals();
Redux의 Provider로 앱 상태를 제공하고 Redux Store에 쉽게 접근 가능하도록 함
BrowserRouter로 라우딩 설정하고 App 컴포넌트 렌더링
export default function App() {
return (
<Routes>
<Route element={<PageLayout/>}>
<Route path='/' element={<Main/>}/>
<Route path='/search' element={<Search/>}/>
<Route path='/detail/:type/:id' element={<ItemDetail/>}/>
<Route path='/detail/:type/:id/credits' element={<CreditsDetail/>}/>
<Route path='/genre/:type/:number' element={<Genre/>}/>
<Route path='/person/:id' element={<PersonDetail/>}/>
<Route path='/:type/season/:id/episode' element={<SeasonDetail/>}/>
</Route>
<Route path="*" element={<NotFound/>}/>
</Routes>
);
}
import {createStore, applyMiddleware, combineReducers} from 'redux';
import thunk from 'redux-thunk';
import movieReducer from './movieReducer';
const rootReducer = combineReducers({
movies: movieReducer,
});
const store = createStore(rootReducer, applyMiddleware(thunk));
export default store;
combineReducers로 여러 리듀서를 합치고 그 값을 createStore 첫번째 매개변수, 비동기 작업을 위한 applyMiddleware(thunk) 를 두번째 매개변수로 넣어서 설정
/** 영화,TV 내용 **/
export const detailUrl = (data) => {
return {
type: "SEND_DATA",
payload: data.data
};
};
/** 작품, 인물 SNS **/
export const socialUrl = (data) => {
return {
type: "SEND_SOCIAL",
payload: data.data
};
};
/** 작품 OTT **/
export const ottUrl = (data) => {
return {
type: "SEND_OTT",
payload: data.data.results.KR
};
};
/** TV 프로그램 시즌 */
export const seasonUrl = (data) => {
return {
type: "SEND_SEASON",
payload: data.data
};
};
액션을 생성하고,
const initialState = {
movieData: null,
socialData: null,
seasonData: null,
ottData: null,
};
const movieReducer = (state = initialState, action) => {
switch (action.type) {
/** 영화,TV 내용 **/
case "SEND_DATA":
return {
...state,
movieData: action.payload,
};
/** 작품, 인물 SNS **/
case "SEND_SOCIAL":
return {
...state,
socialData: action.payload,
}
/** 작품 OTT **/
case "SEND_OTT":
return {
...state,
ottData: action.payload,
};
/** TV 프로그램 시즌 */
case "SEND_SEASON":
return {
...state,
seasonData: action.payload,
};
default:
return state;
}
};
export default movieReducer;
리듀서에서 액션을 받아 상태를 업데이트
import {detailUrl, socialUrl, ottUrl} from '../util/action';
import {movieApi} from "../util/movieApi";
export const movieActions = (id, number) => async (dispatch) => {
try {
const detail = await movieApi.detail(id, number)
dispatch(detailUrl(detail));
const social = await movieApi.social(id, number)
dispatch(socialUrl(social));
const ott = await movieApi.ottList(id, number)
dispatch(ottUrl(ott));
} catch (error) {
console.log(error)
}
};
공통으로 넣어두면 좋을 작품데이터, 작품/인물 소셜, 작품/인물 OTT
import {seasonUrl} from '../util/action';
import {movieApi} from "../util/movieApi";
export const seasonActions = (id, number) => async (dispatch) => {
try {
const season = await movieApi.seasons(id, number)
dispatch(seasonUrl(season));
} catch (error) {
console.log(error)
}
};
SeasonDetail, SeasonList 에서 사용