快速搭建Node.js(Express)使用者註冊、登入以及授權

MrNow發表於2019-05-09

專案準備

  1. 建立一個資料夾,這裡叫 EXPRESS-AUTH
  2. npm init -y

啟動服務

  1. 新建一個server.js 或者 app.js
  2. npm i express
  3. 開啟埠,啟動服務
// server.js
// 引入 express
const express = require('express')
// 建立伺服器應用程式
const app = express()

app.get('/user', async (req, res) => {
  res.send('hello node.js')
})

app.listen(3001, () => {
  console.log('http://localhost:3001')
})
複製程式碼

在命令列執行nodemon .\server.js命令啟動服務

注:nodemon 命令需要全域性安裝 nodemon(npm install --global nodemon), 在瀏覽器訪問/user時如下,則說明開啟成功

快速搭建Node.js(Express)使用者註冊、登入以及授權

實現簡單的 GET 請求介面

  1. 建立處理 get 請求的介面
app.get('/api/get', async (req, res) => {
  res.send('hello node.js')
})
複製程式碼
  1. 在vscode商店中下載 REST Client
    快速搭建Node.js(Express)使用者註冊、登入以及授權
    新建一個 test.http 檔案測試介面,點選Send Request傳送請求
// test.http
@url=http://localhost:3001/api

### 
get {{url}}/user
複製程式碼

快速搭建Node.js(Express)使用者註冊、登入以及授權
如上圖,get 請求成功

操作 MongoDB 資料庫

  1. 連線資料庫
  • 安裝 mongodb 資料庫
  • 在需要啟動的碟符根目錄下新建 data/db 資料夾
  • 在命令列對應的碟符下輸入 mongod 命令,即可開啟服務
  • 有需要可以下載NoSQLBooster for MongoDB軟體
  1. 建立資料庫模型
  • npm i mongoose
  • 新建 model.js 運算元據庫
// 引入 mongoose 
const mongoose = require('mongoose')

// 連線資料庫,自動新建 ExpressAuth 庫
mongoose.connect('mongodb://localhost:27017/ExpressAuth', {
  useNewUrlParser: true,
  useCreateIndex: true
})

// 建立使用者表
const UserSchema = new mongoose.Schema({
  username: {
    type: String,
    unique: true
  },
  password: {
    type: String,
  }
})

// 建立使用者資料庫模型
const User = mongoose.model('User', userSchema)

module.exports = { User }
複製程式碼

簡單的 POST 請求

  1. 建立處理 POST 請求的介面
// server.js
app.post('/api/register', async (req, res) => {
  console.log(req.body);
  res.send('ok')
})
app.use(express.json()) // 設定後可以用 req.body 獲取 POST 傳入 data
複製程式碼
  1. 設定 /api/register
###
POST {{url}}/register
Content-Type: application/json

{
  "username": "user1",
  "password": "123456"
}
複製程式碼
  1. 註冊使用者
// server.js
app.post('/api/register', async (req, res) => {
  // console.log(req.body);
  const user = await User.create({
    username: req.body.username,
    password: req.body.password
  })
  res.send(user)
})
複製程式碼

資料庫裡多了一條使用者資料:

快速搭建Node.js(Express)使用者註冊、登入以及授權

密碼 bcrypt 加密

  1. npm i bcrypt
  2. 在 model.js 中設定密碼入庫前加密,這裡的 hashSync方法接受兩個引數,val 表示傳入的 password,10表示加密的等級,等級越高,所需轉化的時長越長

快速搭建Node.js(Express)使用者註冊、登入以及授權

使用者登入密碼解密

  1. 在 server.js 中新增處理 /login 的POST請求
app.post('/api/login', async (req, res) => {
  const user = await User.findOne({
    username: req.body.username
  })
  if (!user) {
    return res.status(422).send({
      message: '使用者名稱不存在'
    })
  }
  // bcrypt.compareSync 解密匹配,返回 boolean 值
  const isPasswordValid = require('bcrypt').compareSync(
    req.body.password,
    user.password
  )
  if (!isPasswordValid) {
    return res.status(422).send({
      message: '密碼無效'
    })
  }
  res.send({
    user
  })
})
複製程式碼

登入新增 token

  1. 安裝 jsonwebtoken npm i jsonwebtoken
  2. 引入 jsonwebtoken,自定義金鑰
// 引入 jwt
const jwt = require('jsonwebtoken')
// 解析 token 用的金鑰
const SECRET = 'token_secret'
複製程式碼
  1. 在登入成功時建立 token
/* 
生成 token
jwt.sign() 接受兩個引數,一個是傳入的物件,一個是自定義的金鑰
*/
const token = jwt.sign({ id: String(user._id) }, SECRET)
res.send({
    user,
    token
})
複製程式碼

這樣我們在傳送請求時,就能看到建立的 token

快速搭建Node.js(Express)使用者註冊、登入以及授權

解密 token 獲取登入使用者

  1. 先在 server.js 處理 token
app.get('/api/profile', async (req, res) => {
  const raw = String(req.headers.authorization.split(' ').pop())
  // 解密 token 獲取對應的 id
  const { id } = jwt.verify(raw, SECRET)
  req.user = await User.findById(id)
  res.send(req.user) 
})
複製程式碼
  1. 傳送請求,這裡的請求頭是複製之前測試用的 token
### 個人資訊
get {{url}}/profile
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6IjVjZDI5YjFlMTIwOGEzNDBjODRhNDcwMCIsImlhdCI6MTU1NzM2ODM5M30.hCavY5T6MEvMx9jNebInPAeCT5ge1qkxPEI6ETdKR2U
複製程式碼

服務端返回如下圖,則說明解析成功

快速搭建Node.js(Express)使用者註冊、登入以及授權


本文參考1小時搞定NodeJs(Express)的使用者註冊、登入和授權

配套完整程式碼和註釋見Github

相關文章