Toggle navigation
Toggle navigation
This project
Loading...
Sign in
MotherProject
/
myYoutube
Go to a project
Toggle navigation
Toggle navigation pinning
Projects
Groups
Snippets
Help
Project
Activity
Repository
Pipelines
Graphs
Issues
0
Merge Requests
0
Wiki
Snippets
Network
Create a new issue
Builds
Commits
Issue Boards
Authored by
Flare-k
2020-06-16 21:08:27 +0900
Browse Files
Options
Browse Files
Download
Email Patches
Plain Diff
Commit
e0d16dccf8a9188da0b0d954e9ecf333b1ab57e8
e0d16dcc
1 parent
e8633805
[Authenticate] Github Login
Hide whitespace changes
Inline
Side-by-side
Showing
10 changed files
with
116 additions
and
13 deletions
.gitignore
app.js
controllers/userController.js
init.js
package.json
passport.js
routers/globalRouter.js
routes.js
text/study.txt
views/partials/socialLogin.pug
.gitignore
View file @
e0d16dc
...
...
@@ -117,4 +117,6 @@ dist
package-lock.json
uploads
static
\ No newline at end of file
static
text
*.txt
\ No newline at end of file
...
...
app.js
View file @
e0d16dc
import
dotenv
from
"dotenv"
;
import
express
from
"express"
;
import
morgan
from
"morgan"
;
import
helmet
from
"helmet"
;
...
...
@@ -12,9 +13,9 @@ import routes from "./routes";
import
userRouter
from
"./routers/userRouter"
;
import
videoRouter
from
"./routers/videoRouter"
;
import
globalRouter
from
"./routers/globalRouter"
;
import
"./passport"
;
dotenv
.
config
();
const
app
=
express
();
const
CokieStore
=
MongoStore
(
session
);
...
...
@@ -36,6 +37,7 @@ app.use(
store
:
new
CokieStore
({
mongooseConnection
:
mongoose
.
connection
}),
})
);
app
.
use
(
passport
.
initialize
());
app
.
use
(
passport
.
session
());
...
...
controllers/userController.js
View file @
e0d16dc
...
...
@@ -15,7 +15,7 @@ export const postJoin = async (req, res, next) => {
res
.
render
(
"join"
,
{
pageTitle
:
"Join"
});
}
else
{
try
{
const
user
=
await
User
.
create
({
const
user
=
await
User
({
name
,
email
,
});
...
...
@@ -33,16 +33,57 @@ export const postJoin = async (req, res, next) => {
export
const
getLogin
=
(
req
,
res
)
=>
res
.
render
(
"login"
,
{
pageTitle
:
"Login"
});
export
const
postLogin
=
passport
.
authenticate
(
"local"
,
{
failureRedirect
:
routes
.
login
,
successRedirect
:
routes
.
home
,
});
// 깃허브 로그인
export
const
githubLogin
=
passport
.
authenticate
(
"github"
);
// call back 받아오는 함수
export
const
githubLoginCallback
=
async
(
accessToken
,
refreshToken
,
profile
,
cb
)
=>
{
// callback 정보 확인용 console.log
// console.log(accessToken, refreshToken, profile, cb);
const
{
_json
:
{
id
,
avatar_url
:
avatarUrl
,
name
,
email
},
}
=
profile
;
// profile 파라미터로 가져온 내용들
// 파라미터로 받은 cb함수가 처리해준다. True->정보를 쿠키에.. False->error
try
{
const
user
=
await
User
.
findOne
({
email
});
if
(
user
)
{
user
.
githubId
=
id
;
user
.
save
();
return
cb
(
null
,
user
);
}
const
newUser
=
await
User
.
create
({
email
,
name
,
githubId
:
id
,
avatarUrl
,
});
return
cb
(
null
,
newUser
);
}
catch
(
error
)
{
return
cb
(
error
,
null
);
}
};
export
const
postGithubLogin
=
(
req
,
res
)
=>
{
res
.
redirect
(
routes
.
home
);
};
// 로그아웃을 클릭하면 LogOut페이지로 가는 것 대신에, 로그아웃을 처리한 후
// home 페이지로 Redirect로 표현할 것이다.
// 즉, 초반에 만들어둔 logout.pug는 삭제해도 좋다.
export
const
logout
=
(
req
,
res
)
=>
{
// res.render("logout", { pageTitle: "Logout" });
req
.
logout
();
res
.
redirect
(
routes
.
home
);
};
...
...
init.js
View file @
e0d16dc
dotenv
.
config
();
import
dotenv
from
"dotenv"
;
import
app
from
"./app"
;
// app.js에서 export default app했기 때문에 불러올 수 있다.
import
"./db"
;
...
...
@@ -5,8 +6,6 @@ import "./models/Video";
import
"./models/Comment"
;
import
"./models/User"
;
dotenv
.
config
();
const
PORT
=
process
.
env
.
PORT
||
80
;
const
handleListening
=
()
=>
{
...
...
package.json
View file @
e0d16dc
...
...
@@ -35,6 +35,7 @@
"multer"
:
"^1.4.2"
,
"node-sass"
:
"^4.14.1"
,
"passport"
:
"^0.4.1"
,
"passport-github"
:
"^1.1.0"
,
"passport-local"
:
"^1.0.0"
,
"passport-local-mongoose"
:
"^6.0.1"
,
"postcss-loader"
:
"^3.0.0"
,
...
...
passport.js
View file @
e0d16dc
import
dotenv
from
"dotenv"
;
import
passport
from
"passport"
;
import
GithubStrategy
from
"passport-github"
;
import
User
from
"./models/User"
;
import
{
githubLoginCallback
}
from
"./controllers/userController"
;
import
routes
from
"./routes"
;
dotenv
.
config
();
// passport에게 strategy(로그인 방식)를 사용하도록 요청한다.
// passportLocalMongooser가 제공하는 strategy를 이용한다. -> username과 password를 사용.
passport
.
use
(
User
.
createStrategy
());
passport
.
use
(
new
GithubStrategy
(
{
clientID
:
process
.
env
.
GH_ID
,
clientSecret
:
process
.
env
.
GH_SECRET
,
callbackURL
:
`http://localhost:80
${
routes
.
githubCallback
}
`
,
},
githubLoginCallback
)
);
passport
.
serializeUser
(
User
.
serializeUser
());
passport
.
deserializeUser
(
User
.
deserializeUser
());
...
...
routers/globalRouter.js
View file @
e0d16dc
import
express
from
"express"
;
import
passport
from
"passport"
;
import
routes
from
"../routes"
;
import
{
home
,
search
}
from
"../controllers/videoController"
;
import
{
logout
,
getJoin
,
postJoin
,
getLogin
,
logout
,
postJoin
,
postLogin
,
githubLogin
,
postGithubLogin
,
}
from
"../controllers/userController"
;
import
{
onlyPublic
}
from
"../middlewares"
;
import
{
onlyPublic
,
onlyPrivate
}
from
"../middlewares"
;
const
globalRouter
=
express
.
Router
();
...
...
@@ -20,5 +23,15 @@ globalRouter.post(routes.login, onlyPublic, postLogin);
globalRouter
.
get
(
routes
.
home
,
home
);
globalRouter
.
get
(
routes
.
search
,
search
);
globalRouter
.
get
(
routes
.
logout
,
logout
);
globalRouter
.
get
(
routes
.
logout
,
onlyPrivate
,
logout
);
globalRouter
.
get
(
routes
.
gitHub
,
githubLogin
);
// callback으로 받아온 정보를 다뤄야하는 함수도 필요하다.
// callback으로 가면 passport.authenticate 처리 해줘야함
globalRouter
.
get
(
routes
.
githubCallback
,
passport
.
authenticate
(
"github"
,
{
failureRedirect
:
"/login"
}),
postGithubLogin
);
export
default
globalRouter
;
...
...
routes.js
View file @
e0d16dc
...
...
@@ -18,6 +18,10 @@ const VIDEO_DETAIL = "/:id";
const
EDIT_VIDEO
=
"/:id/edit"
;
const
DELETE_VIDEO
=
"/:id/delete"
;
// Github
const
GITHUB
=
"/auth/github"
;
const
GITHUB_CALLBACK
=
"/auth/github/callback"
;
const
routes
=
{
home
:
HOME
,
join
:
JOIN
,
...
...
@@ -57,6 +61,8 @@ const routes = {
return
DELETE_VIDEO
;
}
},
gitHub
:
GITHUB
,
githubCallback
:
GITHUB_CALLBACK
,
};
// template에서 직접 접근이 필요한 경우 함수로 바꿔준다.
export
default
routes
;
...
...
text/study.txt
View file @
e0d16dc
...
...
@@ -2,4 +2,26 @@ express session을 설치한다. npm install express-session
postJoin은 이메일과 비밀번호를 전달하고 next()가 호출되어 postLogin으로 간다.
connect mongo를 통해 저장소를 생성한다.
\ No newline at end of file
connect mongo를 통해 저장소를 생성한다.
- 인증에 대한 정리 -
유저네임과 비밀번호를 이용한 방식(local 방식)은 비교적 간단하다. 유저네임과 비밀번호를 post 방식으로 전달하고
설치해준 플러그인인 Mongoose가 자동으로 체크를 해준다. 만약 비밀번호가 맞으면 passport에게 맞다고 알려주고
passport는 쿠키를 생성한다.
소셜로그인의 경우에는 조금 다르다
먼저 사용자는 깃허브 사이트로 이동하게 되고 거기에서 권한 승인을 한다.
그 이후에 깃헙 사이트는 우리에게 해당 사용자의 정보를 보내주는데 /auth/github/callback이라는 URL로 오게 된다
그렇게 되면 passport가 함수를 호출하는데 githubLoginCallback이라는 우리가 만들어준 함수이다.
passport가 이함수를 실행하는 것이다.
이 함수는 모든 사용자 프로필 정보를 받고 이 정보로 필요한 것을 할 수 있다.
githubLoginCallback 함수의 한가지 조건은 callback(cb) 함수를 리턴해야하는 것이다.
cb 함수를 실행시켜서 에러가 있는지 유저가 있는지 알려줘야 한다.
에러가 존재하면 passport는 에러가 있구나 유저는 없구나하고 끝내고
유저가 존재하면 passport는 이 유저를 가져와 쿠키를 만들고 저장한다.
이렇게 저장된 쿠키를 브라우저로 보내게 된다.
globalRouter에서 깃허브로 갈때 githubLogin이 실행되는데 깃허브로 보내주는 역할을 한다.
그리고 githubCallback(URL)로 돌아왔을 때 passport는 사용자가 알려준 함수인 githubLoginCallback을 실행시킨다.
만약 user를 찾으면 passport는 통과시키며 postGithubLogin을 실행하고 홈으로 리다이렉트한다.
...
...
views/partials/socialLogin.pug
View file @
e0d16dc
.social-login
button.social-login--github
span
i.fab.fa-github
| Continue with Github
a(href=routes.gitHub)
span
i.fab.fa-github
| Continue with Github
button.social-login--facebook
span
i.fab.fa-facebook
...
...
Please
register
or
login
to post a comment