`
yixietianxia
  • 浏览: 13736 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论
阅读更多

        最近在公司发现了一个非常繁琐的事情(后台采用微服务架构开发):后台提供Rest接口的模块实在太多,每天多要有专门的人员去统计今天对应Rest接口有哪些变更,每次都要花费大量的时间,而且有时候发现统计的还跟实际不统一(统计人员还是非常发心思在做这个事情)!另外,前端开发人员一直等待后端开发人员给接口,每次后端人员都说接口快OK了,但是前端开发人员一点信息也查看不到,导致前端人员心里对进度把握很虚。

 

        为了解决这一困局,今天学习了一下互联网主流的解决方案:采用Swagger进行线上沟通。这的确是一种非常不错的方式!它把我们碰到的问题全全解决了,为做这套开源项目的人员点个赞!另外只要接口发生变更直接通过线上就可以看到,降低了人员之间的沟通成本。

 

       一、改造swagger源码(基于1.5.8版本)

       本身swagger还不支持Dubbox,因此需要我们对它进行扩展。稍微看一下swagger的源码发现,这种改造非常简单,只要把Swagger返回的Response对象通过dubbox的Rest接口暴露出来即可。大家只要关注抽象类BaseApiListingResource,它里面有getListingJsonResponse()和getListingYamlResponse()方法,核心返回给前端的数据就是这两个访问透露出来的。前面有说到这个方法是抽象方法,想必就是提供我们去继承了。于是乎定义Rest接口吧:

DubboxSwaggerService.java 
@Path("dubboxswagger")
@Consumes({MediaType.APPLICATION_JSON, MediaType.TEXT_XML})
@Produces({MediaType.APPLICATION_JSON + "; " + "charset=UTF-8", MediaType.TEXT_XML + "; " + "charset=UTF-8"})
public interface DubboxSwaggerService {
	
	 	@GET
	 	@Path("swagger")
	    public Response getListingJson(@Context Application app,
	            @Context ServletConfig sc,@Context HttpHeaders headers,
	            @Context UriInfo uriInfo);
}

 

定义好了接口,我们再写它的实现吧:

DubboxAcceptHeaderApiListingResource.java
@Service
public class DubboxAcceptHeaderApiListingResource extends BaseApiListingResource implements DubboxSwaggerService {
	
	@Context
    ServletContext context;

	@Override
	public Response getListingJson(Application app, ServletConfig sc,
			HttpHeaders headers, UriInfo uriInfo) {
		// TODO Auto-generated method stub
		
		Response rsp = getListingJsonResponse(app, context, sc, headers, uriInfo);

		return rsp;
	}
}

 

 到这里还不是完美的方案,我们要的是一个集中Rest查询中心!每个模块的访问地址都不同,前端JS请求就会涉及跨域问题。一般会报如下错误:Can't read from server. It may not have the appropriate access-control-origin settings。 怎么处理?只要加一段小代码即可解决。把getListingJsonResponse()代码修改一下即可(yaml一样):

 

rsp.header("Access-Control-Allow-Origin", "*");
rsp.header("Access-Control-Allow-Headers","x-requested-with, ssi-token");
rsp.header("Access-Control-Max-Age", "3600");
rsp.header("Access-Control-Allow-Methods","GET,POST,PUT,DELETE,OPTIONS");

 

OK!这样Swagger的修改完成了,打包上传你的私库吧。

 

       二、在dubbox后台开发中使用

       后台使用就只要把需要显示的Rest接口加入注解@api,@ApiOperation,然后配置对应bean即可使用,具体如下:

       1)引入jar包:

		<dependency>
			<groupId>io.swagger</groupId>
			<artifactId>swagger-core</artifactId>
			<version>你的版本号</version>
		</dependency>
		<dependency>
			<groupId>io.swagger</groupId>
			<artifactId>swagger-jaxrs</artifactId>
			<version>你的版本号</version>
		</dependency>
		<dependency>
			<groupId>io.swagger</groupId>
			<artifactId>swagger-jersey-jaxrs</artifactId>
			<version>你的版本号</version>
		</dependency>
		<dependency>
			<groupId>io.swagger</groupId>
			<artifactId>swagger-jersey2-jaxrs</artifactId>
			<version>你的版本号</version>
		</dependency>
		<dependency>
			<groupId>org.reflections</groupId>
			<artifactId>reflections</artifactId>
			<version>0.9.10</version>
		</dependency>

 

       2)在spring的配置文件里加入:

    <bean id="swaggerService" class="io.swagger.jaxrs.listing.DubboxAcceptHeaderApiListingResource" />
    <bean id="beanConfig" class="io.swagger.jaxrs.config.BeanConfig">
        <property name="schemes" value="http" />
        <!-- com.abc.aa这个值不能写成com.abc.aa.*-->
        <property name="resourcePackage" value="com.abc.aa"/>
        <property name="version" value="1.0"/>
        <property name="host" value="10.10.10.23:8888"/>
        <property name="basePath" value="/test"/>
        <property name="title" value="这个是标题啊"/>
        <property name="description" value="这里是描述呢"/>
        <property name="contact" value="abc"/>
        <property name="license" value="Apache 2.0"/>
        <property name="licenseUrl" value="http://www.apache.org/licenses/LICENSE-2.0.html"/>
        <property name="scan" value="true"/>
    </bean>
    <dubbo:service interface="io.swagger.jaxrs.listing.DubboxSwaggerService" ref="swaggerService"/>

      3)对应的接口加入注解。如:

@Path("abc")
@Consumes({MediaType.APPLICATION_JSON, MediaType.TEXT_XML})
@Produces({MediaType.APPLICATION_JSON + "; " + MediaType.CHARSET_PARAMETER + "=UTF-8", MediaType.TEXT_XML + "; " + MediaType.CHARSET_PARAMETER + "=UTF-8"})
@Api("Demo-api")
public interface DemoRestService {

	@GET
    @Path("{id : \\d+}")
	@ApiOperation(value="通过主键获取用户信息")
    Demo getDemo(@PathParam("id") @Min(1) Integer id);
}

 

 恭喜你!要进行的操作完成了。在浏览器输入:http://10.10.10.23:8888/test/dubboxswagger/swagger.json即可看到结果.

 

注意:这里配置的端口号要跟dubbox配置的Rest端口一致。

 

 

 

 

 

 

 

 

 

分享到:
评论
3 楼 lovejavaevil 2017-08-31  
protected Response getListingJsonResponse(
            Application app,
            ServletContext servletContext,
            ServletConfig servletConfig,
            HttpHeaders headers,
            UriInfo uriInfo) {
        Swagger swagger = process(app, servletContext, servletConfig, headers, uriInfo);

        if (swagger != null) {
            ObjectMapper mapper = new ObjectMapper();
            ResponseBuilder rsp = null;
            try {
                mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
                rsp = Response.ok().entity(mapper.writeValueAsString(swagger));
            } catch (JsonProcessingException e) {
                e.printStackTrace();
            }

        rsp.header("Access-Control-Allow-Origin", "*");
        rsp.header("Access-Control-Allow-Headers","x-requested-with, ssi-token");
        rsp.header("Access-Control-Max-Age", "3600");
        rsp.header("Access-Control-Allow-Methods","GET,POST,PUT,DELETE,OPTIONS");
            return rsp.build();
        } else {
            return Response.status(404).build();
        }
    }
2 楼 lovejavaevil 2017-08-31  
1、报js错误。2、接口重复显示,因为get,put,post,path,delete,options都显示出来,这个是由于生成的json中很多null字符串,我进行了修改
1 楼 lovejavaevil 2017-08-31  
首先感谢前辈提供的swagger-core-1.5.8.zip包,但默认直接匹配swagger-ui存在两个问题

相关推荐

Global site tag (gtag.js) - Google Analytics