简体   繁体   English

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

[英]How do you access data that has been inserted using a ADO.NET transaction?

I'm trying to get the data that has been successfully input into the database via ADO.NET transaction. 我正在尝试获取已通过ADO.NET事务成功输入到数据库中的数据。

Once you've called trans.Commit() there doesn't seem to be a way of getting back the data that has been committed since all identity columns that were created during the transaction are 'virtual' since it is an offline dataset until commit 调用trans.Commit()后,似乎没有办法取回已提交的数据,因为在事务处理期间创建的所有标识列都是“虚拟的”,因为它是一个脱机数据集,直到提交为止

Many thanks 非常感谢

[EDIT] [编辑]

Ahh, the problem is, I can't do a reselect as I don't have anything unique to select on other than the identity of the data inserted as part of the transaction. 嗯,问题是,我无法进行重新选择,因为除了作为事务一部分插入的数据的身份之外,我没有别的唯一选择。

I can't get the last entered item as this is a multiuser system 我无法获得最后输入的项目,因为这是一个多用户系统

Code Sample from a book, not the code in question, but good enough to illustrate what I need: 书中的代码示例,不是问题代码,但足以说明我的需要:

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( );
            }
        }
    }
}

Okay, so what i'm after is just after the transaction commit, I want to get the (scope) identity of the the last inserted row. 好的,所以我要做的只是在事务提交之后,我想获得最后插入的行的(作用域)标识。

My application is successful in updating three dataadapters as part of the transaction, however I am having dificulty looking at the final committed data. 我的应用程序成功地更新了三个数据适配器,并将其作为事务的一部分,但是我很难看待最终提交的数据。 I can do a select of the table and see it in there, but that really isn't good enough for production code. 我可以选择一个表并在其中查看,但这对于生产代码来说确实不够好。

SC SC

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

The Books Online says that you should call a Fill again to bring the update your Dataset: 联机丛书说,您应该再次致电Fill来进行数据集更新:

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

I generally set my Insert and Update commands so that they they return back a valid DataRow for my DataTable and control the update of the rows in the application that way. 我通常设置我的插入和更新命令,以便它们为我的数据表返回有效的数据行,并以此方式控制应用程序中行的更新。

Right so I should do: 是的,所以我应该这样做:

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

I assume all the identity colums will be updated. 我假设所有身份列都会更新。

I'll give it a go 我去吧

SC SC

I understand you're using identity columns, but is there any natural key in the data you can use to reselect? 我了解您使用的是身份列,但是数据中是否有任何自然键可用于重新选择?

(that then raises the question of 'why use identities' but that's a whole other subject...) (然后提出了“为什么使用身份”的问题,但这是另一个主题……)

Unfortunately no, I cannot reselect using a natural key... I'm stuck with identities... after 8 hours of head banging I contemplated adding a guid field so I could get it to work, but decided that it is against my principles to give up! 不幸的是,不行,我无法使用自然键进行重新选择...我一直受困于身份...在敲打头部8小时后,我打算添加一个Guid字段,以使其能够正常工作,但认为这违反了我的原则放弃!

SC SC

此MSDN本文介绍如何在调用DataAdapter的Update方法时取回标识值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM