日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

昂首阔步:让开发人员喜欢使用您的REST API

發(fā)布時間:2023/12/3 编程问答 23 豆豆
生活随笔 收集整理的這篇文章主要介紹了 昂首阔步:让开发人员喜欢使用您的REST API 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

隨著JAX-RS API的發(fā)展,以及今年早些時候在JSR-339下發(fā)布的2.0版本,使用出色的Java平臺創(chuàng)建REST服務變得更加容易。

但是,極大的簡化帶來了巨大的責任:記錄所有這些API,以便其他開發(fā)人員可以快速了解如何使用它們。 不幸的是,在這方面開發(fā)人員只能靠自己: JSR-339并沒有太大幫助。 可以肯定的是,從源代碼生成冗長且易于遵循的文檔,而不是要求某人在開發(fā)過程中編寫它,真是太棒了。 聽起來不真實,對吧? 在某種程度上確實如此,但是幫助以Swagger的形式出現。

本質上, Swagger做的是一件簡單但非常強大的事情:通過添加一些附加注釋,它會生成REST API描述( HTTP方法,路徑/查詢/表單參數,響應, HTTP錯誤代碼等),甚至提供了一個簡單的Web UI來玩對您的API的REST調用(更不用說所有這些元數據也可以通過REST獲得)。

在深入研究實現細節(jié)之前,讓我們快速看一下Swagger來自API消費者預期的含義。 假設您已經開發(fā)了一種出色的REST服務來管理人員。 作為良好的公民,此REST服務具有完整的功能,并提供以下功能:

  • 列出所有人( GET )
  • 通過電子郵件查找人( GET )
  • 添加新人( POST )
  • 更新現有人員( PUT )
  • 最后刪除人( DELETE )

從Swagger的角度來看,這是相同的API:

看起來很漂亮。 讓我們做更多的事情,并從Swagger UI調用我們的REST服務,這真棒。 最復雜的用例是添加新人( POST ),因此將仔細研究這一情況。

如您在上面的快照中所見,每一個REST服務調用都存在:

  • 服務說明
  • 相對語境路徑
  • 參數(形式/路徑/查詢),必需或可選
  • HTTP狀態(tài)碼: 201 CREATED和409 CONFLICT
  • 準備出發(fā)嘗試一下! 立即調用REST服務(具有開箱即用的參數驗證功能)

為了完成演示部分,讓我展示另一個示例,其中涉及REST資源(在我們的例子中,這是一個簡單的Person類)。 Swagger能夠提供其屬性和有意義的描述以及預期的響應內容類型。

看起來不錯! 轉到下一部分,所有內容都與實現細節(jié)有關。 Swagger支持與JAX-RS服務的無縫集成,在現有注釋的頂部僅需幾個附加注釋。 首先,在我們的示例中,應該記錄的每個單個JAX-RS服務都應使用@Api注釋進行注釋:

@Path( "/people" ) @Api( value = "/people", description = "Manage people" ) public class PeopleRestService {// ... }

接下來,相同的方法適用于REST服務操作:應該記錄的每個方法都應使用@ApiOperation批注(可選)并使用@ ApiResponses / @ ApiResponse進行批注 。 如果它接受參數,則應使用@ApiParam批注進行批注。 這里有幾個例子:

@Produces( { MediaType.APPLICATION_JSON } ) @GET @ApiOperation( value = "List all people", notes = "List all people using paging", response = Person.class, responseContainer = "List" ) public Collection< Person > getPeople( @ApiParam( value = "Page to fetch", required = true ) @QueryParam( "page") @DefaultValue( "1" ) final int page ) {// ... }

還有一個:

@Produces( { MediaType.APPLICATION_JSON } ) @Path( "/{email}" ) @GET @ApiOperation( value = "Find person by e-mail", notes = "Find person by e-mail", response = Person.class ) @ApiResponses( {@ApiResponse( code = 404, message = "Person with such e-mail doesn't exists" ) } ) public Person getPeople( @ApiParam( value = "E-Mail address to lookup for", required = true ) @PathParam( "email" ) final String email ) {// ... }

REST資源類(或模型類)需要特殊的注釋: @ApiModel和@ApiModelProperty 。 這是我們的Person類的樣子:

@ApiModel( value = "Person", description = "Person resource representation" ) public class Person {@ApiModelProperty( value = "Person's first name", required = true ) private String email;@ApiModelProperty( value = "Person's e-mail address", required = true ) private String firstName;@ApiModelProperty( value = "Person's last name", required = true ) private String lastName;// ... }

最后一步是將Swagger插入JAX-RS應用程序。 我開發(fā)的示例使用Spring Framework , Apache CXF , Swagger UI和嵌入式Jetty (完整項目可在Github上找到 )。 集成Swagger只需添加配置bean( swaggerConfig ),一個附加的JAX-RS服務( apiListingResourceJson )和兩個JAX-RS提供程序( resourceListingProvider和apiDeclarationProvider )即可。

package com.example.config;import java.util.Arrays;import javax.ws.rs.ext.RuntimeDelegate;import org.apache.cxf.bus.spring.SpringBus; import org.apache.cxf.endpoint.Server; import org.apache.cxf.jaxrs.JAXRSServerFactoryBean; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.DependsOn; import org.springframework.core.env.Environment;import com.example.resource.Person; import com.example.rs.JaxRsApiApplication; import com.example.rs.PeopleRestService; import com.example.services.PeopleService; import com.fasterxml.jackson.jaxrs.json.JacksonJsonProvider; import com.wordnik.swagger.jaxrs.config.BeanConfig; import com.wordnik.swagger.jaxrs.listing.ApiDeclarationProvider; import com.wordnik.swagger.jaxrs.listing.ApiListingResourceJSON; import com.wordnik.swagger.jaxrs.listing.ResourceListingProvider;@Configuration public class AppConfig {public static final String SERVER_PORT = "server.port";public static final String SERVER_HOST = "server.host";public static final String CONTEXT_PATH = "context.path"; @Bean( destroyMethod = "shutdown" )public SpringBus cxf() {return new SpringBus();}@Bean @DependsOn( "cxf" )public Server jaxRsServer() {JAXRSServerFactoryBean factory = RuntimeDelegate.getInstance().createEndpoint( jaxRsApiApplication(), JAXRSServerFactoryBean.class );factory.setServiceBeans( Arrays.< Object >asList( peopleRestService(), apiListingResourceJson() ) );factory.setAddress( factory.getAddress() );factory.setProviders( Arrays.< Object >asList( jsonProvider(), resourceListingProvider(), apiDeclarationProvider() ) );return factory.create();}@Bean @Autowiredpublic BeanConfig swaggerConfig( Environment environment ) {final BeanConfig config = new BeanConfig();config.setVersion( "1.0.0" );config.setScan( true );config.setResourcePackage( Person.class.getPackage().getName() );config.setBasePath( String.format( "http://%s:%s/%s%s",environment.getProperty( SERVER_HOST ),environment.getProperty( SERVER_PORT ),environment.getProperty( CONTEXT_PATH ),jaxRsServer().getEndpoint().getEndpointInfo().getAddress() ) );return config;}@Beanpublic ApiDeclarationProvider apiDeclarationProvider() {return new ApiDeclarationProvider();}@Beanpublic ApiListingResourceJSON apiListingResourceJson() {return new ApiListingResourceJSON();}@Beanpublic ResourceListingProvider resourceListingProvider() {return new ResourceListingProvider();}@Bean public JaxRsApiApplication jaxRsApiApplication() {return new JaxRsApiApplication();}@Bean public PeopleRestService peopleRestService() {return new PeopleRestService();}// ... }

為了擺脫任何可能的硬編碼配置,所有參數都通過命名屬性( SERVER_PORT , SERVER_HOST和CONTEXT_PATH )傳遞。 Swagger公開了其他REST端點來提供API文檔,在我們的示例中,可以通過以下網址訪問它: http:// localhost:8080 / rest / api / api-docs 。 Swagger UI使用它,它本身已嵌入最終的JAR存檔中,并由Jetty用作靜態(tài)Web資源。

最后一個難題是啟動嵌入式Jetty容器,該容器將所有這些部件粘合在一起并封裝到Starter類中:

package com.example;import org.apache.cxf.transport.servlet.CXFServlet; import org.eclipse.jetty.server.Server; import org.eclipse.jetty.server.handler.HandlerList; import org.eclipse.jetty.servlet.DefaultServlet; import org.eclipse.jetty.servlet.ServletContextHandler; import org.eclipse.jetty.servlet.ServletHolder; import org.eclipse.jetty.util.resource.Resource; import org.springframework.core.io.ClassPathResource; import org.springframework.web.context.ContextLoaderListener; import org.springframework.web.context.support.AnnotationConfigWebApplicationContext;import com.example.config.AppConfig;public class Starter {private static final int SERVER_PORT = 8080;private static final String CONTEXT_PATH = "rest";public static void main( final String[] args ) throws Exception {Resource.setDefaultUseCaches( false );final Server server = new Server( SERVER_PORT ); System.setProperty( AppConfig.SERVER_PORT, Integer.toString( SERVER_PORT ) );System.setProperty( AppConfig.SERVER_HOST, "localhost" );System.setProperty( AppConfig.CONTEXT_PATH, CONTEXT_PATH ); // Configuring Apache CXF servlet and Spring listener final ServletHolder servletHolder = new ServletHolder( new CXFServlet() ); final ServletContextHandler context = new ServletContextHandler(); context.setContextPath( "/" );context.addServlet( servletHolder, "/" + CONTEXT_PATH + "/*" ); context.addEventListener( new ContextLoaderListener() ); context.setInitParameter( "contextClass", AnnotationConfigWebApplicationContext.class.getName() );context.setInitParameter( "contextConfigLocation", AppConfig.class.getName() );// Configuring Swagger as static web resourcefinal ServletHolder swaggerHolder = new ServletHolder( new DefaultServlet() );final ServletContextHandler swagger = new ServletContextHandler();swagger.setContextPath( "/swagger" );swagger.addServlet( swaggerHolder, "/*" );swagger.setResourceBase( new ClassPathResource( "/webapp" ).getURI().toString() );final HandlerList handlers = new HandlerList();handlers.addHandler( context );handlers.addHandler( swagger );server.setHandler( handlers );server.start();server.join(); } }

幾點評論使事情變得更加清晰:我們的JAX-RS服務將在/ rest / *上下文路徑下可用,而Swagger UI在/ swagger上下文路徑下可用。 關于Resource.setDefaultUseCaches(false)的一個重要說明:因為我們正在從JAR文件提供靜態(tài)Web內容,所以必須將此屬性設置為false作為此bug的解決方法。

現在,讓我們通過輸入以下內容來構建并運行我們的JAX-RS應用程序:

mvn clean package java -jar target/jax-rs-2.0-swagger-0.0.1-SNAPSHOT.jar

稍后,您的瀏覽器中將提供Swagger UI , 網址為: http:// localhost:8080 / swagger /

最后一點,關于Swagger還有很多話要說,但是我希望這個簡單的示例能夠顯示出使我們的REST服務具有自文檔化的功能,并且只需很少的工作即可輕松使用。 非常感謝Wordnik團隊。

  • 源代碼可在Github上獲得 。

參考: Swagger:讓開發(fā)人員喜歡在我們的JCG合作伙伴 Andrey Redko {devmind}博客上使用您的REST API 。

翻譯自: https://www.javacodegeeks.com/2013/10/swagger-make-developers-love-working-with-your-rest-api.html

總結

以上是生活随笔為你收集整理的昂首阔步:让开发人员喜欢使用您的REST API的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。