데이터 액세스 레이어 만들기(VB)

작성자 : Scott Mitchell

PDF 다운로드

이 자습서에서는 처음부터 시작하여 형식화된 DataSets를 사용하여 DAL(데이터 액세스 계층)을 만들어 데이터베이스의 정보에 액세스합니다.

소개

웹 개발자로서 우리의 삶은 데이터 작업을 중심으로 진행됩니다. 데이터를 저장하는 데이터베이스, 데이터를 검색 및 수정하는 코드, 수집 및 요약할 웹 페이지를 만듭니다. 이 자습서는 ASP.NET 2.0에서 이러한 일반적인 패턴을 구현하는 기술을 탐색하는 긴 시리즈의 첫 번째 자습서입니다. 먼저 형식화된 데이터 세트를 사용하여 DAL(데이터 액세스 계층)으로 구성된 소프트웨어 아키텍처 , 사용자 지정 비즈니스 규칙을 적용하는 BLL(비즈니스 논리 계층) 및 공통 페이지 레이아웃을 공유하는 ASP.NET 페이지로 구성된 프레젠테이션 계층을 만듭니다. 이 백 엔드 기초가 마련되면 웹 애플리케이션에서 데이터를 표시, 요약, 수집 및 유효성 검사하는 방법을 보여 주는 보고로 이동합니다. 이러한 자습서는 간결하고 프로세스를 시각적으로 안내하는 다양한 스크린샷이 포함된 단계별 지침을 제공하도록 준비되었습니다. 각 자습서는 C# 및 Visual Basic 버전에서 사용할 수 있으며 사용된 전체 코드의 다운로드를 포함합니다. (이 첫 번째 자습서는 매우 길지만 나머지는 훨씬 더 소화 가능한 청크로 표시됩니다.)

이 자습서에서는 디렉터리에 배치된 Microsoft SQL Server 2005 Express Edition 버전의 Northwind 데이터베이스를 App_Data 사용합니다. 다른 데이터베이스 버전을 사용하려는 경우 데이터베이스 파일 App_Data 외에도 폴더에는 데이터베이스를 만들기 위한 SQL 스크립트도 포함되어 있습니다. 다른 SQL Server 버전의 Northwind 데이터베이스를 사용하는 경우 애플리케이션의 Web.config 파일에서 설정을 업데이트 NORTHWNDConnectionString 해야 합니다. 웹 애플리케이션은 Visual Studio 2005 Professional Edition을 파일 시스템 기반 웹 사이트 프로젝트로 사용하여 빌드되었습니다. 그러나 모든 자습서는 Visual Studio 2005, Visual Web Developer의 무료 버전과 동일하게 잘 작동합니다.

이 자습서에서는 처음부터 DAL(데이터 액세스 계층)을 만든 다음 두 번째 자습서에서 BLL(비즈니스 논리 계층) 을 만들고 세 번째 자습서에서 페이지 레이아웃 및 탐색 작업을 수행합니다. 세 번째 자습서 이후의 자습서는 처음 세 개에 배치된 기초를 기반으로 합니다. 이 첫 번째 자습서에는 많은 내용이 있으므로 Visual Studio를 시작하고 시작하겠습니다.

1단계: 웹 프로젝트 만들기 및 데이터베이스에 연결

DAL(데이터 액세스 계층)을 만들려면 먼저 웹 사이트를 만들고 데이터베이스를 설정해야 합니다. 먼저 새 파일 시스템 기반 ASP.NET 웹 사이트를 만듭니다. 이렇게 하려면 파일 메뉴로 이동하여 새 웹 사이트를 선택하고 새 웹 사이트 대화 상자를 표시합니다. ASP.NET 웹 사이트 템플릿을 선택하고, 위치 드롭다운 목록을 파일 시스템으로 설정하고, 웹 사이트를 배치할 폴더를 선택하고, 언어를 Visual Basic으로 설정합니다.

새 파일 System-Based 웹 사이트 만들기

그림 1: 새 파일 System-Based 웹 사이트 만들기(전체 크기 이미지를 보려면 클릭)

그러면 ASP.NET 페이지, 폴더 및 Web.config 파일이 있는 App_Data 새 웹 사이트가 Default.aspx 생성됩니다.

웹 사이트를 만든 다음 단계는 Visual Studio의 Server Explorer 데이터베이스에 대한 참조를 추가하는 것입니다. 서버 Explorer 데이터베이스를 추가하여 Visual Studio 내에서 테이블, 저장 프로시저, 뷰 등을 모두 추가할 수 있습니다. 쿼리 작성기를 통해 직접 또는 그래픽으로 테이블 데이터를 보거나 고유한 쿼리를 만들 수도 있습니다. 또한 DAL에 대한 Typed DataSets를 빌드할 때 Visual Studio에서 형식화된 데이터 세트를 생성해야 하는 데이터베이스를 가리킬 필요가 있습니다. 이 시점에서 이 연결 정보를 제공할 수 있지만 Visual Studio는 서버 Explorer 이미 등록된 데이터베이스의 드롭다운 목록을 자동으로 채웁니다.

Server Explorer Northwind 데이터베이스를 추가하는 단계는 폴더에서 SQL Server 2005 Express Edition 데이터베이스 App_Data 를 사용할지 아니면 대신 사용하려는 Microsoft SQL Server 2000 또는 2005 데이터베이스 서버 설정이 있는지 여부에 따라 달라집니다.

폴더에서App_Data데이터베이스 사용

연결할 SQL Server 2000 또는 2005 데이터베이스 서버가 없거나 데이터베이스 서버에 데이터베이스를 추가하지 않으려는 경우 다운로드한 웹 사이트의 App_Data 폴더(NORTHWND.MDF)에 있는 Northwind 데이터베이스의 SQL Server 2005 Express Edition 버전을 사용할 수 있습니다.

폴더에 배치된 App_Data 데이터베이스는 서버 Explorer 자동으로 추가됩니다. 컴퓨터에 SQL Server 2005 Express Edition 설치되어 있다고 가정하면 NORTHWND라는 노드가 표시됩니다. 서버 Explorer MDF는 테이블, 뷰, 저장 프로시저 등을 확장하고 탐색할 수 있습니다(그림 2 참조).

폴더는 App_Data Microsoft Access .mdb 파일(예: SQL Server 해당 파일)을 서버 Explorer 자동으로 추가할 수도 있습니다. SQL Server 옵션을 사용하지 않으려면 항상 Northwind Traders 데이터베이스 및 앱을 설치하고 디렉터리에 드롭할 App_Data 수 있습니다. 그러나 Access 데이터베이스는 SQL Server 기능이 풍부하지 않으며 웹 사이트 시나리오에서 사용하도록 설계되지 않았습니다. 또한 35개 이상의 자습서 중 몇 가지는 Access에서 지원되지 않는 특정 데이터베이스 수준 기능을 활용합니다.

Microsoft SQL Server 2000 또는 2005 데이터베이스 서버에서 데이터베이스에 연결

또는 데이터베이스 서버에 설치된 Northwind 데이터베이스에 연결할 수 있습니다. 데이터베이스 서버에 Northwind 데이터베이스가 아직 설치되어 있지 않은 경우 먼저 이 자습서의 다운로드에 포함된 설치 스크립트를 실행하여 데이터베이스 서버에 추가해야 합니다.

데이터베이스가 설치되면 Visual Studio의 서버 Explorer 이동하여 데이터 Connections 노드를 마우스 오른쪽 단추로 클릭하고 연결 추가를 선택합니다. 서버 Explorer 표시되지 않으면 보기/서버 Explorer 이동하거나 Ctrl+Alt+S를 누릅니다. 그러면 연결할 서버, 인증 정보 및 데이터베이스 이름을 지정할 수 있는 연결 추가 대화 상자가 표시됩니다. 데이터베이스 연결 정보를 성공적으로 구성하고 확인 단추를 클릭하면 데이터베이스가 데이터 Connections 노드 아래에 노드로 추가됩니다. 데이터베이스 노드를 확장하여 테이블, 뷰, 저장 프로시저 등을 탐색할 수 있습니다.

데이터베이스 서버의 Northwind 데이터베이스에 연결 추가

그림 2: 데이터베이스 서버의 Northwind 데이터베이스에 연결 추가

2단계: 데이터 액세스 계층 만들기

데이터로 작업할 때 한 가지 옵션은 데이터 관련 논리를 프레젠테이션 계층에 직접 포함하는 것입니다(웹 애플리케이션의 경우 ASP.NET 페이지는 프레젠테이션 계층을 구성). 이는 ASP.NET 페이지의 코드 부분에서 ADO.NET 코드를 작성하거나 태그 부분에서 SqlDataSource 컨트롤을 사용하는 형식일 수 있습니다. 두 경우 모두 이 방법은 데이터 액세스 논리를 프레젠테이션 계층과 긴밀하게 결합합니다. 그러나 권장되는 방법은 데이터 액세스 논리를 프레젠테이션 계층과 분리하는 것입니다. 이 별도의 계층을 데이터 액세스 계층, DAL이라고 하며 일반적으로 별도의 클래스 라이브러리 프로젝트로 구현됩니다. 이 계층화된 아키텍처의 이점은 잘 문서화되어 있으며(이러한 이점에 대한 정보는 이 자습서의 끝에 있는 "추가 읽기" 섹션 참조) 이 시리즈에서 사용할 접근 방식입니다.

데이터베이스에 대한 연결 만들기, 발급SELECT, , , INSERTUPDATE명령 등과 같은 기본 데이터 원본과 DELETE 관련된 모든 코드는 DAL에 있어야 합니다. 프레젠테이션 계층에는 이러한 데이터 액세스 코드에 대한 참조가 포함되어서는 안 되며, 대신 모든 데이터 요청에 대해 DAL을 호출해야 합니다. 데이터 액세스 계층에는 일반적으로 기본 데이터베이스 데이터에 액세스하는 메서드가 포함됩니다. 예를 들어 Northwind 데이터베이스에는 Products 판매용 제품과 해당 제품이 속한 범주를 기록하는 및 Categories 테이블이 있습니다. DAL에는 다음과 같은 메서드가 있습니다.

  • GetCategories(), 모든 범주에 대한 정보를 반환하는
  • GetProducts()- 모든 제품에 대한 정보를 반환합니다.
  • GetProductsByCategoryID(categoryID)- 지정된 범주에 속하는 모든 제품을 반환합니다.
  • GetProductByProductID(productID)- 특정 제품에 대한 정보를 반환합니다.

이러한 메서드는 호출될 때 데이터베이스에 연결하고, 적절한 쿼리를 실행하고, 결과를 반환합니다. 이러한 결과를 반환하는 방법이 중요합니다. 이러한 메서드는 데이터베이스 쿼리로 채워진 DataSet 또는 DataReader를 반환할 수 있지만, 이상적으로는 강력한 형식의 개체를 사용하여 이러한 결과를 반환해야 합니다. 강력한 형식의 개체는 컴파일 시간에 스키마가 엄격하게 정의된 개체인 반면, 느슨하게 형식화된 개체는 런타임까지 스키마를 알 수 없는 개체입니다.

예를 들어 DataReader 및 DataSet(기본적으로)은 스키마가 채우는 데 사용되는 데이터베이스 쿼리에서 반환된 열에 의해 정의되므로 느슨하게 형식이 지정된 개체입니다. 느슨한 형식의 DataTable에서 특정 열에 액세스하려면 와 같은 DataTable.Rows(index)("columnName")구문을 사용해야 합니다. 이 예제에서 DataTable의 느슨한 입력은 문자열 또는 서수 인덱스로 열 이름에 액세스해야 한다는 사실에 의해 표시됩니다. 반면에 강력한 형식의 DataTable에는 각 열이 속성으로 구현되어 다음과 같은 DataTable.Rows(index).columnName코드가 생성됩니다.

강력한 형식의 개체를 반환하기 위해 개발자는 고유한 사용자 지정 비즈니스 개체를 만들거나 Typed DataSets를 사용할 수 있습니다. 비즈니스 개체는 일반적으로 비즈니스 개체가 나타내는 기본 데이터베이스 테이블의 열을 반영하는 속성을 가진 클래스로 개발자가 구현합니다. Typed DataSet은 데이터베이스 스키마를 기반으로 Visual Studio에서 생성되며 이 스키마에 따라 멤버가 강력한 형식의 클래스입니다. 형식화된 DataSet 자체는 ADO.NET DataSet, DataTable 및 DataRow 클래스를 확장하는 클래스로 구성됩니다. 강력한 형식의 DataTable 외에도 Typed DataSets에는 이제 DataSet의 DataTable을 채우고 DataTable 내의 수정 사항을 데이터베이스에 다시 전파하는 메서드가 있는 클래스인 TableAdapters도 포함됩니다.

참고

형식화된 데이터 세트와 사용자 지정 비즈니스 개체를 사용할 때의 장점과 단점에 대한 자세한 내용은 데이터 계층 구성 요소 디자인 및 계층을 통해 데이터 전달을 참조하세요.

이러한 자습서의 아키텍처에는 강력한 형식의 DataSets를 사용합니다. 그림 3에서는 형식화된 데이터 세트를 사용하는 애플리케이션의 여러 계층 간의 워크플로를 보여 줍니다.

모든 데이터 액세스 코드가 DAL로 강등됨

그림 3: 모든 데이터 액세스 코드가 DAL로 강등됨(전체 크기 이미지를 보려면 클릭)

형식화된 데이터 세트 및 테이블 어댑터 만들기

DAL 만들기를 시작하기 위해 먼저 프로젝트에 형식화된 데이터 세트를 추가합니다. 이렇게 하려면 솔루션 탐색기 프로젝트 노드를 마우스 오른쪽 단추로 클릭하고 새 항목 추가를 선택합니다. 템플릿 목록에서 DataSet 옵션을 선택하고 이름을 로 지정 Northwind.xsd합니다.

프로젝트에 새 데이터 세트 추가를 선택합니다.

그림 4: 프로젝트에 새 데이터 세트를 추가하도록 선택합니다(전체 크기 이미지를 보려면 클릭).

추가를 클릭한 후 폴더에 DataSet을 추가하라는 App_Code 메시지가 표시되면 예를 선택합니다. 그러면 형식화된 DataSet에 대한 Designer 표시되고 TableAdapter 구성 마법사가 시작되어 형식화된 데이터 세트에 첫 번째 TableAdapter를 추가할 수 있습니다.

형식화된 데이터 세트는 강력한 형식의 데이터 컬렉션 역할을 합니다. 강력한 형식의 DataTable 인스턴스로 구성되며, 각 인스턴스는 강력한 형식의 DataRow 인스턴스로 구성됩니다. 이 자습서 시리즈에서 작업해야 하는 각 기본 데이터베이스 테이블에 대해 강력한 형식의 DataTable을 만듭니다. 먼저 테이블에 대한 DataTable을 Products 만들어 보겠습니다.

강력한 형식의 DataTable에는 기본 데이터베이스 테이블에서 데이터에 액세스하는 방법에 대한 정보가 포함되지 않습니다. DataTable을 채우기 위해 데이터를 검색하기 위해 데이터 액세스 계층으로 작동하는 TableAdapter 클래스를 사용합니다. Products DataTable의 경우 TableAdapter에는 프레젠테이션 계층에서 호출할 메서드 GetProducts(), GetProductByCategoryID(categoryID)등이 포함됩니다. DataTable의 역할은 계층 간에 데이터를 전달하는 데 사용되는 강력한 형식의 개체 역할을 하는 것입니다.

TableAdapter 구성 마법사는 작업할 데이터베이스를 선택하라는 메시지를 표시하여 시작합니다. 드롭다운 목록에는 서버 Explorer 해당 데이터베이스가 표시됩니다. Northwind 데이터베이스를 서버 Explorer 추가하지 않은 경우 현재 새 연결 단추를 클릭하여 추가할 수 있습니다.

Drop-Down 목록에서 Northwind Database 선택

그림 5: Drop-Down 목록에서 Northwind 데이터베이스 선택(전체 크기 이미지를 보려면 클릭)

데이터베이스를 선택하고 다음을 클릭하면 파일에 연결 문자열 Web.config 저장할지 묻는 메시지가 표시됩니다. 연결 문자열 저장하면 TableAdapter 클래스에서 하드 코딩하지 않아도 되며, 나중에 연결 문자열 정보가 변경될 경우 작업을 간소화합니다. 구성 파일에 연결 문자열 저장하도록 선택하는 경우 섹션에 <connectionStrings> 배치됩니다. 이 섹션은 향상된 보안을 위해 선택적으로 암호화하거나 나중에 IIS GUI 관리 도구 내의 새 ASP.NET 2.0 속성 페이지를 통해 수정할 수 있습니다. 이는 관리자에게 더 적합합니다.

연결 문자열을 저장하여 Web.config

그림 6: 연결 문자열을 에 Web.config 저장합니다(전체 크기 이미지를 보려면 클릭).

다음으로 강력한 형식의 첫 번째 DataTable에 대한 스키마를 정의하고 강력한 형식의 DataSet을 채울 때 TableAdapter에서 사용할 첫 번째 메서드를 제공해야 합니다. 이러한 두 단계는 DataTable에 반영하려는 테이블의 열을 반환하는 쿼리를 만들어 동시에 수행됩니다. 마법사가 끝나면 이 쿼리에 메서드 이름을 지정합니다. 이 작업이 완료되면 프레젠테이션 계층에서 이 메서드를 호출할 수 있습니다. 메서드는 정의된 쿼리를 실행하고 강력한 형식의 DataTable을 채웁다.

SQL 쿼리 정의를 시작하려면 먼저 TableAdapter에서 쿼리를 실행할 방법을 나타내야 합니다. 임시 SQL 문을 사용하거나, 새 저장 프로시저를 만들거나, 기존 저장 프로시저를 사용할 수 있습니다. 이 자습서에서는 임시 SQL 문을 사용합니다.

임시 SQL 문을 사용하여 데이터 쿼리

그림 7: 임시 SQL 문을 사용하여 데이터 쿼리(전체 크기 이미지를 보려면 클릭)

이 시점에서 SQL 쿼리를 직접 입력할 수 있습니다. TableAdapter에서 첫 번째 메서드를 만들 때 일반적으로 쿼리가 해당 DataTable에 표현되어야 하는 열을 반환하도록 합니다. 테이블의 모든 열과 모든 행을 반환하는 쿼리를 만들어 이 작업을 수행할 수 있습니다 Products .

텍스트 상자에 SQL 쿼리 입력

그림 8: 텍스트 상자에 SQL 쿼리를 입력합니다(전체 크기 이미지를 보려면 클릭).

또는 그림 9와 같이 쿼리 작성기를 사용하고 쿼리를 그래픽으로 구성합니다.

쿼리 편집기 통해 그래픽으로 쿼리 만들기

그림 9: 쿼리 편집기 통해 그래픽으로 쿼리 만들기(전체 크기 이미지를 보려면 클릭)

쿼리를 만든 후 다음 화면으로 이동하기 전에 고급 옵션 단추를 클릭합니다. 웹 사이트 프로젝트에서 "삽입, 업데이트 및 삭제 문 생성"은 기본적으로 선택된 유일한 고급 옵션입니다. 클래스 라이브러리 또는 Windows 프로젝트에서 이 마법사를 실행하면 "낙관적 동시성 사용" 옵션도 선택됩니다. 지금은 "낙관적 동시성 사용" 옵션을 선택하지 않은 상태로 둡니다. 향후 자습서에서는 낙관적 동시성을 살펴보겠습니다.

삽입, 업데이트 및 삭제 문 생성 옵션만을 선택합니다.

그림 10: 삽입, 업데이트 및 삭제 문 생성 옵션만 선택합니다(전체 크기 이미지를 보려면 클릭).

고급 옵션을 확인한 후 다음을 클릭하여 최종 화면으로 진행합니다. 여기서는 TableAdapter에 추가할 메서드를 선택하라는 메시지가 표시됩니다. 데이터를 채우는 두 가지 패턴이 있습니다.

  • DataTable을 매개 변수로 사용하고 쿼리 결과에 따라 채우는 메서드가 만들어지는 이 방법으로 DataTable을 채웁니다. 예를 들어 ADO.NET DataAdapter 클래스는 메서드 Fill() 를 사용하여 이 패턴을 구현합니다.
  • 이 방법을 사용하여 DataTable을 반환합니다. 메서드는 DataTable을 만들고 채우며 메서드 반환 값으로 반환합니다.

TableAdapter에서 이러한 패턴 중 하나 또는 둘 다를 구현할 수 있습니다. 여기에 제공된 메서드의 이름을 바꿀 수도 있습니다. 이러한 자습서 전체에서 후자의 패턴만 사용하더라도 두 확인란을 모두 선택된 상태로 둡니다. 또한 제네릭 GetData 메서드의 이름을 로 바꾸겠습니다 GetProducts.

이 옵션을 선택하면 최종 확인란인 "GenerateDBDirectMethods"가 TableAdapter에 대한 , Update()Delete() 메서드를 만듭니다Insert(). 이 옵션을 선택 취소한 상태로 두면 Typed DataSet, DataTable, 단일 DataRow 또는 DataRows 배열을 사용하는 TableAdapter의 유일한 Update() 메서드를 통해 모든 업데이트를 수행해야 합니다. 그림 9의 고급 속성에서 "삽입, 업데이트 및 삭제 문 생성" 옵션을 선택 취소한 경우 이 확인란의 설정은 영향을 주지 않습니다. 이 확인란을 선택한 상태로 둡니다.

메서드 이름을 GetData에서 GetProducts로 변경

그림 11: 메서드 이름을 에서 로 GetDataGetProducts 변경(전체 크기 이미지를 보려면 클릭)

마침을 클릭하여 마법사를 완료합니다. 마법사가 닫히면 방금 만든 DataTable을 보여주는 DataSet Designer 반환됩니다. DataTable(ProductID, , 등)의 열 Products 목록과 (Fill()GetProducts())의 ProductsTableAdapter 메서드를 볼 수 ProductName있습니다.

Products DataTable 및 ProductsTableAdapter가 형식화된 데이터 세트에 추가되었습니다.

그림 12: Products DataTable 및 ProductsTableAdapter 이 형식화된 데이터 세트에 추가되었습니다(전체 크기 이미지를 보려면 클릭).

이 시점에서 단일 DataTable(Northwind.Products)과 메서드를 사용하는 강력한 형식의 DataAdapter 클래스(NorthwindTableAdapters.ProductsTableAdapter)가 있는 Typed DataSet이 있습니다 GetProducts() . 이러한 개체는 다음과 같은 코드에서 모든 제품 목록에 액세스하는 데 사용할 수 있습니다.

Dim productsAdapter As New NorthwindTableAdapters.ProductsTableAdapter()
Dim products as Northwind.ProductsDataTable
products = productsAdapter.GetProducts()
For Each productRow As Northwind.ProductsRow In products
    Response.Write("Product: " & productRow.ProductName & "<br />")
Next

이 코드에서는 한 비트의 데이터 액세스 관련 코드를 작성할 필요가 없었습니다. ADO.NET 클래스를 인스턴스화할 필요가 없었고 연결 문자열, SQL 쿼리 또는 저장 프로시저를 참조할 필요가 없었습니다. 대신 TableAdapter는 하위 수준 데이터 액세스 코드를 제공합니다.

이 예제에서 사용되는 각 개체도 강력한 형식이므로 Visual Studio에서 IntelliSense 및 컴파일 시간 형식 검사를 제공할 수 있습니다. 또한 TableAdapter에서 반환하는 모든 DataTable은 GridView, DetailsView, DropDownList, CheckBoxList 등과 같은 ASP.NET 데이터 웹 컨트롤에 바인딩할 수 있습니다. 다음 예제에서는 메서드에서 반환된 GetProducts() DataTable을 이벤트 처리기 내의 빈약한 3줄 코드로 GridView에 바인딩하는 방법을 Page_Load 보여 줍니다.

AllProducts.aspx

<%@ Page Language="VB" AutoEventWireup="true" CodeFile="AllProducts.aspx.vb"
    Inherits="AllProducts" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>View All Products in a GridView</title>
    <link href="Styles.css" rel="stylesheet" type="text/css" />
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <h1>
            All Products</h1>
        <p>
            <asp:GridView ID="GridView1" runat="server"
             CssClass="DataWebControlStyle">
               <HeaderStyle CssClass="HeaderStyle" />
               <AlternatingRowStyle CssClass="AlternatingRowStyle" />
            </asp:GridView>
             </p>
    </div>
    </form>
</body>
</html>

AllProducts.aspx.vb

Imports NorthwindTableAdapters
Partial Class AllProducts
    Inherits System.Web.UI.Page
    Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) _
        Handles Me.Load
        Dim productsAdapter As New ProductsTableAdapter
        GridView1.DataSource = productsAdapter.GetProducts()
        GridView1.DataBind()
    End Sub
End Class

GridView에 제품 목록이 표시됩니다.

그림 13: 제품 목록이 GridView에 표시됩니다(전체 크기 이미지를 보려면 클릭).

이 예제에서는 ASP.NET 페이지의 이벤트 처리기에 세 줄의 Page_Load 코드를 작성해야 하지만 이후 자습서에서는 ObjectDataSource를 사용하여 DAL에서 데이터를 선언적으로 검색하는 방법을 살펴봅니다. ObjectDataSource를 사용하면 코드를 작성할 필요가 없으며 페이징 및 정렬 지원도 받게 됩니다.

3단계: 데이터 액세스 계층에 매개 변수가 있는 메서드 추가

이 시점에서 클래스 ProductsTableAdapter 에는 데이터베이스의 모든 제품을 반환하는 메서드가 하나 GetProducts()만 있습니다. 모든 제품을 사용할 수 있다는 것은 확실히 유용하지만 특정 제품 또는 특정 범주에 속하는 모든 제품에 대한 정보를 검색하려는 경우가 있습니다. 데이터 액세스 계층에 이러한 기능을 추가하려면 매개 변수가 있는 메서드를 TableAdapter에 추가할 수 있습니다.

메서드를 GetProductsByCategoryID(categoryID) 추가해 보겠습니다. DAL에 새 메서드를 추가하려면 DataSet Designer 돌아가서 섹션에서 마우스 오른쪽 단추로 클릭하고 ProductsTableAdapter 쿼리 추가를 선택합니다.

TableAdapter를 마우스 오른쪽 단추로 클릭하고 쿼리 추가 선택

그림 14: TableAdapter의 Right-Click 쿼리 추가 선택

먼저 임시 SQL 문 또는 새 저장 프로시저 또는 기존 저장 프로시저를 사용하여 데이터베이스에 액세스할지 여부를 묻는 메시지가 표시됩니다. 임시 SQL 문을 다시 사용하도록 선택하겠습니다. 다음으로 어떤 유형의 SQL 쿼리를 사용하려는지 묻는 메시지가 표시됩니다. 지정된 범주에 속하는 모든 제품을 반환하려고 하므로 행을 반환하는 문을 작성 SELECT 하려고 합니다.

행을 반환하는 SELECT 문 만들기를 선택합니다.

그림 15: 행을 SELECT 반환하는 문 만들기 선택(전체 크기 이미지를 보려면 클릭)

다음 단계는 데이터에 액세스하는 데 사용되는 SQL 쿼리를 정의하는 것입니다. 특정 범주에 속하는 제품만 반환하려고 하므로 에서 GetProducts()동일한 SELECT 문을 사용하지만 절 WHEREWHERE CategoryID = @CategoryID을 추가합니다. 매개 변수는 @CategoryID TableAdapter 마법사에 만드는 메서드에 해당 형식의 입력 매개 변수(즉, nullable 정수)가 필요하다는 것을 나타냅니다.

지정된 범주에서만 제품을 반환하는 쿼리를 입력합니다.

그림 16: 지정된 범주에서만 제품을 반환하는 쿼리를 입력합니다(전체 크기 이미지를 보려면 클릭).

마지막 단계에서는 사용할 데이터 액세스 패턴을 선택하고 생성된 메서드의 이름을 사용자 지정할 수 있습니다. 채우기 패턴의 경우 DataTable 반환 패턴(GetX메서드)을 반환하기 위해 이름을 FillByCategoryID 로 변경하고 를 사용GetProductsByCategoryID하겠습니다.

TableAdapter 메서드의 이름 선택

그림 17: TableAdapter 메서드의 이름 선택(전체 크기 이미지를 보려면 클릭)

마법사를 완료한 후 DataSet Designer 새 TableAdapter 메서드를 포함합니다.

이제 범주별로 제품을 쿼리할 수 있습니다.

그림 18: 이제 범주별로 제품을 쿼리할 수 있습니다.

잠시 시간을 내어 동일한 기술을 사용하여 메서드를 추가 GetProductByProductID(productID) 합니다.

이러한 매개 변수가 있는 쿼리는 DataSet Designer 직접 테스트할 수 있습니다. TableAdapter에서 메서드를 마우스 오른쪽 단추로 클릭하고 데이터 미리 보기를 선택합니다. 다음으로 매개 변수에 사용할 값을 입력하고 미리 보기를 클릭합니다.

음료 범주에 속하는 제품이 표시됩니다.

그림 19: 음료 범주에 속하는 제품이 표시됩니다(전체 크기 이미지를 보려면 클릭).

이제 DAL의 GetProductsByCategoryID(categoryID) 메서드를 사용하여 지정된 범주에 해당 제품만 표시하는 ASP.NET 페이지를 만들 수 있습니다. 다음 예제에서는 음료 범주에 있는 모든 제품을 보여 줍니다. 이 범주에는 1이 CategoryID 있습니다.

Beverages.aspx

<%@ Page Language="VB" AutoEventWireup="true" CodeFile="Beverages.aspx.vb"
    Inherits="Beverages" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Untitled Page</title>
    <link href="Styles.css" rel="stylesheet" type="text/css" />
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <h1>Beverages</h1>
        <p>
            <asp:GridView ID="GridView1" runat="server"
             CssClass="DataWebControlStyle">
               <HeaderStyle CssClass="HeaderStyle" />
               <AlternatingRowStyle CssClass="AlternatingRowStyle" />
            </asp:GridView>
             </p>
    </div>
    </form>
</body>
</html>

Beverages.aspx.vb

Imports NorthwindTableAdapters
Partial Class Beverages
    Inherits System.Web.UI.Page
    Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) _
        Handles Me.Load
        Dim productsAdapter As New ProductsTableAdapter
        GridView1.DataSource =
         productsAdapter.GetProductsByCategoryID(1)
        GridView1.DataBind()
    End Sub
End Class

음료 범주의 해당 제품이 표시됩니다.

그림 20: 음료 범주의 해당 제품이 표시됩니다(전체 크기 이미지를 보려면 클릭).

4단계: 데이터 삽입, 업데이트 및 삭제

데이터를 삽입, 업데이트 및 삭제하는 데 일반적으로 사용되는 두 가지 패턴이 있습니다. 데이터베이스 직접 패턴을 호출하는 첫 번째 패턴에는 호출될 때 단일 데이터베이스 레코드에서 작동하는 데이터베이스에 , UPDATE또는 DELETE 명령을 발급INSERT하는 메서드를 만드는 작업이 포함됩니다. 이러한 메서드는 일반적으로 삽입, 업데이트 또는 삭제할 값에 해당하는 일련의 스칼라 값(정수, 문자열, 부울, DateTimes 등)으로 전달됩니다. 예를 들어 테이블에 대해 Products 이 패턴을 사용하면 delete 메서드가 삭제할 레코드의 를 나타내는 ProductID 정수 매개 변수를 사용하고 insert 메서드는 에 대한 문자열, 에 대한 ProductNameUnitPrice10진수, 의 정UnitsOnStock수 등을 사용합니다.

각 삽입, 업데이트 및 삭제 요청은 데이터베이스에 즉시 전송됩니다.

그림 21: 각 삽입, 업데이트 및 삭제 요청이 데이터베이스에 즉시 전송됩니다(전체 크기 이미지를 보려면 클릭).

일괄 업데이트 패턴이라고 하는 다른 패턴은 하나의 메서드 호출에서 전체 DataSet, DataTable 또는 DataRows 컬렉션을 업데이트하는 것입니다. 이 패턴을 사용하면 개발자는 DataTable에서 DataRows를 삭제, 삽입 및 수정한 다음 해당 DataRows 또는 DataTable을 업데이트 메서드에 전달합니다. 그런 다음, 이 메서드는 전달된 DataRows를 열거하고, DataRow의 RowState 속성 값을 통해 수정, 추가 또는 삭제되었는지 여부를 확인하고, 각 레코드에 대한 적절한 데이터베이스 요청을 실행합니다.

업데이트 메서드가 호출될 때 모든 변경 내용이 데이터베이스와 동기화됩니다.

그림 22: 업데이트 메서드가 호출될 때 모든 변경 내용이 데이터베이스와 동기화됨(전체 크기 이미지를 보려면 클릭)

TableAdapter는 기본적으로 일괄 업데이트 패턴을 사용하지만 DB 직접 패턴도 지원합니다. TableAdapter ProductsTableAdapter 를 만들 때 고급 속성에서 "삽입, 업데이트 및 삭제 문 생성" 옵션을 선택했으므로 에는 일괄 업데이트 패턴을 구현하는 메서드가 포함되어 Update() 있습니다. 특히 TableAdapter에는 형식화된 데이터 세트, 강력한 형식의 DataTable 또는 하나 이상의 DataRows를 전달할 수 있는 메서드가 포함되어 Update() 있습니다. TableAdapter를 처음 만들 때 "GenerateDBDirectMethods" 확인란을 선택한 경우 DB 직접 패턴도 , Update()Delete() 메서드를 통해 Insert()구현됩니다.

두 데이터 수정 패턴 모두 TableAdapter의 InsertCommand, UpdateCommandDeleteCommand 속성을 사용하여 데이터베이스에 , UPDATEDELETE 명령을 실행INSERT합니다. DataSet Designer TableAdapter를 클릭한 다음 속성 창 이동하여 , UpdateCommandDeleteCommand 속성을 검사하고 수정InsertCommand할 수 있습니다. (TableAdapter를 선택했고 개체가 ProductsTableAdapter 속성 창 드롭다운 목록에서 선택된 개체인지 확인합니다.)

TableAdapter에는 InsertCommand, UpdateCommand 및 DeleteCommand 속성이 있습니다.

그림 23: TableAdapter에는 InsertCommand, UpdateCommandDeleteCommand 속성이 있습니다(전체 크기 이미지를 보려면 클릭).

이러한 데이터베이스 명령 속성을 검사하거나 수정하려면 하위 속성을 클릭하여 CommandText 쿼리 작성기를 표시합니다.

쿼리 작성기에서 INSERT, UPDATE 및 DELETE 문 구성

그림 24: 쿼리 작성기 INSERT에서 , UPDATEDELETE 문 구성(전체 크기 이미지를 보려면 클릭)

다음 코드 예제에서는 일괄 업데이트 패턴을 사용하여 중단되지 않고 재고가 25개 이하인 모든 제품의 가격을 두 배로 줄이는 방법을 보여 줍니다.

Dim productsAdapter As New NorthwindTableAdapters.ProductsTableAdapter()
Dim products As Northwind.ProductsDataTable = productsAdapter.GetProducts()
For Each product As Northwind.ProductsRow In products
   If Not product.Discontinued AndAlso product.UnitsInStock <= 25 Then
      product.UnitPrice *= 2
   End if
Next
productsAdapter.Update(products)

아래 코드에서는 DB 직접 패턴을 사용하여 프로그래밍 방식으로 특정 제품을 삭제한 다음 업데이트한 다음 새 제품을 추가하는 방법을 보여 줍니다.

Dim productsAdapter As New NorthwindTableAdapters.ProductsTableAdapter()
productsAdapter.Delete(3)
productsAdapter.Update( _
    "Chai", 1, 1, "10 boxes x 20 bags", 18.0, 39, 15, 10, false, 1)
productsAdapter.Insert( _
    "New Product", 1, 1, "12 tins per carton", 14.95, 15, 0, 10, false)

사용자 지정 삽입, 업데이트 및 삭제 메서드 만들기

DB 직접 메서드에서 만든 , Update()Delete() 메서드는 Insert()특히 열이 많은 테이블의 경우 약간 번거로울 수 있습니다. IntelliSense의 도움 없이 이전 코드 예제를 살펴보면 각 입력 매개 변수에 매핑되는 Products 테이블 열이 및 Insert() 메서드에 Update() 특별히 명확하지 않습니다. 단일 열 또는 두 개만 업데이트하거나 새로 삽입된 Insert() 레코드 IDENTITY (자동 증가) 필드의 값을 반환하는 사용자 지정된 메서드를 원하는 경우가 있을 수 있습니다.

이러한 사용자 지정 메서드를 만들려면 DataSet Designer 반환합니다. TableAdapter를 마우스 오른쪽 단추로 클릭하고 쿼리 추가를 선택하고 TableAdapter 마법사로 돌아갑니다. 두 번째 화면에서 만들 쿼리 유형을 나타낼 수 있습니다. 새 제품을 추가한 다음 새로 추가된 레코드 ProductID의 값을 반환하는 메서드를 만들어 보겠습니다. 따라서 쿼리를 만들 INSERT 도록 선택합니다.

Products 테이블에 새 행을 추가하는 메서드 만들기

그림 25: 테이블에 새 행 Products 을 추가하는 메서드 만들기(전체 크기 이미지를 보려면 클릭)

다음 화면에서 가 InsertCommandCommandText 나타납니다. 쿼리의 끝에 를 추가하여 SELECT SCOPE_IDENTITY() 이 쿼리를 보강합니다. 그러면 동일한 scope 열에 IDENTITY 삽입된 마지막 ID 값이 반환됩니다. (@@IDENTITY 대신 SCOPE_IDENTITY()를 사용하려는 이유에 대한 SCOPE_IDENTITY() 자세한 내용은 기술 설명서를 참조하세요.) 문을 추가 SELECT 하기 전에 세미콜론으로 문을 종료 INSERT 해야 합니다.

쿼리를 보강하여 SCOPE_IDENTITY() 값 반환

그림 26: 값을 반환 SCOPE_IDENTITY() 하도록 쿼리 보강(전체 크기 이미지를 보려면 클릭)

마지막으로 새 메서드 InsertProduct의 이름을 로 지정합니다.

새 메서드 이름을 InsertProduct로 설정

그림 27: 새 메서드 이름을 로 InsertProduct 설정(전체 크기 이미지를 보려면 클릭)

DataSet Designer 돌아가면 에 ProductsTableAdapter 새 메서드 InsertProduct가 포함되어 있음을 알 수 있습니다. 이 새 메서드에 테이블의 각 열에 Products 대한 매개 변수가 없으면 세미콜론으로 문을 종료 INSERT 하는 것을 잊어버릴 수 있습니다. 메서드를 InsertProduct 구성하고 및 SELECT 문을 구분하는 세미콜론이 INSERT 있는지 확인합니다.

기본적으로 insert 메서드는 쿼리가 아닌 메서드를 실행합니다. 즉, 영향을 받는 행 수를 반환합니다. 그러나 메서드가 InsertProduct 영향을 받는 행 수가 아니라 쿼리에서 반환된 값을 반환하려고 합니다. 이렇게 하려면 메서드의 InsertProductExecuteMode 속성을 로 조정합니다 Scalar.

ExecuteMode 속성을 스칼라로 변경

그림 28: 속성을 로 Scalar 변경 ExecuteMode 합니다(전체 크기 이미지를 보려면 클릭).

다음 코드는 이 새 InsertProduct 메서드의 동작을 보여줍니다.

Dim productsAdapter As New NorthwindTableAdapters.ProductsTableAdapter()
Dim new_productID As Integer = Convert.ToInt32(productsAdapter.InsertProduct( _
    "New Product", 1, 1, "12 tins per carton", 14.95, 10, 0, 10, false))
productsAdapter.Delete(new_productID)

5단계: 데이터 액세스 계층 완료

클래스는 ProductsTableAdapters 테이블의 CategoryIDSupplierID 값을 Products 반환하지만 테이블의 열 Categories 이나 테이블의 CompanyNameSuppliers 은 포함하지 CategoryName 않지만 제품 정보를 표시할 때 표시하려는 열일 수 있습니다. 이러한 새 열을 포함하도록 강력한 형식의 DataTable을 업데이트하는 및 CompanyName 열 값을 모두 CategoryName 포함하도록 TableAdapter의 초기 메서드 GetProducts()를 보강할 수 있습니다.

그러나 데이터를 삽입, 업데이트 및 삭제하는 TableAdapter의 메서드는 이 초기 메서드를 기반으로 하므로 문제가 발생할 수 있습니다. 다행히 삽입, 업데이트 및 삭제를 위해 자동으로 생성된 메서드는 절의 하위 쿼리에 SELECT 의해 영향을 받지 않습니다. 쿼리 CategoriesSuppliers 를 가 아닌 JOIN 하위 쿼리로 추가하도록 주의하여 데이터를 수정하기 위해 이러한 메서드를 다시 작업할 필요가 없습니다. 에서 메서드를 GetProducts() 마우스 오른쪽 단추로 클릭하고 구성을 ProductsTableAdapter 선택합니다. 그런 다음 다음과 같이 절을 SELECT 조정합니다.

SELECT     ProductID, ProductName, SupplierID, CategoryID,
QuantityPerUnit, UnitPrice, UnitsInStock, UnitsOnOrder, ReorderLevel, Discontinued,
(SELECT CategoryName FROM Categories
WHERE Categories.CategoryID = Products.CategoryID) as CategoryName,
(SELECT CompanyName FROM Suppliers
WHERE Suppliers.SupplierID = Products.SupplierID) as SupplierName
FROM         Products

GetProducts() 메서드에 대한 SELECT 문 업데이트

그림 29: 메서드에 SELECT 대한 GetProducts() 문 업데이트(전체 크기 이미지를 보려면 클릭)

이 새 쿼리를 GetProducts() 사용하도록 메서드를 업데이트한 후 DataTable에는 및 SupplierName라는 두 개의 새 열이 CategoryName 포함됩니다.

Products DataTable에는 두 개의 새 열이 있습니다.

그림 30: DataTable에 Products 두 개의 새 열이 있습니다.

잠시 시간을 내어 메서드의 SELECTGetProductsByCategoryID(categoryID) 도 업데이트합니다.

를 사용하여 JOIN 구문을 업데이트 GetProducts()SELECT 하는 경우 DataSet Designer DB 직접 패턴을 사용하여 데이터베이스 데이터를 삽입, 업데이트 및 삭제하는 메서드를 자동으로 생성할 수 없습니다. 대신 이 자습서의 앞부분에 있는 메서드와 InsertProduct 마찬가지로 수동으로 만들어야 합니다. 또한 일괄 업데이트 패턴을 사용하려면 , UpdateCommandDeleteCommand 속성 값을 수동으로 제공해야 InsertCommand합니다.

나머지 TableAdapters 추가

지금까지 단일 데이터베이스 테이블에 대해 단일 TableAdapter로 작업하는 것만 살펴보았습니다. 그러나 Northwind 데이터베이스에는 웹 애플리케이션에서 작업해야 하는 몇 가지 관련 테이블이 포함되어 있습니다. 형식화된 DataSet에는 관련된 여러 DataTable이 포함될 수 있습니다. 따라서 DAL을 완료하려면 이 자습서에서 사용할 다른 테이블에 대한 DataTable을 추가해야 합니다. 형식화된 데이터 세트에 새 TableAdapter를 추가하려면 DataSet Designer 열고 Designer 마우스 오른쪽 단추로 클릭한 다음 추가/TableAdapter를 선택합니다. 그러면 새 DataTable 및 TableAdapter가 만들어지고 이 자습서의 앞부분에서 살펴 본 마법사를 안내합니다.

다음 쿼리를 사용하여 다음 TableAdapters 및 메서드를 만드는 데 몇 분 정도 걸립니다. 의 쿼리 ProductsTableAdapter 에는 각 제품의 범주 및 공급업체 이름을 가져오기 위한 하위 쿼리가 포함됩니다. 또한 팔로우한 경우 클래스의 GetProducts()GetProductsByCategoryID(categoryID) 메서드를 ProductsTableAdapter 이미 추가했습니다.

  • ProductsTableAdapter

    • GetProducts:

      SELECT     ProductID, ProductName, SupplierID, 
      CategoryID, QuantityPerUnit, UnitPrice, UnitsInStock, 
      UnitsOnOrder, ReorderLevel, Discontinued, 
      (SELECT CategoryName FROM Categories WHERE
      Categories.CategoryID = Products.CategoryID) as 
      CategoryName, (SELECT CompanyName FROM Suppliers
      WHERE Suppliers.SupplierID = Products.SupplierID) 
      as SupplierName
      FROM         Products
      
    • GetProductsByCategoryID:

      SELECT     ProductID, ProductName, SupplierID, CategoryID,
      QuantityPerUnit, UnitPrice, UnitsInStock, UnitsOnOrder,
      ReorderLevel, Discontinued, (SELECT CategoryName
      FROM Categories WHERE Categories.CategoryID = 
      Products.CategoryID) as CategoryName,
      (SELECT CompanyName FROM Suppliers WHERE
      Suppliers.SupplierID = Products.SupplierID)
      as SupplierName
      FROM         Products
      WHERE      CategoryID = @CategoryID
      
    • GetProductsBySupplierID:

      SELECT     ProductID, ProductName, SupplierID, CategoryID,
      QuantityPerUnit, UnitPrice, UnitsInStock, UnitsOnOrder,
      ReorderLevel, Discontinued, (SELECT CategoryName
      FROM Categories WHERE Categories.CategoryID = 
      Products.CategoryID) as CategoryName, 
      (SELECT CompanyName FROM Suppliers WHERE 
      Suppliers.SupplierID = Products.SupplierID) as SupplierName
      FROM         Products
      WHERE SupplierID = @SupplierID
      
    • GetProductByProductID:

      SELECT     ProductID, ProductName, SupplierID, CategoryID,
      QuantityPerUnit, UnitPrice, UnitsInStock, UnitsOnOrder,
      ReorderLevel, Discontinued, (SELECT CategoryName 
      FROM Categories WHERE Categories.CategoryID = 
      Products.CategoryID) as CategoryName, 
      (SELECT CompanyName FROM Suppliers WHERE Suppliers.SupplierID = Products.SupplierID) 
      as SupplierName
      FROM         Products
      WHERE ProductID = @ProductID
      
  • CategoriesTableAdapter

    • GetCategories:

      SELECT     CategoryID, CategoryName, Description
      FROM         Categories
      
    • GetCategoryByCategoryID:

      SELECT     CategoryID, CategoryName, Description
      FROM         Categories
      WHERE CategoryID = @CategoryID
      
  • SuppliersTableAdapter

    • GetSuppliers:

      SELECT     SupplierID, CompanyName, Address,
      City, Country, Phone
      FROM         Suppliers
      
    • GetSuppliersByCountry:

      SELECT     SupplierID, CompanyName, Address,
      City, Country, Phone
      FROM         Suppliers
      WHERE Country = @Country
      
    • GetSupplierBySupplierID:

      SELECT     SupplierID, CompanyName, Address,
      City, Country, Phone
      FROM         Suppliers
      WHERE SupplierID = @SupplierID
      
  • EmployeesTableAdapter

    • GetEmployees:

      SELECT     EmployeeID, LastName, FirstName, Title,
      HireDate, ReportsTo, Country
      FROM         Employees
      
    • GetEmployeesByManager:

      SELECT     EmployeeID, LastName, FirstName, Title, 
      HireDate, ReportsTo, Country
      FROM         Employees
      WHERE ReportsTo = @ManagerID
      
    • GetEmployeeByEmployeeID:

      SELECT     EmployeeID, LastName, FirstName, Title,
      HireDate, ReportsTo, Country
      FROM         Employees
      WHERE EmployeeID = @EmployeeID
      

4개의 TableAdapter가 추가된 후 데이터 세트 Designer

그림 31: 4개의 TableAdapter가 추가된 후 데이터 세트 Designer(전체 크기 이미지를 보려면 클릭)

DAL에 사용자 지정 코드 추가

형식화된 DataSet에 추가된 TableAdapters 및 DataTable은 XML 스키마 정의 파일(Northwind.xsd)로 표현됩니다. 솔루션 탐색기 파일을 마우스 오른쪽 단추로 클릭하고 Northwind.xsd 코드 보기를 선택하여 이 스키마 정보를 볼 수 있습니다.

Northwinds 형식 데이터 세트에 대한 XSD(XML 스키마 정의) 파일

그림 32: Northwinds 형식 데이터 세트에 대한 XSD(XML 스키마 정의) 파일(전체 크기 이미지를 보려면 클릭)

이 스키마 정보는 컴파일 시 또는 런타임(필요한 경우)에 디자인 타임에 C# 또는 Visual Basic 코드로 변환되며, 이때 디버거를 사용하여 단계별로 실행할 수 있습니다. 이 자동 생성된 코드를 보려면 클래스 뷰로 이동하여 TableAdapter 또는 Typed DataSet 클래스로 드릴다운합니다. 화면에 수업용 보기가 표시되지 않으면 보기 메뉴로 이동하여 해당 메뉴에서 선택하거나 Ctrl+Shift+C를 누릅니다. 클래스 뷰에서 Typed DataSet 및 TableAdapter 클래스의 속성, 메서드 및 이벤트를 볼 수 있습니다. 특정 메서드에 대한 코드를 보려면 클래스 뷰에서 메서드 이름을 두 번 클릭하거나 마우스 오른쪽 단추로 클릭하고 정의로 이동을 선택합니다.

클래스 뷰에서 정의로 이동을 선택하여 자동 생성된 코드 검사

그림 33: 클래스 뷰에서 정의로 이동을 선택하여 자동 생성된 코드 검사

자동 생성 코드는 좋은 시간 절약이 될 수 있지만 코드는 종종 매우 일반적이며 애플리케이션의 고유한 요구 사항에 맞게 사용자 지정해야 합니다. 하지만 자동 생성된 코드를 확장할 위험은 코드를 생성한 도구가 사용자 지정을 "다시 생성"하고 덮어쓸 시간을 결정할 수 있다는 것입니다. .NET 2.0의 새로운 부분 클래스 개념을 사용하면 여러 파일에 클래스를 쉽게 분할할 수 있습니다. 이렇게 하면 사용자 지정을 덮어쓰는 Visual Studio에 대해 걱정할 필요 없이 자동 생성된 클래스에 자체 메서드, 속성 및 이벤트를 추가할 수 있습니다.

DAL을 사용자 지정하는 방법을 보여 주려면 클래스에 메서드를 GetProducts()SuppliersRow 추가해 보겠습니다. 클래스는 SuppliersRow 테이블의 Suppliers 단일 레코드를 나타냅니다. 각 공급자는 많은 제품에 0을 공급자할 수 있으므로 GetProducts() 지정된 공급자의 해당 제품을 반환합니다. 이렇게 하려면 라는 SuppliersRow.vb 폴더에 App_Code 새 클래스 파일을 만들고 다음 코드를 추가합니다.

Imports NorthwindTableAdapters
Partial Public Class Northwind
    Partial Public Class SuppliersRow
        Public Function GetProducts() As Northwind.ProductsDataTable
            Dim productsAdapter As New ProductsTableAdapter
            Return productsAdapter.GetProductsBySupplierID(Me.SupplierID)
        End Function
    End Class
End Class

이 partial 클래스는 클래스를 빌드할 때 방금 정의한 메서드를 Northwind.SuppliersRow 포함하도록 컴파일러에 GetProducts() 지시합니다. 프로젝트를 빌드한 다음 클래스 뷰 GetProducts() 로 돌아가면 이제 의 Northwind.SuppliersRow메서드로 나열됩니다.

GetProducts() 메서드는 이제 Northwind.SuppliersRow 클래스의 일부입니다.

그림 34: 메서드가 GetProducts() 이제 클래스의 일부입니다.Northwind.SuppliersRow

이제 다음 GetProducts() 코드와 같이 메서드를 사용하여 특정 공급자에 대한 제품 집합을 열거할 수 있습니다.

Dim suppliersAdapter As New NorthwindTableAdapters.SuppliersTableAdapter()
Dim suppliers As Northwind.SuppliersDataTable = suppliersAdapter.GetSuppliers()
For Each supplier As Northwind.SuppliersRow In suppliers
    Response.Write("Supplier: " & supplier.CompanyName)
    Response.Write("<ul>")
    Dim products As Northwind.ProductsDataTable = supplier.GetProducts()
    For Each product As Northwind.ProductsRow In products
        Response.Write("<li>" & product.ProductName & "</li>")
    Next
    Response.Write("</ul><p> </p>")
Next

이 데이터는 ASP에 표시될 수도 있습니다. NET의 데이터 웹 컨트롤. 다음 페이지에서는 두 필드가 있는 GridView 컨트롤을 사용합니다.

  • 각 공급자의 이름을 표시하는 BoundField 및
  • 각 공급자에 대해 메서드에서 반환한 결과에 바인딩되는 BulletedList 컨트롤을 GetProducts() 포함하는 TemplateField입니다.

향후 자습서에서 이러한 master 세부 보고서를 표시하는 방법을 살펴보겠습니다. 현재 이 예제는 클래스에 추가된 사용자 지정 메서드를 사용하는 방법을 보여 주도록 Northwind.SuppliersRow 설계되었습니다.

SuppliersAndProducts.aspx

<%@ Page Language="VB" CodeFile="SuppliersAndProducts.aspx.vb"
    AutoEventWireup="true" Inherits="SuppliersAndProducts" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Untitled Page</title>
    <link href="Styles.css" rel="stylesheet" type="text/css" />
</head>
<body>
    <form id="form1" runat="server">
    <div>
        <h1>
            Suppliers and Their Products</h1>
        <p>
            <asp:GridView ID="GridView1" runat="server"
             AutoGenerateColumns="False"
             CssClass="DataWebControlStyle">
                <HeaderStyle CssClass="HeaderStyle" />
                <AlternatingRowStyle CssClass="AlternatingRowStyle" />
                <Columns>
                    <asp:BoundField DataField="CompanyName"
                      HeaderText="Supplier" />
                    <asp:TemplateField HeaderText="Products">
                        <ItemTemplate>
                            <asp:BulletedList ID="BulletedList1"
                             runat="server" DataSource="<%# CType(CType(Container.DataItem, System.Data.DataRowView).Row, Northwind.SuppliersRow).GetProducts() %>"
                                 DataTextField="ProductName">
                            </asp:BulletedList>
                        </ItemTemplate>
                    </asp:TemplateField>
                </Columns>
            </asp:GridView>
             </p>
    </div>
    </form>
</body>
</html>

SuppliersAndProducts.aspx.vb

Imports NorthwindTableAdapters
Partial Class SuppliersAndProducts
    Inherits System.Web.UI.Page
    Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) _
        Handles Me.Load
        Dim suppliersAdapter As New SuppliersTableAdapter
        GridView1.DataSource = suppliersAdapter.GetSuppliers()
        GridView1.DataBind()
    End Sub
End Class

공급업체의 회사 이름이 왼쪽 열에 나열되고 오른쪽에 해당 제품이 나열됩니다.

그림 35: 공급자의 회사 이름이 왼쪽 열에 나열되고 오른쪽에 해당 제품이 나열됩니다(전체 크기 이미지를 보려면 클릭).

요약

DAL을 만드는 웹 애플리케이션을 빌드할 때 프레젠테이션 계층 만들기를 시작하기 전에 발생하는 첫 번째 단계 중 하나여야 합니다. Visual Studio에서 Typed DataSets를 기반으로 DAL을 만드는 작업은 코드 줄을 작성하지 않고도 10-15분 내에 수행할 수 있는 작업입니다. 앞으로의 자습서는 이 DAL을 기반으로 합니다. 다음 자습서에서는 다양한 비즈니스 규칙을 정의하고 별도의 비즈니스 논리 계층에서 구현하는 방법을 알아보세요.

행복한 프로그래밍!

추가 정보

이 자습서에서 설명하는 topics 대한 자세한 내용은 다음 리소스를 참조하세요.

이 자습서에 포함된 항목에 대한 비디오 교육

저자 정보

7개의 ASP/ASP.NET 책의 저자이자 4GuysFromRolla.com 창립자인 Scott Mitchell은 1998년부터 Microsoft 웹 기술로 작업해 왔습니다. Scott은 독립 컨설턴트, 트레이너 및 작가로 일합니다. 그의 최신 책은 샘스 티치 유어셀프 ASP.NET 24시간 만에 2.0입니다. 그는 에서mitchell@4GuysFromRolla.com 또는 에서 찾을 http://ScottOnWriting.NET수있는 자신의 블로그를 통해 도달 할 수 있습니다.

특별 감사

이 자습서 시리즈는 많은 유용한 검토자가 검토했습니다. 이 자습서의 수석 검토자는 론 그린, 힐튼 기세나우, 데니스 패터슨, 리즈 슐록, 아벨 고메즈, 카를로스 산토스였습니다. 예정된 MSDN 문서를 검토하는 데 관심이 있으신가요? 그렇다면 에 줄을 놓습니다 mitchell@4GuysFromRolla.com.