`
jgnan
  • 浏览: 87508 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

JAVA简单教程:数据库操作(三)——PreparedStatement和动态SQL

阅读更多
如果我们的SQL语句是固定的,但是参数会不断变化,那我们要怎么办呢?

首先看看以下的处理方式:
statement.executeQuery("select * from user where userid = "+userInputId);


看起来我们是解决了我们的需要,但是其实这种写法会带来很严重的问题。

加入我们的userInputId是1 or 1=1,那么上面的SQL就会编程:
select * from user where userid = 1 or 1=1

这样,无论userid 为多少,我们都会返回所有用户记录。

这种动态SQL会造成我们著名的SQL注入(SQL Injection)的安全漏洞。这种漏洞除了可以窃取你的数据库记录外,严重的时候更能够破坏你的数据库结构,让你的数据库彻底毁掉。例如:
statement.execute("insert int user values(......"+userInput+")");

如果userInput是:
null);delete from user;--
那么,就会执行两条SQL命令,第一条就是创建一个user记录,第二条就会把所有user记录删掉!!

为了解决这种参数会变化但是SQL结构固定的动态SQL语句,jdbc提供了PreparedStatment这种操作方式:

java.sql.PreparedStatement ps = conn.preparedStatement("select * from user where userid = ?");

...

ps.setInt(1,userInputId);
ResultSet rs = ps.executeQuery();
...


这个接口会自动把一些非法字符串进行转换,防止用户串改操作语句。

而且使用PreparedStatement还有利于提高数据库效率,对于数据库,执行以下的两条SQL:
select * from user where userid = 1
select * from user where userid = 2
它会视为两条不同的SQL来执行,并且把执行过程分别存储起来,但是对于preparedStatement,它会记录:
select * from user where userid = ?
每次会根据参数返回操作结果,无论执行多少次都只会保留一份操作副本,能够有效节省数据库的编译SQL性能。

但是PreparedStatement也不是万能,假如我们的变化不是限制在参数上,就有问题,例如我们获取的数据表可能是动态的,或者where条件是动态的。那么我们怎么来处理这种情况并且有效防止SQL Injection呢?
很简单,但是却比较麻烦,就是限制用户的输入,并且不要直接把用户输入直接作为SQL凭借部分。

应用实例:
根据用户输入读取不同数据表的所有信息,要求:
用户输入:user时,获取所有用户表信息(user表)
用户输入:org时,获取所有组织信息(org表)
用户输入其它信息:返回所有新闻记录(news表)

实现:
String sql = "select * from news";
if(userInput != null && userInput.equalsIgnoreCase("user"))
    sql = "select * from user";
if(userInput != null && userInput.equalsIgnoreCase("org"))
    sql = "select * from org";


利用这种方法和PreparedStatement就能够有效防止SQL注入。

无论日后是否使用ORM工具来操作数据库,都必须小心不要造成SQL注入漏洞,否则后果不堪设想。
分享到:
评论

相关推荐

    Java数据库编程宝典3

    目录 前言 第1部分 介绍数据库、SQL和JDBC 第1章 关系型数据库 1.1 理解关系型数据库管理系统 1.1.1 关系模型 1.1.2 Codd法则 1.1.3 表、行、列和关键字 ... 17.3 使用Java XML API——Xerces和JDOM ...

    最新Java面试题视频网盘,Java面试题84集、java面试专属及面试必问课程

    面试题包含了不同技术层面的面试问题,同时也能对一些没有面试开发经验的小白给予不可估量的包装, 让你的薪水绝对翻倍, 本人亲试有效.Java面试题84集、java面试专属及面试必问课程,所有的面试题有视屏讲解, 解答方案....

    Java开发详解.zip

    031707_【第17章:Java数据库编程】_PreparedStatement接口笔记.pdf 031708_【第17章:Java数据库编程】_处理大数据对象(1)—处理CLOB数据笔记.pdf 031709_【第17章:Java数据库编程】_处理大数据对象(2)—处理...

    Java数据库编程宝典2

    目录 前言 第1部分 介绍数据库、SQL和JDBC 第1章 关系型数据库 1.1 理解关系型数据库管理系统 1.1.1 关系模型 1.1.2 Codd法则 1.1.3 表、行、列和关键字 ... 17.3 使用Java XML API——Xerces和JDOM ...

    Java数据库编程宝典1

    目录 前言 第1部分 介绍数据库、SQL和JDBC 第1章 关系型数据库 1.1 理解关系型数据库管理系统 1.1.1 关系模型 1.1.2 Codd法则 1.1.3 表、行、列和关键字 ... 17.3 使用Java XML API——Xerces和JDOM ...

    Java数据库编程宝典4

    目录 前言 第1部分 介绍数据库、SQL和JDBC 第1章 关系型数据库 1.1 理解关系型数据库管理系统 1.1.1 关系模型 1.1.2 Codd法则 1.1.3 表、行、列和关键字 ... 17.3 使用Java XML API——Xerces和JDOM ...

    JAVA EE NZ2001 ——Day39——java EE学习 通宵达旦,终于弄好了数据库连接的相关总结、作业以及笔记

    说明:所示的代码里面我要连接的数据库是 nz2001,所操作的表示的表示user_info表 其中的表设计如图 package com.qianfeng.ps.am.secend; import java.sql.Connection; import java.sql.DriverManager; import java....

    Java Web编程宝典-十年典藏版.pdf.part2(共2个)

    7.4.4 预编译执行SQL语句的PreparedStatement接口 7.4.5 结果集ResultSet接1:2 7.5 JDBC操作数据库 7.5.1 向数据库中插入数据 7.5.2 从数据库中查询所需数据 75.3 修改数据库中的数据 7.5.4 删除无用的数据 7.5.5 ...

    JDBC的使用

    JDBC JDBC是怎么访问操作数据库的?...2.PreparedStatement——执行sql语句的接口(对应第二步) 3.ResultSet——处理查询结果(对应第三步) 在连接数据库之前需要环境搭建,也就是导入数据库的jar包 java连接数据库

    day01_eesy_01mybatis.zip

    学习笔记——mybatis的起步(1) 1.什么是框架? 他是我们软件开发中的一套解决方案,不同的框架解决的是不同的问题。 使用框架的好处: 框架封装了很多的细节,使开发者可以使用极简的方式实现功能。大大提高...

    java经典面试2010集锦100题(不看你后悔)

    —————————————————————————————————————— 题目1: 下面不属于基本类型的是:c (选择1项) A) boolean B) long C) String D) byte 题目2:d 如下程序中: (1)public class ...

    Java——JDBC②

    1. PreparedStatement 1.1 PreparedStatement插入数据 @Test public void testInsert() { User user = new User(1, lb, 851425); Connection connection = null; PreparedStatement preparedStatement = null; ...

    JSP2.0技术手册pdf(带示例源码).zip

    本书图文并茂,以丰富的实例为引导,全面介绍了主流的 Java Web 开发技术—— JSP 2.0,重点介绍Java在展示层的两项重要技术:Java Servlet与JavaServer Pages。 它们是最重要的 Java 核心技术。对这两项技术的深入...

Global site tag (gtag.js) - Google Analytics