java代码动态注入 java动态import
求JAVA 注入进程的例子
此代码注入非依赖注入,是hack里的 代码注入
成都创新互联专注于伊美网站建设服务及定制,我们拥有丰富的企业做网站经验。 热诚为您提供伊美营销型网站建设,伊美网站制作、伊美网页设计、伊美网站官网定制、小程序开发服务,打造伊美网络公司原创品牌,更为您提供伊美网站排名全网营销落地服务。
场景是这样滴:
机器上有一个java进程,我不想停止它,但我想把一段代码植入进去,干
一些事情(获取一些信息,改变一些值,监控一些东西,或者其它猥琐的事情)
这个进程不能停,而且也没有预料到现在的事情,或者这个进程的代码完全不能修改。
好,这篇文章是要干这个事情,它基于 jvm的 jdi或者jvmti 接口
这里用的jvmti,jdi也可以,麻烦不少
应该jdk1.5 就有,需要用c写。1.6 支持另一种方式,java也可以写
以前做过类似的事情,代码找不到了,现在有实现了一番。
直接上代码:
被注入的代码是这样滴:
while(true) {
System.out.println(System.currentTimeMillis());
Thread.sleep(1000);
}
每隔一秒输出当前时间,只是示意用。不管什么java程序都行
我要注入的类,那个方法是固定的:
package com.zms.inject;
import java.lang.instrument.Instrumentation;
public class MyAgent1 {
public static void premain(String s) {
premain(s, null);
}
public static void premain(String s, Instrumentation instru) {
System.out.println("I'm injected! 木哈哈哈哈哈");
System.out.printf("param: %s\n", s);
}
public static void agentmain(String args, Instrumentation inst) {
premain(args, inst);
}
public static void agentmain(String args) {
premain(args);
}
}
编译,打入jar包
MANIFEST.MF
Manifest-Version: 1.0
Created-By: 1.6.0_26 (Apple Inc.)
Agent-Class: com.zms.inject.MyAgent1
Premain-Class: com.zms.inject.MyAgent1
操作代码:
import com.sun.tools.attach.*;
import com.sun.tools.attach.spi.AttachProvider;
VirtualMachine vm=VirtualMachine.attach("24862"); //target java process pid
System.out.println(vm);
vm.loadAgent("/Users/zms/workspace/mt/out/production/agent1.jar","Powered by zms!");
Thread.sleep(1000);
vm.detach();
目标程序结果:
1317283652520
1317283653520
1317283654521
I'm injected! 木哈哈哈哈哈
param: Powered by zms!
1317283655521
1317283656522
java怎样把登陆的用户名动态注入集合中
首先声明一个静态Map,登录成功后讲用户名密码存入Map当中即可。session销毁时移除该记录。
如何利用Java实现资源注入
Java的功能强大,今儿博洋教育将给大家介绍。 需求:一个应用有两个数据库,分别为DB-A,DB-B。 假设持久层框架使用iBatis来实现,那么SqlMapClient对象在创建时,对于两个不同的DB连接要有两个不同的SqlMapClient对象, 假设我们有一个Service类为MyService.java,该类中有两个SqlMapClient对象sqlMapA、sqlMapB分别对应着DB-A、DB-B。 先看看我们的SqlMapClient.java类:(自定义SqlMapClient类,用来演示。) import java.util.Map; import org.apache.commons.lang.builder.ToStringBuilder; import org.apache.commons.lang.builder.ToStringStyle; @SuppressWarnings("unchecked") public class SqlMapClient { public SqlMapClient(String s, String t) { sqlMap = s; type = t; } public SqlMapClient() { } private String type = null; private String sqlMap = null; // get、set方法 略 // 用于演示查询后返回一个String的返回结果 public String selectForObject(String sql, Map in) { return this.toString(); } @Override public String toString() { return new ToStringBuilder(this, ToStringStyle.SHORT_PREFIX_STYLE)。append("sqlMap", sqlMap) .append("type", type)。toString(); } } MyService.java类实现: import java.util.Map; @SuppressWarnings("unchecked") public class MyService { @DataSource(type="B", sqlMap="com/annotation/sql-map-config-B.xml") private SqlMapClient sqlMapB = null; @DataSource(type="A", sqlMap="com/annotation/sql-map-config-A.xml") private SqlMapClient sqlMapA = null; // get、set方法 略 // 模拟在DB-B数据库取得数据 public String selectForObjectFromB(String sql, Map in) { return sqlMapB.selectForObject("", null); } // 模拟在DB-A数据库取得数据 public String selectForObjectFromA(String sql, Map in) { return sqlMapA.selectForObject("", null); } } 接下来就是我们的注解类:DataSource.java import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.FIELD) @Retention(RetentionPolicy.RUNTIME) public @interface DataSource { /** * Dao的类型 * @return */ String type() default "A"; // 连接的数据库类型 A or B String sqlMap() default ""; // Sql-Map-Config文件的路径,用于加载iBatis的SqlMapClient对象 } 定义资源注入的接口 IFieldWiring.java。 之所以这里要定义这个接口,是为了以后扩展用,我们很方便的定义更多的自定义注解。 IFieldWiring.java import java.lang.annotation.Annotation; import java.lang.reflect.Field; public interface IFieldWiring { Class clazz = obj.getClass(); try { String methodname = "get" + StringUtils.capitalize(fieldName); Method method = clazz.getDeclaredMethod(methodname); method.setAccessible(true); return method.invoke(obj); } catch (Exception e) { try { Field field = clazz.getDeclaredField(fieldName); field.setAccessible(true); return field.get(obj); } catch (Exception e1) { e1.printStackTrace(); } } return null; } public static void setFieldValue(Object target, String fname, Class fieldClass, Object fieldObj) { if (!fieldClass.isAssignableFrom(fieldObj.getClass())) { return; } Class clazz = target.getClass(); try { Method method = clazz.getDeclaredMethod("set" + Character.toUpperCase(fname.charAt(0)) + fname.substring(1), fieldClass); method.setAccessible(true); method.invoke(target, fieldObj); } catch (Exception e) { try { Field field = clazz.getDeclaredField(fname); field.setAccessible(true); field.set(target, fieldObj); } catch (Exception e1) { e1.printStackTrace(); } } } } 已经基本大功告成了,只要将我们的DataSourceWiring.java类使用起来即可。 MyAnnotationBeanProcessor.java,这个类主要用于为bean对象注入资源。 import java.lang.reflect.Field; public class MyAnnotationBeanProcessor { /** * 注入资源 * @param serviceObject * @param fieldAutoWirings // 所有实现IFieldWiring的接口的对象,我们可以在此扩展 * @throws Exception */ public void wire(Object serviceObject, IFieldWiring fieldAutoWirings) throws Exception { Class cls = serviceObject.getClass(); for (Field field : cls.getDeclaredFields()) { for (IFieldWiring fieldAutoWiring : fieldAutoWirings) { if (field.isAnnotationPresent(fieldAutoWiring.annotationClass())) { fieldAutoWiring.wiring(serviceObject, field); break; } } } } } 好了,开始我们的测试类:FieldWiringTest.java public class FieldWiringTest { public static void main(String args[]) throws Exception { MyAnnotationBeanProcessor processor = new MyAnnotationBeanProcessor(); MyService b = new MyService(); processor.wire(b, new DataSourceWiring()); // 注入DataSource资源 System.out.println(b.selectForObjectFromB("", null)); System.out.println(b.selectForObjectFromA("", null)); } } 执行结果: SqlMapClient[sqlMap=com/annotation/sql-map-config-B.xml,type=B] SqlMapClient[sqlMap=com/annotation/sql-map-config-A.xml,type=A] 由执行结果可以说明DataSource资源已经被我们正确的注入了。 如果想扩展的话,只需要新建一个类实现IFieldWiring接口即可。假设叫InParamWiring.java,实现了接口定义的两个方法后,在使用的时候,只要用以下代码便可将资源注入了: MyAnnotationBeanProcessor processor = new MyAnnotationBeanProcessor(); MyService b = new MyService(); processor.wire(b, new DataSourceWiring(), new InParamWiring()); // 注入DataSource、InParam资源. 更多Java学习技巧,尽在博洋教育。若您想了解java程序培训价格,欢迎向我们的在线老师进行详细了解。
怎样实现java代码的动态加载
1.将你这段字符串输出到一个文件里,用Java类文件的方式命名。
2.调用外部javac命令将该文件编译。
3.用类加载器(ClassLoad)动态加载新的class文件并用Class.forName()注册该类,然后就可以正常使用了。
上面的每一步都能在baidu中找到实现方法,自己发挥吧。
分享名称:java代码动态注入 java动态import
当前地址:http://pwwzsj.com/article/doippjj.html