0
点赞
收藏
分享

微信扫一扫

JDBC PreparedStatement解决SQL注入方案

月白色的大狒 2024-09-24 阅读 3

文章目录

在这里插入图片描述


获取PreparedStatement对象

PreparedStatement是Statement的子接口,可以防止sql注入问题。可以通过Connection接口中的prepareStatement(sql)方法获得PreparedStatement的对象。

方法如下所示:

//	创建一个 PreparedStatement 对象来将参数化的 SQL 语句发送到数据库。
PreparedStatement prepareStatement(String sql);  

举例:

select *from user where username='zhangsan' and password = '123456';

使用 ?进行占位

select * from user where username = ? and password = ?;
String sql = ”select * from user where username = ? and password = ?;

PreparedStatement是如何解决SQL注入问题的

步骤一:**PreparedStatement pstmt = conn.prepareStatement(sql);** -----需要你事先传递sql。如果sql需要参数,使用?进行占位。

步骤二:设置参数(执行sql之前):pstmt.setXXX(int index, 要放入的值) -----根据不同类型的数据进行方法的选择。第一个参数 index 表示的是 ?出现的位置。从1开始计数,有几个问号,就需要传递几个参数。

方法的参数说明:

第一个参数:int index ;表示的是问号出现的位置。 问号是从1开始计数

第二个参数:给问号的位置传入的值。

步骤三、执行,不需要在传递sql了。

pstmt.executeQuery();—执行select

pstmt.executeUpdate();—执行insert,delete,update


小结:

1.使用预编译接口PreparedStatement 好处:

1.解决sql注入问题
2.提供效率,对sql语句只会预编译一次
    

2.使用编译接口PreparedStatement步骤:

1)使用连接对象调用方法获取预编译接口对象:PreparedStatement  pstmt =  conn.prepareStatement(sql); 
2)给sql语句占位符赋值:pstmt.setXxx(第几个占位符,实际值)
3)运行sql语句:
 	pstmt.executeQuery();---执行select
	pstmt.executeUpdate();---执行insert,delete,update


PreparedStatement的 应用

import java.sql.*;
import java.util.Scanner;

public class JDBCTest06 {
    public static void main(String[] args) throws Exception {
        /*
            使用PreparedStatement接口解决sql注入问题
                1.使用Connection接口对象调用方法,获取PreparedStatement预编译接口
                    PreparedStatement prepareStatement(String sql)
                2.使用预编译接口  PreparedStatement的对象调用PreparedStatement接口中的方法给sql语句中的占位符赋值
                    setXxx(第几个占位符,实际值)
                3.使用预编译接口  PreparedStatement对象调用PreparedStatement接口中的方法执行sql
                     ResultSet executeQuery()  执行DQL(查询语句)
                      int executeUpdate()    执行DML(增删改语句)
         */
        //1.创建键盘录入对象
        Scanner sc = new Scanner(System.in);
        //2.提示输入用户名和密码
        System.out.println("-------请输入用户名:-------");
        //获取用户名
        String inputUsername = sc.nextLine();

        System.out.println("-------请输入密码:-------");
        //获取密码
        String inputPassword = sc.nextLine();
        //3.获取数据
        //4.注册驱动
        //5.获取和数据库连接对象
        Connection conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/day03_heima139", "root", "1234");
        //6.使用Connection接口对象调用方法,获取PreparedStatement预编译接口
        // PreparedStatement prepareStatement(String sql)
        String sql = "select * from user3 where username=? and password=?";
        PreparedStatement pst = conn.prepareStatement(sql);

        //2.使用预编译接口  PreparedStatement的对象调用PreparedStatement接口中的方法给sql语句中的占位符赋值
        //setXxx(第几个占位符,实际值)
        //第一个参数1表示上述sql语句中的第一个占位符(?)位置
        //inputUsername :表示给第一个占位符赋的实际值
        // zhangsan\'\ \-\-
        pst.setString(1,inputUsername);

        //第一个参数2表示上述sql语句中的第二个占位符(?)位置
        //inputPassword :表示给第二个占位符赋的实际值
        pst.setString(2,inputPassword);

        /*
             3.使用预编译接口  PreparedStatement对象调用PreparedStatement接口中的方法执行sql
                     ResultSet executeQuery()  执行DQL(查询语句)
         */
        ResultSet rs = pst.executeQuery();

        //8.处理结果集
        //用户名唯一,查询的是一条数据,所以这里使用if即可
        if(rs.next()){
            //rs.next() :如果当前指针指向的行有数据则返回true
            //获取用户名
            String username = rs.getString("username");
            //输出
            System.out.println("恭喜您,亲,登录成功,欢迎光临我的小店,你的用户名是"+username);
        }else{
            System.out.println("用户名或者密码错误");
        }
        //9.释放资源
        rs.close();
        pst.close();
        conn.close();
    }
}


上述如何解决sql注入的问题呢?

在方法 setXxx()内部解决的。
例如上述 st.setString(1,inputUsername); ,将输入的用户名 "zhangsan' -- " 传入给setString方法体中,在该方法体中使用转义符号 / ,将特殊符号给转义了,转义之后再发送给 mysql 服务器,那么特殊符号例如–就不是注释的意思就是普通字符,mysql 会认为用户名的值是:zhangsan' --




举报

相关推荐

0 条评论