RESTful 端点的输入 DTO 是否应与输出 DTO 匹配?
Should input DTOs for RESTful endpoints match the output DTOs?
我正在研究 RESTful API,我在思考向 API 提供输入的过程时遇到了一些麻烦。
假设我有一个 "Person" 资源可以像这样获取:api/person/{id}
和 returns 一个像这样的对象:
public class Person
{
public int Id { get; set; }
public string Surname { get; set; }
public string GivenName { get; set; }
public DateTime DateOfBirth { get; set; }
}
如果我想更新那个人,API 应该期待一个完整的 Person
实例,还是可以接受使用单独的 DTO?
假设 DateOfBirth
无法更改,是否认为 RESTful 接受此作为输入:
public class UpdatePersonDto
{
public string Surname { get; set; }
public string GivenName { get; set; }
}
这意味着我将在使用 GET
时将此端点 api/person/{id}
returning Person
,而在使用 [= 时接受输入 UpdatePersonDto
20=]。这对我来说听起来不对,但我不确定我是否只是偏执。
所以我想我的问题可以总结为:是否适合在给定资源端点上接受不同于端点 return 的数据结构?
似乎 REST 共识是当使用 PUT 更新时,提供整个实体来替换。
以编程方式,让 PUT /person/{id} 接受在幕后映射到 UpdatePersonDTO 而不是 Person 的输入。
唯一的'problem'可能是它确实违背了普遍预期。
中间解决方案可以是 POST(或 PUT)/person/{id}/mutables,它可以接受 UpdatePersonDTO。
编辑:或者更明显的是:PUT /person/{id}/name 它采用包含两个字段的 PersonName 参数。
当涉及到 REST 严格规则时(只要存在这样的规则:/),您应该将整个实体发送到 PUT
。现在您可以:
- 静默忽略无法更新的字段 - 在某些情况下推荐使用,但应记录在案。
- 如果您检测到无法更新的字段被赋予了新值,则抛出异常。
- 而不是使用
PUT
,使用 PATCH
可以更新一组字段,并且不需要整个实体,例如只能发送名字和姓氏。
我个人认为最好的选择是 1 或 3。我不建议按照@morsor 的建议引入新的端点。这样的端点总是会造成混乱。一般来说,端点越少越好(更干净,更容易理解)API。
我正在研究 RESTful API,我在思考向 API 提供输入的过程时遇到了一些麻烦。
假设我有一个 "Person" 资源可以像这样获取:api/person/{id}
和 returns 一个像这样的对象:
public class Person
{
public int Id { get; set; }
public string Surname { get; set; }
public string GivenName { get; set; }
public DateTime DateOfBirth { get; set; }
}
如果我想更新那个人,API 应该期待一个完整的 Person
实例,还是可以接受使用单独的 DTO?
假设 DateOfBirth
无法更改,是否认为 RESTful 接受此作为输入:
public class UpdatePersonDto
{
public string Surname { get; set; }
public string GivenName { get; set; }
}
这意味着我将在使用 GET
时将此端点 api/person/{id}
returning Person
,而在使用 [= 时接受输入 UpdatePersonDto
20=]。这对我来说听起来不对,但我不确定我是否只是偏执。
所以我想我的问题可以总结为:是否适合在给定资源端点上接受不同于端点 return 的数据结构?
似乎 REST 共识是当使用 PUT 更新时,提供整个实体来替换。
以编程方式,让 PUT /person/{id} 接受在幕后映射到 UpdatePersonDTO 而不是 Person 的输入。
唯一的'problem'可能是它确实违背了普遍预期。
中间解决方案可以是 POST(或 PUT)/person/{id}/mutables,它可以接受 UpdatePersonDTO。
编辑:或者更明显的是:PUT /person/{id}/name 它采用包含两个字段的 PersonName 参数。
当涉及到 REST 严格规则时(只要存在这样的规则:/),您应该将整个实体发送到 PUT
。现在您可以:
- 静默忽略无法更新的字段 - 在某些情况下推荐使用,但应记录在案。
- 如果您检测到无法更新的字段被赋予了新值,则抛出异常。
- 而不是使用
PUT
,使用PATCH
可以更新一组字段,并且不需要整个实体,例如只能发送名字和姓氏。
我个人认为最好的选择是 1 或 3。我不建议按照@morsor 的建议引入新的端点。这样的端点总是会造成混乱。一般来说,端点越少越好(更干净,更容易理解)API。