Javassist 实现代码增强

阅读更多

 

 

/**
 * Desc:TODO
 * 
 * @author zhangwei
 * @since 2016年1月14日 下午9:19:34
 * @version v 0.1
 */
public final class ClassEnhancedGenerator {
	
	private ClassEnhancedGenerator() {
	}

	/**
	 * 类方法增强
* * 对指定类的方法进行代码增强(将指定的原方法名改为$enhanced,同时复制原方法名进行代码注入) * * @param className * 待增强的类名 * @param methodName * 待增强的方法名 * @param provider * {@link ClassInjectProvider}实现类 * @throws Exception */ public static void enhancedMethod(Class cls, Method[] methods, InjectType injectType, ClassInjectProvider provider) throws Exception { CtClass ctClass = ClassPool.getDefault().get(cls.getName()); for (int i = 0; i < methods.length; i++) { injectCodeForMethod(ctClass, methods[i].getName(), injectType, provider); } String resource = cls.getName().replace(".", "/") + ".class"; URI uri = ClassLoader.getSystemClassLoader().getResource(resource).toURI(); String classFilePath = uri.getRawPath().substring(0, uri.getRawPath().length() - resource.length()); ctClass.writeFile(classFilePath); } /*** * 注入增强代码 * * @param ctClass * @param methodName * @param injectType * @param provider * @throws Exception * @author zhangwei */ private static void injectCodeForMethod(CtClass ctClass, String methodName, InjectType injectType, ClassInjectProvider provider) throws Exception { CtMethod oldMethod = ctClass.getDeclaredMethod(methodName); // 修改原有的方法名称为"方法名$enhanced",如果已存在该方法则返回 String originalMethod = methodName + "$enhanced"; CtMethod[] methods = ctClass.getMethods(); for (int i = 0; i < methods.length; i++) { CtMethod method = methods[i]; if (method.getName().equals(originalMethod)) { return; } } oldMethod.setName(originalMethod); // 增加代码,复制原来的方法名作为增强的新方法,同时调用原有方法即"方法名$enhanced" CtMethod enhancedMethod = CtNewMethod.copy(oldMethod, methodName, ctClass, null); // 对复制的方法注入代码 StringBuffer methodBody = new StringBuffer(); methodBody.append("{"); switch (injectType) { case BEFORE: methodBody.append(provider.injectCode(enhancedMethod)); methodBody.append("return " + originalMethod + "($$); "); break; case AFTER: methodBody.append("try{"); methodBody.append("return " + originalMethod + "($$); "); methodBody.append("}finally{"); methodBody.append(provider.injectCode(enhancedMethod)); methodBody.append("}"); break; default: String injectCode = provider.injectCode(enhancedMethod); methodBody.append(injectCode); } methodBody.append("}"); enhancedMethod.setBody(methodBody.toString()); ctClass.addMethod(enhancedMethod); } }

 

 

/**
 * Desc:TODO
 * 
 * @author zhangwei
 * @since 2016年1月14日 下午9:21:51
 * @version v 0.1
 */
public interface ClassInjectProvider {

	/**
	 * 对指定的方法注入代码
	 *
	 * @param ctMethod
	 *            CtMethod
	 * @return
	 */
	public String injectCode(final CtMethod ctMethod) throws Exception;

}

 

/**
 * Desc:TODO
 * 
 * @author zhangwei
 * @since 2016年1月14日 下午9:23:17
 * @version v 0.1
 */
public enum InjectType {
	BEFORE, AFTER, REPLACE;
}

 

你可能感兴趣的:(Javassist 实现代码增强)