上一篇我们写了jdbc工具类:JDBCUtils ,在这里我们使用该工具类来连接数据库,

在之前我们使用 Statement接口下的executeQuery(sql)方法来执行搜索语句,但是这个接口并不安全,容易被注入攻击,注入攻击示例:

首先我们需要一个存放登录用户名密码的表:

use qy97;
create table login(
id int primary key auto_increment,
sname varchar(50),
pwd varchar(50)
);
insert into login values
(1,'zhangsan',''),
(2,'lisi','');

然后我们写代码实现登陆:

package com.zs.Demo;

import JDBCUtils.JDBCUtils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Scanner; public class SQLZhuRu {
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("请输入用户名:");
String name = sc.nextLine();
System.out.println("请输入密码:");
String pwd = sc.nextLine();
login(name,pwd);
} private static void login(String name, String pwd) {
Connection conn = JDBCUtils.getConnection();
String sql = "select * from login where sname='"+name+"'and pwd='"+pwd+"';";
System.out.println(sql);
Statement stat = null;
ResultSet rs=null;
try {
stat = conn.createStatement();
rs = stat.executeQuery(sql);
if (rs.next()) {
System.out.println("登陆成功,欢迎" + rs.getString("sname"));
} else {
System.out.println("登录失败!!");
}
} catch (SQLException e) {
e.printStackTrace();
} JDBCUtils.close(conn,stat,rs);
}
}

运行结果如下:

输入账号密码,然后在数据库中搜索,搜索到数据则登录成功,否则登录失败:

可是,当我们这样输入时,也能登陆成功:

从上面语句可以看出,执行的sql与语句是:select * from login where sname='lisi'and pwd='789 'or'1=1';

1=1是恒成立的,or 只要两边有一个为true 则为 true  ,所以登录成功,这是一个最简单的注入攻击,

解决方法:使用prepareStatement接口,以上一个例子为基础做修改

package com.zs.Demo;

import JDBCUtils.JDBCUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.Scanner; public class PerpareStatementDemo {
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
System.out.println("请输入用户名:");
String name = sc.nextLine();
System.out.println("请输入密码:");
String pwd = sc.nextLine();
try {
login(name,pwd);
} catch (Exception e) {
e.printStackTrace();
}
}
//传递变量name pwd给方法
private static void login(String name, String pwd) throws Exception {
Connection conn = JDBCUtils.getConnection();
// 设置?占位置,将查询的参数用?来替换
String sql="select * from login where sname=? and pwd=?";
PreparedStatement pre = conn.prepareStatement(sql);
// setObject方法来设置占位的?的值
pre.setObject(1,name);//设置第一个?的值为变量name
pre.setObject(2,pwd);//设置第二个?的值为变量pwd
ResultSet rs = pre.executeQuery();
if (rs.next()) {
System.out.println("登陆成功");
} else {
System.out.println("登录失败");
}
JDBCUtils.close(conn, pre, rs);
}
}

运行结果:

可以看出,在不改变sql语句的情况下将?替换为变量的值,当注入攻击时:

可以看出来这个接口更加安全,所以建议使用这个接口来实现增删改查;关于PrepareStatement接口:(官方文档)

  PrepareStatement接口:

    表示预编译的SQL语句的对象。

    SQL语句已预编译并存储在PreparedStatement对象中。 然后可以使用该对象多次有效地执行此语句。

    注意:setter方法( setShortsetString用于设置IN参数值必须指定与所定义的SQL类型的输入参数的兼容的类型,等等)。 例如,如果IN参数具有SQL类型INTEGER ,   则应使用方法setInt

使用PrepareStatemnet接口实现数据库的更新:

package com.zs.Demo;

import JDBCUtils.JDBCUtils;

import java.sql.Connection;
import java.sql.PreparedStatement; public class PrepareStatementDemo2 {
public static void main(String[] args) {
Connection conn = JDBCUtils.getConnection();
String sql="update login set sname = ? where id=?;";
PreparedStatement pst =null;
try {
pst = conn.prepareStatement(sql);
pst.setObject(1, "dijia");
pst.setObject(2,1);
pst.executeUpdate();
} catch (Exception e) {
e.printStackTrace();
}finally {
JDBCUtils.close(conn, pst);
}
}
}

java学习笔记38(sql注入攻击及解决方法)的更多相关文章

  1. SQL反模式学习笔记21 SQL注入

    目标:编写SQL动态查询,防止SQL注入 通常所说的“SQL动态查询”是指将程序中的变量和基本SQL语句拼接成一个完整的查询语句. 反模式:将未经验证的输入作为代码执行 当向SQL查询的字符串中插入别 ...

  2. Java学习之路- SQL注入

    用户名: __________ 密码:——————— 假如没有使用预处理的Statement 对象 拼接字符串查数据库的话,易收到sql注入攻击: 例如说 : mysql 中   #代表的是单行注释 ...

  3. 防止SQL注入攻击的一些方法小结

    SQL注入攻击的危害性很大.在讲解其防止办法之前,数据库管理员有必要先了解一下其攻击的原理.这有利于管理员采取有针对性的防治措施. 一. SQL注入攻击的简单示例. statement := &quo ...

  4. 网站mysql防止sql注入攻击 3种方法总结

    mysql数据库一直以来都遭受到sql注入攻击的影响,很多网站,包括目前的PC端以及手机端都在使用php+mysql数据库这种架构,大多数网站受到的攻击都是与sql注入攻击有关,那么mysql数据库如 ...

  5. 网站如何防止sql注入攻击的解决办法

    首先我们来了解下什么是SQL注入,SQL注入简单来讲就是将一些非法参数插入到网站数据库中去,执行一些sql命令,比如查询数据库的账号密码,数据库的版本,数据库服务器的IP等等的一些操作,sql注入是目 ...

  6. SQL注入原理与解决方法代码示例

    一.什么是sql注入? 1.什么是sql注入呢? 所谓SQL注入,就是通过把SQL命令插入到Web表单递交或输入域名或页面请求的查询字符串,最终达到欺骗服务器执行恶意的SQL命令,比如先前的很多影视网 ...

  7. 【初学Java学习笔记】SQL语句调优

    1, 对查询进行优化,应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引. 2,应尽量避免在 where 子句中对字段进行 null 值判断,创建表时NULL是默认 ...

  8. ASP代码审计学习笔记-1.SQL注入

    ASP注入漏洞 一.SQL注入的原因 按照参数形式:数字型/字符型/搜索型 1.数字型sql查询 sql注入原因: ID=49 这类注入的参数是数字型,SQL语句原貌大致如下: id=request. ...

  9. CTFHub Web题学习笔记(SQL注入题解writeup)

    Web题下的SQL注入 1,整数型注入 使用burpsuite,?id=1%20and%201=1 id=1的数据依旧出现,证明存在整数型注入 常规做法,查看字段数,回显位置 ?id=1%20orde ...

随机推荐

  1. 20190402Linux进阶命令week1.2

    Linux常用命令详解(week1_day1_2) aliasunaliasunamesuhostnamehistorywhichwcwwhowhoamipingkillseqdudffreedate ...

  2. rds下载备份集

    python版本[testuser@localhost tmp]$ python -VPython 2.7.5 需要提前安装RDS[root@localhost ~]# yum -y install ...

  3. [C++ Primer Plus] 第5章、循环和关系表达式(一)程序清单——指针自加减优先级

    程序5.4 #include<iostream> using namespace std; ; void main() { long long factorials[Size]; fact ...

  4. Java 运行时字符编码与解码

    以下仅为个人学习的记录,如有疏漏不妥之处,还请不吝赐教. Java在运行时字符char采用UTF-16进行编码. public class RuntimeEncoding { public stati ...

  5. Java基础学习-Java语言概述

    一.Java语言发展史 创始人:詹姆斯·高斯林(James Gosling) 公司:SUN——(Stanford University Network斯坦福大学网络公司) 1995年5月23日,Jav ...

  6. Sublime text 3 For LINUX 注册方法&关闭更新提示

    在 /etc/hosts 文件加入以下 127.0.0.1 www.sublimetext.com 127.0.0.1 license.sublimehq.com 然后再Sublime输入以下注册码 ...

  7. Odd Gnome【枚举】

    问题 I: Odd Gnome 时间限制: 1 Sec  内存限制: 128 MB 提交: 234  解决: 144 [提交] [状态] [命题人:admin] 题目描述 According to t ...

  8. C# 在创建窗口句柄之前,不能在控件上调用 Invoke 或 BeginInvoke

    http://www.cnblogs.com/fish124423/archive/2012/10/16/2726543.html 在Invoke(....)之前加上1 this.components ...

  9. Bytom合约预编译

    比原项目仓库: Github地址:https://github.com/Bytom/bytom Gitee地址:https://gitee.com/BytomBlockchain/bytom 在开发合 ...

  10. 【Ruby】【环境搭建】macOS Sierra 10.12.6 + Xcode 8 + gpg 2.2.8 + rvm 1.29.3 + Ruby 2.4.0 + RubyMine 2018.1.4

      按出场顺序: macOS Sierra 10.12.6  +  Xcode 8 + gpg 2.2.8 + rvm 1.29.3 +  Ruby 2.4.0 + RubyMine 2018.1.4 ...