Nodejs使用Oauth2协议实现第三方登录GitLab

简述

目前有一个功能需要将自己创建的登录注册功能的httpserver使用GitLab来登录自己的系统,而不需要每次登录HttpServer系统都要重新注册一个用户。(注意:是GitLab而不是GitHub哦)

Oauth2原理部分

原理部分,我在找文档的时候发现一篇挺好,讲解清楚,在此粘贴:
https://www.cnblogs.com/wudimanong/p/10821215.html

Nodejs代码实现部分

废话不说,直接上代码
在server.js代码中使用了路由,所以你会发现连接多了user的路径

const express = require('express');
const http = require('http');
const app = express();
const bodyPaser = require('body-parser');
var path = require("path");
var session = require('express-session');
var interceptMw=require('./middlewares/interceptMw');
var serverHostConfig=require('./config/serverHost.json');

app.use(session({
    secret: 'sessiontest',//与cookieParser一致
    resave: true,
    saveUninitialized: true
}))

app.use(bodyPaser.urlencoded({ extended: false }))
app.use(bodyPaser.json())

//允许跨域
app.all('*', function (req, res, next) {
    //console.log(req.ip);
    res.header("Access-Control-Allow-Origin", "*");
    res.header("Access-Control-Allow-Headers", "Content-Type,Content-Length, Authorization, Accept,X-Requested-With");
    res.header("Access-Control-Allow-Methods", "PUT,POST,GET,DELETE,OPTIONS");
    res.header("X-Powered-By", ' 3.2.1')
    if (req.method == "OPTIONS") res.send(200);/*让options请求快速返回*/
    else next();
});

//使用中间件,将其余的请求直接通过
app.use(interceptMw)

//将user用户的路由引入
let userRouter = require('./router/userRouter');

app.use('/user', userRouter, function (req, res) {
    
})

app.listen(8081, () => {
    console.log('server start.....'+serverHostConfig.global_host);
    //设置全局的启动IP和端口,这样同一个局域网可以正常访问
    global.host = serverHostConfig.global_host;

})

1.GitLab用户的配置-在这里只是进行设置,后续代码中会需要本次设置产生的Application ID和Secret
在这里插入图片描述
在这里插入图片描述
本图中回调地址必须是代码中真正的回调地址路径,api的那个一定要勾选,否则你在回调方法调用的时候根据拿不到token,会报401错误,是因为你没有权限去获取gitlab的用户信息

  1. 登录页面
    在这里插入图片描述
    上图为登录页面,使用最原始的HTML代码实现,其中,代码如下:(其中global.host是自己设置的全局IP和端口)。在此项目中我设置的是:http://localhost:8081/
 <a href="${global.host}user/login/gitHubLogin">GitLab登录接口</a>
  1. 调用GitLab代码实现
    此处就需要使用到第一步设置后产生的两个值了,获取方式如下:还是在setting–Application下的设置
    在这里插入图片描述
    在这里插入图片描述
    我将Application ID和Secret写在了配置文件:

gitLabConfig.json–此处的git_clientId就是Application ID,git_clientSecret就是Secret,git_redirect_url就是回调地址的后半部分,全部路径是:http://localhost:8081/user/login/oauth2/code
config/gitLabConfig.json

{"git_clientId":"70f8c0e295c4224f49a2c7e27535e2f5ea498963d52b5b967b211697b5f819de",
    "git_clientSecret":"60528541f35cfcbf5b6da8fd765502ad7f7bae8f068d39756603aa78b25515d0",
    "git_redirect_url":"user/login/oauth2/code"}

config/serverHost.json

{"global_host":"http://localhost:8081/"}

那么下面就是主要代码实现:
router/userRouter.js

var express = require('express');
const bodyParser = require('body-parser');
//创建编码解析
var urlencodedParser = bodyParser.urlencoded({ extended: false })
//获取路由实例
var router = express.Router();
var gitLabConfig=require('../config/gitLabConfig.json');
var serverConfig=require('../config/serverHost.json');
var git_clientId = gitLabConfig.git_clientId;
var git_clientSecret = gitLabConfig.git_clientSecret;
var git_redirect_url = serverConfig.global_host+gitLabConfig.git_redirect_url;
router.get('/login/gitHubLogin', function (req, res) {
    //1、GitHub认证服务器地址,是公司搭建的内部Git_Lab地址,你根据你实际的地址改写
    var git_url = 'http://202.12.11.201/oauth/authorize';
    //var git_url = 'https://github.com/login/oauth/authorize';这个是gitHub的
    //生成并保存,此处用定值
    var git_state = '921921';
    //传递参数response_type、client_id、state、redirect_uri
    var git_param = 'response_type=code&' + 'client_id=' + git_clientId + '&state=' + git_state + '&redirect_uri=' + git_redirect_url;
    //使用重定向发送get请求
    res.redirect(git_url + '?' + git_param);
})

4.回调代码方法实现-此方法跟上述代码在同一个js中,其中这个方法的url必须是你在GitLab中设置的回调地址
router/userRouter.js

router.get('/login/oauth2/code', function (req, res) {
    let resData = req.query
    //1.验证state,如果不一致,又可能被CSRF攻击
    if (resData["state"] != '921921') {
        res.send('State验证失败');
    }
    //2、向GitHub认证服务器申请令牌,注意此处为POST请求
    //https://github.com/login/oauth/access_token-GitHub的
    request({
        url: 'http://202.11.11.201/oauth/token',
        method: 'POST',
        form: {
            "grant_type":"authorization_code",
            "code": resData["code"],
            "client_id": git_clientId,
            "client_secret": git_clientSecret,
            "redirect_uri": git_redirect_url,
            "state":'921921'
        }
    }, function (error, response, body1) {
        if (!error && response.statusCode == 200) {
            var tokenBody=JSON.parse(body1);
            //拿到了access_token,向资源服务器请求用户信息,携带access_token和tokenType
            //var  userUrl="https://api.github.com/user?access_token=" + accessToken + "&token_type=" + tokenType;
            var params="access_token=" + tokenBody.access_token + "&token_type=" + tokenBody.token_type;
            var userUrl = "http://202.11.11.201/api/v3/user?" + params;
            //申请用户资源
            request({
                url: userUrl,
                method:'GET'
                //下面的headers在跟GitHub中会用到,否则无法调用到获取用户信息
                // headers: {
                //     'User_Agent': 'zhoudadozhou'
                // }
            }, function (error, response, resbody) {
                if (!error && response.statusCode == 200) {
                    var userBody=JSON.parse(resbody)
                    req.session.user=userBody.name
                    //获取用户信息成功
                    res.send(htmlData.indexHtml(userBody.name+"通过第三方登录成功,他的邮箱是:"+userBody.email));
                } else {
                    res.send("获取用户信息失败:" + response.statusCode+":"+response.statusMessage);
                }
            })
        } else {
            res.send("获取token失败:"+response.statusCode+":"+response.statusMessage)
        }
    })
})

上述代码只是GitLab的主要实现代码,具体的包登录注册的包我会上传到博客,需要下载的可以下载使用。地址为:https://download.csdn.net/download/zhoudado921/12320154

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值