zoukankan      html  css  js  c++  java
  • springboot~mockMvc和asciidoctor生成基于TDD的API文档

    API文档是前端与后端快速开发,减少沟通成本的必要条件,有一份完善的文档是很必要的,由通过测试来生成文档的好处就是:测试数据有了,测试返回结果有了,而且可以对这些字段进行说明,很清晰,在springboot框架里,去使用mockMvc文档生成时,需要有以下几个步骤,大叔总结了一下,分享给大家。

    一 mockMvc包引用

    testCompile('org.springframework.restdocs:spring-restdocs-mockmvc')
    asciidoctor 'org.springframework.restdocs:spring-restdocs-asciidoctor'

    二 snippetsDir插件引用

    在buildscript块里添加如下代码

    maven {
    url "https://plugins.gradle.org/m2/"
    }
    mavenCentral()
    dependencies {
    classpath "org.asciidoctor:asciidoctor-gradle-jvm:2.0.0-rc.1"

    }

     添加插件

    apply plugin: "org.asciidoctor.convert"

    三 配置三大路径的地址,三大路径指,asciidoctor文档路径,生成的API文档目录和snippets目录

    jar {
        dependsOn asciidoctor
        from ("${asciidoctor.outputDir}/html5") {
            into 'static/docs'
        }
    }
    
    ext {
        snippetsDir = file('build/generated-snippets')
    }
    
    
    integTest {
        outputs.dir snippetsDir
    }
    
    asciidoctor {
    inputs.dir snippetsDir outputDir "build/asciidoc" dependsOn integTest sourceDir 'src/docs/asciidoc' }

    四 添加API接口

    @RestController
    public class DocController {
      public static final String DOC = "/doc/{name}";
      public static final String DOC_LIST = "/doc/list";
    
      @GetMapping(DOC)
      public Map<String, String> index(@PathVariable String name) {
        Map<String, String> maps = new HashMap<>();
        maps.put("name", "Hello");
        maps.put("sex", "1");
        maps.put("buyer", name);
        return maps;
      }
    }

    五 添加测试用例

    package test.lind.javaLindDay;
    
    import static org.hamcrest.Matchers.containsString;
    import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.document;
    import static org.springframework.restdocs.mockmvc.RestDocumentationRequestBuilders.get;
    import static org.springframework.restdocs.operation.preprocess.Preprocessors.prettyPrint;
    import static org.springframework.restdocs.payload.PayloadDocumentation.fieldWithPath;
    import static org.springframework.restdocs.payload.PayloadDocumentation.relaxedRequestFields;
    import static org.springframework.restdocs.payload.PayloadDocumentation.relaxedResponseFields;
    import static org.springframework.restdocs.request.RequestDocumentation.parameterWithName;
    import static org.springframework.restdocs.request.RequestDocumentation.pathParameters;
    import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
    import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content;
    import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
    
    import org.junit.Before;
    import org.junit.Rule;
    import org.junit.Test;
    import org.junit.runner.RunWith;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.boot.test.context.SpringBootTest;
    import org.springframework.restdocs.JUnitRestDocumentation;
    import org.springframework.restdocs.mockmvc.MockMvcRestDocumentation;
    import org.springframework.restdocs.payload.RequestFieldsSnippet;
    import org.springframework.restdocs.payload.ResponseFieldsSnippet;
    import org.springframework.restdocs.request.PathParametersSnippet;
    import org.springframework.test.context.ActiveProfiles;
    import org.springframework.test.context.junit4.SpringRunner;
    import org.springframework.test.web.servlet.MockMvc;
    import org.springframework.test.web.servlet.setup.MockMvcBuilders;
    import org.springframework.web.context.WebApplicationContext;
    import test.lind.javaLindDay.controller.DocController;
    
    @SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
    @ActiveProfiles("integTest")//指定profile环境
    @RunWith(SpringRunner.class)
    public class MockMvcTest {
      static final ResponseFieldsSnippet orderResponseFieldsParameters = relaxedResponseFields(
          fieldWithPath("name").description("账号"),
          fieldWithPath("buyer").description("购买者"),
          fieldWithPath("sex").description("性别")
      );
      static final RequestFieldsSnippet orderRequestFieldsParameters = relaxedRequestFields(
          fieldWithPath("code").description("凭证号"),
          fieldWithPath("word").description("凭证字"),
          fieldWithPath("batch").description("批次")
      );
      static final PathParametersSnippet orderRequestPathParameters = pathParameters(
          parameterWithName("name").description("购买者")
      );
    
      @Rule
      public JUnitRestDocumentation restDocumentation = new JUnitRestDocumentation();
    
      protected MockMvc mockMvc;
    
      @Autowired
      private WebApplicationContext context;
    
      @Before
      public void setUp() {
        this.mockMvc = MockMvcBuilders.webAppContextSetup(this.context)
            .apply(MockMvcRestDocumentation.documentationConfiguration(restDocumentation)
                .uris().withScheme("http").withHost("localhost").withPort(8080)
                .and()
                .operationPreprocessors().withResponseDefaults(prettyPrint()))
            .build();
      }
    
    
      @Test
      public void get_orders() throws Exception {
        this.mockMvc.perform(
            get(DocController.DOC, "zzl"))
            .andDo(print())
            .andExpect(status().isOk())
            .andExpect(content().string(containsString("Hello")))
            .andDo(document("doc-index", orderRequestPathParameters, orderResponseFieldsParameters));
      }
    
      @Test
      public void get_list() throws Exception {
        this.mockMvc.perform(
            get(DocController.DOC_LIST))
            .andDo(print())
            .andExpect(status().isOk())
            .andDo(document("doc-list", orderResponseFieldsParameters));
      }
    }

    这里有个需要注意的地址,get静态方法的包应该是import static org.springframework.restdocs.mockmvc.RestDocumentationRequestBuilders.get;否则会有找不到路由的

    错误,这点困扰了我很久。

    六 编译,打包,它会同时去下载API DOC所需要的文件

    gradle build

    最后,进入build/asciidoc/html5目录,浏览我们的API说明文件即可。

      

    感谢各位的阅读!

     

  • 相关阅读:
    10 个深恶痛绝的 Java 异常。。
    为什么公司宁愿 25K 重新招人,也不给你加到 20K?原因太现实……
    推荐一款代码神器,代码量至少省一半!
    Spring Cloud Greenwich 正式发布,Hystrix 即将寿终正寝。。
    hdu 3853 LOOPS(概率 dp 期望)
    hdu 5245 Joyful(期望的计算,好题)
    hdu 4336 Card Collector(期望 dp 状态压缩)
    hdu 4405 Aeroplane chess(概率+dp)
    hdu 5036 Explosion(概率期望+bitset)
    hdu 5033 Building (单调栈 或 暴力枚举 )
  • 原文地址:https://www.cnblogs.com/lori/p/9184579.html
Copyright © 2011-2022 走看看