2009-09-06 42 views
12

Tôi đang cân nhắc sử dụng DTO thay vì truyền xung quanh các đối tượng miền của tôi. Tôi đã đọc một số bài viết ở đây cũng như ở nơi khác, và tôi hiểu có một số cách tiếp cận để thực hiện việc này.DTO: thực tiễn tốt nhất

Nếu tôi chỉ có khoảng 10 lớp miền trong tất cả, và xem xét rằng tôi muốn sử dụng DTO hơn là đối tượng miền để sử dụng trong Chế độ xem của tôi (giao diện người dùng WPF), phương pháp được đề xuất là gì. Tôi nghĩ rằng sử dụng các công cụ như automapper vv có thể là một overkill cho tình hình của tôi. Vì vậy, tôi đang nghĩ đến việc viết lớp bản đồ tùy chỉnh của tôi sẽ có các phương thức để chuyển đổi loại miền thành loại DTO.

Cách tốt nhất để làm điều này là có mẫu nào để tôi bắt đầu thực hiện việc này không?

Câu hỏi thứ hai: Khi viết những phương pháp sẽ tạo DTO, làm cách nào để xử lý tất cả dữ liệu, đặc biệt khi loại miền có tham chiếu đến các đối tượng miền khác? Tôi có viết các thuộc tính tương đương trong DTO để ánh xạ tới các kiểu tham chiếu trong lớp miền không? Hãy hỏi nếu tôi không đặt câu hỏi thứ hai của tôi vào những từ thích hợp. Nhưng tôi nghĩ bạn hiểu những gì tôi đang cố gắng hỏi.

Câu hỏi thối: Khi viết DTO, tôi nên viết nhiều DTO, mỗi dữ liệu chứa một phần dữ liệu cho một mô hình miền cụ thể, để mỗi mô hình có thể được sử dụng để đáp ứng yêu cầu của Chế độ xem cụ thể hoặc DTO có tất cả dữ liệu có trong lớp mô hình tương ứng.

+0

Hãy sẵn sàng để cũng viết nhiều đối tượng truyền dữ liệu cụ thể cho các Phương thức dịch vụ cụ thể, không chỉ cho Miền M cụ thể odels. – Lightman

Trả lời

0

Tôi sẽ giả định rằng đối tượng mô hình miền của bạn có ID khóa chính có thể tương ứng với ID của cơ sở dữ liệu hoặc lưu trữ chúng đến từ đó.

Nếu điều trên là đúng, thì DTO của bạn sẽ khắc phục loại giới thiệu đến các DTO khác như đối tượng miền của bạn, dưới dạng ID khóa ngoài. Vì vậy, một mối quan hệ OrderLine.OrderHeader trên đối tượng miền, sẽ được OrderLine.OrderHeaderId cin DTO.

Hy vọng điều đó sẽ hữu ích.

Tôi có thể hỏi lý do bạn chọn sử dụng DTO thay vì đối tượng tên miền phong phú của bạn trong chế độ xem không?

+1

Các DTO có các thuộc tính ID trong đó không? - ví dụ: OrderlineID trong mẫu của bạn. Tôi nghĩ rằng DTO hoàn toàn tự chứa các đối tượng dữ liệu đã giành được; t có bất kỳ tham chiếu nào đến cơ sở dữ liệu và các phụ thuộc bên ngoài khác. Đối với lý do tại sao DTO, dự án của tôi sẽ chuyển thành một hệ thống lớn trong tương lai và tôi muốn đảm bảo rằng tôi xây dựng nó ngay bây giờ để tuân thủ việc có thể hiển thị dữ liệu qua các yêu cầu dịch vụ web, v.v. Beeter để làm theo thực hành tốt từ ngày 0 tôi giả sử. Bạn có bất kỳ ý tưởng nào cho câu hỏi thứ 3 của tôi (mà tôi chỉ thêm một vài phút trở lại). –

3

Tôi là loại sử dụng DTO trong dự án. Tôi có xu hướng làm cho DTO chỉ hiển thị dữ liệu tôi cần cho một chế độ xem được chỉ định. Tôi tìm nạp tất cả dữ liệu được hiển thị trong chế độ xem trong lớp truy cập dữ liệu của tôi. Ví dụ, tôi có thể có một đối tượng theo thứ tự mà tham chiếu đến một đối tượng khách hàng:

public class Client{ 
    public int Id{get;set;} 
    public string Name{get;set;} 
} 

public class Order{ 
    public int OrderID{get;set;} 
    public Client client{get;set;} 
    public double Total{get;set;} 
    public IEnumerable<OrderLine> lines {get;set;} 
} 

Sau đó, trong OrderListDTO của tôi, tôi có thể có một cái gì đó như:

public class OrderListDTO{ 
    public int OrderId{get;set;} 
    public string ClientName{get;set;} 
    ... 
} 

Đó là những lĩnh vực tôi muốn thể hiện quan điểm của tôi . Tôi lấy tất cả các trường này trong mã truy cập cơ sở dữ liệu của mình vì vậy tôi không phải bận tâm với các tổ chức thực thể trong khung nhìn của tôi hoặc mã điều khiển.

+0

Bạn xử lý thuộc tính "đường" trong đối tượng DTO của mình như thế nào? Bạn có làm cho OrderListDTO phẳng hay bạn tải bộ sưu tập "dòng" một số cách như thế nào? –

+0

Phụ thuộc vào ngữ cảnh. Nếu tôi cần các dòng trong giao diện, tôi tải chúng; nếu không, tôi thì không. Đôi khi tôi có thể có một tài sản LineCount trên OrderListDTO của tôi và tôi làm LineCount = order.lines.Count(), hoặc tôi hiển thị tổng số: LineSum = order.lines.Sum (t => t.Quantity) ... –

5

Tôi đã đọc một vài bài đăng ở đây liên quan đến DTO và có vẻ như với tôi rằng rất nhiều người đánh đồng họ với những gì tôi sẽ xem xét một ViewModel. Một DTO chỉ là, đối tượng truyền dữ liệu - đó là những gì được truyền xuống dây. Vì vậy, tôi đã có một trang web và dịch vụ, chỉ các dịch vụ mới có quyền truy cập vào các đối tượng miền/thực thể thực và trả về DTO. Đây có thể là bản đồ 1: 1, nhưng hãy xem xét rằng DTO có thể được điền từ một cuộc gọi dịch vụ khác, một truy vấn cơ sở dữ liệu, đọc một cấu hình - bất cứ điều gì.

Sau đó, trang web sau đó có thể lấy những DTO đó và thêm chúng vào ViewModel hoặc chuyển đổi thành một. ViewModel đó có thể chứa nhiều loại DTO khác nhau.Một ví dụ đơn giản sẽ là một trình quản lý tác vụ - ViewModel chứa cả đối tượng tác vụ bạn đang chỉnh sửa, cũng như một nhóm các đối tượng Dto.User mà nhiệm vụ có thể được gán cho.

Hãy nhớ rằng các dịch vụ trả về DTO có thể được cả trang web sử dụng và có thể là ứng dụng máy tính bảng hoặc điện thoại. Các ứng dụng này sẽ có các khung nhìn khác nhau để tận dụng lợi thế của các màn hình của chúng và vì vậy các ViewModels sẽ khác nhau, nhưng các DTO sẽ vẫn như cũ.

Ở mức nào, tôi thích các loại thảo luận này, vì vậy, bất kỳ ai cũng vui lòng cho tôi biết suy nghĩ của bạn.

Matt

+0

Chỉ cần làm rõ một DTO không phải là một ViewModel. Nó không phải là một DisplayModel một sự bất khả chuyển giao của UIModel của giao diện người dùng. Thậm chí nhiều hơn khi bạn thực hiện các dịch vụ REST chuyển các DTO, chúng sẽ không biết gì về cấu trúc giao diện người dùng. – Elisabeth

1

tôi đến dự án với spring-jdbc và có được sử dụng DAO lớp. Một số lần các thực thể hiện tại không bao gồm tất cả dữ liệu có thể có từ DB. Vì vậy, tôi bắt đầu sử dụng DTO.

Bằng cách áp dụng quy tắc '70 lập trình cấu trúc tôi đặt tất cả DTOs vào gói riêng biệt:

package com.evil.dao;  // DAO interfaces for IOC. 
package com.evil.dao.impl; // DAO implementation classes. 
package com.evil.dao.dto; // DTOs 

Bây giờ tôi suy nghĩ lại và quyết định đặt tất cả DTO như lớp bên trên giao diện DAO cho kết quả-bộ mà không có tái sử dụng. Vì vậy, DAO giao diện trông giống như:

interface StatisticDao { 
    class StatisticDto { 
     int count; 
     double amount; 
     String type; 

     public static void extract(ResultSet rs, StatisticDto dto) { ... } 
    } 

    List<StatisticDto> getStatistic(Criteria criteria); 
} 


class StatisticDaoImpl implements StatisticDao { 
    List<StatisticDto> getStatistic(Criteria criteria) { 
     ... 
     RowCallbackHandler callback = new RowCallbackHandler() { 
      @Override 
      public void processRow(ResultSet rs) throws SQLException { 
       StatisticDao.StatisticDto.extract(rs, dto); 
       // make action on dto 
      } 
     } 
     namedTemplate.query(query, queryParams, callback); 
    } 
} 

Tôi nghĩ rằng nắm giữ dữ liệu liên quan với nhau (tùy chỉnh DTO với giao diện DAO) làm cho mã tốt hơn cho PageUp/PageDown.

0

cách tốt nhất để phát triển DTOs

Cách để bắt đầu DTOs đang phát triển là phải hiểu rằng mục đích duy nhất của họ là để chuyển tập hợp con của dữ liệu của các tổ chức doanh nghiệp của bạn cho các khách hàng khác nhau (có thể là giao diện người dùng, hoặc một dịch vụ bên ngoài). Với sự hiểu biết này, bạn có thể tạo các gói riêng biệt cho từng khách hàng ... và viết các lớp DTO của bạn. Để lập bản đồ, bạn có thể viết giao diện xác định người lập bản đồ của riêng bạn để được chuyển đến một nhà máy tạo các đối tượng DTO dựa trên dữ liệu nào từ thực thể mà DTO đang được tạo sẽ được trích xuất. Bạn cũng có thể xác định các chú thích được đặt trên các trường thực thể của bạn nhưng cá nhân cho số lượng chú thích được sử dụng, tôi thích giao diện. Điều quan trọng cần lưu ý về DTO là chúng cũng là lớp và dữ liệu giữa các DTO nên được sử dụng lại, nói cách khác trong khi có vẻ hấp dẫn khi tạo DTO cho từng trường hợp sử dụng cố gắng sử dụng lại các DTO hiện có để giảm thiểu điều này.

Bắt đầu

về việc bắt đầu như đã nêu trên mục đích duy nhất của DTO là để cung cấp cho khách hàng các dữ liệu cần thiết .... vì vậy bạn hãy nhớ bạn chỉ có thể thiết lập dữ liệu vào dto sử dụng setters ... hoặc xác định một nhà máy tạo ra một DTO từ một thực thể dựa trên một giao diện .....

Về câu hỏi thứ ba của bạn, theo yêu cầu của khách hàng của bạn :)

Các vấn đề liên quan