본문 바로가기
C#

.NET] DTO vs POCO 차이점

by Fastlane 2023. 2. 9.
728x90
반응형

DTO

Data Transfer Object

데이터 전달의 목적을 가진 object이다. DTO는 data만 가지고 있어야 하며, 로직이나 기능은 없다. DTO가 logic(보통 함수에 해당한다.)을 가지고 있다면, DTO가 아니다. DTO는 properties만 있어야 하며, 이 properties는 get, set data만 가지며, validate를 하거나 다른 동작을 실행하지 않는다. 

 

attributes, data annotations 사용은?

DTO에서 사용하지 않는다. attribute가 DTO 자체에 behavior를 추가하는 것은 아니지만, 시스템 다른 곳에서 동작할 수 있게 해주기 때문이다. 

 

ViewModels, API models?

DTO라는 용어가 모호하다. object는 오직 data로만 구성되고, 동작은 없다.  어떻게 사용해야 하는지는 정해진 것이 없다. 많은 architecture에서 DTO는 몇가지 역할을 수행한다. 예를들어, MVC에서는 DTO는 View에 data를 전달하거나 bind하기 위해 사용한다. 이러한 DTO를 ViewModels이라고 부른다. 하지만, 모든 ViewModels을 DTO라고 할 순 없다. ViewModels은 때때로 logic을 갖기도 한다. 이런 경우 더 이상, DTO라고 할 수 없다. 

 

FooDTO라는 class는 사용법에 대한 어떠한 암시도 주지 않는다. FooViewModel은 사용법이 명확하다. 

Example DTO in C#

public class PlatformReadDto
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string Publisher { get; set; }
    public string Cost { get; set; }
}

Encapsulation and Data Transfer Objects

DTO에는 Encapsulation을 적용하지 않는다. DTO에 동작이 없기 때문에, 숨겨야 할 필요가 없다. private setter를 사용할 필요가 없다. DTO는 만들고, 쓰고, 읽기 쉬워야 한다. 

Fields or Properties

DTO가 Encapsulation을 사용하지 않는다면, 왜 fields가 아닌 properties를 갖는가? 둘 다 사용할 수 있지만, 어떤 serialization framdwork는 properties에서만 동작한다. 일반적으로 properties를 사용하지만, 장단점이 있다. 

Immutability and Record Types

불변하는 데이터를 전달하기 위해서는 C# 9에서 소개된 record type을 사용하는 것이 좋다.

DTR(Data Transfer Records)

public record ProductDTO(int Id, string Name, string Description);
var dto = new ProductDTO(1, "devBetter Membership", "A one-year subscription to devBetter.com");
// more traditional manner
public record ProductDTO
{
  public int Id { get; init; }
  public string Name { get; init; }
}

// usage
var dto = new ProductDTO { Id = 1, Name = "some name" };
728x90

Plain Old CLR Objects or Plain Old C# Objects (POCOs)

Persistence Ignorant(PI) 해야한다. 즉, 데이터 저장소와 관련된 논리를 사용하지 않는다. 

// An Example POCO
public class Product
{
  public Product(int id)
  {
    Id = id;
  }

  private Product()
  {
    // required for EF
  }

  public int Id { get; private set; }
  // other properties and methods
}

POCO는 persistence 동작과 같은 third-party framework에 의존하지 않는다. base class를 사용하지 않으며, 특별히 다른 library에 있는 base class를 사용하지 않는다. static helper와 tight coupling하지 않는다. 

POCOs and DTOs

모든 DTOs는 POCOs이다. 모든  POCOs는 DTOs가 아니다. 

728x90
반응형

'C#' 카테고리의 다른 글

C#] Asynchronous VS Multithreading  (0) 2023.04.25
C#] 특수문자 (주석, $, @)  (0) 2023.03.21
C#] System.Security.Cryptography  (0) 2023.01.16
C#] ConcurrentBag  (0) 2023.01.11
C#] IEnumerable vs Enumerable 차이점  (0) 2023.01.09

댓글