目录
一、定义
二、解决
三、实例
1.用JDBC实现查询
2.修改main方法中的username和password传进来的参数
3.修改main方法中的username和password传进来的参数,在username的参数里加上了or
4.解决办法
一、定义
SQL注入的问题是指sql语句拼接带来的问题
二、解决
解决注入问题通过占位符,采用sql预编译的方式,把sql语句中参数用?占位符来表示
三、实例
1.用JDBC实现查询
写一段代码,用JDBC实现查询,要连接数据库
user表:
import java.sql.*;public class Demo1 {public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa","123");System.out.println(login);}public static String login(String username,String password) throws ClassNotFoundException, SQLException {Connection conn=null;Statement stmt=null;ResultSet rs=null;String flag=null;Class.forName("com.mysql.jdbc.Driver");conn= DriverManager.getConnection("jdbc:mysql://localhost:3306/jdbcdemo","root","2020");String sql="select * from user where username='"+username+"' and password='"+password+"'";System.out.println(sql);try {stmt=conn.createStatement();rs=stmt.executeQuery(sql);//遍历数据if(rs.next()){flag="登陆成功";}else {flag="登陆失败";}return flag;}catch (SQLException e){e.printStackTrace();}//释放资源rs.close();stmt.close();conn.close();return null;}
}
运行结果为:
2.修改main方法中的username和password传进来的参数
下面只写main方法中的内容
(1)
public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa11","123");System.out.println(login);
}
运行:
(2)
public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa","123344");System.out.println(login);
}
运行:
(3)
public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa12","123344");System.out.println(login);
}
运行:
3.修改main方法中的username和password传进来的参数,在username的参数里加上了or
(1)
public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa'or'1=1","123");System.out.println(login);}
运行:
(2)
public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa'or'1=1","123asf");System.out.println(login);
}
运行:
可以看出,(1)和(2)这两个运行结果都是运行成功,但是第二个明显密码不对,为什么?
对于or和and:and优先级高,会先执行and,看sql语句:select * from user where username='aaa'or'1=1' and password='123asf'
先执行and,就是先执行'1=1' and password='123asf','1=1'是true,password='123asf'是false,所以这句话的结果是false,
然后执行or,这是sql语句变成select * from user where username='aaa' or false; 'aaa'是true,所以不管or后面是true还是false,最后结果都是true-------登录成功
这就是SQL注入问题,存在sql注入漏洞,是sql语句拼接带来的问题
4.解决办法
用占位符
import java.sql.*;public class Demo3 {public static void main(String[] args) throws SQLException, ClassNotFoundException {String login=login("aaa'or'1=1","123da");System.out.println(login);}public static String login(String username,String password) throws ClassNotFoundException, SQLException {Connection conn=null;PreparedStatement stmt=null;//这里改成预处理对象ResultSet rs=null;String flag=null;Class.forName("com.mysql.jdbc.Driver");conn= DriverManager.getConnection("jdbc:mysql://localhost:3306/jdbcdemo","root","2020");//创建sql语句,使用占位符String sql="select * from user where username=? and password=? ";try {//预编译sql语句,把sql语句固定stmt=conn.prepareStatement(sql);//给username和password设置值stmt.setString(1,username);stmt.setString(2,password);rs=stmt.executeQuery();//遍历数据if(rs.next()){flag="登陆成功";}else {flag="登陆失败";}return flag;}catch (SQLException e){e.printStackTrace();}//释放资源rs.close();stmt.close();conn.close();return null;}
}
再运行就是登陆失败