1 |
|
|
2 |
|
|
3 |
|
|
4 |
|
|
5 |
|
|
6 |
|
package net.sf.tlc.loader; |
7 |
|
|
8 |
|
import java.io.BufferedInputStream; |
9 |
|
import java.io.ByteArrayOutputStream; |
10 |
|
import java.io.File; |
11 |
|
import java.io.FileFilter; |
12 |
|
import java.io.FileInputStream; |
13 |
|
import java.io.IOException; |
14 |
|
import java.net.MalformedURLException; |
15 |
|
import java.net.URL; |
16 |
|
import java.net.URLClassLoader; |
17 |
|
import java.util.ArrayList; |
18 |
|
import java.util.Iterator; |
19 |
|
import java.util.logging.Level; |
20 |
|
import java.util.logging.Logger; |
21 |
|
|
22 |
|
import net.sf.tlc.util.ClassPathUtils; |
23 |
|
|
24 |
|
|
25 |
|
|
26 |
|
|
27 |
|
|
28 |
|
|
29 |
|
|
30 |
|
|
31 |
117 |
public class TlcClassLoader extends URLClassLoader { |
32 |
|
|
33 |
67 |
private final Logger logger = Logger.getLogger(TlcClassLoader.class.getName()); |
34 |
|
|
35 |
13 |
private final File targetDir; |
36 |
|
|
37 |
40 |
private final ArrayList loadedClassFiles = new ArrayList(); |
38 |
|
|
39 |
|
|
40 |
|
|
41 |
|
|
42 |
|
|
43 |
|
public TlcClassLoader(final File targetDir) { |
44 |
40 |
super(new URL[0]); |
45 |
40 |
this.targetDir = targetDir; |
46 |
40 |
if (null != targetDir) { |
47 |
40 |
if (targetDir.isDirectory()) { |
48 |
40 |
findMoreTargets(targetDir); |
49 |
|
} else { |
50 |
0 |
throw new IllegalArgumentException("targetDir must be a directory!"); |
51 |
|
} |
52 |
|
} else { |
53 |
0 |
throw new IllegalArgumentException("targetDir is null!"); |
54 |
|
} |
55 |
40 |
} |
56 |
|
|
57 |
|
|
58 |
|
|
59 |
|
|
60 |
|
|
61 |
|
public TlcClassLoader(final String targetPath) { |
62 |
0 |
this(new File(targetPath)); |
63 |
0 |
} |
64 |
|
|
65 |
|
|
66 |
|
|
67 |
|
|
68 |
|
|
69 |
|
|
70 |
|
class JarFileFilter implements FileFilter { |
71 |
|
|
72 |
|
|
73 |
|
|
74 |
|
|
75 |
|
|
76 |
|
|
77 |
|
public boolean accept(final File file) { |
78 |
|
return file.isFile() && file.canRead() && file.getName().endsWith(".jar"); |
79 |
|
} |
80 |
|
|
81 |
|
} |
82 |
|
|
83 |
40 |
private JarFileFilter jarFileFilter = new JarFileFilter(); |
84 |
|
|
85 |
|
|
86 |
|
|
87 |
|
|
88 |
|
|
89 |
|
private void findMoreTargets(final File dir) { |
90 |
40 |
final ArrayList urls = new ArrayList(); |
91 |
40 |
final File[] jars = dir.listFiles(jarFileFilter); |
92 |
80 |
for (int i = 0; i < jars.length; ++i) { |
93 |
|
try { |
94 |
40 |
addURL(new URL("file://" + jars[i].getAbsolutePath())); |
95 |
0 |
} catch (MalformedURLException e) { |
96 |
0 |
logger.log(Level.SEVERE, "Unexpected MalformedURLException", e); |
97 |
36 |
} |
98 |
|
} |
99 |
44 |
for (final Iterator i = urls.iterator(); i.hasNext();) { |
100 |
0 |
System.out.println(i.next()); |
101 |
|
} |
102 |
40 |
} |
103 |
|
|
104 |
|
|
105 |
|
|
106 |
|
|
107 |
|
|
108 |
|
|
109 |
|
public final Class loadClass(class="keyword">final String className) throws ClassNotFoundException { |
110 |
130 |
final FileFilter filter = new FileFilter() { |
111 |
|
private final String s = targetDir.getAbsolutePath() + "/" + className + ".class"; |
112 |
|
|
113 |
|
|
114 |
|
|
115 |
|
|
116 |
|
|
117 |
|
public boolean accept(final File file) { |
118 |
|
return file.getAbsolutePath().equals(s); |
119 |
|
} |
120 |
|
}; |
121 |
130 |
final File[] found = targetDir.listFiles(filter); |
122 |
130 |
if (found.length == 1 && !loadedClassFiles.contains(found[0])) { |
123 |
30 |
loadClassFromFile(found[0]); |
124 |
|
} |
125 |
130 |
return super.loadClass(className); |
126 |
|
} |
127 |
|
|
128 |
|
|
129 |
|
|
130 |
|
|
131 |
|
|
132 |
|
private void loadClassFromFile(final File file) { |
133 |
30 |
FileInputStream fis = null; |
134 |
30 |
final ByteArrayOutputStream baos = new ByteArrayOutputStream(); |
135 |
|
try { |
136 |
30 |
fis = new FileInputStream(file); |
137 |
30 |
final BufferedInputStream bis = new BufferedInputStream(fis); |
138 |
30 |
int avail = bis.available(); |
139 |
63 |
while (avail > 0) { |
140 |
30 |
final byte[] bytes = new byte[avail]; |
141 |
30 |
bis.read(bytes, 0, avail); |
142 |
30 |
baos.write(bytes); |
143 |
30 |
avail = bis.available(); |
144 |
|
} |
145 |
30 |
loadedClassFiles.add(file); |
146 |
27 |
} catch (IOException e) { |
147 |
0 |
logger.log(Level.SEVERE, "IOException", e); |
148 |
3 |
} finally { |
149 |
3 |
if (null != fis) { |
150 |
|
try { |
151 |
30 |
fis.close(); |
152 |
0 |
} catch (IOException e) { |
153 |
0 |
logger.log(Level.SEVERE, "IOException", e); |
154 |
54 |
} |
155 |
|
} |
156 |
30 |
} |
157 |
36 |
defineClass(ClassPathUtils.toClassName(targetDir.getAbsolutePath(), file.getAbsolutePath()), baos |
158 |
6 |
.toByteArray(), 0, baos.size()); |
159 |
30 |
} |
160 |
|
} |