BaseDALSQLite.cs 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371
  1. using System;
  2. using System.Text;
  3. using System.Collections;
  4. using System.Data;
  5. using System.Data.Common;
  6. using System.Collections.Generic;
  7. using System.Reflection;
  8. using System.Configuration;
  9. //using System.Data.SQLite;
  10. using Microsoft.Practices.EnterpriseLibrary.Data;
  11. using Microsoft.Practices.EnterpriseLibrary.Data.Configuration;
  12. using ProjectBase.Data.BaseDAL;
  13. using ProjectBase.Data.Pager;
  14. using ProjectBase.Data.Logs;
  15. using ProjectBase.Data.Encrypt;
  16. namespace ProjectBase.Data.BaseDAL.BaseDatabase
  17. {
  18. /// <summary>
  19. /// 数据访问层的基类
  20. /// </summary>
  21. public abstract class BaseDALSQLite<T> : AbstractBaseDAL<T>, IBaseDAL<T> where T : BaseEntity, new()
  22. {
  23. #region 构造函数
  24. /// <summary>
  25. /// 默认构造函数
  26. /// </summary>
  27. public BaseDALSQLite() { }
  28. /// <summary>
  29. /// 指定表名以及主键,对基类进构造
  30. /// </summary>
  31. /// <param name="tableName">表名</param>
  32. /// <param name="primaryKey">表主键</param>
  33. public BaseDALSQLite(string tableName, string primaryKey)
  34. : base(tableName, primaryKey)
  35. {
  36. this.parameterPrefix = "$";//或者为@也可以(数据库参数化访问的占位符)
  37. this.safeFieldFormat = "[{0}]"; //防止和保留字、关键字同名的字段格式(尽量避免)
  38. }
  39. #endregion
  40. #region 通用操作方法
  41. /// <summary>
  42. /// 添加记录
  43. /// </summary>
  44. /// <param name="recordField">Hashtable:键[key]为字段名;值[value]为字段对应的值</param>
  45. /// <param name="targetTable">需要操作的目标表名称</param>
  46. /// <param name="trans">事务对象,如果使用事务,传入事务对象,否则为Null不使用事务</param>
  47. public override int Insert2(Hashtable recordField, string targetTable, DbTransaction trans = null)
  48. {
  49. int result = -1;
  50. if (recordField == null || recordField.Count < 1)
  51. {
  52. return result;
  53. }
  54. string fields = ""; // 字段名
  55. string vals = ""; // 字段值
  56. foreach (string field in recordField.Keys)
  57. {
  58. fields += string.Format("[{0}],", field);//加[]为了去除别名引起的错误
  59. vals += string.Format("{0}{1},", parameterPrefix, field);
  60. }
  61. fields = fields.Trim(',');//除去前后的逗号
  62. vals = vals.Trim(',');//除去前后的逗号
  63. string sql = string.Format("INSERT INTO {0} ({1}) VALUES ({2});Select LAST_INSERT_ROWID()", targetTable, fields, vals);
  64. Database db = CreateDatabase();
  65. DbCommand command = db.GetSqlStringCommand(sql);
  66. foreach (string field in recordField.Keys)
  67. {
  68. object val = recordField[field];
  69. val = val ?? DBNull.Value;
  70. if (val is DateTime)
  71. {
  72. if (Convert.ToDateTime(val) <= Convert.ToDateTime("1753-1-1"))
  73. {
  74. val = DBNull.Value;
  75. }
  76. }
  77. db.AddInParameter(command, field, TypeToDbType(val.GetType()), val);
  78. }
  79. if (trans != null)
  80. {
  81. result = Convert.ToInt32(db.ExecuteScalar(command, trans).ToString());
  82. }
  83. else
  84. {
  85. result = Convert.ToInt32(db.ExecuteScalar(command).ToString());
  86. }
  87. return result;
  88. }
  89. /// <summary>
  90. /// 测试数据库是否正常连接
  91. /// </summary>
  92. public override bool TestConnection(string connectionString)
  93. {
  94. bool result = false;
  95. //using (DbConnection connection = new SQLiteConnection(connectionString))
  96. //{
  97. // connection.Open();
  98. // if (connection.State == System.Data.ConnectionState.Open)
  99. // {
  100. // result = true;
  101. // }
  102. //}
  103. return result;
  104. }
  105. #endregion
  106. #region 对象添加、修改、查询接口
  107. /// <summary>
  108. /// 查找记录表中最旧的一条记录
  109. /// </summary>
  110. /// <param name="trans">事务对象</param>
  111. /// <returns></returns>
  112. public override T FindFirst(DbTransaction trans = null)
  113. {
  114. string sql = string.Format("Select {0} From {1} Order by {2} ASC LIMIT 1", selectedFields, tableName, GetSafeFileName(sortField));
  115. Database db = CreateDatabase();
  116. DbCommand command = db.GetSqlStringCommand(sql);
  117. T entity = GetEntity(db, command, trans);
  118. return entity;
  119. }
  120. /// <summary>
  121. /// 查找记录表中最新的一条记录
  122. /// </summary>
  123. /// <param name="trans">事务对象</param>
  124. /// <returns></returns>
  125. public override T FindLast(DbTransaction trans = null)
  126. {
  127. string sql = string.Format("Select {0} From {1} Order by {2} DESC LIMIT 1", selectedFields, tableName, GetSafeFileName(sortField));
  128. Database db = CreateDatabase();
  129. DbCommand command = db.GetSqlStringCommand(sql);
  130. T entity = GetEntity(db, command, trans);
  131. return entity;
  132. }
  133. #region 下面两个覆盖基类函数,指定具体的数据库类型
  134. /// <summary>
  135. /// 根据条件查询数据库,并返回对象集合(用于分页数据显示)
  136. /// </summary>
  137. /// <param name="condition">查询的条件</param>
  138. /// <param name="info">分页实体</param>
  139. /// <param name="fieldToSort">排序字段</param>
  140. /// <param name="desc">是否降序</param>
  141. /// <param name="trans">事务对象</param>
  142. /// <returns>指定对象的集合</returns>
  143. public override List<T> FindWithPager(string condition, PagerInfo info, string fieldToSort, bool desc, DbTransaction trans = null)
  144. {
  145. if (HasInjectionData(condition))
  146. {
  147. LogHelper.log.Error(string.Format("检测出SQL注入的恶意数据, {0}", condition));
  148. throw new Exception("检测出SQL注入的恶意数据");
  149. }
  150. PagerHelper helper = new PagerHelper(tableName, this.selectedFields, fieldToSort,
  151. info.PageSize, info.CurrenetPageIndex, desc, condition);
  152. string countSql = helper.GetPagingSql(DatabaseType.SQLite, true);
  153. string strCount = SqlValueList(countSql, trans);
  154. info.RecordCount = Convert.ToInt32(strCount);
  155. string dataSql = helper.GetPagingSql(DatabaseType.SQLite, false);
  156. List<T> list = GetList(dataSql, null, trans);
  157. return list;
  158. }
  159. /// <summary>
  160. /// 根据条件查询数据库,并返回DataTable集合(用于分页数据显示)
  161. /// </summary>
  162. /// <param name="condition">查询的条件</param>
  163. /// <param name="info">分页实体</param>
  164. /// <param name="fieldToSort">排序字段</param>
  165. /// <param name="desc">是否降序</param>
  166. /// <param name="trans">事务对象</param>
  167. /// <returns>指定DataTable的集合</returns>
  168. public override DataTable FindToDataTable(string condition, PagerInfo info, string fieldToSort, bool desc, DbTransaction trans = null)
  169. {
  170. if (HasInjectionData(condition))
  171. {
  172. LogHelper.log.Error(string.Format("检测出SQL注入的恶意数据, {0}", condition));
  173. throw new Exception("检测出SQL注入的恶意数据");
  174. }
  175. PagerHelper helper = new PagerHelper(tableName, this.selectedFields, fieldToSort,
  176. info.PageSize, info.CurrenetPageIndex, desc, condition);
  177. string countSql = helper.GetPagingSql(DatabaseType.SQLite, true);
  178. string strCount = SqlValueList(countSql, trans);
  179. info.RecordCount = Convert.ToInt32(strCount);
  180. string dataSql = helper.GetPagingSql(DatabaseType.SQLite, false);
  181. return GetDataTableBySql(dataSql, trans);
  182. }
  183. #endregion
  184. /// <summary>
  185. /// 获取前面记录指定数量的记录
  186. /// </summary>
  187. /// <param name="sql">查询语句</param>
  188. /// <param name="count">指定数量</param>
  189. /// <param name="orderBy">排序条件,例如order by id</param>
  190. /// <param name="trans">事务对象</param>
  191. /// <returns></returns>
  192. public override DataTable GetTopResult(string sql, int count, string orderBy, DbTransaction trans = null)
  193. {
  194. string resultSql = string.Format("Select * From ({1} {2}) LIMIT {0} ", count, sql, orderBy);
  195. return SqlTable(resultSql, trans);
  196. }
  197. #endregion
  198. #region 特殊的操作
  199. /// <summary>
  200. /// 兼容Oracle的字段大写的重写函数
  201. /// </summary>
  202. /// <param name="sql">sql语句</param>
  203. /// <param name="trans">事务对象</param>
  204. /// <returns></returns>
  205. public override DataTable SqlTable(string sql, DbTransaction trans = null)
  206. {
  207. //由于Sqlite字段查询不区分大小写,因此要返回大写字段,不能通过改变Sql大写方式
  208. //通过代码改变列的名称为大写即可
  209. DataTable dt = base.SqlTable(sql, trans);
  210. foreach (DataColumn col in dt.Columns)
  211. {
  212. col.ColumnName = col.ColumnName.ToUpper();
  213. }
  214. return dt;
  215. }
  216. /// <summary>
  217. /// 兼容Oracle的字段大写的重写函数
  218. /// </summary>
  219. /// <param name="sql">sql语句</param>
  220. /// <param name="parameters">SQL参数集合</param>
  221. /// <param name="trans">事务对象</param>
  222. /// <returns></returns>
  223. public override DataTable SqlTable(string sql, DbParameter[] parameters, DbTransaction trans = null)
  224. {
  225. //由于Sqlite字段查询不区分大小写,因此要返回大写字段,不能通过改变Sql大写方式
  226. //通过代码改变列的名称为大写即可
  227. DataTable dt = base.SqlTable(sql, parameters, trans);
  228. foreach (DataColumn col in dt.Columns)
  229. {
  230. col.ColumnName = col.ColumnName.ToUpper();
  231. }
  232. return dt;
  233. }
  234. /// <summary>
  235. /// 获取数据库的全部表名称
  236. /// </summary>
  237. /// <returns></returns>
  238. public override List<string> GetTableNames()
  239. {
  240. Database db = CreateDatabase();
  241. List<string> list = new List<string>();
  242. using (DbConnection connection = db.CreateConnection())
  243. {
  244. if (connection.State != ConnectionState.Open)
  245. {
  246. connection.Open();
  247. }
  248. DataTable schemaTable = connection.GetSchema("TABLES");
  249. for (int i = 0; i < schemaTable.Rows.Count; i++)
  250. {
  251. string tablename = schemaTable.Rows[i]["TABLE_NAME"].ToString();
  252. list.Add(tablename);
  253. }
  254. }
  255. return list;
  256. }
  257. #endregion
  258. #region 设置数据库的密码
  259. /// <summary>
  260. /// 根据配置数据库配置名称生成Database对象
  261. /// </summary>
  262. /// <returns></returns>
  263. protected override Database CreateDatabase()
  264. {
  265. Database db = null;
  266. if (string.IsNullOrEmpty(dbConfigName))
  267. {
  268. db = DatabaseFactory.CreateDatabase();
  269. }
  270. else
  271. {
  272. db = DatabaseFactory.CreateDatabase(dbConfigName);
  273. }
  274. DbConnectionStringBuilder sb = db.DbProviderFactory.CreateConnectionStringBuilder();
  275. sb.ConnectionString = GetConnectionString(dbConfigName);
  276. GenericDatabase newDb = new GenericDatabase(sb.ToString(), db.DbProviderFactory);
  277. db = newDb;
  278. return db;
  279. }
  280. /// <summary>
  281. /// 动态改变或者连接字符串
  282. /// </summary>
  283. /// <returns></returns>
  284. protected virtual string GetConnectionString(string dbConfigName)
  285. {
  286. string connectionString = "";
  287. DatabaseSettings setting = ConfigurationManager.GetSection("dataConfiguration") as DatabaseSettings;
  288. if (setting != null)
  289. {
  290. string connection = string.IsNullOrEmpty(dbConfigName) ? setting.DefaultDatabase : dbConfigName;
  291. connectionString = ConfigurationManager.ConnectionStrings[connection].ConnectionString;
  292. #region 加密解密操作
  293. //使用自定义加密
  294. //if (!connectionString.EndsWith(";"))
  295. //{
  296. // connectionString += ";";
  297. //}
  298. //connectionString += string.Format(";Password=wuhuacong2013;");
  299. string password = GetSubValue(connectionString, "password");
  300. if (!string.IsNullOrEmpty(password))
  301. {
  302. //尝试使用AES解密
  303. string decryptStr = password;
  304. try
  305. {
  306. decryptStr = EncodeHelper.AES_Decrypt(password);
  307. }
  308. catch
  309. {
  310. decryptStr = password;
  311. //throw new InvalidOperationException("无法解密数据库");
  312. }
  313. connectionString += string.Format(";Password={0};", decryptStr);
  314. }
  315. #endregion
  316. }
  317. return connectionString;
  318. }
  319. #endregion
  320. }
  321. }