JDBC 1

目录

JDBC概括

JAR包下载使用

 JDBC的操作步骤

粗略步骤

JDBC操作核心类:

DriverManger:驱动管理器

Connection:数据库连接对象

Statements:sql语句执行

ResultSet:结果查询

sql注入

         概述

解决

例子:


JDBC概括

    JDBC(Java与数据库连接):Java DataBase Connectivity

        此技术是Java提供的一种数据库操作技术,提供了统一标准,但是此技术不在JDK中,需要下载相应的JAR包。

        JAR包:其他人写好的类打包

JAR包下载使用

下载::https://mvnrepository.com/搜索mySQL

使用步骤:

                 1,在项目的根目录下创建文件夹,这个文件夹必须命名为lib

                 2,将需要使用的jar包拷贝到lib文件夹下

                 3,选择jar包,点击右键选择add as libxxx

 JDBC的操作步骤

粗略步骤

1,加载驱动,反射的技术

        一个进程一次就行

        Class.forName("驱动类所在的包名.类名");

        如果不写的话也可以运行成功,这是因为JDBC4.0以后新增了新特性:JDBC4.0不再需要显式调用class.forName()注册驱动,DriverManager初始化中会通过ServiceLoader类,在我们classpath中jar(数据库驱动包)中查找,使用META-INF\services\java.sql.Driver文本中的类名称去注册。

2,创建连接

        通过DriverManager建立连接

        Connection c = DriverManger.getConnection(数据库url,数据库账号, 数据库密码)

3,获取sql语句执行对象

        //存在sql注入问题 Statement s = c.createStatement();

        //解决了sql注入问题 PreparedStatement s = c.prepareStatement(sql);

4,执行sql语句

        //用于执行DML操作,返回值时受影响行数 int num = s.executeUpdate();

        //用于执行DQL操作,返回值时查询到的结果 ResultSet set = s.executeWQuery();

5,处理结果

        根据需求处理

6,关闭资源

        如果执行的时查询操作需要关闭查询结果集

        关闭sql语句执行

        关闭连接对象

JDBC操作核心类:

DriverManger:驱动管理器

        作用:获取连接

        提供的静态方法方法: Connection getConnection(url,username,password);

 Class.forName("com.mysql.jdbc.Driver");//使用反射获取类对象
 Connection connection = DriverManager.getConnection(URL, USER, PASSMI);
//使用getConnection方法,驱动管理,获取连接

 URL:

例
String URL = "jdbc:mysql://localhost:3306/zday0301?useSSL=false&characterEncoding=utf-8";

url要写服务器地址和端口号,表名

useSSL=false和true的区别:


                  SSL(Secure Sockets Layer 安全套接字协议),useSSL=false通过账号 密码进行连

                  接,跳过安全验证。useSSL=true是进行安全验证,mysql的版本是5.7之前会默

                  认useSSL=false。之后包括5.7则不会,为了能连接上使用useSSL=false。

                                     

USER:数据库账号

USER = "root";

PASSMI:数据库密码

PASSMI= "123456"

Connection:数据库连接对象

        作用:获取sql语句执行对象,执行事物

        注意:默认自动提交

          提供的方法:

                        Statement createStatement(); //有sql注入风险

                        PreparedStatement prepareStatement(sql);    //解决了sql注入风险

                        CallableStatement prepareCall(String sql); //用于调用存储过程

                        void rollback();//回滚

                        void commit();//提交

                        c.setAutoCommit(false);设置是否自动添加,默认为true //

                        void setAutoCommit(boolean autoCommit);     关闭自动条件并开启事物

Statements:sql语句执行

                作用:执行sql语句

                提供的方法:

  1. int executeUpdate():用于执行DML操作   数据的增加或删除

        返回值为int型,为多少行受到了影响

  2.ResultSet executeWQuery():用于执行DQL操作    数据的查询

        ResultSet 包含符合 SQL 语句中条件的所有行,并且它通过一套 get 方法(这些 get 方法可以访问当前行中的不同列)提供了对这些行中数据的访问。ResultSet.next 方法用于移动到 ResultSet 中的下一行,使下一行成为当前行,此方法是从表头开始移动的

  3.boolean execute():用于执行DDL操作

          Statements 的 子类: PreparedStatement

                               作用:解决sql注入问题

                                     提供的方法:

                                                setInt(?号的位置,替换?号的值);

                                                setString(?号的位置,替换?号的值);

                                                                                        ...

                                                                        注意:?表示占位符,位置从1开始

              Statements    子类: CallableStatement

                                                作用:调用存储过程

ResultSet:结果查询

                作用:存储查询的结果

                提供的方法:

                                boolean next():移动游标

                                getInt(列名);

                                getString(列名);

sql注入

         概述

        程序对用户输入数据的合法性没有判断和处理,导致用户可以在应用程序中事先定义好的 SQL 语句中添加额外的 SQL 语句,以此来实现欺骗数据库服务器,来执行非任意查询语句。

例:恶意拼接查询

        SELECT * FROM users WHERE user_id = $user_id

其中,$user_id 是传入的参数,

如果传入的参数值为“1234; DELETE FROM users”,

那么最终的查询语句会变为:

SELECT * FROM users WHERE user_id = 1234; DELETE FROM users

如果以上语句执行,则会删除 users 表中的所有数据。

解决

参数化查询:

        参数化查询目前被视作是预防 SQL 注入攻击最有效的方法。参数化查询是指在设计与数据库连接并访问数据时,在需要填入数值或数据的地方,使用参数(Parameter)来给值。
        MySQL 的参数格式是以“?”字符加上参数名称而成,如下所示:

UPDATE myTable SET c1 = ?c1, c2 = ?c2, c3 = ?c3 WHERE c4 = ?c4

        在使用参数化查询的情况下,数据库服务器不会将参数的内容视为 SQL 语句的一部分来进行处理,而是在数据库完成 SQL 语句的编译之后,才套用参数运行。因此就算参数中含有破坏性的指令,也不会被数据库所运行。

        

例子:

         做一个使用数据库登录注册功能

import java.sql.*;
import java.util.Scanner;
public class Main {
    static {//静态只在类加载时加载一次
        try {
            Class.forName("com.mysql.jdbc.Driver");
        }catch (ClassNotFoundException e){
            e.printStackTrace();
        }
    }//加载驱动
    private static final String URL = "jdbc:mysql://localhost:3306/zday0301?useSSL=false&characterEncoding=utf-8";
    //url要写服务器地址和端口号,表名
    private static final String USER = "root";//数据库账号        上面的useSSL=false跳过安全验证,
    private static final String PASSMI= "123456";//数据库密码
    public static void main(String[] args) throws SQLException {

       login();
      //  regisr();//调用两个方法

    }

    public static void regisr() throws SQLException {
        System.out.println("输入账号");
        Scanner scanner = new Scanner(System.in);
        String usrname = scanner.next();

        System.out.println("输入密码");
        String mima = scanner.next();

        System.out.println("输入性别");
        String sex = scanner.next();

        System.out.println("输入年龄");
        String age = scanner.next();

        Connection connection = DriverManager.getConnection(URL, USER, PASSMI);//驱动管理,获取连接
        Statement statement = connection.createStatement();//获取sql语句执行对象,执行事物
        String sql = "select u_username from yinhang where u_username='"+usrname+"'";//查询语句
        ResultSet set = statement.executeQuery(sql);//执行DQL操作
        //这东西返回的结果是个集合
        if (set.next()){//向下移动,从表头开始的,如果不能移动的那就一个数据都没有,能移动表名可移动,说明有重复的
            System.out.println("账号以存在");
            return;
        }
        String intoSQL = "insert into yinhang (u_username,u_mima,u_sex,u_age)values('"+usrname+"','"+mima+"','"+sex+"',"+age+")";//插入语句
        int i = statement.executeUpdate(intoSQL);//向里面插入数据,执行
        if (i>0){
            System.out.println("注册成功");
        }else {
            System.out.println("注册失败");
        }
        if (statement != null&&!statement.isClosed()){//不判断的话会空指针异常
            statement.close();
        }
        if (connection != null && !connection.isClosed()){
            connection.close();
        }
    }

    public static  void login() throws SQLException {
        System.out.println("输入账号");
        Scanner scanner = new Scanner(System.in);
        String usrname = scanner.next();

        System.out.println("输入密码");
        Scanner scanner2 = new Scanner(System.in);
        String mima = scanner2.next();

        Connection connection = DriverManager.getConnection(URL, USER, PASSMI);//驱动管理,获取连接

        PreparedStatement statement = connection.prepareStatement( "select u_username from yinhang where u_username = ? and u_mima = ?");
        statement.setString(1,usrname);//前面的参数代表第几个?后面的参数代表需要替换的值
        statement.setString(2,mima);

        /*
         *
         Statement statement = connection.createStatement();//获取sql语句执行对象,执行事物
        String sql = "select u_username from yinhang where u_username="+"'usrname'"+"and"+" u_mima = "+ "'mima'";//查询语句
        ResultSet set = statement.executeQuery(sql);
        用此方法会产生sql注入问题,一般插入删除会比较关注注入问题,需要用 PreparedStatement方法解决
         *
         */

        ResultSet set = statement.executeQuery();//执行dml操作

        System.out.println(set.next());
        //这东西返回的结果是个集合

        if (set.next()){//向下移动,从表头开始的,如果不能移动的那就一个数据都没有,能移动表名可移动,说明有重复的
            System.out.println("账号以存在");
        }
        if(set != null && !set.isClosed()){
            set.close();//关闭结果
        }
        if (statement != null && !statement.isClosed()){
            statement.close();//关闭提交
        }
        if (connection != null && !connection.isClosed()){
            connection.close();//关闭连接
        }
    }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值