Single Page Application (์ฑ๊ธ ํ์ด์ง ์ดํ๋ฆฌ์ผ์ด์ )์ ์ฝ์์ด๋ค.
์ฆ, ํ์ด์ง๊ฐ 1๊ฐ์ธ ์ดํ๋ฆฌ์ผ์ด์ ์ด๋ ๋ป์ผ๋ก ์ ์ ๊ฐ ์์ฒญ ํ ๋ ๋ง๋ค ํ์ด์ง๊ฐ ์๋ก๊ณ ์นจ ์ ๊ณต๋๋ ์ ๋ณด๊ฐ ์ ๋ง ๋ง๊ธฐ ๋๋ฌธ์ ์๋์ ์ธ ์ธก๋ฉด์์ ๋ฌธ์ ๊ฐ ๋ฐ์ํ๊ณ , ๋ถํ์ํ ํธ๋ํฝ์ผ๋ก ์ธํ ๋ญ๋น๊ฐ ์ฌํด์ง๊ธฐ๋๋ฌธ์ ๋ฆฌ์กํธ ๊ฐ์ ๋ผ์ด๋ธ๋ฌ๋ฆฌ ํน์ ํ๋ ์ ์ํฌ๋ฅผ ์ฌ์ฉํด์ ๋ทฐ๋ ๋๋ง์ ์ ์ ์ ๋ธ๋ผ์ฐ์ ๊ฐ ๋ด๋นํ๋๋ก, ํ๊ณ ์ดํ๋ฆฌ์ผ์ด์ ์ ๋ธ๋ผ์ฐ์ ์ ๋ก๋ํ ๋ค์ ํ์ํ ์ ๋ณด๋ง ๋ณด์ฌ์ค๋ค.
๊ทธ๊ฑด No. ์๋ฅผ๋ค์ด ๋ธ๋ก๊ทธ๋ฅผ ๋ง๋ ๋ค๋ฉด, ํ, ํฌ์คํธ ๋ชฉ๋ก, ํฌ์คํธ, ๊ธ์ฐ๊ธฐ ๋ฑ์ ํ๋ฉด์ด ์๋ค.
๋ค๋ฅธ ์ฃผ์์ ๋ฐ๋ผ ๋ค๋ฅธ ๋ทฐ๋ฅผ ๋ณด์ฌ์ฃผ๋๊ฒ์ ๋ผ์ฐํ ์ด๋ผ ํ๋ฉฐ, ๋ฆฌ์กํธ ์์ฒด์๋ ์ด ๊ธฐ๋ฅ์ด ๋ด์ฅ๋์ด์์ง ์๋๋ค. ๋ฐ๋ผ์ ์ฐ๋ฆฌ๊ฐ ์ง์ ๋ธ๋ผ์ฐ์ ์ API ๋ฅผ ์ฌ์ฉํ๊ณ ์ํ๋ฅผ ์ค์ ํ์ฌ ๋ค๋ฅธ ๋ทฐ๋ฅผ ๋ณด์ฌ์ฃผ์ด์ผ ํ๋ค.
react-router ๋, ์จ๋ํํฐ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ก์, ๋น๋ก ๊ณต์์ ์๋์ง๋ง ๊ฐ์ฅ ๋ง์ด ์ฌ์ฉ๋๊ณ ์๋ ๋ผ์ด๋ธ๋ฌ๋ฆฌ์ธ๋ฐ ์ด ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ ํด๋ผ์ด์ธํธ ์ฌ์ด๋์์ ์ด๋ค์ง๋ ๋ผ์ฐํ ์ ๊ฐ๋จํ๊ฒ ํด์ค๋ค.
SPA ์ ๋จ์ ์, ์ฑ์ ๊ท๋ชจ๊ฐ ์ปค์ง๋ฉด ์๋ฐ์คํฌ๋ฆฝํธ ํ์ผ ์ฌ์ด์ฆ๊ฐ ๋๋ฌด ์ปค์ง๋ค๋ ์ ์๋ค.
๋ผ์ฐํ (Routing)์ด๋ผ๋ ๊ฒ์ ๋ค๋ฅธ ๊ฒฝ๋ก(url ์ฃผ์)์ ๋ฐ๋ผ ๋ค๋ฅธ View(ํ๋ฉด)๋ฅผ ๋ณด์ฌ์ฃผ๋ ๊ฒ์ด๋ค.
๋ฆฌ์กํธ ์์ฒด์๋ ์ด๋ฌํ ๊ธฐ๋ฅ์ด ๋ด์ฅ๋์ด์์ง ์๋๋ค.
๐ ๋จผ์ Router.js ํ์ผ์ srcํด๋์ ๋ง๋ค์ด ์ค๋ค.
์์น : App.js
import { useNavigate } from 'react-router-dom';
import './App.scss';
function App() {
const navigate = useNavigate();
const goToLogin = () => {
navigate('/login');
}
return (
<div className='app'>
<div onClick ={goToLogin}>go to Login</div>
</div>
);
}
export default App;
------------------------------------------------------------
์์น : Login.js
import React from 'react';
import { Link } from 'react-router-dom';
const Login = () =>{
return(
<div>
<Link to ="/">go to App</Link>
</div>
);
};
export default Login;
-------------------------------------------------------------
์์น : Nav.js
import React from 'react';
const Nav = () => {
return(
<div>
<h1>Nav</h1>
</div>
);
};
export default Nav;
๐ App.js์ Login.js, Nav.js ํด๋์ ๋ค์ด๊ฐ์ ํ๋ฉด์ ํ์ํ๊ธธ ์ํ๋ ์ฝ๋๋ฅผ ์์ฑํด ์ค๋ค.
๐ Nav.js์ ๊ฒฝ์ฐ๋ ์ปดํฌ๋ํธ๋ก ์ ์ํด์ ๋ฐ๋ณต์ ์ผ๋ก ์ฌ์ฉํ ๋ ์ฉ์ดํ๊ฒ ๊ฐ์ ธ๋ค ์ธ ์์๋๋ก ํ๋ค.
import React from 'react';
import { BrowserRouter, Route, Routes } from 'react-router-dom';
import App from "./App";
import Login from './Login';
import Nav from './Nav';
const Router = () => {
return (
<BrowserRouter>
<Nav />
<Routes>
<Route path="/" element={<App />} />
<Route path="/login" element={<Login />} />
</Routes>
</BrowserRouter>
);
};
export default Router;
๐ Router.js๋ก ์ด๋ํด์ BrowserRouter์์ Routes๋ฅผ ๋ฃ๊ณ Route์ ๋ฃ๊ณ ์ถ์ ํจ์ค์, ์ฐ๊ฒฐํ๊ณ ์ํ๋ ๋ถ๋ถ์ ์์ ์ฝ๋ ์ฒ๋ผ ์์ฑํ๋ค.
๐ก ์ฃผ์ : import App from "./App"์ ๊ฐ์ import๋ฅผ ๋ฐ์์ค๋ ๋ถ๋ถ์ ์์ฑํ๊ณ , export default Login์ ๊ฐ์ export๋ฅผ ๋ด๋ณด๋ด๋ App.js์ ์์ฑํด ์ค๋ค.
๐ terminal์์ npm start๋ฅผ ํด์ค ๋ค ํ๋ฉด์ ๋ณด๋ฉด ์ง์ ํด์ค ํจ์ค์ธ "/ " -> localhost:3001์), "/login" -> localhost:3001/login์ด ์๋์ ๊ฐ์ด ๋์ค๋ ๊ฒ์ ํ์ธ ํ ์ ์๋ค.
Nav๋ ์ปดํฌ๋ํธ๋ก ๋ง๋ค์ด์ ๊ณ ์ ํด ์คฌ๊ธฐ ๋๋ฌธ์ path ๊ฒฝ๋ก๋ฅผ ์ด๋ํ์ฌ๋ ๊ณ ์ ๋์ด ๋ํ๋๋ค.
import React from 'react';
import { BrowserRouter, Route, Routes} from 'react-router-dom';
import App from './App';
import Login from './Login';
const Router = () => {
return (
<BrowserRouter>
<Routes>
<Route path = "/" element = {<App .>} />
</Routes>
</BrowserRouter>
);
};
export default Router;
๋ณดํต ๋๋ฌธ์๋ ์ปดํฌ๋ํธ๋ก ์ธ์ํ๊ณ , ํจ์ค๋ ์์ฑ์ด๋ผ๊ณ ๋ณผ ์ ์๋ค.
import React from 'react';
import {Link} form 'reat-router-dom';
const Login = () => {
return (
<div>
<Link to ="/">go to App</Link>
</div>
);
};
export default Login;
aํ๊ทธ ๊ฐ์ ๊ฒฝ์ฐ ์น์ผ๋ก ๋ณด๋ผ๋ ex) ์ธ์คํ ํ๋? ํ๊ณ ์ฐพ์๋ณด๋ ๊ฒฝ์ฐ,
Link๋ ๊ทธ ์์์ ๋ด์ฉ์ ๋ณด์ฌ์ค ๋ ์ฌ์ฉ ํ๋ค.
์์น : App.js
improt { useNavigaate } from 'react-router-dom';
function App() {
const navigate = userNavigate();
const goToLogin = () => {
navigate('/login');
};
return (
<div>
<div onClick = {goToLogin}>go to Login</div>
</div>
);
}
export default App;
์ ๋ค๋น๊ฒ์ดํธ๋ฅผ ์ฌ์ฉํ ๊น??
a ํ๊ทธ๋ ๋ค๋ฅธ CSSํ์ผ์ ์์ฑํ๊ฒ ๋ ์๊ตฌ๋ฅผ ํ๋ค.
Link๋ ํด๋ฆญํ์ ๊ฒฝ์ฐ ๋ฐ๋ก ์ด๋์ ํ๋๋ฐ, Navigate๊ฐ์ ๊ฒฝ์ฐ๋ ์กฐ๊ฑด์ ๋ฃ์ ์ ์๋ค.
์์น : router.js
import React from "react";
import { BrowserRouter, Route, Routes } from 'react-router-dom';
import App from "./App";
import Login from "./Login";
import Nav from "./Nav";
const Router = () => {
return (
<BrowserRouter>
<Nav />
<Routes>
<Route path="/" element= {<App />} />
<Route path="/login" element = {<Login />} />
</Routes>
</BrowserRouter>
);
};
export default Router;
Sass์ ๊ฐ์ฅ ๊ธฐ๋ณธ์ ์ธ ๊ธฐ๋ฅ์ผ๋ก Nesting ์ด๋ผ๋ ๊ฒ์ด ์๋๋ฐ, JSX ์ต์์ ์์์ 'className'์ ์ปดํฌ๋ํธ ์ด๋ฆ๊ณผ ๋์ผํ๊ฒ ์ค์ ํด์ฃผ๊ณ , '.scss' ํ์ผ์์๋ ์ต์์ ์์ ์ ์ชฝ์์ ํ์ ์์์ ์คํ์ผ ์์ฑ์ ์ ์ํ ์ ์๋๋ก ์ฝ๋๋ฅผ ์์ฑํ๋ฉด ๋๋ค.
๐ CSS
nav ul{
margin :0;
padding: 0;
list-style: none;
}
nav li {
display : inline-block;
}
nav a {
display: block;
padding: 6px 12px;
text-decoration : none;
}
๐ SCSS
nav{
ul{
margin : 0;
padding: 0;
list-style: none;
li{
display: inline-block;
}
}
a{
display: block;
padding: 6px 12px;
text-decoration: none;
}
}
๐ CSS
.login-container{
display: flex;
justify-content: center;
align-items: center;
}
button{
width: 200px;
height: 100px;
background-color: blue;
}
button:hover{
background-color: red;
cursor: pointer;
}
input{
background-color: blue;
}
input:focus{
background-color: red;
}
๐ SCSS
$theme-color: blue;
$border-style: 1px black solid;
@mixin flex-center{
display: flex;
justify-content: center;
align-items: center;
}
.login-container{
@include flex-center;
button{
width: 200px;
height: 100px;
background-color: $theme-color;
&:hover{
backgound-color: red;
cursor: pointer;
}
}
input{
background-color: $theme-color;
}
}