更新或版本化Web服务的策略?

时间:2009-05-31 02:23:00

标签: .net web-services deployment

我很想听听有关如何处理不同版本的Web服务的最佳实践。

为了澄清一下,如果你有一些Web方法作为Web服务公开,那么你想要添加一个特性/功能,从而改变那些方法调用的签名,你如何处理这个问题呢?打破目前呼叫该服务的所有客户?

您是否在不同的网址上部署服务?

你是否在方法名称中添加了一个版本(MyMethod,MyMethodv2等等 - 呃..)

您是否将一个版本作为方法调用的一部分与参数列表一起传递?

有没有人知道Google或亚马逊如何通过广泛的网络服务库处理这种情况?

编辑:到目前为止,我在article from Oracle找到了一些不错的信息。另外this blog entry对某些Java细节也很有用。我仍然很想看到其他一些方法。

5 个答案:

答案 0 :(得分:14)

对Web服务进行版本控制的典型方法是让客户端指定所需的版本。您可以考虑简单的约束,例如“> 2.0”,“< 1.5”或“= 1.1”。当然,您希望最大限度地减少支持的版本数量,以保证您的理智。如果客户端未指定版本,则采用最新版本。

提供版本的技术各不相同。有些人主张使用URL,其他人鼓励使用标题,有些可能会将其作为api调用的参数包含在内。但是,几乎没有人会改变方法的名称。这相当于OSGi链接的“封装”或“命名空间”版本。它会使升级变得非常困难,并且阻碍人们升级,而不是对实际服务的任何改变。

这还取决于您访问Web服务的方式。如果您正在使用REST,那么保持URL的清洁并使用标头是最有意义的(如果需要,将其作为查询参数进行破解是微不足道的)。如果您正在使用SOAP / XMLRPC / whatever-RPC,那么将其放入URL通常就可以了。

  

编辑5/2011 FWIW,虽然我不同意,Apigee's blog recommends putting the version in the URL

客户端如何指定版本通常非常简单。更复杂的是如何同时运行所有版本。大多数语言都没有办法将同一个库/模块/类/函数的多个版本加载到同一个运行时环境中(无论是VM,进程还是拥有它的东西)。您提供的OSGi链接是Java的解决方案,允许这样做。

在实践中,OSGi在大多数情况下都会过度杀伤。通常更容易将已弃用的请求代理到另一个服务器或进程。

然而,“版本化”服务的最佳方式是为它们构建可扩展性和灵活性,以便它们保持向前和向后兼容。这并不意味着所有版本必须相互兼容,但连续版本应相互兼容。

答案 1 :(得分:5)

我可以告诉你,创建doAPIFunction,doAPIFunctionV2和doAPIFunctionV3等的解决方案在我工作的地方只产生了令人头疼的问题。除此之外,缺乏清晰描述性的功能名称意味着各种各样的疯狂。

您需要清晰的API函数名称,如果api正在发生变化,目标是尽可能以向后兼容的方式尝试。我建议对入口点进行版本控制,这样每个入口点都支持一个稳定的API,如果有充分的理由改变语义,example.org /api-1.0/中的doFunction可能与example.org/api-2.0不同。

答案 2 :(得分:1)

我不确定我是否理解你的问题。但我的2美分。 如果方法的签名像另一个新参数那样改变那么为什么它不能成为可选的呢?但是,如果更改现有参数数据类型,则它不适用。

如果明白错误,请投票。 :)

答案 3 :(得分:1)

多年前,当你可以使用相同的webservice方法名称和不同的参数时,它会变得更简单。 :)

一旦您撰写了网络服务,您就会与客户签订合同,这是您将支持的。

对于较旧的方法,我建议记录以查看它们是否被使用,以及由谁来查看是否可以让它们更新。

除此之外,您最好的选择是编写一个新方法,因此您可能有几个类似的函数名称因版本而异。

传递版本号的问题是你必须确保客户端总是传入一个有效的数字,如果你生成的存根可以工作,但是如果你没有,那么这是非常脆弱的。

在名称中放置一个版本号对我来说似乎最合适,因为它显示了旧版本,并且您可以使用AOP更轻松地记录旧版本的Web服务方法。

答案 4 :(得分:0)

缓解这种情况的一种方法是按合同编码并通过设置界面。您永远不能真正更改功能签名,但是,您可以重载它们。考虑.NET API。它弃用了一些方法,但它们继续工作,因为围绕它们编码的程序可能会中断。新版本的服务可能会在不同的URI(v2.webservice.com)上公开,以便为其提供新的路线图,并且需要继续支持v1。