Dubbo Wrapper 原理與實例

Dubbo Wrapper 可以認為是一種反射機制。它既可以讀寫目標實例的字段,也可以調(diào)用目標實例的方法。比如

  • Car是接口;RaceCar是實現(xiàn)類,實現(xiàn)了Car;ferrari和porsche是RaceCar的兩個實例
  • Dubbo為接口Car生成一個Warpper子類,比如Wrapper0;然后創(chuàng)建Wrapper0的實例wrapper0
  • 通過wrapper0#setPropertyValue來修改ferrari的字段,也可以修改porsche的字段
  • 通過wrapper0#invokeMethod來調(diào)用ferrari的方法,也可以調(diào)用porsche的方法
  • 優(yōu)點:通過一個Wrapper0實例就可以操作N個目標接口Car的實例

比如我們有一個Car接口,定義了3個方法:

package org.apache.dubbo.common.bytecode;

public interface Car {
    String getBrand();
    long getWeight();
    void make(String brand, long weight);
}

Wrapper#makeWrapper之后生成的Wrapper子類代碼如下:

package org.apache.dubbo.common.bytecode;

public class Wrapper0 extends Wrapper {
    // 字段名列表
    public static String[] pns;

    // 字段名與字段類型的映射關(guān)系
    public static java.util.Map<String, Class<?>> pts;

    // 方法名列表
    public static String[] mns;

    // 聲明的方法名列表
    public static String[] dmns;

    // 每個public方法的參數(shù)類型
    public static Class[] mts0;
    public static Class[] mts1;
    public static Class[] mts2;

    public String[] getPropertyNames() {
        return pns;
    }

    public boolean hasProperty(String n) {
        return pts.containsKey($1);
    }

    public Class getPropertyType(String n) {
        return (Class) pts.get($1);
    }

    public String[] getMethodNames() {
        return mns;
    }

    public String[] getDeclaredMethodNames() {
        return dmns;
    }

    public void setPropertyValue(Object o, String n, Object v) {
        org.apache.dubbo.common.bytecode.Car w;
        try {
            w = ((org.apache.dubbo.common.bytecode.Car) $1);
        } catch (Throwable e) {
            throw new IllegalArgumentException(e);
        }
        throw new org.apache.dubbo.common.bytecode.NoSuchPropertyException("Not found property \"" + $2 + "\" field or setter method in class org.apache.dubbo.common.bytecode.Car.");
    }

    public Object getPropertyValue(Object o, String n) {
        org.apache.dubbo.common.bytecode.Car w;
        try {
            w = ((org.apache.dubbo.common.bytecode.Car) $1);
        } catch (Throwable e) {
            throw new IllegalArgumentException(e);
        }
        if ($2.equals("brand")) {
            return ($w) w.getBrand();
        }
        if ($2.equals("weight")) {
            return ($w) w.getWeight();
        }
        throw new org.apache.dubbo.common.bytecode.NoSuchPropertyException("Not found property \"" + $2 + "\" field or setter method in class org.apache.dubbo.common.bytecode.Car.");
    }

    public Object invokeMethod(Object o, String n, Class[] p, Object[] v) throws java.lang.reflect.InvocationTargetException {
        org.apache.dubbo.common.bytecode.Car w;
        try {
            w = ((org.apache.dubbo.common.bytecode.Car) $1);
        } catch (Throwable e) {
            throw new IllegalArgumentException(e);
        }
        try {
            if ("make".equals($2) && $3.length == 2) {
                w.make((java.lang.String) $4[0], ((Number) $4[1]).longValue());
                return null;
            }
            if ("getBrand".equals($2) && $3.length == 0) {
                return ($w) w.getBrand();
            }
            if ("getWeight".equals($2) && $3.length == 0) {
                return ($w) w.getWeight();
            }
        } catch (Throwable e) {
            throw new java.lang.reflect.InvocationTargetException(e);
        }
        throw new org.apache.dubbo.common.bytecode.NoSuchMethodException("Not found method \"" + $2 + "\" in class org.apache.dubbo.common.bytecode.Car.");
    }
}

可以認為是重寫了JDK的反射機制。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容