ADO.Net Improvements in .Net 2.0

2,281 views
2,224 views

Published on

New features for data access in .Net 2.0

Published in: Technology
1 Comment
0 Likes
Statistics
Notes
  • Be the first to like this

No Downloads
Views
Total views
2,281
On SlideShare
0
From Embeds
0
Number of Embeds
1
Actions
Shares
0
Downloads
111
Comments
1
Likes
0
Embeds 0
No embeds

No notes for slide
  • ADO.Net Improvements in .Net 2.0

    1. 1. Data Access Changes in .Net 2.0 David Truxall, Ph.D. Principal Consultant NuSoft Solutions
    2. 2. Agenda <ul><li>Enhancements to the DataSet class </li></ul><ul><li>SqlClient Enhancements </li></ul><ul><ul><li>Asynchronous Commands </li></ul></ul><ul><ul><li>SQL Cache Dependency </li></ul></ul><ul><li>SQL Server 2005 Integration </li></ul><ul><ul><li>Multiple Active Result Sets </li></ul></ul><ul><li>Generic Data Structures </li></ul><ul><ul><li>List<T> </li></ul></ul><ul><ul><li>Dictionary </li></ul></ul>
    3. 3. DataSet Enhancements <ul><li>Performance and scalability improvements </li></ul><ul><li>Loading a DataSet, and the new LoadOption enumeration </li></ul><ul><li>Stand-alone DataTable instances </li></ul><ul><li>Batched updates </li></ul><ul><li>XML data type - usability and fidelity </li></ul><ul><li>User-defined Types in a DataSet </li></ul>
    4. 4. Performance Improvements <ul><li>Internal Indexing of Rows </li></ul><ul><ul><li>Inserts and deletes are log-n </li></ul></ul><ul><ul><li>Updates almost constant </li></ul></ul><ul><li>Binary Serialization of Contents </li></ul><ul><ul><li>V 1.x DataSet always serialized to XML </li></ul></ul><ul><ul><ul><li>good for data interchange, bad for performance </li></ul></ul></ul><ul><ul><li>Binary serialization an option in V 2.0 </li></ul></ul><ul><ul><ul><li>fast and compact, especially as row counts increase </li></ul></ul></ul><ul><ul><ul><li>just set: DataSet.RemotingFormat = SerializationFormat.Binary </li></ul></ul></ul>
    5. 5. Binary v XML Serialization Up to 80 x faster for large DataSets!
    6. 6. Loading a DataSet <ul><li>DataAdapter.Fill(DataSet,&quot;table-name&quot;) </li></ul><ul><ul><li>NEW: DataAdapter.FillLoadOption and AcceptChangesDuringUpdate properties </li></ul></ul><ul><li>NEW: DataSet.Load method </li></ul><ul><ul><li>Load(DataReader [, load-option] [, tables-array]) </li></ul></ul><ul><ul><ul><li>optionally can use FillErrorEventHandler to trap errors </li></ul></ul></ul><ul><li>NEW: LoadOption enumeration </li></ul><ul><ul><li>PreserveCurrentValues | UpdateCurrentValues | OverwriteRow </li></ul></ul>
    7. 7. More New Features <ul><li>RowState values are now updateable </li></ul><ul><ul><li>New methods: DataRow.SetAdded and DataRow.SetModified </li></ul></ul><ul><li>DataSet.GetDataReader method </li></ul><ul><ul><li>returns a DataTableReader </li></ul></ul><ul><ul><li>you can specify which tables to include </li></ul></ul>
    8. 8. <ul><li>Loading a DataSet with a DataReader </li></ul><ul><li>Binary Serialization </li></ul><ul><li>Using a DataTableReader </li></ul>
    9. 9. Stand-alone DataTable Instances <ul><li>Common DataSet operations now also available on DataTable: </li></ul><ul><ul><li>ReadXml, ReadXmlSchema, WriteXml, WriteXmlSchema, Clear, Clone, Copy, Merge, GetChanges </li></ul></ul><ul><li>DataTable is now auto-serializable: </li></ul><ul><ul><li>return a DataTable instance from a Web Service or via Remoting </li></ul></ul>
    10. 10. Loading and Using a DataTable <ul><li>DataAdapter.Fill(DataTable) </li></ul><ul><li>DataAdapter.Fill(DataTable[ ]) </li></ul><ul><ul><li>and more, including subsets of rows </li></ul></ul><ul><li>DataAdapter.Update(DataTable) </li></ul><ul><li>DataTable.Load(DataReader [, load-option] [, FillErrorEventHandler]) </li></ul><ul><ul><li>new methods: BeginLoadData, Load, EndLoadData </li></ul></ul><ul><li>DataTable.GetDataReader method </li></ul><ul><ul><li>stream data from a DataTable </li></ul></ul>
    11. 11. Batched Updates <ul><li>DataSet updates are normally processed one by one </li></ul><ul><li>Batching reduces network round-trips </li></ul><ul><li>DataAdapter.UpdateBatchSize = batch_size </li></ul><ul><li>Works inside transactions </li></ul><ul><li>Works with SQL Server 7.0, 2000, 2005 </li></ul><ul><li>Also available for OracleClient classes </li></ul>
    12. 12. <ul><li>Stand-alone DataTable </li></ul><ul><li>Batched Updates feature </li></ul>
    13. 13. XML Data Types in a DataSet <ul><li>The DataTable accepts columns of data-type 'xml' </li></ul><ul><ul><li>type is System.Data.SqlTypes.SqlXml </li></ul></ul><ul><ul><ul><li>defaults to a String unless DataAdapter. UseProviderSpecificType = true </li></ul></ul></ul><ul><ul><li>exposed as an XPathDocument instance </li></ul></ul><ul><ul><li>can also be accessed via an XmlReader </li></ul></ul><ul><ul><li>makes it easier to work with XML as a document rather than a rowset of values </li></ul></ul><ul><ul><li>maintains fidelity of the XML content </li></ul></ul>
    14. 14. User-Defined Types in a DataSet <ul><li>Populate DataSet with SQL or Stored Procedure </li></ul><ul><li>Update with SQL Statement or Stored Procedure </li></ul><ul><ul><li>create the Command and Parameters </li></ul></ul><ul><ul><ul><li>param = da.UpdateCommand.Parameters.Add (&quot;@ name &quot;,SqlDbType.Udt) </li></ul></ul></ul><ul><ul><ul><li>param.UdtTypeName = &quot; type-name &quot; </li></ul></ul></ul><ul><ul><ul><li>param.SourceColumn = &quot; column-name &quot; </li></ul></ul></ul><ul><ul><li>or can use a SqlCommandBuilder </li></ul></ul><ul><ul><ul><li>use timestamp column for conflict resolution </li></ul></ul></ul><ul><ul><ul><li>otherwise UDT conflicts will not be detected </li></ul></ul></ul>
    15. 15. Agenda <ul><li>Enhancements to the DataSet class </li></ul><ul><li>SqlClient Enhancements </li></ul><ul><ul><li>Asynchronous Commands </li></ul></ul><ul><ul><li>SQL Cache Dependency </li></ul></ul><ul><li>SQL Server 2005 Integration </li></ul><ul><ul><li>Multiple Active Result Sets </li></ul></ul><ul><li>Generic Data Structures </li></ul><ul><ul><li>List<T> </li></ul></ul><ul><ul><li>Dictionary </li></ul></ul>
    16. 16. Asynchronous Commands <ul><li>Ideal for multiple database queries </li></ul><ul><li>Usual Begin xxx and End xxx model </li></ul><ul><li>Supports Polling, Wait and Callback models </li></ul><ul><li>Catching asynchronous execution errors </li></ul><ul><li>Should not generally be used with MARS </li></ul><ul><ul><li>use a separate connection for each Command </li></ul></ul><ul><li>Add &quot;async=true&quot; to connection string </li></ul>
    17. 17. Asynchronous Polling Model <ul><li>Start asynchronous command execution: </li></ul><ul><ul><li>IAsyncResult result = MyCommand.BeginExecuteReader() </li></ul></ul><ul><li>Wait until execution is complete: </li></ul><ul><ul><li>while (! result.IsCompleted) { </li></ul></ul><ul><ul><li> // execute other code here </li></ul></ul><ul><ul><li>} </li></ul></ul><ul><li>Fetch results: </li></ul><ul><ul><li>SqlDataReader reader = MyCommand.EndExecuteReader(result ) </li></ul></ul>
    18. 18. Asynchronous Wait (All) Model <ul><li>Start one or more asynchronous commands: </li></ul><ul><ul><li>IAsyncResult result x = MyCommand.BeginExecuteReader() </li></ul></ul><ul><li>Wait for all commands to complete: </li></ul><ul><ul><li>WaitHandle.WaitAll(new WaitHandle[] {result1.AsyncWaitHandle, result2.AsyncWaitHandle, result3.AsyncWaitHandle}, timeout-ms, true) </li></ul></ul><ul><li>Fetch results: </li></ul><ul><ul><li>SqlDataReader reader = MyCommand.EndExecuteReader(result x ) </li></ul></ul><ul><li>Ideal for ASP.NET Web applications </li></ul>
    19. 19. Asynchronous Wait (Any) Model <ul><li>Start one or more asynchronous commands as an array of IAsyncResult instances: </li></ul><ul><ul><li>IAsyncResult result x = MyCommand.BeginExecuteReader() </li></ul></ul><ul><li>Wait for each command to complete: </li></ul><ul><ul><li>for(int i=0; i < result_array.Length, i++) { </li></ul></ul><ul><ul><li>index = WaitHandle.WaitAny(result_array, </li></ul></ul><ul><ul><li>timeout, true); </li></ul></ul><ul><ul><li> switch(index) { </li></ul></ul><ul><ul><li>case 0: SqlDataReader reader = </li></ul></ul><ul><ul><li> MyCommand.EndExecuteReader(result x ); </li></ul></ul><ul><ul><li> ...etc... </li></ul></ul>
    20. 20. Asynchronous Callback Model <ul><li>Start execution, specifying callback and passing command as the AsyncState: </li></ul><ul><ul><li>MyCommand.BeginExecuteReader(new AsyncCallback(MyCallback), cmd) </li></ul></ul><ul><li>Provide a callback handler: </li></ul><ul><ul><li>void MyCallback(IAsyncResult result) { </li></ul></ul><ul><ul><li> SqlCommand cmd = </li></ul></ul><ul><ul><li>(SqlCommand) result.AsyncState; </li></ul></ul><ul><ul><li> SqlDataReader reader = </li></ul></ul><ul><ul><li>cmd.EndExecuteReader(result); </li></ul></ul><ul><ul><li>} </li></ul></ul>
    21. 21. Catching Timeouts and Errors <ul><li>For the WaitOne and WaitAll methods: </li></ul><ul><ul><li>use try/catch around each &quot;End&quot; method </li></ul></ul><ul><li>For the WaitAny method: </li></ul><ul><ul><li>return value is equal to timeout value </li></ul></ul><ul><li>When using the Callback model: </li></ul><ul><ul><li>use try/catch around &quot;End&quot; method </li></ul></ul>
    22. 22. <ul><li>Asynchronous Commands </li></ul><ul><li>Execution Models </li></ul>
    23. 23. Agenda <ul><li>Enhancements to the DataSet class </li></ul><ul><li>SqlClient Enhancements </li></ul><ul><ul><li>Asynchronous Commands </li></ul></ul><ul><ul><li>SQL Cache Dependency </li></ul></ul><ul><li>SQL Server 2005 Integration </li></ul><ul><ul><li>Multiple Active Result Sets </li></ul></ul>
    24. 24. Notifications & SqlDependency <ul><li>Cache the data and then be notified when ANYTHING happens that would give a different result if the query was re-executed </li></ul><ul><li>Uses SQL Server 2005 Query Notifications </li></ul><ul><ul><li>bind SqlDependency to Command and execute it </li></ul></ul><ul><ul><li>fully integrated with ASP.NET as well </li></ul></ul><ul><li>Notifications Service for SQL 2000 </li></ul><ul><ul><li>Query Notifications add-in available </li></ul></ul>
    25. 25. Creating a SqlDependency <ul><li>Bind a SqlDependency to Command: </li></ul><ul><li>SqlDependency dependency = new SqlDependency(cmd); </li></ul><ul><li>Specify the Callback Handler: </li></ul><ul><li>dep.OnChanged += new OnChangedEventHandler(DataChanged); </li></ul><ul><li>Add Callback Handler to project: </li></ul><ul><li>static void DataChanged(Object sender, SqlNotificationEventArgs args) </li></ul><ul><li>{ // display details of the event </li></ul><ul><li>// refresh the data that was displayed last } </li></ul><ul><li>Execute the Command: </li></ul><ul><li>reader = cmd.ExecuteReader(); </li></ul>
    26. 26. Agenda <ul><li>Enhancements to the DataSet class </li></ul><ul><li>SqlClient Enhancements </li></ul><ul><ul><li>Asynchronous Commands </li></ul></ul><ul><ul><li>SQL Cache Dependency </li></ul></ul><ul><li>SQL Server 2005 Integration </li></ul><ul><ul><li>Multiple Active Result Sets </li></ul></ul><ul><li>Generic Data Structures </li></ul><ul><ul><li>List<T> </li></ul></ul><ul><ul><li>Dictionary </li></ul></ul>
    27. 27. Multiple Active Results Sets <ul><li>Perform other database operations while a SqlDataReader is open on the connection </li></ul><ul><ul><li>execute another query to get another DataReader/XmlReader </li></ul></ul><ul><ul><li>execute DML statements </li></ul></ul><ul><li>Multiple results sets can be active </li></ul><ul><ul><li>interleave fetches to each Reader </li></ul></ul><ul><ul><li>interleave queries that do not return a result set </li></ul></ul>
    28. 28. Interleaving Results Sets <ul><li>Typical scenario: </li></ul><ul><ul><li>get a list of customers and iterate through them </li></ul></ul><ul><ul><li>for each customer, get a list of orders </li></ul></ul><ul><ul><li>for each order, get a list of order lines </li></ul></ul><ul><li>Previously this would require multiple connections </li></ul><ul><li>With MARS, use only one connection </li></ul><ul><ul><li>providing data is in the same database </li></ul></ul><ul><ul><li>requires SQL Server 2005 or MDAC9 </li></ul></ul>
    29. 29. Interleaved Results Sets Example <ul><li>DataReader parentReader = Command1.ExecuteReader(); </li></ul><ul><li>while (parentReader.Read()) { </li></ul><ul><li>// process parent row data here </li></ul><ul><li>// then get rowset from child table </li></ul><ul><li>Command2.Parameters[&quot;@id&quot;].Value </li></ul><ul><li>= parentReader[&quot;id&quot;]; </li></ul><ul><li>DataReader childReader </li></ul><ul><li>= Command2.ExecuteReader(); </li></ul><ul><li>// process child rows here </li></ul><ul><li>childReader.Close(); </li></ul><ul><li>} </li></ul><ul><li>parentReader.Close(); </li></ul>
    30. 30. <ul><li>Multiple Active Result Sets </li></ul>
    31. 31. Agenda <ul><li>Enhancements to the DataSet class </li></ul><ul><li>SqlClient Enhancements </li></ul><ul><ul><li>Asynchronous Commands </li></ul></ul><ul><ul><li>SQL Cache Dependency </li></ul></ul><ul><li>SQL Server 2005 Integration </li></ul><ul><ul><li>Multiple Active Result Sets </li></ul></ul><ul><li>Generic Data Structures </li></ul><ul><ul><li>List<T> </li></ul></ul><ul><ul><li>Dictionary </li></ul></ul>
    32. 32. Generics - List<T> <ul><li>Self Re-dimensioning array </li></ul><ul><li>Similar to ArrayList but better </li></ul><ul><ul><li>Type-safe == faster </li></ul></ul><ul><ul><li>Easy to cast </li></ul></ul>List<string> employees = new List<string> employees.Add(“Joe”); employees.Add(“Jane”); string[] developers = employees.ToArray();
    33. 33. Generics – Dictionary<T, F> <ul><li>A type-safe Hashtable </li></ul><ul><li>Add, Remove, and Search are Constant time: O (1) </li></ul><ul><li>Different Collision resolution </li></ul>
    34. 34. © 2005 Microsoft Corporation. All rights reserved. This presentation is for informational purposes only. Microsoft makes no warranties, express or implied, in this summary.

    ×