001package io.ebean.enhance.querybean;
002
003import io.ebean.enhance.asm.ClassVisitor;
004import io.ebean.enhance.asm.Label;
005import io.ebean.enhance.asm.Opcodes;
006import io.ebean.enhance.asm.Type;
007
008/**
009 * Changes the existing constructor to remove all the field initialisation as these are going to be
010 * initialised lazily by calls to our generated methods.
011 */
012public class TypeQueryConstructorAdapter extends BaseConstructorAdapter implements Opcodes, Constants {
013
014  private final ClassInfo classInfo;
015
016  private final String domainClass;
017
018  private final ClassVisitor cv;
019
020  private final String desc;
021
022  private final String signature;
023
024  /**
025   * Construct for a query bean class given its associated entity bean domain class and a class visitor.
026   */
027  public TypeQueryConstructorAdapter(ClassInfo classInfo, String domainClass, ClassVisitor cv, String desc, String signature) {
028    super();
029    this.cv = cv;
030    this.classInfo = classInfo;
031    this.domainClass = domainClass;
032    this.desc = desc;
033    this.signature = signature;
034  }
035
036  @Override
037  public void visitCode() {
038
039    boolean withEbeanServer = WITH_EBEANSERVER_ARGUMENT.equals(desc);
040
041    mv = cv.visitMethod(ACC_PUBLIC, "<init>", desc, signature, null);
042    mv.visitCode();
043    Label l0 = new Label();
044    mv.visitLabel(l0);
045    mv.visitLineNumber(1, l0);
046    mv.visitVarInsn(ALOAD, 0);
047    mv.visitLdcInsn(Type.getType("L" + domainClass + ";"));
048    if (withEbeanServer) {
049      mv.visitVarInsn(ALOAD, 1);
050      mv.visitMethodInsn(INVOKESPECIAL, TQ_ROOT_BEAN, "<init>", "(Ljava/lang/Class;Lio/ebean/EbeanServer;)V", false);
051    } else {
052      mv.visitMethodInsn(INVOKESPECIAL, TQ_ROOT_BEAN, "<init>", "(Ljava/lang/Class;)V", false);
053    }
054
055    Label l1 = new Label();
056    mv.visitLabel(l1);
057    mv.visitLineNumber(2, l1);
058    mv.visitVarInsn(ALOAD, 0);
059    mv.visitVarInsn(ALOAD, 0);
060    mv.visitMethodInsn(INVOKEVIRTUAL, classInfo.getClassName(), "setRoot", "(Ljava/lang/Object;)V", false);
061    Label l2 = new Label();
062    mv.visitLabel(l2);
063    mv.visitLineNumber(3, l2);
064    mv.visitInsn(RETURN);
065    Label l3 = new Label();
066    mv.visitLabel(l3);
067    mv.visitLocalVariable("this", "L" + classInfo.getClassName() + ";", null, l0, l3, 0);
068    if (withEbeanServer) {
069      mv.visitLocalVariable("server", "Lio/ebean/EbeanServer;", null, l0, l3, 1);
070      mv.visitMaxs(3, 2);
071    } else {
072      mv.visitMaxs(2, 1);
073    }
074    mv.visitEnd();
075  }
076
077}