前端实现 MD5 + AES 加密的安全登录请求

发布于:2025-08-12 ⋅ 阅读:(20) ⋅ 点赞:(0)

在实际开发中,直接将用户的明文密码传输到后端存在较大安全风险。为了提高安全性,常见的做法是在前端发送前先对密码进行 MD5 哈希,再用 AES 对称加密 进行二次加密,然后使用 application/x-www-form-urlencoded 格式发送给后端。本文将介绍如何在 Vue 项目中实现这一登录流程。


一、需求背景

后端要求登录接口接收三个字段:

  • account:用户名

  • password:先 MD5 再 AES 加密的密码

  • grant_type:固定值 'password'

接口需要使用 POST 方法,且 Content-Type 必须为 application/x-www-form-urlencoded


二、依赖安装

我们需要三个依赖库:

npm install qs js-md5 crypto-js
  • qs:将对象序列化为 key=value&key=value 格式

  • js-md5:实现 MD5 哈希算法

  • crypto-js:实现 AES 对称加密


三、AES 加密工具封装

创建 src/utils/encrypt.js

import CryptoJS from 'crypto-js'

// 注意:key 和 iv 必须与后端保持一致
const key = CryptoJS.enc.Utf8.parse('1234567890abcdef') // 16 字节密钥
const iv = CryptoJS.enc.Utf8.parse('abcdef1234567890') // 16 字节向量

export const aesEncryption = {
  encrypt(word) {
    const srcs = CryptoJS.enc.Utf8.parse(word)
    const encrypted = CryptoJS.AES.encrypt(srcs, key, {
      iv: iv,
      mode: CryptoJS.mode.CBC,
      padding: CryptoJS.pad.Pkcs7
    })
    return encrypted.toString()
  },
  decrypt(ciphertext) {
    const decrypted = CryptoJS.AES.decrypt(ciphertext, key, {
      iv: iv,
      mode: CryptoJS.mode.CBC,
      padding: CryptoJS.pad.Pkcs7
    })
    return decrypted.toString(CryptoJS.enc.Utf8)
  }
}

安全提示:生产环境中 keyiv 不建议直接写死在前端,可通过后端下发、动态生成等方式提高安全性。


四、改造登录接口

src/api/auth.js

import qs from 'qs'
import request from '@/utils/request'
import { httpUri } from '@/config'

// 登录接口
export function login(data) {
  return request({
    url: `${httpUri}/api/oauth/Login`,
    method: 'post',
    headers: {
      'Content-Type': 'application/x-www-form-urlencoded'
    },
    data: qs.stringify(data) // 转为 x-www-form-urlencoded 格式
  })
}

五、调用示例

import md5 from 'js-md5'
import { aesEncryption } from '@/utils/encrypt'
import { login } from '@/api/auth'
import { ElMessage } from 'element-plus'

// 假设这是 Vue3 中的表单
const form = ref({
  user: '',
  password: ''
})

async function handleLogin() {
  if (!form.value.user || !form.value.password) {
    ElMessage.warning('请输入账号和密码')
    return
  }

  try {
    // 1. MD5 加密
    const md5Pwd = md5(form.value.password)

    // 2. AES 再加密
    const encryptedPwd = aesEncryption.encrypt(md5Pwd)

    // 3. 构造请求参数
    const payload = {
      account: form.value.user,
      password: encryptedPwd,
      grant_type: 'password'
    }

    // 4. 调用登录接口
    const res = await login(payload)

    // 5. 登录成功处理
    console.log('登录成功', res.data)
    ElMessage.success('登录成功')
  } catch (err) {
    console.error('登录失败', err)
    ElMessage.error(err?.response?.data?.message || '登录失败')
  }
}

六、执行流程图

用户输入密码
     ↓
 MD5 哈希
     ↓
AES 加密 (key + iv)
     ↓
x-www-form-urlencoded 序列化
     ↓
POST 请求发送到后端

七、总结

通过 MD5 + AES 双重加密,我们在一定程度上减少了密码在传输过程中的风险;配合 application/x-www-form-urlencoded 提交格式,可以更好地适配一些后端框架的解析方式。

完整实现中需要注意:

  1. keyiv 必须与后端保持一致。

  2. 加密并不能完全防止泄露,HTTPS 仍然是必不可少的传输加密手段。

  3. 如果想进一步简化调用,可以将加密逻辑放到 login 方法内部或请求拦截器中,调用时只传明文密码。


网站公告

今日签到

点亮在社区的每一天
去签到