将DTO重用于各种请求/响应类型与显示所需内容/应返回的内容

Bar*_*osz 14 architecture rest dto asp.net-web-api

我开始想知道我是不是在这里遇到反模式,所以请告知最佳实践.

我正在设计一个带有一组各种端点的REST API,我想将请求和响应参数包装到漂亮的DTO中.

例如,一些端点:

public async Task<JobStateResponse> GetJobState(JobStateRequest request);
public async Task<JobDownloadRespose> DownloadJob(JobDownloadRequest request);
public async Task<CreateJobResponse> CreateJob(CreateJobRequest request);
Run Code Online (Sandbox Code Playgroud)

问题是这些请求和响应是相对类似的DTO,例如:

public class JobStateResponse{
    public int TaskId {get;set;}
    public string ExternalId {get;set;}
    public State State {get;set;}
}
public class JobDownloadResponse {
    public int TaskId {get;set;}
    public string ExternalId {get;set;}
    public string JobContent {get;set;}
}
Run Code Online (Sandbox Code Playgroud)

我想为这些和继承创建一个基类,但在某些情况下,某些属性可能是多余的...这意味着这些方法没有明确指出它们工作所需的参数.

我的意思是,使用DTO参数公开API端点,该参数具有7个属性,但实际上只需要2个声音非常糟糕 ......

另一方面,为大多数端点维护单独的DTO似乎也是一种过度杀伤,也是维护地狱.

而且我想要最后一件事是请求的几个基类的复杂关系,因为这可能是一个更糟糕的主要问题.

那么,请求<>响应处理的正确方法是什么?

编辑:关于'基于意见'的标志 - 我正在寻找处理这个问题的最佳做法.我知道它可以通过多种方式完成,但我想避免使用地雷/反模式.另外,我要说到目前为止我对这些答案非常满意.

小智 23

独立,简单的DTO将使您的生活更加轻松.它将需要更多的代码,但它将是无聊的,简单的代码,易于测试,并允许您的接口独立地改变和发展.

为每个请求端点创建一个DTO,为每个响应创建一个单独的DTO.否则,你最终会伤心.

如果找到多个端点共有的元素,请将它们提取到自己的对象中,并将它们包含在两者中.

是的,在这里使用继承是错误的.坚持组成模式,你会没事的.


dee*_* zg 7

您肯定希望将每个端点的 DTO 分成 2 个组:请求组和响应组。

现在,说到继承,您可以拥有基本的 Request 和基本的 Response 类,其中包含一些通用的、非特定的内容(例如,插入数据的请求和响应包装消息),但您不想在请求之间混合继承和响应方。

正如其他人已经指出的那样,一开始的代码有点多,但这样你就永远不会碰壁。相反,混合它们很快就会让你进行大量的重构,与以清晰、单独的方式开始相比,你会损失更多的时间和精力。

  • 如果 dto 用于相同的资源/端点,请使用相同的 dto。将它们拆分为请求和响应是没有意义的,特别是对于 REST API 而言。如果您想隐藏某些内容,请不要映射它,将其设置为 null 并让您的 null 值不被序列化。让所有字段都可以为空。在这种情况下,Dto 只是传输数据的一种方式,无需过度复杂化。您的真正逻辑应该位于域模型或地图服务中。 (2认同)

Mar*_*man 5

使用单独的DTO,可以通过数据访问调用的行为来优化数据传输,还可以限制对您可能不想公开的属性的访问。尽管它是更多的代码,但是您正在确切定义要公开的内容并完全控制它。