1 package com.atlassian.plugin.osgi.util;
2
3 import aQute.bnd.osgi.AbstractResource;
4 import aQute.bnd.osgi.ClassDataCollector;
5 import aQute.bnd.osgi.Clazz;
6 import aQute.bnd.osgi.Descriptors;
7 import com.google.common.base.Function;
8 import com.google.common.collect.Collections2;
9 import com.google.common.collect.ImmutableSet;
10 import com.google.common.collect.Sets;
11 import org.apache.commons.io.IOUtils;
12
13 import javax.annotation.Nullable;
14 import java.io.IOException;
15 import java.io.InputStream;
16 import java.util.Set;
17
18
19
20
21
22
23 public class ClassBinaryScanner {
24
25
26
27
28
29
30
31
32 public static ScanResult scanClassBinary(Clazz clazz) throws IOException {
33 final ImmutableSet.Builder<String> allReferredClasses = new ImmutableSet.Builder<String>();
34 final String[] superClassName = new String[]{null};
35 try {
36
37 clazz.parseClassFileWithCollector(new ClassDataCollector() {
38
39 @Override
40 public void extendsClass(Descriptors.TypeRef ref) {
41 superClassName[0] = ref.getBinary();
42 allReferredClasses.add(ref.getBinary());
43 }
44
45 @Override
46 public void implementsInterfaces(Descriptors.TypeRef[] refs) {
47 for (Descriptors.TypeRef ref : refs) {
48 allReferredClasses.add(ref.getBinary());
49 }
50 }
51
52 @Override
53 public void addReference(Descriptors.TypeRef ref) {
54 allReferredClasses.add(ref.getBinary());
55 }
56 });
57 } catch (Exception e) {
58 throw new IOException("Error parsing class file", e);
59 }
60
61 Set<String> referredPackages = Sets.newHashSet(Collections2.transform(clazz.getReferred(),
62 new Function<Descriptors.PackageRef, String>() {
63 @Override
64 public String apply(@Nullable Descriptors.PackageRef packageRef) {
65 if (packageRef != null) {
66 return packageRef.getFQN();
67 } else {
68 return null;
69 }
70 }
71 }));
72 return new ScanResult(allReferredClasses.build(), referredPackages, superClassName[0]);
73 }
74
75
76
77
78
79
80 public static class ScanResult {
81
82 private Set<String> referredClasses;
83 private Set<String> referredPackages;
84 private String superClass;
85
86 public ScanResult(Set<String> referredClasses, Set<String> referredPackages, String superClass) {
87 this.referredClasses = referredClasses;
88 this.referredPackages = referredPackages;
89 this.superClass = superClass;
90 }
91
92 public Set<String> getReferredClasses() {
93 return referredClasses;
94 }
95
96 public Set<String> getReferredPackages() {
97 return referredPackages;
98 }
99
100 public String getSuperClass() {
101 return superClass;
102 }
103 }
104
105
106
107
108
109
110 public static class InputStreamResource extends AbstractResource {
111 private InputStream inputStream;
112
113 public InputStreamResource(InputStream inputStream) {
114 super(-1);
115 this.inputStream = inputStream;
116 }
117
118 @Override
119 protected byte[] getBytes() throws Exception {
120 return IOUtils.toByteArray(inputStream);
121 }
122
123 public void close() {
124 IOUtils.closeQuietly(inputStream);
125 }
126
127 }
128 }