先了解什么是SQL注入
在使用statement拼接字符串的时候,有一些SQL的特殊关键字参与字符串的拼接,这就会造成安全性的问题!
例如:sql = "select * from user where username = ’ "+ username + " 'and password = ’ " + password + " ’ ";
上面的这样一条SQL语句,在向里面传递参数时,如果登录者登录下面这样一套用户密码:
用户名:rong(随便写)
密码: a' or 'a' = 'a
依然可以实现用户的登录,而这种密码称为SQL注入万能码,类似的密码还有很多,只需要遵从一定的格式就可以实现登录,绕开SQL语句的验证.
那为什么会这样呢?
当我们这样登录以后:
select * from user where username = rong and password = a or a =a ;
sql 语句居然变成了上面这样一条语句,没错,我们给where后面的布尔值增添了一个条件*(a = a )这样的话where后面的值就发生了变化:
username = rong ---->false
password = a ----->false
a = a ----- true
而最终结果就是:**false and false or true ------------> true!!!!**
所以我们绕开了密码的检测,这个时候就可以看出,SQL注入万能码为什么不是唯一的,它的原理就是改变了我们的SQL语句结构,所以只要符合这种结构,就可以称为万能码;
注:SQL注入输入恶意攻击服务器行为,可以去靶场练习,不可以随便攻击其他网站,
怎么使用preparedStatement防止SQL注入
preparedStatement对象可以预编译SQL语句,参数使用?作为占位符
preparedStatement是Statement的一个子类!通过占位符的使用也就强行限制住了SQL语句传参时的个数,也就不会被拼接字符串之后or恒为true
使用步骤:
1.导入驱动jar包 mysql-connector - java - 5.1.37-bin.jar
2.注册驱动
3.获取数据库连接的对象:Connection
4.定义SQL语句
* sql语句的参数使用?占位符,例如:
* select * from user where username = ? and password = ?;
5.获取执行SQL语句的对象PerparedStatement(创建的时候传递预编译SQL语句)
*PerparedStatement Connection.prepareStatement(String SQL)
6.给?赋值
*setXxx(第几个站位参数位置,参数内容)
7.执行PreparedStatement.executeQuery()方法(不传参数时执行子类方法,传递参数时执行父类方法),接收返回结果集ResultSet
8.处理结果集
9.关闭资源
注:由此可以看出使用preparedStatement对象更符合JDBC的需求,更安全,效率更高