首页 > 编程语言 >Node.js+Express+Koa2开发接口学习笔记(六)

Node.js+Express+Koa2开发接口学习笔记(六)

时间:2024-02-09 14:55:57浏览次数:21  
标签:Node username const Express escape js sql password

预防sql注入

sql注入

  • 最原始、最简单的攻击,从有了web2.0就有了sql注入攻击
  • 攻击方式:输入一个sql片段,最终拼接成一段攻击代码
  • 预防措施:使用mysql的escape函数处理输入内容即可

例如登录,访问http://localhost:8080/login.html

正常情况下是输入正确的用户名和密码来进行登录,这个登录是根据传入的username和password参数拼接sql语句来实现的。

// src/controller/user.js
const login = ({ username, password }) => {
  const sql = `
    select username,realname from users where username='${username}' and password='${password}'
  `;
  return exec(sql).then((rows) => {
    return rows[0] || {};
  });
};
-- 拼接出来的语句
select username,realname from users where username='zhangsan' and password='123456'; 

因为username和password是传进去的,如果传进去的是(zhangsan'-- ),拼接语句就变成了

-- 拼接出来的语句
select username,realname from users where username='zhangsan'-- ' and password='123456'; 

在sql中 -- +空格是用来写注释语句的,可以看到上面的拼接语句密码处已经是无效的了。在登录页输入(zhangsan'-- )竟然可以登录成功,并且可以新建博客等操作。

如何预防?

在mysql.js文件中导出mysqlescape函数

const mysql = require("mysql");
const { MYSQL_CONF } = require("../conf/db");
...
module.exports = {
  exec,
  escape: mysql.escape,
};

然后在 src/controller/user.js使用该函数对参数进行处理,以及修改去掉拼接语句处的单引号

const { exec, escape } = require("../db/mysql");
const login = ({ username, password }) => {
  username = escape(username);
  password = escape(password);
  const sql = `
    select username,realname from users where username=${username} and password=${password}
  `;
  console.log("sql", sql);
  return exec(sql).then((rows) => {
    return rows[0] || {};
  });
};
module.exports = {
  login,
};

在登录页输入(zhangsan'-- )已经提示登录错误了,说明预防sql注入成功。通过escape函数后得到的拼接语句变成了

select username,realname from users where username='zhangsan\'-- ' and password='1'

('--)escape去掉特殊化,只当作普通字符串,被整体包裹起来而非起到注释作用。

XSS攻击

  • 攻击方式:在页面展示内容中掺杂js代码,以获取网页信息
  • 预防措施:转换生成js的特殊字符
& -> &
< -> &lt;
> -> &gt;
" -> &quot;
' -> &#x27;
/ -> &#x2F;

例如在新建博客页面中,在标题处输入以下文本

<script>alert(document.cookie)</script>

它会在创建成功后返回管理页面执行脚本,弹出获取到的信息。

安装工具:npm i xss --save,使用这个工具可以转换生成js的特殊字符

在controller->blog.js

const xss = require("xss");

const newBlog = (blogData = {}) => {
  	const title = xss(blogData.title);
 	const content = xss(blogData.content);
	...
}

在新建博客页面中,在标题或内容处输入刚才的文本,可能会由于sql存储字符串长度限制报错,但是在控制台可以看到语句经过xss转义变成了不具有攻击能力的语句:

&lt;script&gt;alert(document.cookie)&lt;/script&gt;

用户加密

  • 万一数据库被用户攻破,最不应该泄漏的就是用户信息
  • 攻击方式:获取用户名和密码,再去尝试登录其他系统
  • 预防措施:将密码加密,即使拿到密码也不知道明文

在utils->crypt.js,通过node提供的crypto库编写加密函数

const crypto = require("crypto");

// 密钥
const SECRET_KEY = "WJiol_8776#";

// md5加密
function md5(content) {
  let md5 = crypto.createHash("md5");
  return md5.update(content).digest("hex");
}
// 加密函数
function genPassword(password) {
  const str = `password=${password}&key=${SECRET_KEY}`;
  return md5(str);
}
module.exports = {
  genPassword,
};

md5加密生出来的字符串是32位长度,需要去修改数据库中password的长度。

通过genPassword('123')可以看到加密后的密码为524ab85686df0e52ada43b11b53cce35,为了方便登录验证,将数据库中密码为123的其中一位用户密码改为加密后的密码。

在controller->login.js中将接收到的password参数进行加密

const { exec, escape } = require("../db/mysql");
const { genPassword } = require("../utils/crypt");
const login = ({ username, password }) => {
  username = escape(username);

  // 生成加密密码
  password = genPassword(password);
  password = escape(password);
    
  const sql = `
    select username,realname from users where username=${username} and password=${password}`;
  return exec(sql).then((rows) => {
    return rows[0] || {};
  });
};
module.exports = {
  login,
};

分别验证被加密以及未加密的用户登录。

标签:Node,username,const,Express,escape,js,sql,password
From: https://www.cnblogs.com/Small-Windmill/p/18012470

相关文章

  • Express+Koa2开发接口学习笔记(五)
    日志介绍日志可以记录系统的日常和错误行为系统日志有2种类型:①访问日志accesslog(server端最重要的日志)②自定义日志(包括自定义事件、错误记录等)系统日志通常是写在一个文件中,而不是写进Mysql或者redis中。nodejs文件操作新建一个项目file-text在目录下创建test.js和data......
  • C#的DataTable、List、Dictionary、JSON、XML之间的转换
    1.DataTable转List//创建一个DataTable对象DataTabledataTable=newDataTable();//将DataTable转换为List<DataRow>List<DataRow>dataList=dataTable.AsEnumerable().ToList(); 2、DataTable转Dictionary//创建一个DataTable对象DataTabledataTable=new......
  • lrn-tfjs-merge-6
    TensorFlow.js学习手册(七)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0结语“那么为什么要尝试预测未来,如果这是如此困难,几乎不可能呢?因为做出预测是一种在我们看到自己朝着危险方向漂移时发出警告的方式。因为预测是指出更安全、更明智的途径的有用方式。最重......
  • lrn-tfjs-merge-5
    TensorFlow.js学习手册(六)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0第十一章:迁移学习“向他人的错误学习。你活不到足够长的时间来犯所有的错误。”—埃莉诺·罗斯福拥有大量数据、经过实战检验的模型结构和处理能力可能是具有挑战性的。能不能简单点?在......
  • lrn-tfjs-merge-4
    TensorFlow.js学习手册(五)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0第九章:分类模型和数据分析“先见之明,后事之师。”—AmeliaBarr你不仅仅是把数据丢进模型中是有原因的。神经网络以极快的速度运行并执行复杂的计算,就像人类可以瞬间做出反应一样。然而......
  • lrn-tfjs-merge-3
    TensorFlow.js学习手册(四)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0第七章:模型制作资源“通过寻找和失误我们学习。”—约翰·沃尔夫冈·冯·歌德你不仅限于来自TensorFlowHub的模型。每天都有新的令人兴奋的模型被推文、发表和在社区中受到关注。这......
  • lrn-tfjs-merge-2
    TensorFlow.js学习手册(三)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0第五章:介绍模型“他从哪里弄来那些美妙的玩具?”—杰克·尼科尔森(蝙蝠侠)现在您已经进入大联盟。在第二章中,您访问了一个完全训练好的模型,但您根本不需要了解张量。在这里的第五章,您将能......
  • lrn-tfjs-merge-1
    TensorFlow.js学习手册(二)原文:LearningTensorFlow.js译者:飞龙协议:CCBY-NC-SA4.0第三章:引入张量“哇!”—基努·里维斯(《比尔和特德的冒险》)我们已经多次提到张量这个词,它是TensorFlow.js中的主要词汇,所以是时候了解这些结构是什么了。这一关键章节将让您亲身体验管......
  • js 事件冒泡 事件捕获
    <!DOCTYPEhtml><htmllang="en"><head><metacharset="UTF-8"/><metaname="viewport"content="width=device-width,initial-scale=1.0"/><title>test</title>......
  • Chrome修改添加JS与dll交互
    注入dll后拦截js相关函数,可以通讯以及控制安全沙箱问题前面有写文章为了方便快速,使用Uint8Array::Set函数拦截之前尝试了crypto.subtle相关的函数,这些函数速度很慢,而且是异步,很不方便C++的dll代码BOOL CChrome::HookUint8ArraySetByte(){ BYTE *pCode; BOOL......