package tk.antoine_roux.wiki.configuration; import org.springframework.core.annotation.AnnotationUtils; import org.springframework.web.servlet.mvc.condition.*; import org.springframework.web.servlet.mvc.method.RequestMappingInfo; import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping; import tk.antoine_roux.wiki.annotation.ApiPrefix; import tk.antoine_roux.wiki.annotation.ApiVersion; import java.lang.reflect.Method; /** * create custom {@link org.springframework.web.bind.annotation.RequestMapping} Handler to add versioning into uri */ public class ApiVersionRequestMappingHandlerMapping extends RequestMappingHandlerMapping { private final String versionPrefix; /** * create @{@link org.springframework.web.bind.annotation.RequestMapping} handler classe * this class add some prefix to uri * * @param versionPrefix */ public ApiVersionRequestMappingHandlerMapping(String versionPrefix) { this.versionPrefix = versionPrefix; } @Override protected RequestMappingInfo getMappingForMethod(Method method, Class handlerType) { RequestMappingInfo info = super.getMappingForMethod(method, handlerType); if (info == null) { return null; } ApiVersion methodAnnotation = AnnotationUtils.findAnnotation(method, ApiVersion.class); if (methodAnnotation != null) { RequestCondition methodCondition = this.getCustomMethodCondition(method); // Concatenate our ApiVersion with the usual request mapping info = this.createApiVersionInfo(methodAnnotation, methodCondition).combine(info); } else { ApiVersion typeAnnotation = AnnotationUtils.findAnnotation(handlerType, ApiVersion.class); if (typeAnnotation != null) { RequestCondition typeCondition = this.getCustomTypeCondition(handlerType); // Concatenate our ApiVersion with the usual request mapping info = this.createApiVersionInfo(typeAnnotation, typeCondition).combine(info); } } ApiPrefix annotationApiPrefix = AnnotationUtils.findAnnotation(handlerType, ApiPrefix.class); if (annotationApiPrefix != null) { RequestMappingInfo requestMappingInfo = new RequestMappingInfo( new PatternsRequestCondition( new String[]{annotationApiPrefix.value()}, false, this.getPathMatcher() ), new RequestMethodsRequestCondition(), new ParamsRequestCondition(), new HeadersRequestCondition(), new ConsumesRequestCondition(), new ProducesRequestCondition(), null); info = requestMappingInfo.combine(info); } return info; } private RequestMappingInfo createApiVersionInfo(ApiVersion annotation, RequestCondition customCondition) { String[] values = annotation.value(); String[] patterns = new String[values.length]; for (int i = 0; i < values.length; i++) { // Build the URL prefix patterns[i] = this.versionPrefix + values[i]; } return new RequestMappingInfo( new PatternsRequestCondition(patterns, false, this.getPathMatcher()), new RequestMethodsRequestCondition(), new ParamsRequestCondition(), new HeadersRequestCondition(), new ConsumesRequestCondition(), new ProducesRequestCondition(), customCondition); } }