Spring 中參數名稱解析 - ParameterNameDiscoverer

Spring 中參數名稱解析 - ParameterNameDiscoverer

Spring 系列目錄(http://www.javashuo.com/article/p-kqecupyl-bm.html)html

JDK 1.8 以後引入 Parameter 類,能夠經過它獲取方法中參數的名稱。Spring 中也增長了對它的支持 ParameterNameDiscoverer,特別是在 Spring MVC 中大量使用。java

1、ParameterNameDiscoverer 使用

@Test
public void testStandardReflectionParameterNameDiscoverer() {
    ParameterNameDiscoverer discoverer = new StandardReflectionParameterNameDiscoverer();
    // discoverer = new LocalVariableTableParameterNameDiscoverer();
    // discoverer = new DefaultParameterNameDiscoverer();

    Method method = ReflectionUtils.findMethod(InnerClass.class, "method", List.class);
    String[] actualParams = discoverer.getParameterNames(method);
    assertThat(actualParams, is(new String[]{"users"}));
}

public class InnerClass {
    public void method(@PathVariable("username") @RequestBody final List<Map<String, List<Integer>>> users) {
    }
}

2、ParameterNameDiscoverer 源碼分析

Spring 中經過 ParameterNameDiscoverer 獲取方法中參數的名稱,它有有兩個幾個默認的實現。其中:spring

  • PrioritizedParameterNameDiscoverer 用來管理 Spring 中註冊的全部的 ParameterNameDiscoverer 解析器,內部維護了一個 List 集合,只要有解析參數名稱成功的就返回,從而保證了優先級順序。其子類 DefaultParameterNameDiscoverer 默認往這個集合中註冊了 KotlinReflectionParameterNameDiscoverer、StandardReflectionParameterNameDiscoverer、LocalVariableTableParameterNameDiscoverer 三個解析器。源碼分析

  • StandardReflectionParameterNameDiscoverer 使用 JDK 的 Parameter 解析參數名稱,關於 JDK 中參數解析見 <>。code

  • LocalVariableTableParameterNameDiscoverer 使用 ASM 類庫解析參數名稱。htm

ParameterNameDiscoverer 接口以下,用於解析構造器和方法中的參數名稱:blog

public interface ParameterNameDiscoverer {
    String[] getParameterNames(Method method);
    String[] getParameterNames(Constructor<?> ctor);
}

2.1 StandardReflectionParameterNameDiscoverer

public class StandardReflectionParameterNameDiscoverer implements ParameterNameDiscoverer {
    public String[] getParameterNames(Method method) {
        return getParameterNames(method.getParameters());
    }
    public String[] getParameterNames(Constructor<?> ctor) {
        return getParameterNames(ctor.getParameters());
    }

    // 使用 JDK 自帶的 Parameter 解析參數名稱
    private String[] getParameterNames(Parameter[] parameters) {
        String[] parameterNames = new String[parameters.length];
        for (int i = 0; i < parameters.length; i++) {
            Parameter param = parameters[i];
            if (!param.isNamePresent()) {
                return null;
            }
            parameterNames[i] = param.getName();
        }
        return parameterNames;
    }
}

天天用心記錄一點點。內容也許不重要,但習慣很重要!接口

相關文章
相關標籤/搜索