10. maj 2003 - 10:49Der er
8 kommentarer og 1 løsning
Returnere ny IDENTITY fra SQL Server via dataadapater
Jeg ønsker indsætte en ny række i en simpel tabel i en SQL Server 2000 database, og skal umiddelbart derefter bruge dén værdi som SQL Server har givet den nye række i ID-feltet, som er et identity/primary key felt.
Tabellen, tbl_Test, indeholder kun to felter, og ser sådan ud: ID (int, identity, autoincrement = 1) strTitle (varchar(50)
Min VB.NET kode ser således ud:
'######### dim cnnCon as new SQLClient.SQLConnection(strConn) dim daData as new SQLClient.SQLDataAdapter("SELECT ID, strTitle FROM tbl_Test", cnnCon) dim cbCmdBuilder as new SQLClient.SQLCommandBuilder(daData)
dim dsData as new DataSet()
daData.Fill(dsData, "tbl_Test")
dim rwRow as DataRow rwRow = dsData.Tables("tbl_Test").NewRow() rwRow.Item("ID") = 0 rwRow.Item("strTitle") = "Hello World" dsData.Tables("tbl_Test").Rows.Add(rwRow)
trace.warn(rwRow.Item("ID")) ' ##### Og HER går det så galt: rwRow.Item("ID") indeholder stadigvæk 0 (nul), og selv hvis jeg ikke giver den nogen værdi før daData.Update(..) sker der heller ingenting. Rækken bliver iøvrigt fint indsat i tabellen som forventet.
Normalt plejer jeg at lave alle INSERT statements via Stored Procedures, som slutter af med at returnere den nye ID-værdi, men det er desværre ikke en mulighed i det pågældende projekt (don't ask). Fusk-løsninger med at slutte af med en SELECT MAX(ID) dur selvsagt heller ikke... :)
Så mit spørgsmål er følgende: Hvordan får jeg den SQL Server-tildelte primær nøgle værdi ud, når jeg indsætter data via et dataset og tilhørende dataadapter???
Jeg håber I kan hjælpe mig, på forhånd tak for hjælpen.
Umiddelbart tror jeg ikke det er løsningen (eller om det overhovedet kan lade sig gøre). Et dataset indeholder en slags disconnected kopi af dataene fra tabellen, og man kan foretage updates, inserts og deletes, for så til sidst at lave én batchupdate som commit'er data tilbage til databasen. Det er altså ikke muligt i denne problemstilling at ligge noget logik på database-siden udover den fortløbende primærnøgle i tabellen.
Og selvom det er en disconnected kopi af data, så må den enten kommunikere det autoincremented numre til databasen eller vente med at generere dem indtil de bliver committed, fordi ellers kan den jo ikke garantere uniqueness.
Det er lige præcis hvad der sker: .NET-koden aner ikke en meter om hvilken værdi SQL Serveren har tænkt sig at tildele den FØR der bliver committed til databasen igen, hvis jeg eksempelvis angiver en værdi i ID-feltet, bliver det ignoreret når dataene bliver gemt og erstattet af en "rigtig" unik primærnøgle. Og det er hér mit spørgsmål bliver relevant, jeg forventede at rwRow.Item("ID") ville indeholde den tildelte værdi, men det gør den tilsyneladende ikke...
Du skal være sikker på at det er den samme forbindelse du bruger. Update-funktionen åbner og lukker selv forbindelsen til databasen (cnnCon) hvis ikke den er åben i forvejen, men hvis den er det forbliver den også åben og du kan save din "SELECT @@IDENTITY AS 'Identity'". Prøv sådan her.
cnnCon.Open(); Update(); AcceptChanges(); daData.Fill(dsData, "SELECT @@IDENTITY AS 'Identity'") cnnCon.Close();
så tror jeg den er der.
Synes godt om
Ny brugerNybegynder
Din løsning...
Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.