ASP.NET 팁

ADO.NET 2.0의 새로운기능 테디 평점: 없음 조회: 5729

Bob Beauchemin
DevelopMentor

적용 대상:
   Microsoft ADO.NET 2.0
   Microsoft SQL Server 2005

요약: ADO.NET 2.0에는 새로운 기본 클래스 공급자 모델, 모든 공급자를 위한 기능 및 System.Data.SqlClient의 변경 사항이 포함되어 있습니다. 새 기능의 개요 및 사용 예제, 그리고 모든 공급자에게 공통적인 기능과 SqlClient 고유의 기능을 보여 주는 차트를 살펴보십시오.

목차

기본 클래스 기반 공급자 모델
향상된 연결 풀링
비동기 명령
대량 가져오기
공급자 통계
AttachDbFileName
SqlClient의 SQL Server 2005 특정 기능
결론

ADO.NET 2.0에는 많은 새 기능이 포함되어 있습니다. 이러한 기능으로는 새 기본 클래스 기반 공급자 모델, 모든 공급자가 활용할 수 있는 기능, System.Data.SqlClient와 관련된 변경 사항 등이 있습니다. .NET Framework 2.0이 SQL Server 2005와 함께 릴리스되기 때문에 이러한 기능 중 일부는 SQL Server 2005가 있어야 사용할 수 있습니다. 이 기사는 새 기능의 개요 및 안내서의 역할을 수행하면서 이러한 기능의 사용 예제와 함께 모든 공급자에게 공통적인 기능과 SqlClient 고유의 기능에 대한 차트를 제공합니다. 이 시리즈의 이후 기사에서는 일부 기능을 보다 자세하게 살펴볼 예정입니다. DataSet 및 관련 클래스에도 다양한 새 기능이 포함되어 있습니다. 이에 대해서는 이후 기사에서 다루도록 하겠습니다.

기본 클래스 기반 공급자 모델

ADO.NET 1.0 및 1.1에서 공급자 작성자는 일련의 공급자 특정 클래스를 구현했습니다. 이러한 버전에서는 각 클래스가 일반 인터페이스를 구현한다는 사실에 기초하여 일반 코딩이 가능했습니다. 예를 들어, System.Data.SqlClientSqlConnection 클래스를 포함하고 이 클래스는 IDbConnection을 구현합니다. System.Data.OracleClientOracleConnection 클래스를 포함하고 이 클래스도 IDbConnection을 구현합니다. 공급자 특정 클래스는 데이터 원본 특정 속성과 메서드를 구현할 수 있습니다. 예를 들어, SqlConnection은 Database 속성과 ChangeDatabase 메서드를 구현합니다. OracleConnection의 경우에는 Oracle 데이터베이스가 각 데이터베이스 인스턴스에 대한 여러 "데이터베이스"(ANSI SQL에서 카탈로그로 알려져 있음)의 개념을 갖고 있지 않기 때문에 이에 해당하지 않습니다. ADO.NET 2.0의 새 공급자 모델은 System.Data.Common에 있는 일련의 기본 클래스를 기반으로 합니다. 이러한 클래스는 일반 기능을 기본적으로 구현하며, 각 기본 클래스는 이전 버전과의 호환성을 위해 여전히 필요한 일반 인터페이스를 구현합니다. 공급자 작성자는 기본 클래스를 사용하거나 이러한 인터페이스를 지원하도록 선택할 수 있습니다.

이전 버전의 인터페이스 모델에는 두 가지 예외, 즉 DataAdapter/DbDataAdapterCommandBuilder가 있었습니다. CommandBuilder 클래스는 단순한 SELECT 명령에 대해 동일한 열 집합을 사용하는 INSERT, UPDATE 및 DELETE 명령을 자동으로 구현합니다. SqlCommandBuilder가 sealed 클래스이기 때문에 동작 문을 만드는 데 사용되었던 기본 알고리즘을 유지하면서 CommandBuilder를 확장할 수 없었습니다. 지금도 SqlCommandBuilder 매개 변수 파서를 다시 사용할 수 있는 방법은 없지만, System.Data.Common에는 DbCommandBuilder 기본 클래스가 있습니다. 또한 이러한 클래스의 기본 클래스 수준에서 새 기능이 제공됩니다. DataAdapter/DbDataAdapter 기본 클래스는 SQL Server SqlTypes와 같은 공급자 특정 유형을 DataSet(ReturnProviderSpecificTypes 속성)에 푸시하기 위한 메커니즘과 일괄 업데이트(StatementType.Batch 열거 값 및 UpdateBatchSize 속성)를 위한 메커니즘을 제공합니다. DbCommandBuilder 일반 기본 클래스는 동시성 정책 선택을 나타내는 속성(ConflictDetection 속성)을 포함합니다.

공급자 팩터리

ADO.NET 1.0 및 1.1에서 인터페이스 기반 접근 방법의 한 가지 문제는 인터페이스에서 생성자를 호출할 수 없으며 특정 클래스의 구체적인 인스턴스를 만들어야 한다는 것입니다. OLE DB 및 ADO 등의 이전 API는 연결 문자열을 오버로드하여 이 문제를 해결했습니다. 연결 문자열은 공급자의 COM PROGID를 포함했으며, 이 PROGID를 기반으로 하여 올바른 DataSource 클래스가 만들어졌습니다. 이는 OLE DB DataSource PROGID가 레지스트리에 저장되기 때문에 가능했습니다.

'' VB6 ADO code, Connection is an interface (actually it''s _Connection)
Dim conn as Connection
'' note that the default provider is MSDASQL, the OLE DB provider for ODBC
'' this uses the OLE DB provider for SQL Server
conn.ConnectionString = "provider=sqloledb;.."  '' other parameters deleted
conn.Open

ADO.NET 2.0을 통해 이를 해결할 수 있습니다. 각 데이터 공급자는 ProviderFactory 클래스 및 공급자 문자열을 .NET machine.config에 등록합니다. machine.config에 등록된 다른 데이터 공급자에 대한 정보의 DataTable을 반환할 수 있으며, 또한 공급자 문자열(ProviderInvariantName이라고 함) 또는 DataTable의 DataRow가 있을 때 올바른 ProviderFactory를 검색할 수 있는 기본 ProviderFactory 클래스(DbProviderFactory) 및 System.Data.Common.ProviderFactories 클래스가 있습니다. 조건부 코드는 원래 다음과 같이 작성되었습니다.

enum provider {sqlserver, oracle, oledb, odbc};
// 구성에서 공급자 확인
provider prov = GetProviderFromConfigFile();
IDbConnection conn = null;
switch (prov) {
  case provider.sqlserver: 
    conn = new SqlConnection(); break;
  case provider.oracle:     
    conn = new OracleConnection(); break;
  case provider.oledb:      
    conn = new OleDbConnection(); break;
  case provider.odbc:       
    conn = new OdbcConnection(); break;
  // 응용 프로그램에서 지원하므로 새 공급자를 추가

}(참고: 프로그래머 코멘트는 샘플 프로그램 파일에는 영문으로 제공되며 기사에는 설명을 위해 번역문으로 제공됩니다.)

위 코드를 이제 다음과 같이 작성할 수 있습니다.

  // 구성에서 ProviderInvariantString 가져오기
  string provstring = GetProviderInvariantString(); 
  DbProviderFactory fact = DbProviderFactories.GetFactory(provstring);
  IDbConnection = fact.CreateConnection();  

컴퓨터에 설치된 데이터 공급자와 각 공급자에 대한 ProviderFactory를 검색하기 위한 표준을 통해 몇 가지 다른 시도를 해 볼 수도 있습니다.

서버 열거

machine.config의 공급자 구성 항목은 이 공급자가 지원하는 기본 클래스 또는 기본 인터페이스를 나타내는 비트 마스크를 지정합니다. 이는 모든 데이터 공급자가 System.Data.Common의 모든 기능을 지원할 필요는 없기 때문입니다. 예를 들어, CommandBuilder는 "있으면 유용한" 클래스이지만 제대로 작업하기 위해 반드시 필요한 것은 아닙니다.

DbEnumerator는 ADO.NET 2.0의 조합에 새로 추가된 기본 클래스입니다. 이 클래스는 자신을 지원하는 데이터 공급자가 데이터 원본 목록을 가져올 수 있도록 허용합니다. 예를 들어, SqlClient는 이 클래스를 지원하며 네트워크에서 사용할 수 있는 SQL Server 인스턴스 목록을 반환합니다. 이것은 프로그램과 도구에서 데이터 원본을 선택할 수 있는 기능을 사용자에게 제공할 수 있게 합니다. 이러한 도구의 한 예가 Visual Studio 2005입니다.

연결 문자열 작성기 및 메타데이터 스키마

Visual Studio .NET은 지금까지 OLE DB 구성 요소로 연결 문자열을 작성하여 데이터 원본을 나타냈습니다. Visual Studio 2005의 서버 탐색기를 사용하여 Visual Studio .NET 2003에서 새 데이터 연결을 추가하면 .NET 데이터 공급자가 아니라 사용자의 컴퓨터에 설치된 OLE DB 공급자를 나열하는 OLE DB 연결 문자열 작성기가 표시됩니다. 그런 다음 공급자(OLE DB 공급자이기는 하지만)를 선택하고 해당 공급자에 대한 ADO.NET 연결 문자열을 작성할 수 있습니다. Visual Studio 2005에서 앞서 언급한 DbProviderFactories는 .NET 데이터 공급자 목록을 제공할 수 있으며, DbConnectionStringBuilder 클래스는 그래픽 사용자 인터페이스 구성 요소에 사용되어 프로그래머가 연결 문자열을 그래픽으로 작성하고 구성 파일에서 연결 문자열을 로드 및 저장할 수 있도록 합니다.

Visual Studio 2005 서버 탐색기는 또한 테이블, 열, 뷰 및 저장 프로시저 목록과 같은 데이터 원본 메타데이터를 가져와서 표시합니다. ANSI SQL 사양은 이 메타데이터(INFORMATION_SCHEMA 뷰로 알려져 있음)에 대한 기본 사양을 가지고 있습니다. 이러한 일반 뷰는 그대로 사용할 수도 있지만 경우에 따라서는 데이터베이스 특정 뷰 또는 정보로 확장해야 합니다. 일부 데이터베이스는 아직 INFORMATION_SCHEMA 뷰를 지원하지 않으므로 ADO.NET 2.0에서 데이터 공급자는 사용 가능한 메타데이터와 데이터베이스에서 이러한 메타데이터를 가져오는 방법을 나열하는 XML 형식 구성 파일을 제공할 수 있습니다. 이것은 공급자가 정의하는 확장된 정보 집합을 도구 프로그래머가 가져올 수 있도록 하는 데 큰 도움이 됩니다. 공급자 모델의 향상된 기능에 대한 내용은 이후 기사에서 자세하게 설명할 것입니다.

추적

프로그래머와 지원 담당자가 데이터베이스 API 호출을 추적할 수 있도록 허용하는 것은 매우 유용합니다. 이렇게 하면 사용자가 설명을 제공하거나 프로그램에서 오류 메시지가 제공된 경우 데이터베이스 액세스 스택에서 문제가 존재하는 부분을 찾아낼 수 있습니다. 일반적으로 다음 경우에 문제가 발생할 수 있습니다.

  1. 클라이언트 프로그램과 실제 데이터베이스 사이의 스키마 불일치
  2. 데이터베이스 사용 불가능 또는 네트워크 라이브러리 문제
  3. 잘못 하드 코딩되었거나 응용 프로그램에 의해 잘못 생성된 SQL
  4. 잘못된 프로그래밍 논리

ODBC 등의 일부 API에 사실상의 표준이 일부 존재하기는 하지만 이전에는 추적을 허용하는 측정 코드는 전적으로 개별 공급자 작성자가 작성했습니다. 표준 OLE DB 추적이 부족했기 때문에 OLE DB 및 ADO 문제를 해결하는 것이 더 어려웠습니다. ADO.NET 전용 아키텍처는 아니지만 ADO.NET 2.0의 Microsoft 공급자는 일반화된 추적 및 측정 API를 활용합니다. 새 기능을 사용하면 응용 프로그램 스택의 모든 수준에서 문제를 추적할 수 있습니다. Microsoft ADO.NET 공급자를 측정(instrumented)할 수 있을 뿐 아니라, 이 기능은 데이터 액세스 스택의 다른 부분에서도 사용할 수 있으며 구현할 공급자 작성자에서도 역시 사용할 수 있습니다. ADO.NET 2.0 DataSet 및 관련 클래스에도 진단 기능이 기본 제공됩니다. 추적에 대해서는 이후 기사에서 자세히 설명할 것입니다.

향상된 SqlClient

Microsoft의 핵심 데이터베이스는 SQL Server이며 SqlClient는 SQL Server 특정 공급자입니다. ADO.NET 2.0은 실제로 다음 네 개의 Microsoft 공급자를 포함합니다.

  1. SqlClient - SQL Server용 Microsoft 공급자
  2. OracleClient - Oracle 데이터베이스용 Microsoft 공급자
  3. OleDb - ADO.NET에서 OLE DB 공급자를 사용하기 위한 브리지 공급자
  4. Odbc - ADO.NET에서 ODBC 드라이버를 사용하기 위한 브리지 공급자

ADO.NET 2.0에서는 부분적으로 신뢰할 수 있는 환경에서 사용할 수 있도록 이러한 네 개의 공급자가 모두 향상되었습니다. .NET CAS(코드 액세스 보안)를 제대로 구성하면 더욱 많은 데이터 중심 모바일 코드 시나리오를 사용할 수 있습니다. ADO.NET 1.1에서는 SqlClient 공급자만 이 기능을 지원했습니다.

또한 데이터 공급자는 데이터베이스 회사(Oracle의 ODP.NET 및 IBM의 DB2용 데이터 공급자), 공급자 전문업체(DataDirect Technologies) 및 오픈 소스 프로젝트와 개인에 의해 작성됩니다. 그 외에도 Microsoft는 Host Integration Server 2004 제품에서 DB2 데이터 공급자를 제공할 예정입니다.

SQL Server는 소프트웨어에서 중요한 역할을 하므로, 모든 Microsoft 지원 공급자의 향상된 기능 외에도 ADO.NET 2.0에서는 SqlClient의 많은 기능이 향상되었습니다. 이러한 기능 중 일부는 모든 버전의 SQL Server를 지원하지만 대부분의 새 기능은 SQL Server 2005("Yukon"이라는 코드 이름으로 널리 알려져 있음)에서 제공되는 여러 새 기능을 지원하도록 되어 있습니다. SQL Server 2005는 서버 내에서 실행되는 .NET 코드를 지원합니다. 또한 공급자 모델을 사용한 서버 내의 데이터 액세스가 최적화되었습니다. 분명하게 드러나지는 않지만 중요한 내부 변경 사항 중 하나는 ADO.NET 2.0의 SqlClient 데이터 공급자가 MDAC(Microsoft Data Access Components)를 사용하지 않는다는 것입니다. 또한 전반적으로 더 구체적인 오류 메시지 및 네트워크 오류에 대한 보다 분명한 오류 메시지와 함께 공급자에서 오류 처리가 향상되었습니다. 프로그래머가 사용할 수 있는 SqlClient 특정 기능의 개요를 아래에서 설명하도록 하겠습니다.

연결 풀링 향상

ADO.NET 1.0은 데이터베이스 연결을 풀링하기 위한 새 인프라를 도입했습니다. Microsoft SqlClient OracleClient 데이터 공급자는 이 인프라를 사용하지만 OleDb 및 Odbc 데이터 공급자는 사용하지 않습니다. 새 풀링 메커니즘은 최소 및 최대 풀 크기와 풀에서 연결을 사용할 수 있을 때까지 사용자가 정의한 시간 동안 풀 관리자가 대기할 수 있는 기능을 포함하는 연결 풀링 매개 변수의 정교한 지원을 제공했습니다. ADO.NET은 연결 풀을 프로그래밍 방식으로 고갈시킬 수 있는, 즉 풀러에 의해 현재 유지되고 있는 모든 연결을 닫을 수 있는 향상된 연결 풀링 기능을 제공합니다. Visual Basic .NET에서 공유되는 정적 메서드 SqlConnection.ClearPool을 사용하여 특정 연결 풀을 지우거나 SqlConnection.ClearPools 메서드를 사용하여 appdomain의 모든 연결 풀을 지울 수 있습니다. SqlClient 및 OracleClient는 모두 이 기능을 구현합니다.

비동기 명령

경우에 따라서는 클라이언트 또는 미들웨어 코드에서 동시에 여러 작업을 수행하려고 할 수 있습니다. 기본적으로 다중 스레드 미들웨어 코드에서 이것은 처리량을 늘리기 위한 주요 방법입니다. ADO.NET 2.0에서 SqlClient는 이제 비동기 명령 실행을 지원합니다.

비동기 작업에 대한 .NET 패러다임은 동기 작업을 위한 메서드와 함께 BeginEnd 메서드 집합을 작업에 제공하는 것입니다. 데이터베이스 명령 실행이 오래 걸릴 수 있기 때문에 SqlClient는 이제 비동기 실행을 제공하는 SqlCommand 메서드를 기본적으로 제공합니다. 아래 표에는 비동기 실행을 지원하는 메서드와 이에 해당하는 동기 메서드가 나열되어 있습니다.

동기 메서드 비동기 메서드
ExecuteNonQuery BeginExecuteNonQuery, EndExecuteNonQuery
ExecuteReader BeginExecuteReader, EndExecuteReader
ExecuteXmlReader BeginExecuteXmlReader, EndExecuteXmlReader

비동기 실행은 유용한 기능일 수 있지만 불필요하게 사용해서는 안 됩니다. 명령이 오래 실행될 것으로 예상되고 비동기 실행을 수행할 만한 이유가 있을 경우에만 비동기 실행을 사용해야 합니다. Windows NT 제품군 운영 체제의 Windows 스레드 스케줄러(Windows 9x 및 Me 클라이언트에서는 사용할 수 없는 기능)에서는 스레드 간에 전환하는 데 있어 자체적인 오버헤드가 발생합니다. 또한 일부 .NET 라이브러리는 스레드에 따라 달라지므로 비동기를 사용할 경우 작업을 시작하는 데 사용한 스레드가 작업이 끝날 때의 스레드와 다를 수 있습니다. 그러나 SQL Server 네트워크 라이브러리 스택은 I/O 완료 포트를 통해 비동기를 지원하도록 향상되었으며, 이를 통해 비동기 SQL Server 작업 처리량을 향상시킬 수 있습니다. 비동기 작업은 여러 동작 문과 저장 프로시저 실행에 대해 효과적일 뿐만 아니라, SQL Server 2005의 다중 활성 결과 집합 기능과 함께 사용하면 단일 데이터베이스 연결을 통해 비동기 SELECT 문을 다면화할 수 있습니다.

대량 가져오기

대부분의 데이터베이스 응용 프로그램은 많은 행을 일괄적으로 SQL Server에 신속하게 삽입할 수 있습니다. 하드웨어 장치(예: 전화 교환기 또는 병원 환자 모니터 장치)에서 읽은 데이터에 해당하는 행을 SQL Server에 삽입하는 응용 프로그램을 일반적인 예로 들 수 있습니다. 이러한 점을 수용하기 위해 SQL Server에서는 bcp와 같은 여러 유틸리티가 제공되지만 이러한 유틸리티에는 일반적으로 입력을 위해 파일이 사용됩니다.

SqlClient에는 SqlBulkCopy라는 새 클래스가 포함되어 있습니다. 이 클래스는 BCP와 같이 파일의 입력을 직접 사용하여 파일 출력을 생성하는 것이 아니라 클라이언트에서 많은 행을 데이터베이스에 신속하고 효율적으로 삽입할 수 있게 되어 있습니다. SqlBulkCopy는 DataReader 및 DataSet으로부터 입력을 가져올 수 있습니다. 이는 일련의 행을 공급자(DataReader)에서 직접 스트리밍할 수 있을 뿐만 아니라 공급자가 아닌 하드웨어 장치에서 가져온 외부 데이터로 DataSet을 채우고 직접 업데이트할 수 있음을 의미합니다. 이 경우에는 소스로 사용할 공급자가 필요하지 않습니다.

// DataSet 채우기
DataSet ds = new DataSet();
FillDataSetFromHardwareDevice(ds);
// 데이터를 SqlServer에 복사
string connect_string = GetConnectStringFromConfigFile();
SqlBulkCopy bcp = new SqlBulkCopy(connect_string);
bcp.DestinationTableName = "hardware_readings";
bcp.WriteToServer(ds);

공급자 통계

일부 응용 프로그램 작성자의 경우 응용 프로그램에서 "실시간" 모니터링을 수행하는 것이 유용하다는 것을 알고 있습니다. Windows 성능 모니터를 사용하거나, 고유한 성능 클래스를 정의하거나, 시간이 지나면 취약해질 수 있는 내부 SQL Server 메타데이터 호출을 사용하여 이 정보를 가져올 수도 있지만 SqlClient에는 이제 이 정보를 얻을 방법이 기본적으로 제공됩니다. SqlConnection 클래스의 인스턴스 메서드를 사용하면 각 연결에 대해 ODBC API에서와 비슷한 통계를 수집할 수 있습니다. 이러한 통계 저장 및 수집 과정에서는 자체 오버헤드가 발생하므로, 통계 수집을 토글하는 데 사용할 수 있는 속성이 있습니다. 또한 카운터를 다시 설정하는 메서드도 있습니다. 통계 수집은 기본적으로 해제되며, 풀링 시나리오에서 Dispose 또는 Close를 호출하여 연결 풀에 연결을 반환할 때도 해제됩니다. 다음은 생성된 통계의 예입니다.

string connect_string = GetConnectStringFromConfigFile();
SqlConnection conn = new SqlConnection(connect_string);
conn.Open();

// 활성화
conn.StatisticsEnabled = true;

// 일부 작업 수행
//
SqlCommand cmd = new SqlCommand("select * from authors", conn);
SqlDataReader rdr = cmd.ExecuteReader();

Hashtable stats = (Hashtable)conn.RetrieveStatistics();

// 통계 처리
IDictionaryEnumerator e = stats.GetEnumerator();
while (e.MoveNext())
Console.WriteLine("{0} : {1}", e.Key, e.Value);

conn.ResetStatistics();

Connection-specific statistics
BuffersReceived   : 1
BuffersSent       : 1
BytesReceived     : 220
BytesSent         : 72
ConnectionTime    : 149
CursorFetchCount  : 0
CursorFetchTime   : 0
CursorOpens       : 0
CursorUsed        : 0
ExecutionTime     : 138
IduCount          : 0
IduRows           : 0
NetworkServerTime : 79
PreparedExecs     : 0
Prepares          : 0
SelectCount       : 0
SelectRows        : 0
ServerRoundtrips  : 1
SumResultSets     : 0
Transactions      : 0
UnpreparedExecs   : 1

이러한 통계가 정확히 무엇을 나타내는지에 대한 자세한 내용은 ADO.NET 2.0 또는 ODBC 설명서를 참조하십시오.

AttachDbFileName

SqlClient 데이터 공급자는 사용자의 데스크톱에서 데이터베이스가 저장되는 데스크톱 응용 프로그램과 클라이언트/서버 및 미들웨어 기반 응용 프로그램을 지원합니다. SQL Server에는 MSDE로 알려진 특수한 버전이 있습니다. 이 제품의 SQL Server 2005 명칭은 SQL Server 2005 Express Edition입니다. 데스크톱 응용 프로그램에서 이 데이터베이스 자체는 응용 프로그램과 관련되며 응용 프로그램과 함께 제공됩니다. 응용 프로그램 설치 프로그램이 SQL Server Express 설치를 실행하므로 사용자는 SQL Server가 데이터 리포지토리로 사용된다는 것을 모를 수 있습니다.

응용 프로그램 내의 SQL Server Express 인스턴스에 데이터베이스 파일을 쉽게 연결할 수 있도록 ADO.NET 1.0에는 연결 문자열 매개 변수 AttachDbFileName이 포함되어 있었습니다. 그러나 이 매개 변수는 하드 코딩된 경로 이름으로 지정해야 했기 때문에 사용자는 기본 위치가 아닌 다른 위치에 응용 프로그램을 설치하기가 쉽지 않았습니다. ADO.NET 2.0에서는 AttachDbFileName 매개 변수에 상대 경로를 사용할 수 있으며, 응용 프로그램 구성 설정과 연결하여 사용됩니다. 따라서 SQL Server Express에 대해 데스크톱 응용 프로그램을 설정하는 것이 Microsoft Access 파일 기반 데이터 저장소에 연결하는 것만큼 간단합니다.

SqlClient의 SQL Server 2005 특정 기능

MARS

독립 실행형으로 또는 저장 프로시저 내에서 SQL SELECT 문을 사용하여 행 집합을 선택하면 SQL Server는 일부 데이터베이스가 그런 것처럼 행 집합 위에 커서를 자동으로 생성하지 않습니다. 대신 최적화된 메서드를 사용하여 네트워크에서 결과 집합을 스트리밍하며, 때때로 네트워크 라이브러리가 패킷 크기 청크로 데이터를 풀링할 때 데이터베이스 버퍼에서 직접 읽습니다. 이것은 SQL Server 온라인 설명서에서 "SQL Sever의 기본 결과 집합" 또는 "커서 없는 결과 집합"으로 알려져 있습니다. SQL Server 2005 이전 버전의 SQL Server에서는 하나의 연결에서 커서 없는 결과 집합이 한 번에 하나만 활성화될 수 있었습니다.

또한 서로 다른 데이터베이스 API 및 라이브러리는 하나의 연결/하나의 커서 없는 결과 집합 동작을 서로 다르게 처리했습니다. ADO.NET 1.0 및 1.1에서는 두 번째 커서 없는 결과 집합을 열려고 하면 오류가 발생합니다. 이러한 "전통적" ADO는 실제로 보이지 않는 곳에서 새 데이터베이스 연결을 열었습니다. 원래는 오류가 발생해야 맞는 것이지만 사용자의 입장에서 보면 새 데이터베이스 연결을 여는 것이 더 편리했습니다. 이 편리한 기능은 일부 프로그래머에 의해 부주의하게 남용되었기 때문에 결과적으로 기대한 것보다 많은 데이터베이스 연결이 설정되었습니다.

SQL Server 2005에서 데이터베이스는 단일 연결에서 동시에 여러 개의 커서 없는 결과 집합을 활성화할 수 있도록 향상되었으며 이에 따라 다중 활성 결과 집합, 즉 "MARS"라는 기능을 사용할 수 있게 되는 것입니다. 이 동작을 지원하도록 네트워크 라이브러리가 변경되었으며, MARS를 사용하려면 새 네트워크 라이브러리와 새 데이터베이스가 모두 필요합니다.

SqlClient 코드에서는 여러 SqlCommand 인스턴스가 동일한 연결을 사용하게 하여 결과 집합을 다면화합니다. 각 SqlCommand는 Command.ExecuteReader를 호출하여 생성한 SqlDataReader를 수용할 수 있으며 여러 SqlDataReader를 나란히 사용할 수 있습니다. ADO.NET 1.0 및 1.1에서는 여러 SqlCommand가 사용될 경우에도 하나의 SqlDataReader를 닫아야 다른 SqlDataReader를 가져올 수 있습니다. 동일한 SqlCommand 인스턴스에서는 여러 ExecuteReader 호출에 의해 생성된 SqlDataReader를 다면화할 수 없습니다. 다음은 간단하지만 기능이 그리 유용하지 않은 예입니다.

// 연결 문자열을 하드 코딩해서는 안 됨
string connstr = GetConnStringFromConfigFile();
SqlConnection conn = new SqlConnection(connstr);
SqlCommand cmd1 = new SqlCommand(
  "select * from employees", conn)
SqlCommand cmd2 = new SqlCommand(
  "select * from jobs", conn)
SqlDataReader rdr1 = cmd1.ExecuteReader();
// 다음 문으로 인해 SQL Server 2005 이전에서 오류 발생
SqlDataReader rdr2 = cmd2.ExecuteReader();
// 이제 rdr1 및 rdr2에서 동시에 읽을 수 있음

이 기능을 사용하면 오류를 줄이거나 ADO 라이브러리의 편리한 기능을 쉽게 설명할 수 있을 뿐 아니라, 위에 설명한 비동기 작업과 함께 사용하면 매우 유용할 수 있습니다. 여러 비동기 SELECT 문이나 저장 프로시저 호출을 동시에 실행하여 데이터베이스 연결을 절약하고 처리량을 최적화할 수 있습니다. 단일 연결을 사용하여 양식에 있는 20개의 드롭다운 목록 상자를 동시에 채우는 경우를 가정해 볼 수 있습니다. 또한 결과 집합을 활성화한 상태에서 결과 집합을 반환하지 않는 문을 실행할 수도 있습니다.

여러 실행 스트림을 동시에 활성화할 수 있지만 모든 실행 스트림은 동일한 트랜잭션(트랜잭션이 존재할 경우)을 공유해야 합니다. 트랜잭션은 명령 범위가 아니라 여전히 연결 범위입니다. 이전 버전의 ADO.NET에서와 마찬가지로 SqlCommand Transaction 속성을 설정하여 SqlTransaction 인스턴스를 SqlCommand에 연결합니다.

SqlDependency 및 SqlNotificationRequest

누군가가 데이터베이스의 행을 변경했다는 사실을 기반으로 하여 캐시를 새로 고칠 수 있다면 중간 계층 캐싱 상황에서 매우 큰 도움이 될 것입니다. 이를 위해 프로그래머는 테이블이나 뷰가 변경될 때 파일을 업데이트하는 트리거를 작성하거나 데이터베이스 변경 여부에 상관없이 코드를 자주 새로 고치는 것과 같은 몇 가지 다른 기술을 사용했습니다. SqlClient SqlNotificationRequest SqlDependency 클래스 이전에는 데이터베이스 알림을 등록하는 간단한 방법이 없었습니다.

SqlDependency는 SqlNotificationRequest를 래핑하고 알림 정보를 .NET 이벤트로 제공하는 고급 클래스입니다. SqlNotificationRequest의 경우에는 이벤트가 없으며 알림을 등록하고 정보를 수집하는 번거로운 작업을 직접 수행해야 합니다. 따라서 대부분의 프로그래머는 SqlDependency를 사용할 것입니다. SqlDependency는 독립 실행형으로 사용할 수 있으며 ASP.NET Cache 클래스 사용 시 그 기능을 직접 사용할 수 있습니다.

이 SQL Server 2005 특정 기능은 확장 가능한 대기열 시스템을 구현하는 SQL Server Service Broker(서비스 브로커)라는 새 기능을 사용합니다. ASP.NET 캐시 클래스를 사용할 때는 Service Broker(서비스 브로커) 대신에 데이터베이스 풀링을 사용하여 비슷한 기능을 구현합니다. Service Broker(서비스 브로커)와 SQL Server 2005를 사용할 때는 알림을 받기 위해 데이터베이스에 대한 연결을 유지 관리할 필요가 없습니다. SqlDependency는 사용자가 선택한 HTTP 또는 TCP 프로토콜을 사용하여 기본 행이 변경되었을 때 이러한 사실을 알립니다. 알림에 행 특정 정보가 포함되지 않으므로 알림을 받으면 전체 행 집합을 다시 가져오고 알림을 다시 등록해야 합니다.

이 기능은 단일 캐시나 제한된 사용자 집합에는 적합하지만, 수신 중인 많은 수의 사용자에 대해 동시에 사용하는 경우에는 주의해야 합니다. 각 사용자는 행이 변경되면 캐시의 전체 행 집합을 새로 고쳐야 합니다. 따라서 많은 내용이 변경되고 사용자 수가 많을 경우 새로 고침에 사용되는 SELECT 문은 데이터베이스에 심각한 영향을 줄 수 있습니다.

암호 변경

SQL Server 2005는 로그인(SQL Server에 연결하는 Windows 로그인)을 통합했던 다른 암호 정책과 동일한 만료 설정이 적용되는 SQL 로그인을 사용하기 위한 메커니즘을 제공합니다. 이 기능을 사용하려면 Windows Server 2003에서 SQL Server 2005가 실행 중이어야 합니다. SQL 로그인 암호(예: ''sa'')가 만료될 예정이면 이 암호를 변경하는 데 일반 Windows 메커니즘과 암호 변경 API를 사용할 수 없게 됩니다. 이 암호는 Transact SQL ALTER LOGIN 동사를 호출하며 종료되는 SQL Server 클라이언트를 사용해야만 변경할 수 있습니다.

SqlClient는 SqlConnection 클래스의 ChangePassword 메서드를 통해 암호 변경을 수행합니다. 이 메서드는 SQL Server 2005 인터페이스에 대해 실행할 경우에만 유용합니다. 이전 버전의 데이터베이스에서도 SQL 로그인을 변경할 수 있지만 이 API는 다른 버전의 SQL Server가 지원하지 않는 네트워크 패킷 유형을 사용합니다. 암호 변경과 관련하여 고려해야 할 또 다른 측면은 프로그램에서 연결 문자열의 SQL Server 로그인 ID와 암호를 더 이상 하드 코딩할 수 없다는 것입니다. 암호를 변경할 때마다 .NET 중간 언어를 생성하고 실행 파일을 바꾸려는 경우(이는 실행 가능성이 없음)가 아니라면 SQL Server 암호를 구성 파일에 저장해야 합니다. 신중한 SQL Server 개발자들은 오랫동안 구성 파일을 사용하여 암호(대개 암호화됨)를 저장해 왔습니다. 더 좋은 방법은 가능하다면 항상 SQL Server 통합 보안을 사용하는 것입니다.

System.Transactions 통합

ADO.NET 2.0의 SqlClient 공급자는 새 System.Transactions 네임스페이스와 통합되어, 승격 가능한 트랜잭션으로 알려진 동작을 실행할 수 있도록 합니다. Transact SQL을 사용하여 로컬 또는 분산 트랜잭션(BEGIN TRANSACTION 및 BEGIN DISTRIBUTED TRANSACTION)을 시작할 수 있지만 특히 클라이언트 쪽/중간 계층 프로그래밍에서는 프로그래머가 단일 데이터베이스 또는 여러 데이터베이스 시나리오에서 사용할 수 있는 구성 요소를 작성하고자 할 수 있습니다. 이러한 시나리오는 여러 SQL Server 인스턴스를 포함할 수 있으며 SQL Server는 다중 인스턴스 액세스를 자동으로 감지하여 트랜잭션을 로컬에서 다중 인스턴스(분산)로 "승격"할 수 있습니다. 이것은 첫 번째 데이터베이스(분산 트랜잭션에서는 리소스 관리자로 알려져 있음)가 SQL Server인 경우 여러 데이터베이스 제품이나 연결이 사용될 경우에도 가능합니다. 승격 가능한 트랜잭션은 ADO.NET에서 기본적으로 사용됩니다.

클라이언트 장애 조치

SQL Server 2005는 데이터베이스 미러링을 통해 "핫 스페어(hot spare)" 기능을 지원합니다. 특정 SQL Server 인스턴스가 실패하면 작업을 백업 서버로 자동 전환할 수 있습니다. 이렇게 하려면 "증인(witness) 인스턴스"로 알려진 장애 조치를 인스턴스에서 목격해야 합니다. 또한 핫 스페어(hot spare) 시나리오에서는 기존 클라이언트 연결이 장애 조치(새 서버 인스턴스와의 연결 설정)를 "알아야" 합니다. 다음 번에 액세스를 시도할 때 오류를 생성하고 클라이언트 프로그래밍에서 수동으로 "장애 조치"를 취해야 하는 클라이언트 연결은 최적의 연결이 아닙니다. ADO.NET 2.0의 SqlClient는 응용 프로그램의 특별한 프로그래밍 없이도 클라이언트 장애 조치를 지원합니다.

새 트랜잭션 격리 수준 지원

SQL Server 2005는 잠금과 버전 관리의 두 가지 방법을 통해 트랜잭션 격리를 지원합니다. 이전 버전의 SQL Server는 잠금을 지원했지만 버전 관리는 지원하지 않았습니다. 문 수준 버전 관리와 트랜잭션 수준 버전 관리의 두 가지 유형이 지원됩니다. 이 기능은 극단적인 상황에서 선택적으로 잠금을 줄이고 버전 관리 데이터베이스용으로 설계된 응용 프로그램을 쉽게 변환하는 데 그 목적이 있습니다. 버전 관리 데이터베이스용으로 설계된 응용 프로그램은 잠금 데이터베이스에 이식할 때 종종 많은 부분을 변경해야 합니다. 그 반대의 경우도 마찬가지입니다. 버전 관리 데이터베이스의 기본 동작은 거의 항상 문 수준 버전 관리입니다. 차이점에 대한 자세한 내용은 Beauchemin, Berglund 및 Sullivan의 A First Look at SQL Server 2005 for Developers 를 참조하십시오.

다양한 버전 관리 및 잠금 동작은 모두 특정 트랜잭션 격리 수준을 사용하여 트랜잭션을 시작하는 것과 같습니다. ANSI SQL 사양에는 다음 네 개의 트랜잭션 격리 수준이 정의되어 있습니다.

  • READ UNCOMMITED
  • READ COMMITTED
  • REPEATABLE READ
  • SERIALIZABLE

SQL Server는 네 개의 격리 수준을 모두 지원하며 이는 SQL Server 2005 이전 버전에서도 마찬가지였습니다. 버전 관리 데이터베이스는 일반적으로 READ COMMITTED 및 SERIALIZABLE만 지원합니다. READ COMMITTED는 문 수준 버전 관리를 구현하고 SERIALIZABLE은 버전 관리 데이터베이스에서 트랜잭션 수준 버전 관리를 구현합니다. READ COMMITTED는 잠금이 사용되든 버전 관리가 사용되든 상관없이 거의 모든 데이터베이스에서 기본 동작입니다.

문 수준 버전 관리는 데이터베이스별로 데이터베이스 옵션을 설정하여 활성화되며, 기본 동작입니다. 문 버전 관리가 활성화되면 IsolationLevel.ReadCommitted 또는 IsolationLevel.ReadUncommitted 지정에 이 동작이 사용됩니다. 트랜잭션 수준 격리를 지원하기 위해 SQL Server 2005는 새 격리 수준인 IsolationLevel.Snapshot을 정의합니다. SqlClient만이 이 격리 수준을 지원합니다. 문 수준 또는 트랜잭션 수준 버전 관리를 개별적으로 설정할 수 있으며, 잠금 동작에 해당하도록 SQL Server가 이미 IsolationLevel.Serializable를 사용하므로 이 격리 수준이 필요합니다.

데이터 형식 - UDT, XML 데이터 형식 및 "MAX" BLOB와 CLOB

SQL Server 2005는 사용자 정의 형식과 기본 XML 데이터 형식을 추가로 지원하며 Transact-SQL 형식 VARCHAR(MAX), NVARCHAR(MAX) 및 VARBINARY(MAX)를 사용함으로써 향상된 대규모 데이터 지원을 제공합니다. 사용자 정의 형식과 원시 XML 형식은 SQL:1999 및 SQL:2003 사양에 정의되어 있습니다. SqlClient와 함께 이러한 데이터 형식을 사용하기 위해 System.Data.SqlTypes 네임스페이스에 새 클래스(SqlUdtSqlXml)가 정의되었고, SqlDbTypes 열거 지원이 추가되었으며, UDT를 .NET 개체 유형으로 반환하고 XML을 .NET 문자열로 반환할 수 있도록 IDataReader.GetValue가 향상되었습니다.

이러한 새 SQL Server 2005 형식은 SQL SELECT 문에서 반환된 SqlParameter를 사용하여 매개 변수로 반환된 DataReader에서 지원됩니다. 특수한 클래스인 SqlMetaData는 엄격한 형식의 XML 열이 준수하는 XML 스키마 컬렉션과 같은 이러한 새 데이터 형식의 확장된 속성에 대한 정보나 UDT의 데이터베이스 이름을 반환할 수 있습니다. 이러한 형식은 클라이언트에서 직접 사용할 수도 있고 일반 코드와 DataSet에서 사용할 수도 있습니다. 마지막으로 클라이언트에서 "MAX" 데이터 형식의 부분 업데이트를 수행할 수 있습니다. ADO.NET 2.0 이전에는 이러한 업데이트에 특수한 SQL 함수를 사용해야 했습니다. 이 사이트의 이후 기사에서 이에 대한 자세한 내용을 다룰 것입니다.

결론

제공되는 기능이 너무 많기 때문에 모두 살펴보는 것은 거의 불가능합니다. 많은 기능이 서로 혼동되지 않도록 이 기사에서는 마지막으로 각각의 새 기능과 해당 기능에 필요한 데이터베이스, 공급자 및 버전이 나열된 차트를 제공합니다. 현재는 ADO.NET의 일부분인 네 개의 공급자에 대한 정보만 있지만, 조만간 다른 공급자 제공업체가 추가될 것입니다. 이후 기사에서는 이 차트에 지금보다 더 많은 내용이 있었으면 합니다.

새 기능 사용 가능 여부

  모든 공급자 SQL Server 7/2000 SQL Server 2005
공급자 팩터리 X X X
부분 트러스트로 실행 X X X
서버 열거 X X X
연결 문자열 작성기 X X X
메타데이터 스키마 X X X
일괄 업데이트 지원 X X X
공급자 특정 유형 X X X
충돌 감지 X X X
추적 지원 X X X
향상된 풀링 SqlClient 및 OracleClient X X
MARS     X
SqlNotificationRequest     X
SqlDependency     X
IsolationLevel.Snapshot     X
비동기 명령 X X X
클라이언트 장애 조치     X
대량 가져오기 X X X
암호 변경 API     X
통계 X X X
새 데이터 형식     X
승격 가능한 트랜잭션   X X
AttachDbFileName   X X

Bob Beauchemin은 DevelopMentor의 강사, 코스 개발자 및 데이터베이스 커리큘럼 관리자로 일하고 있습니다. Bob은 25년 이상의 데이터 중심 분산 시스템 설계자, 프로그래머 및 관리자 경력을 보유하고 있습니다. Bob은 Microsoft Systems Journal, SQL Server Magazine 등에 ADO.NET, OLE DB 및 SQL Server에 대한 기사를 기고했으며 A First Look at SQL Server 2005 for Developers Essential ADO.NET 을 저술했습니다.

 

태그 :
작성자 정보
테디
Level 91
 [EXP.50/250]

메일:  비공개

글등록 +12 7862 덧글등록 +3 1045
자기소개
자유롭게..............
글 공유하기 |
  tweet facebook
2007-01-27 오후 10:47:10
나도한마디
태그로 엮인글
글리스트
[Smart Place펌] ASP.NET AJAX로 알아보는 웹 개발  김경일
Web2.0과 AJAX [2]  김경일
aspnet_regsql.exe sql문입니다. 2줄 수정본입니다. 파일첨부 김훈철
ASP.NET AJAX Control Toolkit : Accordion 2부[1]  양기만
ASP.NET AJAX Control Toolkit : Accordion 1부[7]  양기만
[정규화] - 예전에 정리했던 자료입니다.[2]  테디
ADO.NET 2.0의 쿼리 알림  테디
ADO.NET 2.0의 DataSet 기능[1]  테디
ADO.NET 2.0의 XML 지원  테디
ADO.NET 2.0의 스키마  테디
 ★현재글->   ADO.NET 2.0의 새로운기능  테디
XML을 사용한 출장 보고서 작성  테디
ASP.NET에서의 쿠키 암호화   테디
[DB]트랜잭션의 기본성질ACID  테디
페이징 목록 구현에서의 응용프로그램 성능 향상  테디
[DOM]DOM-기반 웹 애플리케이션 구현하기  김경일
[DOM] DOM을 이해하자!!  김경일
[DOM]웹 응답에 DOM 활용하기   김경일
ASP.NET AJAX에 대한 전망[4]  HOONS
DOM 과 SAX?   김경일
[DOM]Document Object Model ?[2]  김경일