コード例 #1
0
  private static void replaceImplementation(CtMethod m, String src) throws Exception {
    removeNativeModifier(m);

    if (src == null || src.trim().length() == 0) {
      m.setBody(null);
    } else {
      src = src.trim();
      if (!src.startsWith("{")) {
        if (!m.getReturnType().equals(CtClass.voidType) && !src.startsWith("return")) {
          src = "{ return ($r)($w) " + src;
        } else {
          src = "{ " + src;
        }
      }

      if (!src.endsWith("}")) {
        if (!src.endsWith(";")) {
          src = src + "; }";
        } else {
          src = src + " }";
        }
      }
      try {
        m.setBody(src);
      } catch (CannotCompileException e) {
        throw new RuntimeException("Unable to compile body " + src, e);
      }
    }
  }
コード例 #2
0
  private static void populateMetricsAndOperations(
      List<Class<?>> classes, Props props, boolean withNamePrefix) throws Exception {
    props.setHasOperations(true);
    props.setHasMetrics(true);
    for (Class<?> clazz : classes) {
      MBean mbean = clazz.getAnnotation(MBean.class);
      String prefix = withNamePrefix ? mbean.objectName() + '.' : "";
      CtClass ctClass = classPool.get(clazz.getName());

      CtMethod[] ctMethods = ctClass.getMethods();
      for (CtMethod ctMethod : ctMethods) {
        ManagedAttribute managedAttr =
            (ManagedAttribute) ctMethod.getAnnotation(ManagedAttribute.class);
        ManagedOperation managedOp =
            (ManagedOperation) ctMethod.getAnnotation(ManagedOperation.class);

        Metric rhqMetric = (Metric) ctMethod.getAnnotation(Metric.class);
        if (rhqMetric != null) {
          debug("Metric annotation found " + rhqMetric);
          // Property and description resolution are the reason why annotation scanning is done
          // here.
          // These two fields are calculated from either the method name or the Managed*
          // annotations,
          // and so, only the infinispan side knows about that.
          String property = prefix + getPropertyFromBeanConvention(ctMethod);
          if (!rhqMetric.property().isEmpty()) {
            property = prefix + rhqMetric.property();
          }
          MetricProps metric = new MetricProps(property);
          String displayName =
              withNamePrefix
                  ? "[" + mbean.objectName() + "] " + rhqMetric.displayName()
                  : rhqMetric.displayName();
          metric.setDisplayName(displayName);
          metric.setDisplayType(rhqMetric.displayType());
          metric.setDataType(rhqMetric.dataType());
          metric.setUnits(rhqMetric.units());
          if (managedAttr != null) {
            debug("Metric has ManagedAttribute annotation " + managedAttr);
            metric.setDescription(managedAttr.description());
          } else if (managedOp != null) {
            debug("Metric has ManagedOperation annotation " + managedOp);
            metric.setDescription(managedOp.description());
          } else {
            log.debug(
                "Metric has no managed annotations, so take the description from the display name.");
            metric.setDescription(rhqMetric.displayName());
          }
          props.getMetrics().add(metric);
        }

        Operation rhqOperation = (Operation) ctMethod.getAnnotation(Operation.class);
        if (rhqOperation != null) {
          debug("Operation annotation found " + rhqOperation);
          String name;
          if (!rhqOperation.name().isEmpty()) {
            name = prefix + rhqOperation.name();
          } else {
            name = prefix + ctMethod.getName();
          }
          OperationProps operation = new OperationProps(name);
          String displayName =
              withNamePrefix
                  ? "[" + mbean.objectName() + "] " + rhqOperation.displayName()
                  : rhqOperation.displayName();
          operation.setDisplayName(displayName);
          if (managedAttr != null) {
            debug("Operation has ManagedAttribute annotation " + managedAttr);
            operation.setDescription(managedAttr.description());
          } else if (managedOp != null) {
            debug("Operation has ManagedOperation annotation " + managedOp);
            operation.setDescription(managedOp.description());
          } else {
            debug(
                "Operation has no managed annotations, so take the description from the display name.");
            operation.setDescription(rhqOperation.displayName());
          }

          Object[][] paramAnnotations = ctMethod.getParameterAnnotations();
          int i = 0;
          for (Object[] paramAnnotationsInEach : paramAnnotations) {
            boolean hadParameter = false;
            for (Object annot : paramAnnotationsInEach) {
              debug("Parameter annotation " + annot);
              if (annot instanceof Parameter) {
                Parameter param = (Parameter) annot;
                SimpleProperty prop = new SimpleProperty(param.name());
                prop.setDescription(param.description());
                operation.getParams().add(prop);
                hadParameter = true;
              }
            }
            if (!hadParameter) {
              operation.getParams().add(new SimpleProperty("p" + i++));
            }
          }
          CtClass returnType = ctMethod.getReturnType();
          if (!returnType.equals(CtClass.voidType)) {
            if (!returnType.equals(Void.TYPE)) {
              SimpleProperty prop = new SimpleProperty("operationResult");
              operation.setResult(prop);
            }
          }
          props.getOperations().add(operation);
        }
      }

      CtField[] ctFields = ctClass.getDeclaredFields();
      for (CtField ctField : ctFields) {
        debug("Inspecting field " + ctField);

        Metric rhqMetric = (Metric) ctField.getAnnotation(Metric.class);
        if (rhqMetric != null) {
          debug("Field " + ctField + " contains Metric annotation " + rhqMetric);
          String property;
          if (!rhqMetric.property().isEmpty()) {
            property = prefix + rhqMetric.property();
          } else {
            property = prefix + getPropertyFromBeanConvention(ctField);
          }
          MetricProps metric = new MetricProps(property);
          String displayName =
              withNamePrefix
                  ? "[" + mbean.objectName() + "] " + rhqMetric.displayName()
                  : rhqMetric.displayName();
          metric.setDisplayName(displayName);
          metric.setDisplayType(rhqMetric.displayType());
          metric.setDataType(rhqMetric.dataType());
          metric.setUnits(rhqMetric.units());
          ManagedAttribute managedAttr =
              (ManagedAttribute) ctField.getAnnotation(ManagedAttribute.class);
          if (managedAttr != null) {
            debug("Metric has ManagedAttribute annotation " + managedAttr);
            metric.setDescription(managedAttr.description());
          } else {
            log.debug(
                "Metric has no managed annotations, so take the description from the display name.");
            metric.setDescription(rhqMetric.displayName());
          }
          props.getMetrics().add(metric);
        }
      }
    }
  }
コード例 #3
0
  public ClazzInfo classProcessing(String clazzName)
      throws NotFoundException, CannotCompileException {
    ClassPool classPool = ClassPool.getDefault();
    CtClass cz = classPool.get(clazzName);
    classPool.importPackage(clazzName); // 继承
    classPool.importPackage("java.lang.reflect.Method"); // 添加反射引用

    CtClass newClass = classPool.makeClass(clazzName + "$MC_IMPL"); // 新建代理类
    newClass.setSuperclass(cz); // 继承

    // 构造块
    CtConstructor tempC;
    CtConstructor[] ctConstructors = cz.getDeclaredConstructors();
    newClass.addConstructor(CtNewConstructor.defaultConstructor(newClass));
    for (CtConstructor c : ctConstructors) {
      try {
        tempC = CtNewConstructor.copy(c, newClass, null);
        tempC.setBody("{super($$);}");
        newClass.addConstructor(tempC);
      } catch (Exception e) {
        // e.printStackTrace();
      }
    }

    // 字段块
    //		CtField[] ctFields = cz.getDeclaredFields();
    //		for (CtField f : ctFields)
    //			System.out.println(f.getFieldInfo().getConstantValue());

    // 方法块
    CtMethod[] ctMethods = cz.getDeclaredMethods();
    CtMethod tempM; // 复制方法名
    Map<String, Method> tempMethod = new HashMap<String, Method>();
    for (CtMethod m : ctMethods) {
      tempMethod.put(
          String.format(
              "%s %s %s(%s);",
              Modifier.toString(m.getModifiers()),
              m.getReturnType().getName(),
              m.getName(),
              Util.getParameterTypes(m.getParameterTypes())),
          null);
      // System.err.println(String.format("%s %s %s(%s);", Modifier.toString(m.getModifiers()),
      // m.getReturnType().getName(), m.getName(), Util.getParameterTypes(m.getParameterTypes())));
      tempM = CtNewMethod.copy(m, newClass, null);
      if ("void".equals(tempM.getReturnType().getName()))
        tempM.setBody("{super." + tempM.getName() + "($$);}");
      else tempM.setBody("{ return super." + tempM.getName() + "($$);}");
      //				CtNewMethod.make(src, declaring, delegateObj, delegateMethod)
      // 方法修改
      //			if (m.getName().equals("x")) {
      //				//tempM.setBody("{$proceed($$);}", "this", "mba");
      //				//tempM.setBody("{n nn = new n();" + "Method a = n.class.getDeclaredMethod(\"a\", new
      // Class[] { Integer.TYPE });" + "a.invoke(nn, new Object[] { Integer.valueOf(1) });}");
      //				tempM.setBody("{Method a = n.class.getDeclaredMethod(\"axx\", new Class[] { Integer.TYPE
      // });}");
      //			}
      newClass.addMethod(tempM);
    }

    // 测试输出
    try {
      newClass.writeFile("D:/Desktop");
    } catch (IOException e) {
      e.printStackTrace();
    }

    //		Class clazz = newClass.toClass();
    //		System.out.println(clazz.getCanonicalName());
    //		DefaultCachePoolFactory.newInstance().addNFloop4Map(new ClazzInfo(clazz, tempMethod),
    // DefaultPool.NORNAL_BEAN, clazz.getCanonicalName());
    //		return clazz;
    return new ClazzInfo(newClass.toClass(), tempMethod);
  }
コード例 #4
0
  /** Generate Javassist Proxy Classes */
  private static <T> void generateProxyClass(
      Class<T> primaryInterface, String superClassName, String methodBody) throws Exception {
    String newClassName = superClassName.replaceAll("(.+)\\.(\\w+)", "$1.Hikari$2");

    CtClass superCt = classPool.getCtClass(superClassName);
    CtClass targetCt = classPool.makeClass(newClassName, superCt);
    targetCt.setModifiers(Modifier.FINAL);

    System.out.println("Generating " + newClassName);

    targetCt.setModifiers(Modifier.PUBLIC);

    // Make a set of method signatures we inherit implementation for, so we don't generate delegates
    // for these
    Set<String> superSigs = new HashSet<>();
    for (CtMethod method : superCt.getMethods()) {
      if ((method.getModifiers() & Modifier.FINAL) == Modifier.FINAL) {
        superSigs.add(method.getName() + method.getSignature());
      }
    }

    Set<String> methods = new HashSet<>();
    Set<Class<?>> interfaces = getAllInterfaces(primaryInterface);
    for (Class<?> intf : interfaces) {
      CtClass intfCt = classPool.getCtClass(intf.getName());
      targetCt.addInterface(intfCt);
      for (CtMethod intfMethod : intfCt.getDeclaredMethods()) {
        final String signature = intfMethod.getName() + intfMethod.getSignature();

        // don't generate delegates for methods we override
        if (superSigs.contains(signature)) {
          continue;
        }

        // Ignore already added methods that come from other interfaces
        if (methods.contains(signature)) {
          continue;
        }

        // Ignore default methods (only for Jre8 or later)
        if (isDefaultMethod(intf, intfCt, intfMethod)) {
          continue;
        }

        // Track what methods we've added
        methods.add(signature);

        // Clone the method we want to inject into
        CtMethod method = CtNewMethod.copy(intfMethod, targetCt, null);

        String modifiedBody = methodBody;

        // If the super-Proxy has concrete methods (non-abstract), transform the call into a simple
        // super.method() call
        CtMethod superMethod = superCt.getMethod(intfMethod.getName(), intfMethod.getSignature());
        if ((superMethod.getModifiers() & Modifier.ABSTRACT) != Modifier.ABSTRACT) {
          modifiedBody = modifiedBody.replace("((cast) ", "");
          modifiedBody = modifiedBody.replace("delegate", "super");
          modifiedBody = modifiedBody.replace("super)", "super");
        }

        modifiedBody = modifiedBody.replace("cast", primaryInterface.getName());

        // Generate a method that simply invokes the same method on the delegate
        if (isThrowsSqlException(intfMethod)) {
          modifiedBody = modifiedBody.replace("method", method.getName());
        } else {
          modifiedBody =
              "{ return ((cast) delegate).method($$); }"
                  .replace("method", method.getName())
                  .replace("cast", primaryInterface.getName());
        }

        if (method.getReturnType() == CtClass.voidType) {
          modifiedBody = modifiedBody.replace("return", "");
        }

        method.setBody(modifiedBody);
        targetCt.addMethod(method);
      }
    }

    targetCt.writeFile("target/classes");
  }