一旦成功的发布API后,使用者将依赖于你所提供的服务。但是变更总是无法避免的,因此谨慎的制定ASP.NET Web API的版本策略就变得非常重要。一般来说,新的功能需要无缝的接入,有时新老版本需要并行,以便给使用者足够的时间来进行迁移和配套的变更。设置,老的版本会一直持续被使用。
简单版本管理
假设我们现在对StudentsController进行修改,将GET方法中返回“FirstName” 和 “LastName”修改为返回“FullName”和 “CoursesDuration”。
最简单的方法就是新建一个类似于StudentsV2Controller的新服务。请留意V2,接下来将依赖这个引入管理策略。这种方法来自于Shawn Wildermuth的plural sight course文章。旧版本的服务返回的json应该是这样的:
   1:  [{2: "id": 2,
3: "url": "http://localhost:8323/api/students/HasanAhmad",
4: "firstName": "Hasan",
5: "lastName": "Ahmad",
6: "gender": 0,
7: "enrollmentsCount": 4
   8:  },   9:  {10: "id": 3,
11: "url": "http://localhost:8323/api/students/MoatasemAhmad",
12: "firstName": "Moatasem",
13: "lastName": "Ahmad",
14: "gender": 0,
15: "enrollmentsCount": 4
  16:  }]而新版本的返回如下:
   1:  [{2: "id": 2,
3: "url": "http://localhost:8323/api/students/HasanAhmad",
4: "fullName": "Hasan Ahmad",
5: "gender": 0,
6: "enrollmentsCount": 4,
7: "coursesDuration": 13
   8:  },   9:  {10: "id": 3,
11: "url": "http://localhost:8323/api/students/MoatasemAhmad",
12: "fullName": "Moatasem Ahmad",
13: "gender": 0,
14: "enrollmentsCount": 4,
15: "coursesDuration": 16
  16:  }]新版本的GET函数的实现为:
1: public IEnumerable<StudentV2BaseModel> Get(int page = 0, int pageSize = 10)
   2:      {   3:          IQueryable<Student> query;   4:      5:          query = TheRepository.GetAllStudentsWithEnrollments().OrderBy(c => c.LastName);   6:      7:          var totalCount = query.Count();8: var totalPages = Math.Ceiling((double)totalCount / pageSize);
   9:   10: var urlHelper = new UrlHelper(Request);
11: var prevLink = page > 0 ? urlHelper.Link("Students", new { page = page - 1, pageSize = pageSize }) : "";
12: var nextLink = page < totalPages - 1 ? urlHelper.Link("Students", new { page = page + 1, pageSize = pageSize }) : "";
  13:   14: var paginationHeader = new
  15:          {  16:              TotalCount = totalCount,  17:              TotalPages = totalPages,  18:              PrevPageLink = prevLink,  19:              NextPageLink = nextLink  20:          };  21:   22: System.Web.HttpContext.Current.Response.Headers.Add("X-Pagination",
  23:          Newtonsoft.Json.JsonConvert.SerializeObject(paginationHeader));  24:     25:          var results = query  26:          .Skip(pageSize * page)  27:          .Take(pageSize)  28:          .ToList()  29:          .Select(s => TheModelFactory.CreateV2Summary(s));  30:   31: return results;
  32:      }StudentV2BaseModel和CreateV2Summary只是为了举例方便,实际可以根据需要是否要进行这样的修改或者无须修改。
具体的代码如下:
1: public class StudentV2BaseModel
   2:      {3: public int Id { get; set; }
4: public string Url { get; set; }
5: public string FullName { get; set; }
6: public Data.Enums.Gender Gender { get; set; }
7: public int EnrollmentsCount { get; set; }
8: public double CoursesDuration { get; set; }
   9:      }  10:   11: public class ModelFactory
  12:      {13: public StudentV2BaseModel CreateV2Summary(Student student)
  14:          {15: return new StudentV2BaseModel()
  16:              {17: Url = _UrlHelper.Link("Students", new { userName = student.UserName }),
  18:                  Id = student.Id,19: FullName = string.Format("{0} {1}", student.FirstName, student.LastName),
  20:                  Gender = student.Gender,  21:                  EnrollmentsCount = student.Enrollments.Count(),  22:                  CoursesDuration = Math.Round(student.Enrollments.Sum(c => c.Course.Duration))  23:              };  24:          }  25:      }来源:http://bitoftech.net/2013/12/16/asp-net-web-api-versioning-strategy/