SOAP vs. REST Challenges

本文深入探讨了SOAP和REST这两种Web API设计模型的区别。从消息格式、传输协议到服务描述语言等方面进行了全面比较,并分析了各自的优缺点。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

The term web API generally refers to both sides of computer systems communicating over a network: the API services offered by a server, as well as the API offered by the client such as a web browser. The server-side portion of the web API is a programmatic interface to a defined request-response message system, and is typically referred to as the Web Service. There are several design models for web services, but the two most dominant are SOAP and REST.

SOAP

SOAP – Simple Object Access Protocol – is probably the better known of the two models.

SOAP relies heavily on XML, and together with schemas, defines a very strongly typed messaging framework. Every operation the service provides is explicitly defined, along with the XML structure of the request and response for that operation. Each input parameter is similarly defined and bound to a type: for example an integer, a string, or some other complex object. 

All of this is codified in the WSDL – Web Service Description (or Definition, in later versions) Language. The WSDL is often explained as a contract between the provider and the consumer of the service. In programming terms the WSDL can be thought of as a method signature for the web service.

Example:

A sample message exchange looks like the following.

A request from the client:

POST http://www.stgregorioschurchdc.org/cgi/websvccal.cgi HTTP/1.1
Accept-Encoding: gzip,deflate
Content-Type: text/xml;charset=UTF-8
SOAPAction: "http://www.stgregorioschurchdc.org/Calendar#easter_date"
Content-Length: 479
Host: www.stgregorioschurchdc.org
Connection: Keep-Alive
User-Agent: Apache-HttpClient/4.1.1 (java 1.5)
<?xml version="1.0"?>
<soapenv:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:cal="http://www.stgregorioschurchdc.org/Calendar">
<soapenv:Header/>
<soapenv:Body>
   <cal:easter_date soapenv:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">
   <year xsi:type="xsd:short">2014</year>
</cal:easter_date>
</soapenv:Body>
</soapenv:Envelope>

The response from the service:

HTTP/1.1 200 OK
Date: Fri, 22 Nov 2013 21:09:44 GMT
Server: Apache/2.0.52 (Red Hat)
SOAPServer: SOAP::Lite/Perl/0.52
Content-Length: 566
Connection: close
Content-Type: text/xml; charset=utf-8
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body>
   <namesp1:easter_dateResponse
xmlns:namesp1="http://www.stgregorioschurchdc.org/Calendar">   
<s-gensym3 xsi:type="xsd:string">2014/04/20</s-gensym3>
</namesp1:easter_dateResponse>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>

From this example we can see the message was sent over HTTP. SOAP is actually agnostic of the underlying transport protocol and can be sent over almost any protocol such as HTTP, SMTP, TCP, or JMS. As was already mentioned, the SOAP message itself must be XML-formatted. As is normal for any XML document, there must be one root element: the Envelope in this case. This contains two required elements: the Header and the Body. The rest of the elements in this message are described by the WSDL.

The accompanying WSDL that defines the above service looks like this (the details are not important, but the entire document is shown here for completeness):

<?xml version="1.0"?>
<definitions xmlns:tns="http://www.stgregorioschurchdc.org/Calendar"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns="http://schemas.xmlsoap.org/wsdl/"
name="Calendar" targetNamespace="http://www.stgregorioschurchdc.org/Calendar">
<message name="EasterDate">
   <part name="year" type="xsd:short"/>
</message>
<message name="EasterDateResponse">
   <part name="date" type="xsd:string"/>
</message>
<portType name="EasterDateSoapPort">
   <operation name="easter_date" parameterOrder="year">
     <input message="tns:EasterDate"/>
     <output message="tns:EasterDateResponse"/>
   </operation>
</portType>
<binding name="EasterDateSoapBinding" type="tns:EasterDateSoapPort">
   <soap:binding style="rpc" transport="http://schemas.xmlsoap.org/soap/http"/>
   <operation name="easter_date">
     <soap:operation soapAction="http://www.stgregorioschurchdc.org/Calendar#easter_date"/>
     <input>
      <soap:body use="encoded" namespace="http://www.stgregorioschurchdc.org/Calendar" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
     </input>
     <output>
       <soap:body use="encoded" namespace="http://www.stgregorioschurchdc.org/Calendar" encodingStyle="http://schemas.xmlsoap.org/soap/encoding/"/>
     </output>
   </operation>
</binding>
<service name="Calendar">
   <port name="EasterDateSoapPort" binding="tns:EasterDateSoapBinding">
     <soap:address location="http://www.stgregorioschurchdc.org/cgi/websvccal.cgi"/>
   </port>
</service>
</definitions>

Notice that all the parts of the message body are described in this document. Also note that, even though this document is intended to be primarily read by a computer, it is still relatively easy for a person with some programming knowledge to follow.

WSDL

The WSDL defines every aspect of the SOAP message. It is even able to define whether any element or attribute is allowed to appear multiple times, if it is required or optional, and can even dictate a specific order the elements must appear in.

It is a common misconception that the WSDL is a requirement.

It is a common misconception that the WSDL is a requirement for a SOAP service. SOAP was designed before the WSDL, and therefore the WSDL is optional. Although arguably, it is significantly harder to interface with a web service that does not have a WSDL. 

On the other hand, if a developer is asked to interface with an existing SOAP web service, he only needs to be given the WSDL, and there are tools that do service discovery - generate method stubs with appropriate parameters in almost any language from that WSDL. Many test tools on the market work in the same way - a tester provides a URL to a WSDL, and the tools generate all the calls with sample parameters for all the available methods.

Critique

While the WSDL may seem like a great thing at first – it is self documenting and contains almost the complete picture of everything that is required to integrate with a service – it can also become a burden. Remember, the WSDL is a contract between you (the provider of the service) and every single one of your customers (consumers of the service).

WSDL changes also means client changes.

If you want to make a change to your API, even something as small as adding an optional parameter, the WSDL must change. And WSDL changes also means client changes - all your consumers must recompile their client application against this new WSDL. This small change greatly increases the burden on the development teams (on both sides of the communication) as well as the test teams. For this reason, the WSDL is viewed as a version lock-in, and most providers are very resistant to updating their API.

Furthermore, while SOAP offers some interesting flexibility, such as the ability to be transmitted over any transport protocol, nobody has really taken advantage of most of these. Thanks to how the Internet evolved, everything that matters runs over HTTP. There are new advances, but most of these are being hampered by infrastructure routers refusing to route non-standard HTTP traffic. Just consider: how long has the world been trying to switch over to IPv6?

There is definitely a need for a more lightweight and flexible model [than SOAP].

Any situation where the size of the transmitted message does not matter, or where you control everything end-to-end, SOAP is almost always the better answer. This applies primarily to direct server to server communication, generally used for internal communication only within the confines of one company. However, there is a need for a world where almost every person on the planet has several low-memory, low-processing-power devices connected to multiple services at all times, there is definitely a need for a more lightweight and flexible model.

REST

REST – REpresentational State Transfer – is quickly becoming the preferred design model for public APIs. Some interesting statistics regarding the growth of REST in the public sphere are available at, for example, the Programmable Web.

REST is an architectural style, unlike SOAP which is a standardized protocol. REST makes use of existing and widely adopted technologies, specifically HTTP, and does not create any new standards. It can structure data into XML, YAML, or any other machine readable format, but usually JSON – JavaScript Object Notation – is preferred. As can be expected from JavaScript, the objects are not strongly typed. REST follows the object oriented programming paradigm of noun-verb. REST is very data-driven, compared to SOAP, which is strongly function-driven. In the REST paradigm, metadata is structured hierarchically and represented in the URI; this takes the place of the noun. The HTTP standard offers several verbs representing operations or actions you can perform on the data, most commonly: GET, POST, PUT, and DELETE.



Source: http://dret.net/netdret/docs/soa-rest-www2009/rest-ws.pdf



For example, let's say we need three operations: a user login, logout, and retrieve the current user's account balance. While a SOAP service would implement each of these as separate operations (with the username and password passed as arguments to the login operation), REST would define a URI like http://sample.test/api/session. A POST action (with username and password passed in the body) to this URI would accomplish a user being logged into the session, and a DELETE action to the same URI would accomplish the session being terminated – effectively a logout. A GET action to sayhttp://sample.test/api/session/balance would retrieve the current user's balance.

Example:

A sample message exchange could contain as little as this.

Request:

GET http://www.catechizeme.com/catechisms/catechism_for_young_children/daily_question.js HTTP/1.1
Accept-Encoding: gzip,deflate
Host: www.catechizeme.com
Connection: Keep-Alive
User-Agent: Apache-HttpClient/4.1.1 (java 1.5)

Response:

HTTP/1.1 200 OK
Date: Fri, 22 Nov 2013 22:32:22 GMT
Server: Apache
X-Powered-By: Phusion Passenger (mod_rails/mod_rack) 3.0.17
ETag: "b8a7ef8b4b282a70d1b64ea5e79072df"
X-Runtime: 13
Cache-Control: private, max-age=0, must-revalidate
Content-Length: 209
Status: 200
Keep-Alive: timeout=2, max=100
Connection: Keep-Alive
Content-Type: js; charset=utf-8
{
   "link": "catechisms\/catechism_for_young_children\/questions\/36",
   "catechism": "Catechism for Young Children",
   "a": "Original sin.",
   "position": 36,
   "q": " What is that sinful nature which we inherit from Adam called?"
}

As is already expected this message was sent over HTTP, and used the GET verb. Further note that the URI, which also had to be included in the SOAP request, but there it had no meaning, here actually takes on a meaning. The body of the message is significantly smaller, in this example there actually isn't one.

A REST service also has a schema in what is called a WADL – Web Application Description Language. The WADL for the above call would look like this:

<?xml version="1.0"?>
<application xmlns="http://wadl.dev.java.net/2009/02">
<doc xml:lang="en" title="http://www.catechizeme.com"/>
<resources base="http://www.catechizeme.com">
<resource path="catechisms/{CATECHISM_NAME}/daily_question.js" id="Daily_question.js">
<doc xml:lang="en" title="Daily_question.js"/>
<param xmlns:xs="http://www.w3.org/2001/XMLSchema" name="CATECHISM_NAME" style="template" type="string"/>
<method name="GET" id="Daily_question.js">
   <doc xml:lang="en" title="Daily_question.js"/>
   <request/>
   <response status="200">
     <representation mediaType="json" element="data"/>
     <representation mediaType="js; charset=utf-8" element="data"/>
   </response>
</method>
</resource>
</resources>
</application>

The WADL uses XML syntax to describe the metadata and the available actions. It can also be written to be as strict as the WSDL: defining types, optional parameters, etc.

WADL

The WADL does not have any mechanism to represent the data itself, which is what must be sent on the URI. This means that the WADL is able to document only about half of the information you need in order to interface with the service. Take for example the parameter CATECHISM_NAME in the above sample. The WADL only tells you where in the URI the parameter belongs, and that it should be a string. However, if you had to glean the valid values for yourself, it would probably take you quite a long time. Note that it is possible to add a schema to the WADL, so that you can define even complex variable types such as enumerations; however, this is even more rare than providing a WADL.

The WADL is completely optional.

Further the WADL is completely optional; in fact, it is quite rare that the WADL is supplied at all! Due to the nature of the service, in order to make any meaningful use of it, you will almost undoubtedly need additional documentation.

Critique

Having a very small footprint and making use of the widely adopted HTTP standard makes REST a very attractive option for public APIs. Coupled together with JSON, which makes something like adding an optional parameter very simple, makes it very flexible and allows for frequent releases without impacting your consumers.

Arguably, the biggest drawback is the WADL – optional and lacking some necessary information. To address this deficiency, there are several frameworks available on the market that help document and produce RESTful APIs, such as SwaggerRAML, or JSON-home

However, since there is no clear “standard” the domain flourishes with a multitude of different frameworks. This can make it hard to quickly grasp how the API works, if you prefer to work with clearly defined standards. On the other hand, if you thrive among disruptive technologies, then REST will probably be right up your alley. There are of course numerous discussions on best practices on the subject; one possible place to get you started is Martin Fowler's “Richardson Maturity Model”.

Reference: http://www.soapui.org/testing-dojo/world-of-api-testing/soap-vs--rest-challenges.html

资源下载链接为: https://pan.quark.cn/s/d9ef5828b597 在本文中,我们将探讨如何通过 Vue.js 实现一个带有动画效果的“回到顶部”功能。Vue.js 是一款用于构建用户界面的流行 JavaScript 框架,其组件化和响应式设计让实现这种交互功能变得十分便捷。 首先,我们来分析 HTML 代码。在这个示例中,存在一个 ID 为 back-to-top 的 div 元素,其中包含两个 span 标签,分别显示“回到”和“顶部”文字。该 div 元素绑定了 Vue.js 的 @click 事件处理器 backToTop,用于处理点击事件,同时还绑定了 v-show 指令来控制按钮的显示与隐藏。v-cloak 指令的作用是在 Vue 实例渲染完成之前隐藏该元素,避免出现闪烁现象。 CSS 部分(backTop.css)主要负责样式设计。它首先清除了一些默认的边距和填充,对 html 和 body 进行了全屏布局,并设置了相对定位。.back-to-top 类则定义了“回到顶部”按钮的样式,包括其位置、圆角、阴影、填充以及悬停时背景颜色的变化。此外,与 v-cloak 相关的 CSS 确保在 Vue 实例加载过程中隐藏该元素。每个 .page 类代表一个页面,每个页面的高度设置为 400px,用于模拟多页面的滚动效果。 接下来是 JavaScript 部分(backTop.js)。在这里,我们创建了一个 Vue 实例。实例的 el 属性指定 Vue 将挂载到的 DOM 元素(#back-to-top)。data 对象中包含三个属性:backTopShow 用于控制按钮的显示状态;backTopAllow 用于防止用户快速连续点击;backSeconds 定义了回到顶部所需的时间;showPx 则规定了滚动多少像素后显示“回到顶部”按钮。 在 V
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值