A review of JDBC basic knowledge of java operating database

What is JDBC?

  • JDBC is (java database connectivity), which is a standard rule interface for linking databases written by sun company in java language.

What can JDBC do for us?

  • jdbc uses a unified set of java codes to operate all relational databases. The interface operation is as follows:
    Insert picture description here
  • Sun company provides a unified database driver interface. Major database vendors write their own implementation classes according to the interface provided by sun company and package them into jar packages. Such jar packages have become the database drivers of major manufacturers. When you need to use a certain database, you only need to import the jar package corresponding to the database to connect to the database normally. (The actual code executed is the implementation class in the driver jar package).

How is JDBC used?

Steps for usage:

1. Import the driver jar package

Manual import

  1. Copy mysql-connector-java-5.1.37-bin.jar to the libs directory of the project
  2. Right click -> Add As Library
    Insert picture description here

maven dependency import

Register driver steps

1. Obtain the database connection object connection
2. Define SQL
3. Obtain the object statement of the
SQL statement 4. Execute SQL and receive the returned result
5. Process the result
7. Release resources

Java operation database case

public class JdbcTest {
    public static void main(String[] args) throws ClassNotFoundException {
        Connection connection = null;
        Statement statement = null;
        try {
            Class.forName("com.mysql.jdbc.Driver");
            /*connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/test2",
            "root","root");*/
             connection = DriverManager.getConnection("jdbc:mysql:///test2",
                    "root", "root");
            statement = connection.createStatement();

            String  sql = "update account set balance = 1000; -- where id =1;";
            int i = statement.executeUpdate(sql);
            if(i<1){
                System.out.println("执行失败!!!");
            }else{
                System.out.println(i);
                System.out.println("执行成功!!!");
            }

        } catch (SQLException throwables) {
            throwables.printStackTrace();
        }finally {
            if(statement !=null){
                try {
                    statement.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
            if(connection !=null){
                try {
                    connection.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
        }
    }
}

Commonly used objects in jdbc

DriverManager driver management object

What does the DriverManager management object do?
In fact, what DriverManager does is mainly composed of the following two parts.

1. Register the driver

Registering the driver actually tells the system which database driver jar package is being used.
There is a static function in DriverManager:

public static void registerDriver(Driver driver)
                           throws SQLException

But when I wrote the code, I found that Class.forName was used directly to load the driver

Class.forName("com.mysql.jdbc.Driver");

What is the relationship between the two?
In fact, the secret lies in the source code of com.mysql.jdbc.Driver. There are static methods in the source code. When the file is loaded with class.forName("xxx"), the static code block of com.mysql.jdbc.Driver is automatically executed, and the static code is The code of the registered driver in the block will be executed automatically, and part of the source code is as follows:

public class Driver extends NonRegisteringDriver implements java.sql.Driver {
    public Driver() throws SQLException {
    }

    static {
        try {
            DriverManager.registerDriver(new Driver());
        } catch (SQLException var1) {
            throw new RuntimeException("Can't register driver!");
        }
    }
}

Notes: After mysql-connector-java version 5.0, the statement Class.forName("xxx") can be omitted. Because the configuration file was added after 5.0, the content in the configuration file will be automatically read when the program is loaded, so the above steps can be omitted.
Insert picture description here

2. Get database connection

Get the code method:

  static Connection getConnection(String url, String user, String password)
 

parameter

  • url: Specify the connection path
    Syntax: jdbc:mysql://ip address (domain name): port number/database name
    Example: jdbc:mysql://localhost:3306/test1
    Details: If the connection is the local mysql server, and The default port of mysql service is 3306, then the url can be abbreviated as: jdbc:mysql:///database name
    user: user name
    password: password

Connection database connection object

Features
  1. Get database connection:
 Statement  createStatement();
 PrepareStatement  prepareStatement(String sql);
  1. Management affairs
  • Start the transaction: setAutoCommit(boolean autoCommit): The calling method is false to start the transaction.
  • Commit the transaction commit();
  • Roll back the transaction rollback();

Statement object to execute sql

An object used to execute static SQL statements and return the results they generate.

boolean execute(String sql) throws SQLException

The above sql can execute any sql;

int executeUpdate(String sql) throws SQLException

Under normal circumstances, the sql executes DML (insert, update, delete) statements, DDL (data definition language) (create, alter, drop) statement
return value, indicating the number of rows of impression, you can judge the DML statement by the number of rows affected Whether the execution is successful and the return value is >0, the execution is successful, otherwise, it fails.

ResultSet executeQuery(String sql)  :执行DQL(select)语句

ResultSet: result set object

It is used to encapsulate the results of the query.
getXxx(): Get data.
Xxx: represents the data type such as int getInt(), String getString();
parameters:

  • int: represents the column number, starting from 1, such as: getString();
    String: represents the column name. Such as: getDouble("balance")
Case number one
public class Jdbc02Test {
    public static void main(String[] args) {
        List<Emp> all = findAll();
        for (Emp emp :
                all) {
            System.out.println(emp);
        }
    }
    public static List<Emp> findAll(){
        Connection connection =null;
        Statement statement = null;
        ResultSet resultSet = null;
        LinkedList<Emp> emps =null;
        try {
            Class.forName("com.mysql.jdbc.Driver");
            connection = DriverManager.getConnection("jdbc:mysql:///test2",
                    "root", "root");
            statement = connection.createStatement();
            String sql = "select * from account;";
            resultSet = statement.executeQuery(sql);

            /*while (resultSet.next()){
                int anInt = resultSet.getInt(1);
                String name = resultSet.getString("name");
                double balance = resultSet.getDouble("balance");
                System.out.println(anInt+"----->"+name+"----->"+balance);
            }*/
             emps = new LinkedList<>();

            while (resultSet.next()){
                Emp emp = new Emp();
                emp.setId(resultSet.getInt(1));
                emp.setName(resultSet.getString("name"));
                emp.setBalance(resultSet.getDouble("balance"));
                emps.add(emp);
            }

        } catch (ClassNotFoundException | SQLException e) {
            e.printStackTrace();
        }finally {

            if(resultSet != null){
                try {
                    resultSet.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
            if(statement != null){
                try {
                    statement.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
            if(connection != null){
                try {
                    connection.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
        }
        return emps;
    }
}

search result:
Insert picture description here

Case two

Use the list form to print out the results of the query.
Entity class:

public class Emp {
    private  int id;
    private  String name;
    private  Double balance;
    public Emp() {
    }
    public Emp(int id, String name, Double balance) {
        this.id = id;
        this.name = name;
        this.balance = balance;
    }
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Double getBalance() {
        return balance;
    }

    public void setBalance(Double balance) {
        this.balance = balance;
    }
    @Override
    public String toString() {
        return "Emp{" +
                "id=" + id +
                ", name='" + name + '\'' +
                ", balance=" + balance +
                '}';
    }
}

Test category:

public class JdbcTest {
    public static void main(String[] args) throws ClassNotFoundException {
        Connection connection = null;
        Statement statement = null;
        try {
            Class.forName("com.mysql.jdbc.Driver");
            /*connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/test2",
            "root","root");*/
             connection = DriverManager.getConnection("jdbc:mysql:///test2",
                    "root", "root");
            statement = connection.createStatement();
            String  sql = "update account set balance = 1000; -- where id =1;";

            int i = statement.executeUpdate(sql);
            if(i<1){
                System.out.println("执行失败!!!");
            }else{
                System.out.println(i);
                System.out.println("执行成功!!!");
            }

        } catch (SQLException throwables) {
            throwables.printStackTrace();
        }finally {
            if(statement !=null){
                try {
                    statement.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
            if(connection !=null){
                try {
                    connection.close();
                } catch (SQLException throwables) {
                    throwables.printStackTrace();
                }
            }
        }
    }
}

Insert picture description here

PreparedStatement

SQL injection problem:
  • When splicing SQL, some special keywords of SQL participate in the splicing of strings. Will cause security problems, such as sql injection in case two in JDBCUtils
  1. Enter the user casually, enter the password: a'or'a' ='a
  2. The sql executed in the actual database is as follows
select 
	* 
from 
	account 
where 
	username = 'woailuo' 
and 
	password= 'wo' 
or 
	'ailuo' = 'ailuo';
How to solve the SQL injection problem

Sun provides a PreparedStatement object to solve the problem of SQL injection.

Pre-compiled SQL

Parameter use? as a placeholder

Extract the JDBCUtils class

Case number one

Abstract loading resource files and releasing resource files into a tool class, and then implement database operations

resource

url=jdbc:mysql:///test2
username=root
password=root
driver=com.mysql.jdbc.Driver

Entity class

public class Emp {
    private  int id;
    private  String name;
    private  Double balance;
    public Emp() {
    }
    public Emp(int id, String name, Double balance) {
        this.id = id;
        this.name = name;
        this.balance = balance;
    }
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Double getBalance() {
        return balance;
    }

    public void setBalance(Double balance) {
        this.balance = balance;
    }
    @Override
    public String toString() {
        return "Emp{" +
                "id=" + id +
                ", name='" + name + '\'' +
                ", balance=" + balance +
                '}';
    }
}

Tools

public class JDBCUtils {
    private  static  String url;
    private  static  String username;
    private  static  String password;
    private  static  String driver;
    //静态代码块,加载资源文件
    static {
        try {
            Properties properties = new Properties();
            //加载文件
            ClassLoader classLoader = JDBCUtils.class.getClassLoader();
            URL resource = classLoader.getResource("jdbc.properties");
            String path = resource.getPath();
            System.out.println(path);
            properties.load(new FileReader(path));
            url = properties.getProperty("url");
            username = properties.getProperty("username");
            password = properties.getProperty("password");
            driver = properties.getProperty("driver");
            Class.forName(driver);
        } catch (IOException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }

    public static  Connection  getConnection(){
        Connection connection = null;
        try {
             connection = DriverManager.getConnection(url, username, password);
        } catch (SQLException throwables) {
            throwables.printStackTrace();
        }finally {
            return connection;
        }
    }

    public static void close(Statement statement, Connection connection){
        if(statement != null){
            try {
                statement.close();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
        }
        if(connection != null){
            try {
                connection.close();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
        }
    }

    public static void close(ResultSet resultSet, Statement statement, Connection connection){
        if(resultSet != null){
            try {
                resultSet.close();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
        }
        if(statement != null){
            try {
                statement.close();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
        }
        if(connection != null){
            try {
                connection.close();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
        }
    }
}

Test class

Connection connection =null;
        Statement statement = null;
        ResultSet resultSet = null;
        LinkedList<Emp> emps =null;
        try {
             connection = JDBCUtils.getConnection();
            String sql = "select * from account;";
            statement = connection.createStatement();
            resultSet = statement.executeQuery(sql);
             emps = new LinkedList<>();
            while (resultSet.next()){
                Emp emp = new Emp();
                emp.setId(resultSet.getInt(1));
                emp.setName(resultSet.getString("name"));
                emp.setBalance(resultSet.getDouble("balance"));
                emps.add(emp);
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JDBCUtils.close(resultSet,statement,connection);
            return emps;
        }

Test Results
Insert picture description here

Case two

Demonstration code: The
tool classes and resource files are consistent with the case 1, and case 2 does not require entity classes, so the data table needs to be slightly modified.
Need to modify the database.

use test2;

alter TABLE account  add PASSWORD VARCHAR(20);

ALTER TABLE account CHANGE PASSWORD password VARCHAR(20);

ALTER TABLE account CHANGE NAME username VARCHAR(20);

UPDATE account SET PASSWORD = 'zhangsan' WHERE `NAME`='zhangsan'; 
UPDATE account SET PASSWORD = 'lisi' WHERE `NAME`='lisi'; 
SELECT * FROM account;
desc account;

The database tables and table structure are as follows:

Insert picture description hereInsert picture description here
Test category:

public class jdbc03Test {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        System.out.println("请输入用户名:");
        String username = scanner.nextLine();
        System.out.println("请输入密码:");
        String password = scanner.nextLine();
        boolean flag = login(username, password);
        if(flag){
            System.out.println("登录成功!!!");
        }else {
            System.out.println("登录失败!!!");
        }

    }
    public static boolean login(String username, String password){
        Connection connection =null;
        Statement statement = null;
        ResultSet resultSet = null;
        boolean loginFlag = false;
        try {
            connection = JDBCUtils.getConnection();
            String sql = "select * from account where username = '"+username+"' and password= '"+password+"';";
            System.out.println(sql);
            statement = connection.createStatement();
            resultSet = statement.executeQuery(sql);

            if(resultSet.next()){
                loginFlag = true;
                System.out.println(resultSet.getString(2));
                return  loginFlag;
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JDBCUtils.close(resultSet,statement,connection);
        }
        return loginFlag;
    }
}

Demonstrate sql injection problem.
When you just enter the account number: woailuo Password: wo' or'ailuo' ='ailuo,
we found that the login was successful.
Insert picture description here
It can be seen that the SQL injection problem is still quite serious.
We already know that PreparedStatement can solve the SQL injection problem. The following case three will show how to use PreparedStatement objects.

Case three

The resource class and tool class remain the same as in Case 2, and the statement object is changed to preparestatement

public class JDBC04Test {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        System.out.println("请输入用户名:");
        String username = scanner.nextLine();
        System.out.println("请输入密码:");
        String password = scanner.nextLine();
        boolean flag = login(username, password);
        if(flag){
            System.out.println("登录成功!!!");
        }else {
            System.out.println("登录失败!!!");
        }
    }
    public static boolean login(String username,String password){
        if(username == null || password==null){
            return false;
        }
        Connection connection =null;
        PreparedStatement preparedStatement = null;
        ResultSet resultSet = null;
        boolean loginFlag = false;
        try {
            connection = JDBCUtils.getConnection();
            String sql = "select * from account where username = ? and password= ?;";
            System.out.println(sql);
            preparedStatement = connection.prepareStatement(sql);
            //需要给问好赋值
            preparedStatement.setString(1,username);
            preparedStatement.setString(2,password);
            resultSet = preparedStatement.executeQuery();

            if(resultSet.next()){
                loginFlag = true;
                System.out.println(resultSet.getString(2));
                return  loginFlag;
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JDBCUtils.close(resultSet,preparedStatement,connection);
        }
        return loginFlag;
    }
}

Insert picture description here
SQL injection failed, this problem is resolved.

jdbc transaction control

jdbc transaction control process

Transaction control can use the Connection object.
Open the transaction:

  • setAutoCommit(boolean autoCommit): Call this method to set the parameter to false, that is, start the transaction before executing SQL:

Commit the transaction:

  • commit(); Submit the transaction after all SQL execution in the same transaction is completed.

Roll back the transaction:

  • rollback(); Roll back the transaction in catch

It can also implement transaction management

Case number one

In this case, the tool class and resource class are consistent with the extracted JDBCUtils class

Test class

public class JDBC05Test {
    public static void main(String[] args) {
        System.out.println("----------交易开始前----------");
        List<Emp> all = findAll();
        for (Emp emp :
                all) {
            System.out.println(emp);
        }
        transaction("zhangsan","lisi",500);
        System.out.println("------交易完成后-------");
        all=findAll();
        for (Emp emp :
                all) {
            System.out.println(emp);
        }
    }

    public static boolean transaction(String user1, String user2, double val ){
        Connection connection =null;
        PreparedStatement preparedStatement1 = null, preparedStatement2=null;
        ResultSet resultSet = null;
        try {
            connection = JDBCUtils.getConnection();
            connection.setAutoCommit(false);
            String sql1 = " update account set balance = balance - ? where username = ?";
            String sql2 = " update account set balance = balance + ? where username = ?";
            preparedStatement1 = connection.prepareStatement(sql1);
            preparedStatement2 = connection.prepareStatement(sql2);
            preparedStatement1.setDouble(1,val);
            preparedStatement1.setString(2,user1);
            preparedStatement2.setDouble(1,val);
            preparedStatement2.setString(2,user2);

            int i = preparedStatement1.executeUpdate();
           // int i2= 4/0;
            int i1 = preparedStatement2.executeUpdate();
            connection.commit();

        } catch (Exception e) {
            try {
                if(connection !=null){
                    connection.rollback();
                }
            } catch (SQLException sqlException) {
                sqlException.printStackTrace();
            }
            e.printStackTrace();
            return false;
        }finally {
            JDBCUtils.close(resultSet,preparedStatement1,connection);
            JDBCUtils.close(resultSet,preparedStatement2,connection);
        }
        return  true;
    }
    
    public static List<Emp> findAll(){
        Connection connection =null;
        PreparedStatement preparedStatement = null;
        ResultSet resultSet = null;
        LinkedList<Emp> emps =null;
        try {
            connection = JDBCUtils.getConnection();
            String sql = "select * from account;";
            preparedStatement = connection.prepareStatement(sql);
            resultSet = preparedStatement.executeQuery();
            emps = new LinkedList<>();
            while (resultSet.next()){
                Emp emp = new Emp();
                emp.setId(resultSet.getInt(1));
                emp.setUsername(resultSet.getString("username"));
                emp.setBalance(resultSet.getDouble("balance"));
                emp.setPassword("password");
                emps.add(emp);
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JDBCUtils.close(resultSet,preparedStatement,connection);
            return emps;
        }
    }
}

When there is no exception in the transaction, the entire transaction runs normally.
Insert picture description here
When there is an exception in the transaction, the transaction is rolled back directly.

public class JDBC05Test {
    public static void main(String[] args) {
        System.out.println("----------交易开始前----------");
        List<Emp> all = findAll();
        for (Emp emp :
                all) {
            System.out.println(emp);
        }
        transaction("zhangsan","lisi",500);
        System.out.println("------交易完成后-------");
        all=findAll();
        for (Emp emp :
                all) {
            System.out.println(emp);
        }
    }

    public static boolean transaction(String user1, String user2, double val ){
        Connection connection =null;
        PreparedStatement preparedStatement1 = null, preparedStatement2=null;
        ResultSet resultSet = null;
        try {
            connection = JDBCUtils.getConnection();
            connection.setAutoCommit(false);
            String sql1 = " update account set balance = balance - ? where username = ?";
            String sql2 = " update account set balance = balance + ? where username = ?";
            preparedStatement1 = connection.prepareStatement(sql1);
            preparedStatement2 = connection.prepareStatement(sql2);
            preparedStatement1.setDouble(1,val);
            preparedStatement1.setString(2,user1);
            preparedStatement2.setDouble(1,val);
            preparedStatement2.setString(2,user2);

            int i = preparedStatement1.executeUpdate();
            int i2= 4/0;
            int i1 = preparedStatement2.executeUpdate();
            connection.commit();

        } catch (Exception e) {
            try {
                if(connection !=null){
                    connection.rollback();
                }
            } catch (SQLException sqlException) {
                sqlException.printStackTrace();
            }
            e.printStackTrace();
            return false;
        }finally {
            JDBCUtils.close(resultSet,preparedStatement1,connection);
            JDBCUtils.close(resultSet,preparedStatement2,connection);
        }
        return  true;
    }

    public static List<Emp> findAll(){
        Connection connection =null;
        PreparedStatement preparedStatement = null;
        ResultSet resultSet = null;
        LinkedList<Emp> emps =null;
        try {
            connection = JDBCUtils.getConnection();
            String sql = "select * from account;";
            preparedStatement = connection.prepareStatement(sql);
            resultSet = preparedStatement.executeQuery();
            emps = new LinkedList<>();
            while (resultSet.next()){
                Emp emp = new Emp();
                emp.setId(resultSet.getInt(1));
                emp.setUsername(resultSet.getString("username"));
                emp.setBalance(resultSet.getDouble("balance"));
                emp.setPassword("password");
                emps.add(emp);
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JDBCUtils.close(resultSet,preparedStatement,connection);
            return emps;
        }
    }
}

Insert picture description here
So far, the basic knowledge of jdbc is reviewed here.

Guess you like

Origin blog.csdn.net/xueshanfeitian/article/details/109086494