• 使用ABAP的RTTI和Java反射机制访问static private属性


    In ABAP we can define a static attribute for a class via keyword CLASS-DATA, whose validity is not associated with instances of a class but with the class itself. In order to prove this fact I use the following simple Pointer class for demonstration:

    class ZCL_POINT definition
      public
      final
      create public .
    public section.
      data X type I .
      methods CONSTRUCTOR
        importing
          !IV_X type I
          !IV_Y type I .
    private section.
      data Y type I .
      class-data COUNT type I .
    ENDCLASS.
    CLASS ZCL_POINT IMPLEMENTATION.
      method CONSTRUCTOR.
        me->x = iv_x.
        me->y = iv_y.
        count = count + 1.
      endmethod.
    ENDCLASS.
    

    In this class, static attribute count is responsible to maintain the number of created Point instances.
    Then create four point instances:

    data(a) = new zcl_point( iv_x = 1 iv_y = 1 ).
    data(b) = new zcl_point( iv_x = 1 iv_y = 2 ).
    data(c) = new zcl_point( iv_x = 1 iv_y = 3 ).
    data(d) = new zcl_point( iv_x = 1 iv_y = 4 ).
    

    Via any variable of a, b, c or d, we can monitor the value of count in debugger.

    Can we access the static attribute of a class without object instance in debugger?

    Since in theory the static attribute belongs to class instead of any dedicated object instance, so question comes: is there approach to monitor the static attribute value in ABAP debugger directly from class instead? Yes it is possible.

    (1) type text “{C:ZCL_POINT} in debugger and press enter key

    (2) double click, and you can see the attribute value is directly maintained in class ZCL_POINT, without any object instance created on top of it.

    And I try to change its visibility dynamically via class descriptor via the following code and actually it is not possible:

    data(lo) = CAST cl_abap_objectdescr( cl_abap_classdescr=>describe_by_name( 'ZCL_POINT' ) ).
    
    read TABLE lo->attributes ASSIGNING FIELD-SYMBOL(<count>) WITH KEY name = 'COUNT'.
    CHECK SY-SUBRC = 0.
    <count>-visibility = 'U'.
    

    Since the structure is read-only and not editable outside cl_abap_objectdescr.


    This makes sense otherwise the encapsulation will be violated. Just check many other attribute marked as read-only in Class/Object descriptor class.

    Reflection in Java

    Check the following code which demonstrates how to access private static attribute value in code via Reflection.

    import java.lang.reflect.Field;
    
    public class Point {
    	private int x;
    	private int y;
    	static private int count = 0;
    	public Point(int x, int y){
    		this.x = x;
    		this.y = y;
    		count++;
    	}
    	private static void accessStaticPrivate(Point point){
    		Class classObject = point.getClass();
    		try {
    			Field countField = classObject.getDeclaredField("count");
    			System.out.println("count: " + countField.get(point));
    		} catch (NoSuchFieldException | SecurityException | IllegalArgumentException
    				| IllegalAccessException e1 ) {
    			e1.printStackTrace();
    		} 
    	}
    	public static void main(String[] arg){
    		Point a = new Point(1,2);
    		accessStaticPrivate(a);
    		
    		Point b = new Point(1,3);
    		accessStaticPrivate(b);
    		
    		Point c = new Point(1,4);
    		accessStaticPrivate(c);
    		
    		Point d = new Point(1,5);
    		accessStaticPrivate(d);
    	}
    }
    

    For ABAPer it is easy to understand the usage of Class object in Java by just comparing it with CL_ABAP_CLASSDESCR in ABAP.
    When running this small program locally, you will get output in console:

    count: 1
    count: 2
    count: 3
    count: 4
    

    Unlike RTTI in ABAP, Java reflection can sometimes lead to security issues, see one example how Java Singleton would be bypassed in blog Singleton bypass – ABAP and Java.

    要获取更多Jerry的原创文章,请关注公众号"汪子熙":

  • 相关阅读:
    2015年10月28日 json深切感受
    2015年10月27日 json数据小谈
    2015年10月26日 插件的使用
    2015/10/25 用bootstrap selectpicker实现带模糊查询的下拉列表
    2015年10月24号 哇,原来这JSP页面还可以用这东西!
    2015年10月23日 关于spring mvc的初认识
    2015年10月22日 杂感
    2015/10/21 http请求数据处理后显示
    2015/10/19总结:ajax传参、jquery.validate自定义日期校验
    记录一下----关于设计模式和面向对象设计原则
  • 原文地址:https://www.cnblogs.com/sap-jerry/p/13548895.html
Copyright © 2020-2023  润新知