NHibernate-데이터 유형 매핑

이 장에서는 매핑 데이터 유형을 다룰 것입니다. 엔티티 매핑은 간단하며 엔티티 클래스는 항상 다음을 사용하여 데이터베이스 테이블에 매핑됩니다.<class>, <subclass>, and <joined-subclass>매핑 요소. 값 유형에는 더 많은 것이 필요하며 여기서 매핑 유형이 필요합니다.

NHibernate는 다양한 데이터 유형을 매핑 할 수 있습니다. 다음은 지원되는 가장 일반적인 데이터 유형 목록입니다.

매핑 유형 .NET 유형 System.Data.DbType
Int16 System.Int16 DbType.Int16
Int32 System.Int32 DbType.Int32
Int64 System.Int64 DbType.Int64
단일 System.Single DbType.Single
더블 System.Double DbType.Double
소수 System.Decimal DbType.Decimal
System.String DbType.String
AnsiString System.String DbType.AnsiString
바이트 System.Byte DbType.Byte
System.Char DbType.StringFixedLength-한 문자
AnsiChar System.Char DbType.AnsiStringFixedLength-한 문자
부울 System.Boolean DbType.Boolean
Guid System.Guid DbType.Guid
PersistentEnum System.Enum (열거 형) 기본 값에 대한 DbType
허위 사실 System.Boolean DbType.AnsiStringFixedLength- 'T'또는 'F'
예 아니오 System.Boolean DbType.AnsiStringFixedLength- 'Y'또는 'N'
날짜 시간 날짜 시간 DbType.DateTime-밀리 초 무시
진드기 System.DateTime DbType.Int64
시간 범위 System.TimeSpan DbType.Int64
타임 스탬프 System.DateTime DbType.DateTime— 데이터베이스가 지원하는 특정
바이너리 System.Byte [] DbType.Binary
BinaryBlob System.Byte [] DbType.Binary
StringClob System.String DbType.String
직렬화 가능 SerializableAttribute로 표시된 모든 System.Object DbType.Binary
문화 정보 System.Globalization.CultureInfo DbType.String-culture 용 5 자
유형 System.Type 어셈블리 정규화 된 이름을 보유하는 DbType.String

위에 주어진 표는 아래 언급 된 포인터를 자세히 설명합니다.

  • 간단한 숫자 유형에서 문자열에 이르기까지 모든 것을 다음을 사용하여 다양한 방법으로 매핑 할 수 있습니다. varchars, chars 문자열 blob 및 데이터베이스가 지원하는 모든 다양한 유형이 있습니다.

  • 또한 매핑 할 수 있습니다 Booleans, 모두 0과 1을 사용하는 필드, true, false 또는 T와 F를 포함하는 문자 필드.

  • 그것이 데이터베이스의 백엔드, 부울 값에 매핑되는 방법을 정의하는 다양한 방법이 있습니다.

  • 우리는 매핑을 처리 할 수 ​​있습니다. DateTime, 시간대 오프셋, 일광 절약 시간 등을 포함하거나 제외합니다.

  • 우리는 또한 매핑 할 수 있습니다 enumerations; 이를 문자열 또는 기본 숫자 값에 매핑 할 수 있습니다.

데이터베이스와 Student 클래스 모두에서 동일한 속성 이름을 갖는 간단한 예제를 살펴 보겠습니다.

이제 Student 클래스에서 FirstMidName을 FirstName으로 변경해 보겠습니다. 여기서 FirstMidName 열은 변경하지 않지만 NHibernate에게이 변환을 수행하도록 알리는 방법을 살펴 보겠습니다. 다음은 업데이트 된 학생 수업입니다.

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Threading.Tasks;

namespace NHibernateDemoApp { 
  
   class Student { 
      public virtual int ID { get; set; } 
      public virtual string LastName { get; set; } 
      public virtual string FirstName { get; set; } 
   }
}

다음은 NHibernate 매핑 파일의 구현입니다.

<?xml version = "1.0" encoding = "utf-8" ?> 
<hibernate-mapping xmlns = "urn:nhibernate-mapping-2.2" assembly = "NHibernateDemoApp" 
   namespace = "NHibernateDemoApp"> 
   
   <class name = "Student">
	
      <id name = "ID"> 
         <generator class = "native"/>
      </id> 
   
      <property name = "LastName"/> 
      <property name = "FirstName" column = "FirstMidName" type = "String"/> 
   </class> 

</hibernate-mapping>

이 예에서 FirstName 필드는 .NET 문자열이고 FirstMidName 열은 SQL nvarchar. 이제 NHibernate에게이 변환을 수행하는 방법을 알리려면 이름을 다음과 같이 설정하십시오.FirstName 및 다음과 같은 열 FirstMidName 이 특정 변환에 적합한 문자열과 동일한 매핑 유형을 지정합니다.

다음은 Program.cs 파일 구현.

using HibernatingRhinos.Profiler.Appender.NHibernate; 
using NHibernate.Cfg; 
using NHibernate.Dialect; 
using NHibernate.Driver; 

using System; 
using System.Linq; 
using System.Reflection;

namespace NHibernateDemoApp { 

   class Program { 
	
      static void Main(string[] args) { 
		
         NHibernateProfiler.Initialize(); 
         var cfg = new Configuration(); 
			
         String Data Source = asia13797\\sqlexpress;
         String Initial Catalog = NHibernateDemoDB;
         String Integrated Security = True;
         String Connect Timeout = 15;
         String Encrypt = False;
         String TrustServerCertificate = False;
         String ApplicationIntent = ReadWrite;
         String MultiSubnetFailover = False;
         
         cfg.DataBaseIntegration(x = > { x.ConnectionString = "Data Source + 
            Initial Catalog + Integrated Security + Connect Timeout + Encrypt +
            TrustServerCertificate + ApplicationIntent + MultiSubnetFailover"; 
            
            x.Driver<SqlClientDriver>(); 
            x.Dialect<MsSql2008Dialect>(); 
            x.LogSqlInConsole = true; 
         }); 
         
         cfg.AddAssembly(Assembly.GetExecutingAssembly()); 
         var sefact = cfg.BuildSessionFactory();
			
         using (var session = sefact.OpenSession()) { 
            
            using (var tx = session.BeginTransaction()) { 
               var students = session.CreateCriteria<Student>().List<Student>(); 
               Console.WriteLine("\nFetch the complete list again\n"); 
               
               foreach (var student in students) { 
                  Console.WriteLine("{0} \t{1} \t{2}", student.ID, student.FirstName,
                     student.LastName); 
               } 
					
               tx.Commit(); 
            } 
				
            Console.ReadLine(); 
         } 
      } 
   }
}

이제 애플리케이션을 실행하면 다음 출력이 표시됩니다.

NHibernate: SELECT this_.ID as ID0_0_, this_.LastName as LastName0_0_, 
   this_.FirstMidName as FirstMid3_0_0_ FROM Student this_

Fetch the complete list again
3 Allan Bommer
4 Jerry Lewis

보시다시피 다른 속성 이름을 데이터베이스의 열 이름에 매핑했습니다.

Student 클래스에 다른 속성을 추가하는 또 다른 예를 살펴 보겠습니다. enum유형. 다음은 Student 클래스 구현입니다.

using System; 
using System.Collections.Generic; 
using System.Linq; using System.Text; 
using System.Threading.Tasks; 

namespace NHibernateDemoApp { 
   
   class Student { 
      public virtual int ID { get; set; } 
      public virtual string LastName { get; set; } 
      public virtual string FirstName { get; set; } 
      public virtual StudentAcademicStanding AcademicStanding { get; set; } 
   } 
   
   public enum StudentAcademicStanding { 
      Excellent, 
      Good, 
      Fair, 
      Poor, 
      Terrible 
   } 
}

보시다시피 열거 형에는 Excellent, Good, Fair, Poor 및 Terrible과 같이 가질 수있는 다양한 값이 있습니다.

매핑 파일로 이동하면 새로 추가 된 속성을 포함하여 매핑 파일에 이러한 각 속성이 나열되어있는 것을 볼 수 있습니다. AcademicStanding 특성.

<?xml version = "1.0" encoding = "utf-8" ?> 
<hibernate-mapping xmlns = "urn:nhibernate-mapping-2.2" 
   assembly = "NHibernateDemoApp" namespace = "NHibernateDemoApp"> 
   
   <class name = "Student"> 
	
      <id name = "ID"> 
         <generator class = "native"/> 
      </id> 

      <property name = "LastName"/> 
      <property name = "FirstName" column = "FirstMidName" type = "String"/> 
      <property name = "AcademicStanding"/> 
   </class>  

</hibernate-mapping>

이제 데이터베이스도 변경해야하므로 SQL Server 개체 탐색기로 이동하여 데이터베이스를 마우스 오른쪽 단추로 클릭하고 새 쿼리… 옵션을 선택합니다.

It will open the query editor and then specify the below query.

DROP TABLE [dbo].[Student]

CREATE TABLE [dbo].[Student] ( 
   [ID] INT IDENTITY (1, 1) NOT NULL, 
   [LastName] NVARCHAR (MAX) NULL, 
   [FirstMidName] NVARCHAR (MAX) NULL, 
   [AcademicStanding] NCHAR(10) NULL, 
   CONSTRAINT [PK_dbo.Student] PRIMARY KEY CLUSTERED ([ID] ASC) 
);

This query will first drop the existing student table and then create a new table.

Clcik on the Execute icon as shown above. Once the query is executed succesfully then you see a message.

Expand database and Table dropdown, and then right-click on the Student table and select View Designer.

Now, you will see the newly created table, which also has the new property AcademicStanding.

Let’s add two records as shown in the following Program.cs file.

using HibernatingRhinos.Profiler.Appender.NHibernate; 
using NHibernate.Cfg; 
using NHibernate.Dialect; 
using NHibernate.Driver; 

using System; 
using System.Linq; 
using System.Reflection;

namespace NHibernateDemoApp { 

   class Program { 
      
      static void Main(string[] args) { 
		
         NHibernateProfiler.Initialize(); 
         var cfg = new Configuration(); 
			
         String Data Source = asia13797\\sqlexpress;
         String Initial Catalog = NHibernateDemoDB;
         String Integrated Security = True;
         String Connect Timeout = 15;
         String Encrypt = False;
         String TrustServerCertificate = False;
         String ApplicationIntent = ReadWrite;
         String MultiSubnetFailover = False;
         
         cfg.DataBaseIntegration(x = > { x.ConnectionString = "Data Source + 
            Initial Catalog + Integrated Security + Connect Timeout + Encrypt +
            TrustServerCertificate + ApplicationIntent + MultiSubnetFailover"; 
            
            x.Driver<SqlClientDriver>(); 
            x.Dialect<MsSql2008Dialect>(); 
         }); 
         
         cfg.AddAssembly(Assembly.GetExecutingAssembly()); 
         var sefact = cfg.BuildSessionFactory(); 
         
         using (var session = sefact.OpenSession()) { 
            using (var tx = session.BeginTransaction()) { 
               
               var student1 = new Student { 
                  ID = 1, 
                  FirstName = "Allan", 
                  LastName = "Bommer",
                  AcademicStanding = StudentAcademicStanding.Excellent 
               };
               
               var student2 = new Student { 
                  ID = 2, 
                  FirstName = "Jerry", 
                  LastName = "Lewis", 
                  AcademicStanding = StudentAcademicStanding.Good 
               };
					
               session.Save(student1); 
               session.Save(student2);
               var students = session.CreateCriteria<Student>().List<Student>(); 
               Console.WriteLine("\nFetch the complete list again\n");
               
               foreach (var student in students) { 
                  Console.WriteLine("{0} \t{1} \t{2} \t{3}", student.ID,
                     student.FirstName, student.LastName, student.AcademicStanding); 
               } 
					
               tx.Commit(); 
            }
				
            Console.ReadLine(); 
         } 
      } 
   } 
}

Now let’s run your application and you will see the following output on your console window.

Fetch the complete list again

1 Allan Bommer Excellent
2 Jerry Lewis Good

Now let’s have look into the database by right clicking on the Student Table.

Select View Data and you will see the two records in the student table as shown in the following screenshot.

You can see that two records are added and Allan has AcademicStanding 0 and Jerry has AcademicStanding 1. This is because in .Net the first enumeration value by default has 0, which is Excellent if you look at StudentAcademicStanding. Whereas, in Student.cs file Good is the second one, so it has a value of 1.