package com.xxx.xxx.dao;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List; import org.apache.log4j.Logger;
import org.apache.log4j.PropertyConfigurator; import com.ft.hsm.Util.ConstantValue;
import com.ft.hsm.Util.StringUtil; /*
* 使用java以及jdbc执行sql脚本的工具示例代码
*/ public class SqlHelper {
private static Logger logger; static {
logger = Logger.getLogger(ScreenDaoImpl.class);
PropertyConfigurator.configure(ConstantValue.PATH_SCREENSERVER_LOG4J_PROPERTIES);
} public static boolean createDBFromSQLFile(String SQLPath, String SQLFileCharsetName, String dbFilePath,
int[] retRowsExpected) {
if (StringUtil.isEmpty(SQLPath) || StringUtil.isEmpty(SQLFileCharsetName) || StringUtil.isEmpty(dbFilePath)
|| 0 >= retRowsExpected.length) {
logger.error("参数错误");
return false;
} // 检验是否己创建
File dbfile = new File(dbFilePath);
if (dbfile.exists() || dbfile.isDirectory()) {
logger.error(dbFilePath + "数据库文件己存在或存在同名文件夹");
return false;
} // 读取SQL文件
String sql = getText(SQLPath, SQLFileCharsetName); // "UTF-8"
if (StringUtil.isEmpty(sql)) {
logger.error("读取SQL文件失败");
return false;
} // 转换为SQL语句
List<String> sqlList = getSql(sql, SQLFileCharsetName);
for (int i = 0; i < sqlList.size(); i++) {
logger.info(i + ":" + sqlList.get(i));
} boolean isSuccess = false;
try { // 执行SQL语句
int[] rows = SqlHelper.execute(getConn(dbFilePath), sqlList);
logger.info("Row count Expected:" + Arrays.toString(retRowsExpected)); // 执行结果集鉴定
isSuccess = Arrays.equals(rows, retRowsExpected); // 调试打印执行结果集
if (null == rows || rows.length != retRowsExpected.length) {
logger.error("返回结果与期望个数不符, rows.length=" + rows.length + ", retRowsExpected.length="
+ retRowsExpected.length);
} else {
for (int index = 0; index < rows.length; index++) {
logger.info("rows[" + index + "] return=" + rows[index] + ", expected=" + retRowsExpected[index]
+ ",sql=" + sqlList.get(index)); }
}
} catch (Exception e) {
e.printStackTrace();
} return isSuccess;
} private static Connection getConn(String dbFile) {
String driver = "org.sqlite.JDBC"; // "com.mysql.jdbc.Driver";
String url = "jdbc:sqlite:" + dbFile; // "数据库连接";
// String username = "账号";
// String password = "密码";
Connection conn = null;
try {
Class.forName(driver); //classLoader,加载对应驱动
conn = (Connection) DriverManager.getConnection(url/*, username, password*/);
} catch (ClassNotFoundException e) {
e.printStackTrace();
} catch (SQLException e) {
e.printStackTrace();
}
return conn;
} public static int[] execute(Connection conn, List<String> sqlList) throws Exception {
Statement stmt = null;
stmt = conn.createStatement();
for (String sql : sqlList) {
sql = sql.trim();
if (sql != null && !sql.trim().equals(""))
stmt.addBatch(sql);
}
int[] rows = stmt.executeBatch();
logger.info("Row count returned:" + Arrays.toString(rows));
conn.close(); return rows;
} /*
* getText方法吧path路径里面的文件按行读数来放入一个大的String里面去
* 并在换行的时候加入\r\n
*/
public static String getText(String path, String SQLFileCharsetName) {
File file = new File(path);
if (!file.exists() || file.isDirectory()) {
logger.error(path + "文件不存在或存在同名文件夹");
return null;
}
StringBuilder sb = new StringBuilder();
try {
FileInputStream fis = new FileInputStream(path);
InputStreamReader isr = new InputStreamReader(fis, SQLFileCharsetName);
BufferedReader br = new BufferedReader(isr);
String temp = null;
temp = br.readLine();
while (temp != null) {
if (temp.length() >= 2) {
String str1 = temp.substring(0, 1);
String str2 = temp.substring(0, 2);
if (str1.equals("#") || str2.equals("--") || str2.equals("/*") || str2.equals("//")) {
temp = br.readLine();
continue;
}
sb.append(temp + "\r\n");
} temp = br.readLine();
}
br.close(); } catch (Exception e) {
e.printStackTrace();
}
return sb.toString();
} /*
* getSqlArray方法
* 从文件的sql字符串中分析出能够独立执行的sql语句并返回
*/
public static List<String> getSql(String sql, String SQLFileCharsetName) {
String s = sql; s = tryDeleteBOM(SQLFileCharsetName, s); s = s.replaceAll("\r\n", "\r");
s = s.replaceAll("\r\n", "\r");
s = s.replaceAll("\r", "\n");
List<String> ret = new ArrayList<String>();
String[] sqlarry = s.split(";"); //用;把所有的语句都分开成一个个单独的句子
sqlarry = filter(sqlarry);
ret = Arrays.asList(sqlarry);
return ret;
} public static String[] filter(String[] ss) {
List<String> strs = new ArrayList<String>();
for (String s : ss) {
if (s != null && !s.equals("")) {
strs.add(s);
}
}
String[] result = new String[strs.size()];
for (int i = 0; i < strs.size(); i++) {
result[i] = strs.get(i).toString(); }
return result;
} private static String tryDeleteBOM(String SQLFileCharsetName, String s) {
byte[] byteSQL = null; logger.info("判断是否含有UTF-8的BOM头"); try {
byteSQL = s.getBytes(SQLFileCharsetName); // 去掉UTF-8的BOM头
if (byteSQL[0] == (byte) 0xef && byteSQL[1] == (byte) 0xbb && byteSQL[2] == (byte) 0xbf) {
logger.info("含有UTF-8的BOM头");
logger.info("去掉UTF-8的BOM头前" + Arrays.toString(byteSQL)); s = new String(byteSQL, 3, byteSQL.length - 3, SQLFileCharsetName); logger.info("去掉UTF-8的BOM头后为:" + Arrays.toString(s.getBytes(SQLFileCharsetName)));
} else {
logger.info("不含有UTF-8的BOM头");
}
} catch (UnsupportedEncodingException ex) {
ex.printStackTrace();
}
return s;
} public static void main(String[] args) {
String SQLPath = "config/xxx_create.utf8.sql";
String dbFile = "db" + File.separator + "test.db";
String SQLFileCharsetName = "UTF-8";
// String SQLFileCharsetName = "GBK";
int[] retRowsExpected = { 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; boolean isSuccess = createDBFromSQLFile(SQLPath, SQLFileCharsetName, dbFile, retRowsExpected);
logger.info("创建数据库" + (isSuccess ? "成功" : "失败"));
} }

  

去掉utf-8的Bom头:使用java以及jdbc不使用第三方库执行sql文件脚本的更多相关文章

  1. 使用java以及jdbc不使用第三方库执行sql文件脚本

    使用java以及jdbc不使用第三方库执行sql文件脚本 2017年02月15日 15:51:45 阅读数:660 使用java执行sql脚本的方法 解析sql脚本,删除不必要的注释和空行 将语句按分 ...

  2. C#和Java中执行SQL文件脚本的代码(非常有用)

    原文:C#和Java中执行SQL文件脚本的代码(非常有用) 我们在做程序的时候有事后会涉及到利用sql文件 直接执行,可是在sql文件中有很多注释,我们要一句一句的执行首先必须的得把sql文件解析 去 ...

  3. [疯狂Java]JDBC:PreparedStatement预编译执行SQL语句

    1. SQL语句的执行过程——Statement直接执行的弊病: 1) SQL语句和编程语言一样,仅仅就会普通的文本字符串,首先数据库引擎无法识别这种文本字符串,而底层的CPU更不理解这些文本字符串( ...

  4. 10.1(java学习笔记)JDBC基本操作(连接,执行SQL语句,获取结果集)

    一.JDBC JDBC的全称是java database connection java数据库连接. 在java中需要对数据库进行一系列的操作,这时就需要使用JDBC. sun公司制定了关于数据库操作 ...

  5. java调用含第三方库的py文件

    这是一个心酸的历程. py文件如下: 这里调用出现的问题主要是第三方包的问题,因为你的py文件里可能含有很多三方库文件,jython的jar包里可能不含有这个,所以这时需要你找到你已有三方库文件的ex ...

  6. java当中JDBC当中请给出一个sql server的helloworld例子

    [学习笔记] 1.sql server的helloworld例子: import java.sql.*; public class JdbcHelloSqlServer {  public stati ...

  7. java当中JDBC当中请给出一个sql server的stored procedure例子

    3.sql server的stored procedure例子: import java.sql.*;public class StoredProc0 {public static void main ...

  8. java当中JDBC当中请给出一个sql server的dataSource的helloworld例子

     [学习笔记] 4. sql server的dataSource的helloworld: import java.sql.*;import javax.sql.*;import net.sourcef ...

  9. java 执行sql文件

    # 背景 用例执行完毕,期望回滚数据,因此希望执行sql来回滚数据 # 步骤 直接show代码,借助的是mybatis的ScriptRunner /** * 执行xx库下的表备份脚本 * * @par ...

随机推荐

  1. 网络编程基础----并发编程 ---守护进程----同步锁 lock-----IPC机制----生产者消费者模型

    1  守护进程: 主进程 创建 守护进程   辅助主进程的运行 设置进程的 daemon属性 p1.daemon=True 1 守护进程会在主进程代码执行结束后就终止: 2 守护进程内无法再开启子进程 ...

  2. POJ2411Mondriaan's Dream(DP+状态压缩 or 插头DP)

    问题: Squares and rectangles fascinated the famous Dutch painter Piet Mondriaan. One night, after prod ...

  3. openfl更新2.0后,android输入法又不能输中文了

    今天手贱更新了一下openfl,fd里面又各种报错.最伤心的是,之前修改MainView.java输入中文的方法现在居然失效了.还好这段时间研究c2dx,总算是能读能懂修改的那段代码,捣鼓了一下午,算 ...

  4. 执行.class文件

    java packageName.className即可 但是注意,如果是有包的,这段指令一定是packageName的上层目录(即bin目录)执行!

  5. 自己写的工具:把Evernote(印象笔记)的笔记导入到博客(Blog)中

    Evernote是个强大的工具, 这个伴随了我快4年的工具让我积累好多笔记.但是,如何把evernote(印象笔记)中的笔记发布到博客中呢? 自己空闲时候用python 3写了个工具Evernote2 ...

  6. MySQL 用户权限详细汇总(转)

    1,MySQL权限体系 MySQL 的权限体系大致分为5个层级: 全局层级: 全局权限适用于一个给定服务器中的所有数据库.这些权限存储在mysql.user表中.GRANT ALL ON .和REVO ...

  7. TCP之半关闭与CLOSE_WAIT

    终止一个连接要经过4次握手.这由TCP的半关闭(half-close)造成的.既然一个TCP连接是全双工(即数据在两个方向上能同时传递,可理解为两个方向相反的独立通道),因此每个方向必须单独地进行关闭 ...

  8. Oracle导出导入

    导出 exp 用户名/密码 file=文件名.dmp full=y; 导入 imp 用户名/密码 file=文件名.dmp full=y; 使用EXPDP和IMPDP时应该注意的事项: EXP和IMP ...

  9. struts2中常用constant命令配置

    struts.objectFactory这个属性用 于说明Struts2的 对象池创建工厂,Struts2也有自己的对象池,就像Spring那样,在配置文件中你可以引用对象池中的对象,你可以借助于Sp ...

  10. SQL 2008提供几种数据同步方式

    SQL 2008提供几种数据同步的方式如下. 1.日志传送(Log Shipping),定时将主数据库的日志备份,恢复到目标数据库. 2.数据库镜像(Database Mirror),原理同日志传送, ...