有时候我们可能不想显示某个实体中的所有字段。比如客户端发出如下请求:
locaohost:43321/api/groups/1/items?fields=idlocaohost:43321/api/groups/1/items?fields=id,name以上,对于Item这个类,我们可能只想显示id,也有可能是想显示id和name,等等。如何实现呢?→ 后端接受fields这个查询字符串的值,split到数组或集合中→ 遍历这些字段,使用反射获取字段的值,并把每个键值存储起来假设有如下的领域:
public class Group{ public int Id{ get;set;} public int UserId{ get;set;} public string Title{ get;set;} public string Descritpion{ get;set;} public int StatusId{ get;set;} public ICollection- Items{ get;set;}}public class Item{ public int Id{ get;set;} public string Name{ get;set;}}
针对Item的控制器如下:
public class ItemsController : ApiController{ [Route("groups/{groupId}/items", Name="ItemsForGroup")] public IHttpActionResult Get(int groupId, string fields = null) { ListlstOfFields = new List (); if(fields != null) { lstOfFields = fields.ToLower().Split('').ToList(); } var result = _repo.GetItems() .ToList() .Select(e => ItemFactory.CreateDataShapedObject(e, lstOfFields)); return Ok(result); }}public staic class ItemFactory{ public object CreateDataShapedObject(Item item, List lstOfFields) { if(!lstOfFields.Any()) { return item; } else { //运行时对象 ExpandObject objectToReturn = new ExpandObject(); foreach(var field in lstOfFields) { //获取字段值 var fieldValue = item.GetType() .GetProperty(field, BindingFlags.IgnoreCase | BindingFlags.Public | BindingFlags.Instance) .GetValue(item, null); ((IDictionary )objectToReturn).Add(field, fieldValue); } return objectToReturn; } }}
以上,ExpandObject是运行时对象,实现IDictionary<string, object>接口,通过反射,把字段作为ExpandObject的key,把字段值作为ExpandObject的value。