Konfigurace připojení vrstvy přístupu k datům a nastavení na úrovni příkazu (C#)
Objekty TableAdapter v zadané datové sadě se automaticky starají o připojení k databázi, vydávání příkazů a naplnění datatable výsledky. Existují ale situace, kdy se chceme o tyto podrobnosti postarat sami, a v tomto kurzu se dozvíme, jak získat přístup k nastavení připojení k databázi a k nastavení na úrovni příkazů v objektu TableAdapter.
Úvod
V celé sérii kurzů jsme použili typed datasets k implementaci vrstvené architektury pro přístup k datům a obchodních objektů. Jak je popsáno v prvním kurzu, typed DataSet s DataTables slouží jako úložiště dat, zatímco Objekty TableAdapter fungují jako obálky pro komunikaci s databází za účelem načtení a úpravy podkladových dat. Funkce TableAdapter zapouzdřují složitost práce s databází a šetří nás před tím, abychom museli psát kód pro připojení k databázi, vydávat příkaz nebo naplnit výsledky do tabulky DataTable.
Někdy se však musíme ponořit do hloubky objektu TableAdapter a napsat kód, který funguje přímo s objekty ADO.NET. V kurzu Zabalení úprav databáze v rámci transakce jsme například do objektu TableAdapter přidali metody pro zahájení, potvrzení a vrácení zpět ADO.NET transakcí. Tyto metody používaly interní ručně vytvořený SqlTransaction
objekt, který byl přiřazen k objektům TableAdapter s SqlCommand
.
V tomto kurzu se podíváme, jak získat přístup k nastavení připojení k databázi a nastavení na úrovni příkazů v objektu TableAdapter. Konkrétně do objektu ProductsTableAdapter
přidáme funkce, které umožní přístup k základnímu nastavení připojovací řetězec a vypršení časového limitu příkazů.
Práce s daty pomocí ADO.NET
Rozhraní Microsoft .NET Framework obsahuje celou řadu tříd navržených speciálně pro práci s daty. Tyto třídy, které se nacházejí v oboruSystem.Data
názvů, se označují jako třídy ADO.NET. Některé třídy pod zastřešující ADO.NET jsou vázané na konkrétního poskytovatele dat. Poskytovatele dat si můžete představit jako komunikační kanál, který umožňuje tok informací mezi ADO.NET třídami a podkladovým úložištěm dat. Existují zobecněné zprostředkovatelé, jako jsou OleDb a ODBC, a také poskytovatelé, kteří jsou speciálně navrženi pro konkrétní databázový systém. Přestože je například možné se připojit k databázi Microsoft SQL Server pomocí zprostředkovatele OleDb, poskytovatel SqlClient je mnohem efektivnější, protože byl navržen a optimalizován speciálně pro SQL Server.
Při programovém přístupu k datům se běžně používá následující model:
- Navázat připojení k databázi.
- Vydejte příkaz.
- U
SELECT
dotazů pracujte s výslednými záznamy.
Pro provedení každého z těchto kroků existují samostatné třídy ADO.NET. Pokud se chcete připojit k databázi pomocí zprostředkovatele SqlClient, použijte SqlConnection
například třídu . Pokud chcete do databáze vydat INSERT
příkaz , UPDATE
DELETE
, neboSELECT
, použijte SqlCommand
třídu .
S výjimkou kurzu Obtékání úprav databáze v rámci kurzu Transakce jsme nemuseli sami zapisovat žádný kód ADO.NET nízké úrovně, protože automaticky vygenerovaný kód TableAdapter obsahuje funkce potřebné pro připojení k databázi, vydávání příkazů, načítání dat a naplnění dat do DataTables. Může se ale stát, že tato nastavení nízké úrovně budeme muset přizpůsobit. V dalších několika krocích prozkoumáme, jak se připojit k objektům ADO.NET, které interně používají Objekty TableAdapter.
Krok 1: Zkoumání vlastnosti připojení
Každá třída TableAdapter má Connection
vlastnost, která určuje informace o připojení k databázi. Datový typ a ConnectionString
hodnota této vlastnosti jsou určeny výběrem provedenými v průvodci konfigurací objektu TableAdapter. Připomeňme si, že když poprvé přidáme TableAdapter do zadané datové sady, tento průvodce nás požádá o zdroj databáze (viz obrázek 1). Rozevírací seznam v tomto prvním kroku obsahuje databáze zadané v konfiguračním souboru a také všechny ostatní databáze v datovém Connections Průzkumníka serveru. Pokud databáze, kterou chceme použít, v rozevíracím seznamu neexistuje, je možné zadat nové připojení k databázi kliknutím na tlačítko Nové připojení a poskytnutím potřebných informací o připojení.
Obrázek 1: První krok Průvodce konfigurací nástroje TableAdapter (kliknutím zobrazíte obrázek v plné velikosti)
Pojďme chvíli zkontrolovat kód pro vlastnost TableAdapter s Connection
. Jak je uvedeno v kurzu Vytvoření vrstvy přístupu k datům , automaticky vygenerovaný kód objektu TableAdapter můžeme zobrazit tak, že přejdeme do okna Zobrazení třídy, přejdeme k příslušné třídě a poklikáním na název člena.
Přejděte do okna Zobrazení třídy tak, že přejdete do nabídky Zobrazení a zvolíte Zobrazení třídy (nebo zadáte Ctrl+Shift+C). V horní polovině okna Zobrazení třídy přejděte k NorthwindTableAdapters
oboru názvů a vyberte ProductsTableAdapter
třídu. ProductsTableAdapter
Zobrazí se členy s v dolní polovině zobrazení třídy, jak je znázorněno na obrázku 2. Poklikáním na Connection
vlastnost zobrazíte její kód.
Obrázek 2: Double-Click vlastnost connection v zobrazení třídy k zobrazení automaticky generovaného kódu
Vlastnost TableAdapter s Connection
a další kód související s připojením jsou následující:
private System.Data.SqlClient.SqlConnection _connection;
private void InitConnection() {
this._connection = new System.Data.SqlClient.SqlConnection();
this._connection.ConnectionString =
ConfigurationManager.ConnectionStrings["NORTHWNDConnectionString"].ConnectionString;
}
internal System.Data.SqlClient.SqlConnection Connection {
get {
if ((this._connection == null)) {
this.InitConnection();
}
return this._connection;
}
set {
this._connection = value;
if ((this.Adapter.InsertCommand != null)) {
this.Adapter.InsertCommand.Connection = value;
}
if ((this.Adapter.DeleteCommand != null)) {
this.Adapter.DeleteCommand.Connection = value;
}
if ((this.Adapter.UpdateCommand != null)) {
this.Adapter.UpdateCommand.Connection = value;
}
for (int i = 0; (i < this.CommandCollection.Length); i = (i + 1)) {
if ((this.CommandCollection[i] != null)) {
((System.Data.SqlClient.SqlCommand)
(this.CommandCollection[i])).Connection = value;
}
}
}
}
Při vytvoření instance třídy TableAdapter je člen proměnná _connection
rovna null
. Při přístupu k Connection
vlastnosti se nejprve zkontroluje, jestli _connection
došlo k vytvoření instance členské proměnné. Pokud není, InitConnection
vyvolá se metoda, která vytvoří instanci _connection
a nastaví její ConnectionString
vlastnost na hodnotu připojovací řetězec zadanou v prvním kroku Průvodce konfigurací TableAdapter.
Vlastnost Connection
lze také přiřadit k objektu SqlConnection
. Tím přidružíte nový SqlConnection
objekt ke každému objektu TableAdapter s SqlCommand
.
Krok 2: Zveřejnění nastavení Connection-Level
Informace o připojení by měly zůstat zapouzdřené v objektu TableAdapter a neměly by být přístupné jiným vrstvám v architektuře aplikace. Mohou však narazit situace, kdy informace na úrovni připojení tableadapter musí být přístupné nebo přizpůsobitelné pro dotaz, uživatele nebo ASP.NET stránku.
ProductsTableAdapter
Rozšiřme objekt v Northwind
datové sadě tak, aby zahrnoval ConnectionString
vlastnost, která může být použita vrstvou obchodní logiky ke čtení nebo změně připojovací řetězec používané objektem TableAdapter.
Poznámka
připojovací řetězec je řetězec, který určuje informace o připojení k databázi, jako je poskytovatel, který se má použít, umístění databáze, přihlašovací údaje pro ověřování a další nastavení související s databází. Seznam připojovací řetězec vzorů používaných různými úložišti dat a poskytovateli najdete v tématu ConnectionStrings.com.
Jak je popsáno v kurzu Vytvoření vrstvy přístupu k datům , automaticky generované třídy Typed DataSet s lze rozšířit pomocí částečných tříd. Nejprve vytvořte novou podsložku v projektu s názvem ConnectionAndCommandSettings
pod složkou ~/App_Code/DAL
.
Obrázek 3: Přidání podsložky s názvem ConnectionAndCommandSettings
Přidejte nový soubor třídy s názvem ProductsTableAdapter.ConnectionAndCommandSettings.cs
a zadejte následující kód:
using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
namespace NorthwindTableAdapters
{
public partial class ProductsTableAdapter
{
public string ConnectionString
{
get
{
return this.Connection.ConnectionString;
}
set
{
this.Connection.ConnectionString = value;
}
}
}
}
Tato částečná public
třída přidá vlastnost s názvem ConnectionString
třídyProductsTableAdapter
, která umožňuje jakékoli vrstvě číst nebo aktualizovat připojovací řetězec pro základní připojení TableAdapter.
Po vytvoření (a uložení) této částečné třídy otevřete ProductsBLL
třídu. Přejděte na některou z existujících metod a zadejte Adapter
a stisknutím klávesy tečky vyvolejte IntelliSense. Měla by se zobrazit nová ConnectionString
vlastnost dostupná v IntelliSense, což znamená, že tuto hodnotu můžete programově číst nebo upravovat z BLL.
Zveřejnění celého objektu připojení
Tato částečná třída zveřejňuje pouze jednu vlastnost objektu základního připojení: ConnectionString
. Pokud chcete zpřístupnit celý objekt připojení nad rámec omezení objektu TableAdapter, můžete také změnit Connection
úroveň ochrany vlastností. Automaticky vygenerovaný kód, který jsme prozkoumali v kroku 1, ukázalo, že vlastnost TableAdapter s Connection
je označena jako internal
, což znamená, že k ní mohou přistupovat pouze třídy ve stejném sestavení. To je však možné změnit prostřednictvím vlastnosti TableAdapter s ConnectionModifier
.
Otevřete datová Northwind
sada, klikněte na ProductsTableAdapter
Designer a přejděte na okno Vlastnosti. Tam uvidíte hodnotu nastavenou ConnectionModifier
na výchozí hodnotu Assembly
. Pokud chcete vlastnost zpřístupnit Connection
mimo sestavení Typed DataSet s, změňte ConnectionModifier
vlastnost na Public
.
Obrázek 4: Úroveň Connection
přístupnosti vlastnosti lze nakonfigurovat prostřednictvím ConnectionModifier
vlastnosti (kliknutím zobrazíte obrázek v plné velikosti)
Uložte DataSet a pak se vraťte do ProductsBLL
třídy. Stejně jako předtím přejděte na některou z existujících metod a zadejte Adapter
a stisknutím klávesy tečky vyvolejte IntelliSense. Seznam by měl obsahovat Connection
vlastnost, což znamená, že teď můžete programově číst nebo přiřadit nastavení na úrovni připojení z BLL.
Krok 3: Prozkoumání vlastností Command-Related
Objekt TableAdapter se skládá z hlavního dotazu, který má ve výchozím nastavení automaticky vygenerované INSERT
příkazy , UPDATE
a DELETE
. Tento hlavní dotaz s INSERT
, UPDATE
a DELETE
příkazy jsou implementovány v kódu TableAdapter jako ADO.NET objekt datového adaptéru Adapter
prostřednictvím vlastnosti. Podobně jako u vlastnosti Connection
Adapter
je datový typ vlastnosti určen použitým poskytovatelem dat. Vzhledem k tomu, že tyto kurzy používají zprostředkovatele SqlClient, Adapter
je vlastnost typu SqlDataAdapter
.
Vlastnost TableAdapter s Adapter
má tři vlastnosti typu SqlCommand
, které používá k vydání INSERT
příkazů , UPDATE
a DELETE
:
InsertCommand
UpdateCommand
DeleteCommand
Objekt SqlCommand
zodpovídá za odeslání konkrétního dotazu do databáze a má vlastnosti jako: CommandText
, který obsahuje ad hoc příkaz SQL nebo uloženou proceduru, která se má spustit; a Parameters
, což je kolekce SqlParameter
objektů. Jak jsme viděli v kurzu Vytvoření vrstvy přístupu k datům, tyto objekty příkazů je možné přizpůsobit prostřednictvím okno Vlastnosti.
Kromě hlavního dotazu může objekt TableAdapter obsahovat proměnný počet metod, které při vyvolání odešlou zadaný příkaz do databáze. Objekt příkazu hlavního dotazu s a objekty příkazů pro všechny další metody jsou uloženy ve vlastnosti TableAdapter s CommandCollection
.
Pojďme se na chvíli podívat na kód vygenerovaný objektem ProductsTableAdapter
v Northwind
datové sadě pro tyto dvě vlastnosti a jejich podpůrné členské proměnné a pomocné metody:
private System.Data.SqlClient.SqlDataAdapter _adapter;
private void InitAdapter() {
this._adapter = new System.Data.SqlClient.SqlDataAdapter();
... Code that creates the InsertCommand, UpdateCommand, ...
... and DeleteCommand instances - omitted for brevity ...
}
private System.Data.SqlClient.SqlDataAdapter Adapter {
get {
if ((this._adapter == null)) {
this.InitAdapter();
}
return this._adapter;
}
}
private System.Data.SqlClient.SqlCommand[] _commandCollection;
private void InitCommandCollection() {
this._commandCollection = new System.Data.SqlClient.SqlCommand[9];
... Code that creates the command objects for the main query and the ...
... ProductsTableAdapter�s other eight methods - omitted for brevity ...
}
protected System.Data.SqlClient.SqlCommand[] CommandCollection {
get {
if ((this._commandCollection == null)) {
this.InitCommandCollection();
}
return this._commandCollection;
}
}
Kód vlastností Adapter
a CommandCollection
úzce napodobuje Connection
kód vlastnosti. Existují členské proměnné, které obsahují objekty používané vlastnostmi. Přístupové objekty vlastností get
začínají kontrolou, jestli je null
odpovídající proměnná člena . Pokud ano, je volána metoda inicializace, která vytvoří instanci členské proměnné a přiřadí základní vlastnosti související s příkazy.
Krok 4: Zveřejnění nastavení Command-Level
V ideálním případě by informace na úrovni příkazů měly zůstat zapouzdřené ve vrstvě přístupu k datům. Pokud by však tyto informace byly potřeba v jiných vrstvách architektury, mohou být zpřístupněny prostřednictvím částečné třídy, stejně jako u nastavení na úrovni připojení.
Vzhledem k tomu, že TableAdapter má pouze jednu Connection
vlastnost, je kód pro zveřejnění nastavení na úrovni připojení poměrně jednoduchý. Při úpravě nastavení na úrovni příkazů jsou věci trochu složitější, protože Objekt TableAdapter může mít více objektů příkazů – InsertCommand
, UpdateCommand
a , spolu DeleteCommand
s proměnným počtem objektů příkazů ve CommandCollection
vlastnosti. Při aktualizaci nastavení na úrovni příkazů bude potřeba tato nastavení rozšířit na všechny objekty příkazů.
Představte si například, že v objektu TableAdapter byly určité dotazy, které trvalo mimořádně dlouho. Při použití objektu TableAdapter ke spuštění jednoho z těchto dotazů můžeme chtít zvýšit vlastnost objektu s CommandTimeout
příkazu. Tato vlastnost určuje počet sekund čekání na spuštění příkazu a výchozí hodnotu je 30.
Pokud chcete povolit úpravu CommandTimeout
vlastnosti pomocí BLL, přidejte do ProductsDataTable
souboru s částečnou třídou vytvořeným v kroku 2 (ProductsTableAdapter.ConnectionAndCommandSettings.cs
) následující public
metodu:
public void SetCommandTimeout(int timeout)
{
if (this.Adapter.InsertCommand != null)
this.Adapter.InsertCommand.CommandTimeout = timeout;
if (this.Adapter.DeleteCommand != null)
this.Adapter.DeleteCommand.CommandTimeout = timeout;
if (this.Adapter.UpdateCommand != null)
this.Adapter.UpdateCommand.CommandTimeout = timeout;
for (int i = 0; i < this.CommandCollection.Length; i++)
if (this.CommandCollection[i] != null)
this.CommandCollection[i].CommandTimeout = timeout;
}
Tato metoda může být vyvolána z vrstvy BLL nebo Presentation k nastavení časového limitu příkazu pro všechny příkazy problémy dané instance TableAdapter.
Poznámka
Vlastnosti Adapter
a CommandCollection
jsou označené jako private
, což znamená, že k nim lze přistupovat pouze z kódu v objektu TableAdapter. Connection
Na rozdíl od vlastnosti nejsou tyto modifikátory přístupu konfigurovatelné. Proto pokud potřebujete zpřístupnit vlastnosti na úrovni příkazů jiným vrstvám v architektuře, musíte použít metodu částečné třídy popsané výše k poskytnutí public
metody nebo vlastnosti, která čte nebo zapisuje do private
objektů příkazů.
Souhrn
Objekty TableAdapter v zadané datové sadě slouží k zapouzdření podrobností a složitosti přístupu k datům. Při použití objektů TableAdapter se nemusíme starat o zápis ADO.NET kódu pro připojení k databázi, vydání příkazu nebo naplnění výsledků do tabulky DataTable. Všechno se zpracovává automaticky za nás.
Může se ale stát, že budeme potřebovat přizpůsobit specifika ADO.NET nízké úrovně, například změnit připojovací řetězec nebo výchozí hodnoty časového limitu připojení nebo příkazu. Objekt TableAdapter má automaticky vygenerované Connection
vlastnosti , Adapter
a CommandCollection
, ale ve výchozím nastavení jsou to buď internal
nebo private
. Tyto interní informace lze zpřístupnit rozšířením objektu TableAdapter pomocí částečných tříd tak, aby zahrnoval public
metody nebo vlastnosti. Alternativně lze modifikátor přístupu vlastnosti TableAdapter s Connection
nakonfigurovat prostřednictvím vlastnosti TableAdapter s ConnectionModifier
.
Šťastné programování!
O autorovi
Scott Mitchell, autor sedmi knih o ASP/ASP.NET a zakladatel 4GuysFromRolla.com, pracuje s webovými technologiemi Microsoftu od roku 1998. Scott pracuje jako nezávislý konzultant, školitel a spisovatel. Jeho nejnovější kniha je Sams Teach Yourself ASP.NET 2.0 in 24 Hours. Můžete ho najít na mitchell@4GuysFromRolla.comadrese . nebo prostřednictvím jeho blogu, který najdete na http://ScottOnWriting.NETadrese .
Zvláštní poděkování
Tato série kurzů byla zkontrolována mnoha užitečnými recenzenty. Hlavními recenzenty tohoto kurzu byli Burnadette Leigh, S ren Jacob Lauritsen, Teresa Murphy a Hilton Geisenow. Chcete si projít moje nadcházející články na WEBU MSDN? Pokud ano, dejte mi čáru na mitchell@4GuysFromRolla.comadresu .