如何访问使用ADO.NET事务插入的数据?

时间:2009-06-02 15:47:56

标签: sql sql-server-2005 ado.net transactions

我正在尝试通过ADO.NET事务获取已成功输入数据库的数据。

一旦调用了trans.Commit(),似乎没有办法找回已提交的数据,因为在事务期间创建的所有标识列都是“虚拟”,因为它是脱机的数据集直到提交

非常感谢

[编辑]

啊,问题是,我不能重新选择,因为除了作为交易的一部分插入的数据的身份之外,我没有任何独特的选择。

我无法获取最后输入的项目,因为这是一个多用户系统

代码来自一本书的样本,而不是有问题的代码,但足以说明我需要的内容:

using System.Data;
using System.Data.SqlClient;

namespace DataAdapterTransaction
{
    class Program
    {
        private static string sqlConnectString = "Data Source=(local);" +
            "Integrated security=SSPI;Initial Catalog=AdoDotNet35Cookbook;";

        private static string sqlSelect = "SELECT * FROM DataAdapterTransaction";

        static void Main(string[] args)
        {
            object[,] o1 = {{ "1", "field 1.1", "field 2.1" },
                          { "2", "field 1.2", "field 2.2" }};
            InsertRecords(o1);

            object[,] o2 = {{ "3", "field 1.3", "field 2.3" },
                           { null, "field 1.4", "field 2.4" }};
            InsertRecords(o2);

            // Retrieve and output the contents of the table
            SqlDataAdapter daRead = new SqlDataAdapter(sqlSelect, sqlConnectString);
            DataTable dtRead = new DataTable( );
            daRead.Fill(dtRead);
            Console.WriteLine("---TABLE DataAdapterTransaction---");
            foreach (DataRow row in dtRead.Rows)
                Console.WriteLine("Id = {0}\tField1 = {1}\tField2 = {2}",
                    row["Id"], row["Field1"], row["Field2"]);

            Console.WriteLine("\nPress any key to continue.");
            Console.ReadKey( );
        }

        static void InsertRecords(object[,] o)
        {
            DataTable dt = new DataTable( );
            SqlTransaction tran;

            SqlConnection connection = new SqlConnection(sqlConnectString);

            // Create a DataAdapter
            SqlDataAdapter da = new SqlDataAdapter(sqlSelect, connection);
            // Stop updating when an error is encountered for roll back.
            da.ContinueUpdateOnError = false;
            // Create CommandBuilder and generate updating logic.
            SqlCommandBuilder cb = new SqlCommandBuilder(da);
            // Create and fill a DataTable with schema and data
            da.Fill(dt);
            // Open the connection
            connection.Open( );
            // Begin a new transaction and assign it to the DataAdapter
            tran = connection.BeginTransaction( );
            da.SelectCommand.Transaction = tran;

            // Add two rows that will succeed update
            for (int i = 0; i <= o.GetUpperBound(0); i++)
            {
                dt.Rows.Add(new object[] { o[i, 0], o[i, 1], o[i, 2] });
                Console.WriteLine(
                    "=> Row with [Id = {0}] added to DataTable.", o[i, 0]);
            }

            Console.WriteLine("=> Updating data source using DataAdapter.");
            try
            {
                da.Update(dt);
                tran.Commit( );

                Console.WriteLine("\nTRANSACTION COMMIT.\n");
            }
            catch (Exception ex)
            {
                tran.Rollback( );
                Console.WriteLine("\nTRANSACTION ROLLBACK.\n{0}\n", ex.Message);
            }
            finally
            {
                connection.Close( );
            }
        }
    }
}

好的,我所追求的就是在事务提交之后,我想得到最后一个插入行的(范围)标识。

我的应用程序成功更新了三个数据适配器作为事务的一部分,但是我正在查看最终提交的数据。我可以选择一个表并在那里看到它,但这对于生产代码来说真的不够好。

SC

6 个答案:

答案 0 :(得分:1)

您可能只需要重新选择数据。

答案 1 :(得分:0)

联机丛书表示,您应该再次致电填写以更新您的数据集:

http://msdn.microsoft.com/en-us/library/33y2221y(VS.71).aspx

我通常设置我的插入和更新命令,以便他们为我的DataTable返回一个有效的DataRow,并以这种方式控制应用程序中行的更新。

答案 2 :(得分:0)

是的,所以我应该这样做:

// update datatable
da.Update(dt);
// commit updates
tran.Commit( );
// get the updated datatable
da.Fill(dt);

我假设所有的标识栏都会更新。

我会试一试

SC

答案 3 :(得分:0)

我知道您正在使用标识列,但是您可以使用重新选择的数据中是否有任何自然键?

(然后提出了“为什么要使用身份”的问题,但这是另一个主题......)

答案 4 :(得分:0)

不幸的是,不能,我无法使用自然键重新选择...我被困在身份......经过8个小时的头撞击后,我打算添加一个guid字段,这样我就能让它工作,但我决定它是反对我的原则放弃!

SC

答案 5 :(得分:0)

This MSDN article描述了在调用DataAdapter的Update方法时如何获取标识值。