All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.ebean.enhance.querybean.FieldInfo Maven / Gradle / Ivy

package io.ebean.enhance.querybean;

import io.ebean.enhance.asm.ClassVisitor;
import io.ebean.enhance.asm.Label;
import io.ebean.enhance.asm.MethodVisitor;
import io.ebean.enhance.asm.Opcodes;
import io.ebean.enhance.asm.Type;

/**
 * Field information.
 */
public class FieldInfo implements Opcodes, Constants {

  private final ClassInfo classInfo;
  private final String name;
  private final String desc;
  private final String internalName;
  private final String signature;

  public FieldInfo(ClassInfo classInfo, String name, String desc, String signature) {
    this.classInfo = classInfo;
    this.name = name;
    this.desc = desc;
    this.internalName = Type.getType(desc).getInternalName();
    this.signature = signature;
  }

  public String toString() {
    return "name:" + name + " desc:" + desc + " sig:" + signature;
  }

  /**
   * Add the 'property access method' that callers should use (instead of get field).
   */
  public void writeMethod(ClassVisitor cw, boolean typeQueryRootBean) {

    // simple why to determine the property is an associated bean type
    boolean assocProperty = desc.contains("/QAssoc");

    if (classInfo.isLog(4)) {
      classInfo.log(" ... add method _" + name + " assocProperty:" + assocProperty + " rootBean:" + typeQueryRootBean);
    }

    MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, "_"+name, "()"+desc, "()"+signature, null);
    mv.visitCode();
    Label l0 = new Label();
    mv.visitLabel(l0);
    mv.visitLineNumber(1, l0);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), name, desc);
    Label l1 = new Label();
    mv.visitJumpInsn(IFNONNULL, l1);
    Label l2 = new Label();
    mv.visitLabel(l2);
    mv.visitLineNumber(2, l2);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitTypeInsn(NEW, internalName);
    mv.visitInsn(DUP);
    mv.visitLdcInsn(name);
    mv.visitVarInsn(ALOAD, 0);

    if (assocProperty) {
      if (typeQueryRootBean) {
        mv.visitInsn(ICONST_1);
        mv.visitMethodInsn(INVOKESPECIAL, internalName, "", "(Ljava/lang/String;Ljava/lang/Object;I)V", false);
      } else {
        mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), FIELD_ROOT, "Ljava/lang/Object;");
        mv.visitVarInsn(ALOAD, 0);
        mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), FIELD_PATH, "Ljava/lang/String;");
        mv.visitInsn(ICONST_1);
        mv.visitMethodInsn(INVOKESPECIAL, internalName, "", "(Ljava/lang/String;Ljava/lang/Object;Ljava/lang/String;I)V", false);
      }

    } else {
      if (typeQueryRootBean) {
        mv.visitMethodInsn(INVOKESPECIAL, internalName, "", "(Ljava/lang/String;Ljava/lang/Object;)V", false);
      } else {
        mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), FIELD_ROOT, "Ljava/lang/Object;");
        mv.visitVarInsn(ALOAD, 0);
        mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), FIELD_PATH, "Ljava/lang/String;");
        mv.visitMethodInsn(INVOKESPECIAL, internalName, "", "(Ljava/lang/String;Ljava/lang/Object;Ljava/lang/String;)V", false);
      }
    }

    mv.visitFieldInsn(PUTFIELD, classInfo.getClassName(), name, desc);
    mv.visitLabel(l1);
    mv.visitLineNumber(3, l1);
    mv.visitFrame(Opcodes.F_SAME, 0, null, 0, null);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitFieldInsn(GETFIELD, classInfo.getClassName(), name, desc);
    mv.visitInsn(ARETURN);
    Label l3 = new Label();
    mv.visitLabel(l3);
    mv.visitLocalVariable("this", "L" + classInfo.getClassName() + ";", null, l0, l3, 0);
    if (assocProperty) {
      if (typeQueryRootBean) {
        mv.visitMaxs(6, 1);
      } else {
        mv.visitMaxs(7, 1);
      }
    } else {
      if (typeQueryRootBean) {
        mv.visitMaxs(5, 1);
      } else {
        mv.visitMaxs(6, 1);
      }
    }
    mv.visitEnd();
  }

  /**
   * Initialise the field (used by 'Alias' constructor).
   */
  public void writeFieldInit(MethodVisitor mv) {
    Label l10 = new Label();
    mv.visitLabel(l10);
    mv.visitLineNumber(3, l10);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitTypeInsn(NEW, internalName);
    mv.visitInsn(DUP);
    mv.visitLdcInsn(name);
    mv.visitVarInsn(ALOAD, 0);
    mv.visitMethodInsn(INVOKESPECIAL, internalName, "", "(Ljava/lang/String;Ljava/lang/Object;)V", false);
    mv.visitFieldInsn(PUTFIELD, classInfo.getClassName(), name, desc);
  }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy