数据库事务(简称: 事务)是数据库管理系统执行过程中的一个逻辑单位,由一个有限的数据库操作序列构成。当事务被提交给了DBMS(数据库管理系统),则DBMS(数据库管理系统)需要确保该事务中的所有操作都成功完成且其结果被永久保存在数据库中,如果事务中有的操作没有成功完成,则事务中的所有操作都需要被回滚,回到事务执行前的状态;同时,该事务对数据库或者其他事务的执行无影响,所有的事务都好像在独立的运行。
事务的特性(ACID性质)
原子性(Atomic)
事务作为一个整体被执行,包含在其中的对数据库的操作要么全部被执行,要么都不执行。
一致性(Consistency)
事务应确保数据库的状态从一个一致状态转变为另一个一致状态。一致状态的含义是数据库中的数据应满足完整性约束。
隔离性(Isolation)
多个事务并发执行时,一个事务的执行不应影响其他事务的执行。
持久性(Durability)
已被提交的事务对数据库的修改应该永久保存在数据库中。
下面介绍事务的具体使用。
事务在数据库中的使用
- BEGIN TRANSACTION
- --向Table1表中插入记录
- INSERT INTO Table1 VALUES('1','1')
- SET @Err1=@@ERROR
- --向Table2表插入记录
- INSERT INTO Table2 VALUES('1','1')
- SET @Err2=@@ERROR
- IF(@Err1=0 AND @Err2=0)
- COMMIT TRANSACTION --事务提交
- ELSE
- ROLLBACK TRANSACTION --事务回滚
@@ERROR:完成 Transact-SQL 语句的执行时,如果语句执行成功,则 @@ERROR 设置为 0。若出现一个错误,则返回一条错误信息。@@ERROR 返回此错误信息代码,直到另一条 Transact-SQL 语句被执行。
事务在.NET代码中的使用
首先添加引用usingSystem.Transactions;
(1)只在D层使用事务
- //设定事务的级别
- TransactionOptions option = new TransactionOptions();
- option.IsolationLevel = System.Transactions.IsolationLevel.ReadCommitted;
- using (TransactionScope ts = new TransactionScope(TransactionScopeOption.Required, option))
- {
- //标志是否更改成功
- bool flag = false;
- bool flagUpdate = false;
- //更新Table1中数据
- string sqlUpText = "UPDATE Table1 SET actionReason = '1'";
- flagUpdate = sqlHelper.ExecuteNonQuery(sqlUpText,CommandType.Text);
- //更新Table2中数据
- string sqlText = "UPDATE Table2 SET isAvailable ='否' ";
- flag = sqlHelper.ExecuteNonQuery(sqlText, CommandType.Text);
- if (flag && flagUpdate)
- {
- ts.Complete();
- return true;
- }
- else {
- return false;
- }
- }
(2)事务在B层的使用
B层代码
- //首先引用 System.Data和System.Data.SqlClient命名空间
- //定义事务执行所使用的链接
- SqlConnection sqlCon = new SqlConnection(ConfigurationManager.ConnectionStrings["strConnDB"].ToString());
- //打开连接
- sqlCon.Open();
- //定义事务
- SqlTransaction sqlTran = sqlCon.BeginTransaction(IsolationLevel.ReadCommitted);
- //用try...Catch...finally保证事务在出错时会回滚
- try
- {
- //向课程表中添加数据
- OptionalCourseScheduleLinkDAL OptionalCourseSchedule = new OptionalCourseScheduleLinkDAL();
- //将新建立的连接和事务一起传回D层
- IsAddOptionalCourseSchedule = OptionalCourseSchedule.AddOptionalCourseSchedule(enOptionalCourseSchedule,sqlCon,sqlTran);
- //更新授课关系表中的单双周
- CourseTeachClassLinkDAL CourseTeachClass = new CourseTeachClassLinkDAL();
- //添加D层的方法,调用sqlHelper中执行事务的方法:ExecNoSelect(string cmdText, SqlParameter[] paras, CommandType cmdType, SqlConnection sqlConns, SqlTransaction sqlTran)
- //将新建立的连接和事务一起传回D层
- IsUpdateCourseTeachClass = CourseTeachClass.UpdateCourseTeachClassOddEven(enCourseTeachClass,sqlCon,sqlTran);
- //若添加和更新有一者返回false,事务回滚
- if (IsAddOptionalCourseSchedule && IsUpdateCourseTeachClass)
- {
- //如果都为真,提交
- sqlTran.Commit();
- sqlCon.Close();
- return true;
- }
- else {
- sqlTran.Rollback();
- }
- }
- catch (Exception)
- {
- //出现异常时,事物回滚
- sqlTran.Rollback();
- }
- finally {
- sqlCon.Close();
- }
- return false;
D层代码
- public Boolean AddOptionalCourseSchedule(OptionalCourseScheduleLinkEntity enOptionalCourseScheduleLink, SqlConnection sqlCon, SqlTransaction sqlTran)
- {
- //声明一个布尔型变量
- Boolean blnIsResult = false;
- //执行SQL字符串名
- string strSQL = "insert into TBR_OptionalCourseScheduleLink(TeachClassID,RoomID,WorkDay,ClassBegin,ClassEnd) VALUES(@TeachClassID,@RoomID,@WorkDay,@ClassBegin,@ClassEnd)";
- //字符串数组
- SqlParameter[] param = new SqlParameter[]
- {
- new SqlParameter("@TeachClassID",enOptionalCourseScheduleLink.TeachClassID),//虚拟班ID
- new SqlParameter("@RoomID",enOptionalCourseScheduleLink.RoomID),//房间ID
- new SqlParameter("@WorkDay",enOptionalCourseScheduleLink.WorkDay),//星期
- new SqlParameter("@ClassBegin",enOptionalCourseScheduleLink.ClassBegin),//开始时间(如:上午第一节)
- new SqlParameter("@ClassEnd",enOptionalCourseScheduleLink.ClassEnd)//结束时间
- };
- //SQL语句类型
- CommandType cmdType = CommandType.Text;
- //SQLHELPER函数返回值
- blnIsResult = sqlHelper.ExecNoSelect(strSQL, param, cmdType, sqlCon, sqlTran);
- //返回函数值
- return blnIsResult;
- }
SqlHelper中关于事务的代码
- #region 执行sql语句(事务中使用)
- /// <summary>执行sql语句(事务中使用)
- /// 执行sql语句(事务中使用)
- /// </summary>
- /// <param name="cmdText">在事务中执行的某个SQL语句或存储过程</param>
- /// <param name="paras">参数集合</param>
- /// <param name="cmdType">命令类型</param>
- /// <param name="sqlConn">数据库连接</param>
- /// <param name="sqlTran">事务</param>
- public Boolean ExecNoSelect(string cmdText, SqlParameter[] paras, CommandType cmdType, SqlConnection sqlConns, SqlTransaction sqlTran)
- {
- try
- {
- //实例化数据库命令SqlCommand
- sqlCmd = new SqlCommand(cmdText, sqlConns);
- //命令类型:存储过程or SQL语句
- sqlCmd.CommandType = cmdType;
- //添加参数
- sqlCmd.Parameters.AddRange(paras);
- //事务
- sqlCmd.Transaction = sqlTran;
- //定义事务执行结果
- int intResult = sqlCmd.ExecuteNonQuery();
- //执行事务:大于0返回true,否则返回false。
- if (intResult > 0)
- {
- //事务执行成功
- return true;
- }
- else
- {
- //事务执行失败
- return false;
- }
- }
- catch (Exception ex)
- {
- //抛出异常
- throw ex;
- }
- }
- #endregion