本文共 3747 字,大约阅读时间需要 12 分钟。
数据库连接被用于向数据库服务器发送命令和 SQL 语句,并接受数据库服务器返回的结果。其实一个数据库连接就是一个Socket连接。
在 java.sql 包中有 3 个接口分别定义了对数据库的调用的不同方式:
Connection conn = null;Statement st = null;conn=JDBCUtils.getConnection();//已经封装好的连接st = conn.createStatement();
Statement 接口中定义了下列方法用于执行 SQL 语句:
int excuteUpdate(String sql):执行更新操作INSERT、UPDATE、DELETEResultSet executeQuery(String sql):执行查询操作SELECT
但是使用Statement操作数据表存在弊端:
SQL 注入是利用某些系统没有对用户输入的数据进行充分的检查,而在用户输入数据中注入非法的 SQL 语句段或命令(如:SELECT user, password FROM user_table WHERE user=‘a’ OR 1 = ’ AND password = ’ OR ‘1’ = ‘1’) ,从而利用系统的 SQL 引擎完成恶意行为的做法。
对于 Java 而言,要防范 SQL 注入,只要用 PreparedStatement(从Statement扩展而来) 取代 Statement 就可以了。
代码演示:package com.atguigu2.statement.crud;import java.io.InputStream;import java.lang.reflect.Field;import java.sql.Connection;import java.sql.DriverManager;import java.sql.ResultSet;import java.sql.ResultSetMetaData;import java.sql.SQLException;import java.sql.Statement;import java.util.Properties;import java.util.Scanner;import org.junit.Test;public class StatementTest { // 使用Statement的弊端:需要拼写sql语句,并且存在SQL注入的问题 //如何避免出现sql注入:只要用 PreparedStatement(从Statement扩展而来) 取代 Statement @Test public void testLogin() { Scanner scanner = new Scanner(System.in); System.out.print("请输入用户名:"); String user = scanner.nextLine(); System.out.print("请输入密码:"); String password = scanner.nextLine(); //SELECT user,password FROM user_table WHERE user = '1' or ' AND password = '=1 or '1' = '1' String sql = "SELECT user,password FROM user WHERE user = '"+ user +"' AND password = '"+ password +"'"; User returnUser = get(sql,User.class); if(returnUser != null){ System.out.println("登录成功"); }else{ System.out.println("用户名不存在或密码错误"); } } // 使用Statement实现对数据表的查询操作 publicT get(String sql, Class clazz) { T t = null; Connection conn = null; Statement st = null; ResultSet rs = null; try { // 1.加载配置文件 InputStream is = StatementTest.class.getClassLoader().getResourceAsStream("jdbc.properties"); Properties pros = new Properties(); pros.load(is); // 2.读取配置信息 String user = pros.getProperty("user"); String password = pros.getProperty("password"); String url = pros.getProperty("url"); String driverClass = pros.getProperty("driverClass"); // 3.加载驱动 Class.forName(driverClass); // 4.获取连接 conn = DriverManager.getConnection(url, user, password); st = conn.createStatement(); rs = st.executeQuery(sql); // 获取结果集的元数据 ResultSetMetaData rsmd = rs.getMetaData(); // 获取结果集的列数 int columnCount = rsmd.getColumnCount(); if (rs.next()) { t = clazz.newInstance(); for (int i = 0; i < columnCount; i++) { // //1. 获取列的名称 // String columnName = rsmd.getColumnName(i+1); // 1. 获取列的别名 String columnName = rsmd.getColumnLabel(i + 1); // 2. 根据列名获取对应数据表中的数据 Object columnVal = rs.getObject(columnName); // 3. 将数据表中得到的数据,封装进对象 Field field = clazz.getDeclaredField(columnName); field.setAccessible(true); field.set(t, columnVal); } return t; } } catch (Exception e) { e.printStackTrace(); } finally { // 关闭资源 if (rs != null) { try { rs.close(); } catch (SQLException e) { e.printStackTrace(); } } if (st != null) { try { st.close(); } catch (SQLException e) { e.printStackTrace(); } } if (conn != null) { try { conn.close(); } catch (SQLException e) { e.printStackTrace(); } } } return null; }}
综上:
转载地址:http://xmqq.baihongyu.com/