Jef*_*man 8 java android annotations bcel javassist
我们正在使用一个包含使用JAXB注释注释的bean的库.我们使用这些类的方式取决于JAXB.换句话说,我们不需要JAXB,也不依赖于注释.
但是,由于注释存在,它们最终会被处理注释的其他类引用.这需要我在我们的应用程序中捆绑JAXB,这是不允许的,因为JAXB在javax.*包中(android不允许"核心库"包含在你的应用程序中).
所以,考虑到这一点,我正在寻找一种从编译的字节代码中删除注释的方法.我知道有用于操作字节代码的实用程序,但这对我来说是一个新的东西.任何帮助开始朝这个目的将不胜感激.
我推荐BCEL 6。你也可以使用ASM,但我听说BCEL更容易使用。这是使字段最终确定的快速测试方法:
public static void main(String[] args) throws Exception {
System.out.println(F.class.getField("a").getModifiers());
JavaClass aClass = Repository.lookupClass(F.class);
ClassGen aGen = new ClassGen(aClass);
for (Field field : aGen.getFields()) {
if (field.getName().equals("a")) {
int mods = field.getModifiers();
field.setModifiers(mods | Modifier.FINAL);
}
}
final byte[] classBytes = aGen.getJavaClass().getBytes();
ClassLoader cl = new ClassLoader(null) {
@Override
protected synchronized Class<?> findClass(String name) throws ClassNotFoundException {
return defineClass("F", classBytes, 0, classBytes.length);
}
};
Class<?> fWithoutDeprecated = cl.loadClass("F");
System.out.println(fWithoutDeprecated.getField("a").getModifiers());
}
Run Code Online (Sandbox Code Playgroud)
当然,您实际上可以将类作为文件写入磁盘,然后将它们打包,但这更容易尝试。我手边没有 BCEL 6,所以我无法修改这个示例来删除注释,但我想代码会是这样的:
public static void main(String[] args) throws Exception {
...
ClassGen aGen = new ClassGen(aClass);
aGen.setAttributes(cleanupAttributes(aGen.getAttributes()));
aGen.getFields();
for (Field field : aGen.getFields()) {
field.setAttributes(cleanupAttributes(field.getAttributes()));
}
for (Method method : aGen.getMethods()) {
method.setAttributes(cleanupAttributes(method.getAttributes()));
}
...
}
private Attribute[] cleanupAttributes(Attribute[] attributes) {
for (Attribute attribute : attributes) {
if (attribute instanceof Annotations) {
Annotations annotations = (Annotations) attribute;
if (annotations.isRuntimeVisible()) {
AnnotationEntry[] entries = annotations.getAnnotationEntries();
List<AnnotationEntry> newEntries = new ArrayList<AnnotationEntry>();
for (AnnotationEntry entry : entries) {
if (!entry.getAnnotationType().startsWith("javax")) {
newEntries.add(entry);
}
}
annotations.setAnnotationTable(newEntries);
}
}
}
return attributes;
}
Run Code Online (Sandbox Code Playgroud)