Swagger 和 Swagger 的区别仇恨 [英] Difference between Swagger & HATEOAS

查看:57
本文介绍了Swagger 和 Swagger 的区别仇恨的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

谁能解释一下 Swagger 和 Swagger 之间的区别?讨厌.我可以搜索很多次但没有朋友可以解释这两个方面的正确详细答案.

Can anyone explain difference between Swagger & HATEOAS. I can Search many time but no buddy can explain the proper detailed answer this two aspects.

推荐答案

Swagger 和 HATEOAS IMO 之间的主要区别是,Swagger 仅适用于 RPC'esque API.然而,这些 API 实际上与 REST 几乎没有任何关系.

The main difference between Swagger and HATEOAS IMO, which is not covered in the accepted answer, is, that Swagger is only needed for RPC'esque APIs. Such APIs, however, have actually hardly anything to do with REST.

还有一个更广泛的误解,即通过 HTTP 交换的任何内容都自动是 RESTful(~ 根据 REST 架构风格),但事实并非如此.REST 只是定义了一组约束,这些约束不是选择或选项,而是强制性的.从开始到结束.不使用 RESTful 并没有错,但是将这样的架构称为 REST 是错误的.

There is a further, widespread misconception that anything exchanged via HTTP is automatically RESTful (~ in accordance with the REST archtitectural style), which it is not. REST just defines a set of constraints that are not choices or options but are mandatory. From start to finish. There is nothing wrong from being not RESTful, but it is wrong to term such an architecture REST.

Swagger 描述了可以在端点上执行的操作以及需要发送到服务的有效负载(包括标头和预期的表示格式),还描述了客户端可能期望的响应.这使得 Swagger 既可以用作文档,也可以用作 API 的测试框架.由于 Swagger 与 API 的紧密耦合,它的行为很像典型的 RPC 服务描述,即类似于 SOAP 中的 WSDL 文件或 RMI 或 CORBA 中的存根或骨架类.如果端点发生更改或负载中的某些内容发生更改,则根据 Swagger 文档实现的客户端可能会随着时间的推移而中断,只是重新引入典型 RPC 实现所具有的相同问题.

Swagger describe the operations that can be performed on an endpoint and the payload (including headers and the expected representation formats) that needs to be sent to the service and also describe what a client might expect as response. This allows Swagger to be used both as documentation as well as testing-framework for the API. Due to the tight coupling of Swagger to the API it behaves much like a typical RPC service description, i.e. similar to WSDL files in SOAP or stub or skeletton classes in RMI or CORBA. If either the endpoint changes or something in the payload changes, clients implementing against a Swagger documentation will probably break over time just reintroducing the same problems typical RPC implementations have.

另一方面,REST 和 HATEOAS 是为探索和进一步开发而设计的.REST 不是一种协议,而是一种架构风格,它描述了分布式系统中客户端和服务器之间的交互流程.它基本上采用了使 Web 如此成功的概念并将其转化为应用层.因此,适用于可浏览 Web 的相同概念也适用于 REST.因此,HATEOAS(链接、链接关系和链接名称的使用和支持)的行为与 Web 类似也就不足为奇了.

REST and HATEOAS, on the other side, are designed for disovery and further development. REST isn't a protocol but an architectural style to start with that describes the interaction flow between a client and server in a distributed system. It basically took the concepts which made the Web so successful and translated it onto the application layer. So the same concepts that apply to the browsable Web also apply to REST. Therefore it is no miracle that also HATEOAS (the usage of and support for links, link relations and link names) behave similar to the Web.

在设计 REST 架构时,考虑一个状态机是有益的,在该状态机中,服务器提供客户端采取进一步操作所需的所有信息.Asbjørn Ulsberg 在 2016 年举行了一场精彩的演讲,他解释了可供性和如何通过 HATEOAS 实现状态机.除了通用或标准化的媒体类型和关系名称之外,不需要带外知识来进一步与服务交互.在 Asbjørn 在他的演讲中给出的烤面包机示例中,烤面包机可能具有 offon加热idle 状态 打开烤面包机会导致状态从 off 转换到 on 然后转换到 加热 直到某个温度到达状态转换为 idle 并在 idle加热 之间切换,直到烤面包机关闭.

On designing a REST architecture it is benefitial to think of a state machine where a server provides all of the information a client needs to take further actions. Asbjørn Ulsberg held a great talk back in 2016 where he explains affordances and how a state machine might be implemented through HATEOAS. Besides common or standardized media-types and relation names no out-of-band knowledge is necessary to interact with the service further. In the case of the toaster example Asbjørn gave in his talk, a toaster may have the states off, on, heating and idle where turning a toaster on will lead to a state transition from off to on followed by a transition to heating till a certain temperature is reached where the state is transitioned to idle and switches between idle and heating till the toaster is turned off.

HATOAS 将为客户端提供有关当前状态的信息,并包含客户端可以调用以转换到下一个状态(即再次关闭烤面包机)的链接.在这里需要强调的是,客户端是由服务器提供的,客户端接下来可能执行的每个操作.客户端实现者无需查阅任何专有 API 文档即可使客户端能够与 REST 服务进行交互.此外,URI 不必有意义或设计为传达语义表达结构,因为客户端将确定通过链接关系名称调用该 URI 是否有意义.此类关系名称由 IANA 指定,由一个常见的方法,例如 Dublin Coreschema.org 或作为 扩展属性,它可能指向人类可读的描述,进一步可能通过鼠标悬停工具提示等传播给用户.

HATOAS will provide a client with the information on the current state and include links a client can invoke to transition to the next state, i.e. turning the toaster off again. It's important to stress here, that a client is provided by the server with every action the client might perform next. There is no need for a client implementor to consult any proprietary API documentation in order for a client to be able to interact with a REST service. Further, URIs do not have to be meaningful or designed to convey a semantical-expressive structure as clients will determine whether invoking that URI makes sense via the link-relation name. Such relation names are either specified by IANA, by a common approach such as Dublin Core or schema.org or by absolut URIs acting as extension attributes which might point to a human-readable description, which further might be propagated to the user via mouse-over tooltips or such.

我希望你自己能看到,Swagger 仅用于描述 RPC Web-API,而不是遵循 REST 架构设计的应用程序.通过 REST API 交换的消息应包含客户端在下一次状态转换时做出明智选择所需的所有信息.因此,将此类消息流和交互设计为状态机是有益的.

I hope you can see by yourself that Swagger is only needed to describe RPC Web-APIs rather than applications that follow the REST architectural design. Messages exchanged via REST APIs should include all the information needed by a client to make informed choices on the next state transition. As such it is benefitial to design such message flows and interactions as state machine.

更新:

Swagger 和 HATEOAS 如何相互排斥?前者记录您的端点(使自动生成代码成为可能),后者向您的端点添加元信息,告诉消费者他们可以做什么(即哪些其他端点可用).这些是非常不同的东西.

How are Swagger and HATEOAS mutually exclusive? The former documents your endpoints (making auto-generating code possible) and the latter adds meta-information to your endpoints which tell the consumer what they can do (i.e. which other endpoints are available). These are very different things.

我从来没有说过它们是相互排斥的,只是它们有两个不同的目的,如果你遵循一种方法,另一种方法或多或少会变得毫无用处.但是,两者都使用没有任何意义.

I never stated that they are mutually exclusive, just that they serve two different purposes, where if you follow one approach the other gets more or less useless. Using both does not make any sense though.

让我们将讨论转移到 Web 领域,因为这可能更容易理解,而 REST 实际上只是 Web 上使用的概念的概括,因此执行此步骤很自然,并且在设计方面也是一个很好的建议一般的 REST 架构.想一想您作为用户想要向服务器发送一些数据的情况.您以前从未使用过该服务,因此您基本上不知道请求的外观.

Let's move the discussion to the Web domain as this is probably more easily understandable and REST is de facto just a generalization of the concepts used on the Web, so doing this step is just natural and also a good recommendation in terms of designing REST architectures in general. Think of a case where you as a user want to send some data to the server. You have never used the service before so you basically don't know how a request has to look like.

在 Swagger 中,您将调用端点文档,选择最有可能解决您的任务的选项,阅读请求的外观并将测试用例破解到您的应用程序中,最终生成一个 HTTP 请求被发送到相应的位置.自动生成代码可能会为您节省一些破解时间,尽管您仍然需要将存根类集成到您的应用程序中并至少测试一次整个事情以确保安全.如果您以后需要集成该 API 或其他一般 API 的第二个服务,您需要从头开始并查找 Swagger 文档,生成或破解交互代码并将其集成到您的域中.涉及大量手动步骤,并且在 API 更改的情况下,您需要更新您的客户端,否则它可能会停止工作.

In Swagger you would call the endpoint documentation, select the option that most likely might solve your task, read up on how the request needs to look like and hack a test-case into your application that ends up generating a HTTP request that is sent to the respective location. Auto-generating code might spare you some hacking time, though you still need to integrate the stub classes into your application and test the whole thing at least once just to be safe. If you later on need to integrate a second service of that API or of yet an other API in general, you need to start from the beginning and look up the Swagger documentation, generate or hack the interaction code and integrate it into your domain. Plenty of manual steps involved and in cases of API changes you need to update your client as otherwise it might stop working.

然而,在 Web 示例中,您只需启动浏览器/Web 客户端,调用相应的 URI 即可将数据发送到服务器,服务器很可能会向您发送一个 HTML 表单,您只需填写和单击发送按钮,该按钮会自动将请求发送到将开始处理它的服务器.这是仇恨.您使用给定的控件来驱动您的工作流程.服务器会教您的客户端发出有效请求所需的每一个小细节.它为您的客户端提供目标 URI 以将请求发送到,它应该使用的 HTTP 方法,以及最常见的隐式有效负载应该在的媒体类型.除此之外,它还为您的客户端提供了预期的框架和/或有效负载应包含的受支持元素.IE.该表单可能要求您填写几个输入字段,在一组给定的选项中进行选择,或使用其他一些控件,例如日期或时间选择器值,该值会为您转换为有效的日期或时间表示.您需要做的就是调用 Web 客户端中的相应资源.没有自动生成,没有集成到您的浏览器/应用程序中.使用其他服务(来自相同或不同的提供商)很可能只是以相同的方式工作,因此只要支持交换媒体类型的请求和响应,就无需更改或更新您的 HTTP 客户端(浏览器).

In the Web example however, you just start your browser/Web client, invoke the respective URI that allows you to send the data to the server and the server will most likely send you a HTML form you just need to fill out and click the send button which automatically sends the request to the server which will start to process it. This is HATEOAS. You used the given controls to drive your workflow. The server taught your client every little detail it needed to make a valid request. It served your client with the target URI to send the request to, the HTTP method it should use and most often also implicitly the media type the payload should be in. In addition to that it also gave your clients a skeleton of the expected and/or supported elements the payload should contain. I.e. the form may require you to fill out a couple of input fields, select among a given set of choices or use some other controls such as a date or time picker value that is translated to a valid date or time representation for you. All you needed to do was to invoke the respective resource in your Web client. No auto-generation, no integration into your browser/application. Using other services (from the same or different providers) will, most likely, just work the same way so no need to change or update your HTTP client (browser) as long as the media-type request and responses are exchanged are supported.

在您依赖 Swagger RPC 式文档的情况下,该文档是关于如何与服务交互的真相.混入一些 HATEOAS 信息不会给您带来任何好处.在 Swagger 案例中,由于参考文档中提供了所有必需的信息,因此携带额外的元信息会使请求/响应膨胀,因为所有必需的信息都在参考文档中给出,这在一定程度上会导致人们开始质疑该服务的开发人员并要求减少有效负载.只看这里一段时间,你会发现足够多的问题,询问如何进一步优化交互并将消息大小减少到最小,因为它们处理每个小请求并且根本不使用响应缓存.在 HATEOAS 案例中,指向外部引用是没有用的,因为这种架构中的对等点很可能已经支持所需的必需品,例如 URI、HTTP 和相应的媒体类型,在其中实现.在使用自定义媒体类型的情况下,可以在运行时通过插件或附加组件动态添加支持(如果支持).

In the case where you rely on Swagger RPC'esque documentation, that documentation is the truth on how to interact with the service. Mixing in some HATEOAS information doesn't provide you any benefits. In the Swagger case, carrying around additional meta-information that bloat up the request/response for no obvious reasons, as all the required information is given in the reference documentation, will, with some certainty, lead to people starting questioning the sanity of the developers of that service and ask for payload reduction. Just look here at SO for a while and you will find enough question asking on how to optimize the interaction further and further and reducing message size to a minimum as they process every little request and don't make use of response caching at all. In the HATEOAS case, pointing to an external reference is just useless as peers in such an architecture most likely already have support for the required necessities, such as URI, HTTP and the respective media types, implemented into it. In cases where custom media-types are used, support can be added at runtime via plug-ins or add-ons dynamically (if supported).

因此,Swagger 和 HATEOAS 并不是相互排斥的,但是一旦您决定选择一条路线或另一条路线,另一个就会或多或少地变得无用.

So, Swagger and HATEOAS are not mutually exclusive but the other gets more or less useless once you decided for one route or the other.

这篇关于Swagger 和 Swagger 的区别仇恨的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆