$ npm install gh-pages
gh-pages
란, 프로젝트 결과물을 github pages에 publish 업로드 할 수 있도록 도와주는 패키지입니다. package.json 파일에 있는 scripts 속성에 build 명령어를 실행하면, 우리가 만든 결과물을 코드가 압축되고 모든 것이 최적화된 상태인 production ready code로 생성해서 build 폴더에 담겨집니다.
"homepage": "https://eunjeong-97.github.io/commerce_web_211126",
// 속성들 생략
"scripts": {
"build": "webpack --mode production",
"predeploy": "npm run build",
"deploy": "gh-pages -d build"
},
홈페이지 URL의 구조는 https://{github 아이디}.github.io/{github repository 이름}
입니다.
$ npm run deploy
설치한 gh-pages 패키지를 실행시키고 최적화된 코드들을 build
라는 디렉터리로 가져가는데, 이러한 build 작업을 하고 deploy를 각각 해주면 번거롭기 때문에 predeploy
명령어를 만듭니다.
deploy 명령어를 입력하면 predeploy가 자동으로 먼저 실행되기 때문에 혹시나 build 폴더가 없어도 다시 생성할 수 있습니다. 따라서 프로젝트에서 코드를 변경하고 나서 npm run deploy
명령어를 실행해주면 됩니다.
이러한 과정을 통해, gh-pages
패키지는 build폴더에 있는 production ready code들을 package.json파일의 homepage 속성에 적은 URL의 웹 사이트로 업로드 합니다.
main branch에서 배포를 하게 되면 URL에서 readme.md의 내용만 보이기 때문에 github repository branch 에서 gh-pages
branch 생성된거 확인하고, Github repository의 settings에서 Source
항목에 gh-pages
branch 로 배포한다고 수정합니다.
404.html
파일 생성기본적으로 Github Pages에서는 SPA기능을 지원하지 않기 때문에 동적인 URL을 입력을 하면 인식을 못해 404Error페이지를 보여줍니다. 따라서 저희는 404.html
을 만들어서 해당 URL을 쿼리로 만들어서 리다이렉션을 하도록 하겠습니다.
MIT license 의 오픈 소스입니다. 프로젝트 포함시 라이센스를 명시해주세요.
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Single Page Apps for GitHub Pages</title>
<script type="text/javascript">
// Single Page Apps for GitHub Pages
// https://github.com/rafrex/spa-github-pages
// Copyright (c) 2016 Rafael Pedicini, licensed under the MIT License
// ---------------------------------------------- ------------------------
// This script takes the current url and converts the path and query
// string into just a query string, and then redirects the browser
// to the new url with only a query string and hash fragment,
// e.g. http://www.foo.tld/one/two?a=b& c=d#qwe, becomes
// http://www.foo.tld/?p=/one/two& q=a=b~and~c=d#qwe
// Note: this 404.html file must be at least 512 bytes for it to work
// with Internet Explorer (it is currently > 512 bytes)
// If you're creating a Project Pages site and NOT using a custom domain,
// then set segmentCount to 1 (enterprise users may need to set it to > 1).
// This way the code will only replace the route part of the path, and not
// the real directory in which the app resides, for example:
// https://username.github.io/repo-name/one/two? a=b&c=d#qwe becomes
// https://username.github.io/repo-name/? p=/one/two&q=a=b~and~c=d#qwe
// Otherwise, leave segmentCount as 0.
var segmentCount = 1;
var l = window.location;
l.replace(
l.protocol + '//' + l.hostname + (l.port ? ':' + l.port : '') +
l.pathname.split('/').slice(0, 1 + segmentCount).join('/') + '/?p=/' +
l.pathname.slice(1).split('/').slice (segmentCount).join('/').replace(/&/g, '~and~') +
(l.search ? '&q=' + l.search.slice(1) .replace(/&/g, '~and~') : '') +
l.hash
);
</script>
</head>
<body>
</body>
</html>
index.html
수정404.html 을 통해서 쿼리로 변경된 URL 을 index.html 에서 받게됩니다. 이 때 index.html 에서 해당 쿼리를 해석하여 올바른 URL 로 변경하도록 스크립트를 추가합니다.
MIT license 의 오픈 소스입니다. 프로젝트 포함시 라이센스를 명시해주세요.
<head>
...
<!-- Start Single Page Apps for GitHub Pages -->
<script type="text/javascript">
// Single Page Apps for GitHub Pages
// https://github.com/rafrex/spa-github-pages
// Copyright (c) 2016 Rafael Pedicini, licensed under the MIT License
// ----------------------------------------------------------------------
// This script checks to see if a redirect is present in the query string
// and converts it back into the correct url and adds it to the
// browser's history using window.history.replaceState(...),
// which won't cause the browser to attempt to load the new url.
// When the single page app is loaded further down in this file,
// the correct url will be waiting in the browser's history for
// the single page app to route accordingly.
(function (l) {
if (l.search) {
var q = {};
l.search.slice(1).split('&').forEach(function (v) {
var a = v.split('=');
q[a[0]] = a.slice(1).join('=').replace(/~and~/g, '&');
});
if (q.p !== undefined) {
window.history.replaceState(null, null,
l.pathname.slice(0, -1) + (q.p || '') +
(q.q ? ('?' + q.q) : '') +
l.hash
);
}
}
}(window.location))
</script>
<!-- End Single Page Apps for GitHub Pages -->
</head>
마지막으로 App.js의 BrowserRouter에 basename을 지정합니다.
해당 프로젝트의 경우 homepage의 URL이 "homepage": "https://eunjeong-97.github.io/commerce_web_211126",
이기 때문에 basename을 '/commerce_web_211126'
으로 설정해주면 됩니다.
// React v6버전으로 작성했습니다.
const App = () => {
return (
<Router basename='/commerce_web_211126'>
<Nav />
<Routes>
<Route path='/' element={<Home />} />
<Route path='/todolist' element={<ToDoList />} />
<Route path='/coin' element={<CoinTracker />} />
<Route path='/movie' element={<Movie />} />
<Route path='/movie/:id' element={<Detail />} />
<Route path='*' element={<NotFound />} />
</Routes>
</Router>
)
}