2

Preface

springfox-swagger2@2.9.2 version used by the project

To integrate the swagger document function in Spring, you need to @ApiModel parameter classes with the 061109a42c6374 annotation, but if there are two classes with the same name under two different packages that use the @ApiModel annotation, the document will be overwritten, for example:

  • com.example.demo.login.dto.UserDTO
package com.example.demo.login.dto;

@Data
@ApiModel
public class UserDTO{
  @ApiModelProperty("姓名")
  private String name;
  @ApiModelProperty("年龄")
  private Integer age;
}
  • com.example.demo.vip.dto.UserDTO
package com.example.demo.vip.dto;

@Data
@ApiModel
public class UserDTO{
  @ApiModelProperty("姓名")
  private String name;
  @ApiModelProperty("会员级别")
  private Integer vipLevel;
}

The documents generated by the above two classes will become a swagger model :

As a result, the interface document displays an error:

Conflict resolution

Modify @ApiModel annotation (recommended)

By modifying the value attribute of @ApiModel to avoid conflicts with the same name, after the modification is:

package com.example.demo.login.dto;

@Data
@ApiModel("login$UserDTO")
public class UserDTO{}
package com.example.demo.vip.dto;

@Data
@ApiModel("vip$UserDTO")
public class UserDTO{}

You can see that two swagger model generated:

Modify the class name

Modify the two class names so that the class names do not conflict.

Custom swagger plugin

However, the above method of resolving conflicts is still too cumbersome. It is only necessary to define the entry and exit parameters of a document, and the problem of the same class name should also be considered. This kind of problem of increasing mental burden and workload should be avoided as much as possible. I am thinking about it. It is impossible to add @ApiModel annotations to each class, and all the remaining conflict issues do not need to be considered.

So by tracking the source code, I found the swagger model was generated, see: github

Logical name can be seen that, taking a priority @ApiModel the value value will be used if no defaultTypeName , into a look now, defaultTypeName is direct access class abbreviated, as follows:

It is taken as default class short, resulting in the same name as the class name generated out of different packages swagger model covered.
The reason has been out of the analysis, the next is to see if you can actually customize this super.nameFor(type) method, however unfortunately this is to write dead, no place to start, but ApiModelTypeNameProvider this class two notes @Component and @Order have expressed this It is a Spring bean , and it is Spring plug-in mechanism, so you can customize a plug-in to complete it. By default, the unique swagger model is generated by the complete class path and class name. The code is as follows:

@Component
@Order(SwaggerPluginSupport.SWAGGER_PLUGIN_ORDER - 100)
public class FullPathTypeNameProvider extends DefaultTypeNameProvider {

    public static final String SPLIT_CHAR = "$";

    @Override
    public String nameFor(Class<?> type) {
        ApiModel annotation = AnnotationUtils.findAnnotation(type, ApiModel.class);
        if (annotation == null) {
            return super.nameFor(type);
        }
        if (StringUtils.hasText(annotation.value())) {
            return annotation.value();
        }
        // 如果@ApiModel的value为空,则默认取完整类路径
        int packagePathLength = type.getPackage().getName().length();
        return Stream.of(type.getPackage().getName().split("\\."))
                .map(path -> path.substring(0, 1))
                .collect(Collectors.joining(SPLIT_CHAR))
                + SPLIT_CHAR
                + type.getName().substring(packagePathLength + 1);
    }

}

The effect is as follows:

postscript

Through this small optimization, unnecessary communication costs in many teams can be reduced, allowing us to focus more on business development.

I’m MonkeyWie , welcome to scan the code 👇👇 follow! From time to time, share the knowledge of dry goods such as JAVA , Golang , front end, docker , k8s

wechat


mokeyWie
2.5k 声望643 粉丝

全干工程师~