WebService处理分布式数据库事务

  注:摘自单刀向斜阳  http://hi.baidu.com/free_leo/blog/item/015c2734afb2dc385bb5f5c0.html

 

   如果在WEB服务中有这样一个场景,某个WEB服务的方法要执行两个任务,它首先要在数据库中创建一个新表,接着调用对象来收集和格式化数据,并在新表中插入数据。象这样的一组方法,我们必须保证他们都成功执行,否则会造成很多脏数据在系统中,这时事务就出场了。
关于事务的基本概念再次就不过多涉及,只需要记住它的四个属性ACID即可。
WEB服务中的事务是用WebMethod特性的TransactionOption属性来申明的。如果WEB服务方法执行时发生异常,则自动会终止事务,反之则提交事务。WEB服务的方法仅有两种可能的行为:Disabled,NotSupported,Supported表示不参与事务;Required,RequiresNew表示创建一个新的事务。意思是说当TransactionOption的属性为Required或RequiresNew的WEB服务方法调用另一个TransactionOption的属性为Required或RequiresNew的WEB服务方法时,每个WEB服务方法将参与他们自己的事务。
PS:WEB服务方法的TransactionOption默认属性为Disabled
同时我们也可以显示调用System.EnterpriseServices.ContextUtil类的SetAbort方法取消事务,调用SetCompleted方法完成事务。
例子1:
using System.EnterpriseServices;
Class WebServiceTransaction:WebService
{
    pulic void Write(string user,string msg)
    {
      //将接收这两个参数写入数据库。。。
    }

    [WebMethod(TransactionOption=TransactionOption.RequiresNew)]
    public void WiteToDataBaseV2(string user,string msg)
    {
       Write(user,msg);
       if(user!="kim")
       {
        ContextUtil.SetAbort();
       }
        else
       {
          ContextUtil.SetComplete();
       }
    }
}

例子2:

    public void test2()
    {
        try
        {
            ServiceConfig sc = new ServiceConfig();
            //指定事务类型
            sc.Transaction = TransactionOption.Required;
            //设置启动跟踪
            sc.TrackingEnabled = true;
            //创建一个上下文,该上下文的配置由作为 cfg 参数传递的 ServiceConfig 对象来指定。
            //随后,客户端和服务器端的策略均被触发,如同发生了一个方法调用。
            //接着,新的上下文被推至上下文堆栈,成为当前上下文
            ServiceDomain.Enter(sc);

            SqlHelper.ExecuteNonQuery(dbConnectionString, CommandType.Text, "insert into ct_order(orderid) values ('001')");
            ContextUtil.SetComplete();
        }
        catch
        {
            ContextUtil.SetAbort();
        }
        finally
        {
            //触发服务器端的策略,随后触发客户端的策略,如同一个方法调用正在返回。
            //然后,当前上下文被弹出上下文堆栈,调用 Enter 时正在运行的上下文成为当前的上下文。
            ServiceDomain.Leave();
        }


测试和预期完全正确。

部署和安装问题:

经常出的错误主要有以下三条:
一、该伙伴事务管理器已经禁止了它对远程/网络事务的支持;
二、在分布式事务中登记时出错;
三、事务被明的或暗的终止。

通常这三条错误是有前后关系的,所以以下这些设置,可能要大多都要设置一次。

解决方案如下:
一、这个问题是因为你没有启用远程/网络事务。因为Win2003默认是不安装这个的。
安装步骤如下:
1. 单击“开始”,指向“控制面板”,然后单击“添加/删除程序”。
2. 单击“添加/删除 Windows 组件”。
3. 选择“应用程序服务器”,然后单击“详细信息”。
4. 选择“启用网络 DTC 访问”,然后单击“确定”。
5. 单击“下一步”。
6. 单击“完成”。
7. 停止分布式事务协调器服务:“Distributed Transaction Coordinator”,然后重新予以启动。
          可以命令行执行:
          net stop msdtc
          net start msdtc
8. 停止参与分布式事务的任何资源管理器服务(如 Microsoft SQL Server 或 Microsoft Message Queue Server),然后重新予以启动。

二、
1、首先检查两台机器的msdtc是否都已经打开了。如是不是,那就全都打开。
2、按如下步骤做设置:

a.点击“开始”按钮,指向管理工具,选择"组件服务"。
   b.展开"组件服务"树,然后展开"我的电脑"。
   c.右键单击"我的电脑",然后选择"属性"。
   d.在   MSDTC   选项卡中,点“安全配置”按钮,
   e.确保选中了下列选项:“网络DTC访问”与"XA事务"
   f.另外,"DTC   登录帐户"一定要设置为"NT   Authority\NetworkService"。

   g.勾选"不要求进行验证" (参与分布事务的全部机器)
3、单击"确定"。这样将会提示您"MS   DTC   将会停止并重新启动。
    所有的依赖服务将被停止。请按'是'继续"。单击"是"继续。
4、.单击"确定"关闭"我的电脑"属性窗口。
5、其他要说明的,在我的案例中没有这些设置,因为都已经满足了
   打开135端口、SQLServer至少打到sp3的补丁,现在已经有sp4了、如果是WIN2000,升级到SP4、升级MDAC到2.6以上,最好是2.8。
三、

在数据库服务器(MS SQL)上的 hosts 文件中加入 Web 服务器(IIS) 的 IP 和 主机名 映射对

a. 定位到 C:\WINDOWS\system32\drivers\etc 目录

b. 记事本打开 hosts 文件(没有扩展名)

c. 添加一行 Web 服务器 IP 和 Web 服务器主机名映射, 两者以至少一个空格相隔, 如

10.10.1.118 MyWebServerHostName

d. Save,OK!

 

posted @ 2010-01-26 13:20  wenhaow  阅读(630)  评论(0)    收藏  举报