Hi,
This is a little test application, generating and compiling code at runtime.
The loadClassLoader () method of the Factory Object suppose to unload all class previously loaded.
It does not work!!!
Somebody knows why?
Thanks in advance for your help
inetjack
*************** *********** File Test.java
import java.io.Buffere dWriter;
import java.io.FileWri ter;
import java.io.File;
public class Test {
public static void main(String[] args) {
try {
Factory o;
BufferedWriter out;
OneBeans a;
String srcf;
String binf;
o = new Factory("OneBea ns");
out = new BufferedWriter( new FileWriter(o.ge tSrcFile("NewBe an")));
out.write("publ ic class NewBean extends OneBeans {\n");
out.write(" public NewBean() {\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public String getPropString() {\n");
out.write(" return \"Hello World\";\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public Integer getPropInteger( ) {\n");
out.write(" return 2;\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public void otherPrint() {\n");
out.write(" System.out.prin tln(\"otherPrin t()\");\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public void print() {\n");
out.write(" System.out.prin tln(\"NewBean exist!\");\n");
out.write(" }\n");
out.write("}\n" );
out.close();
a = o.newInstance(" NewBean");
a.print();
System.out.prin tln(a.invoke("g etPropString")) ;
System.out.prin tln(a.invoke("g etPropInteger") );
a.invoke("other Print");
a = null;
o.loadClassLoad er();
srcf = o.getSrcFile("N ewBean");
binf = o.getBinFile("N ewBean");
System.out.prin tln("delete " + srcf + " = " + (((new File(srcf)).del ete()) ? "Yes" : "No"));
System.out.prin tln("delete " + binf + " = " + (((new File(binf)).del ete()) ? "Yes" : "No"));
out = new BufferedWriter( new FileWriter(o.ge tSrcFile("NewBe an")));
out.write("publ ic class NewBean extends OneBeans {\n");
out.write(" public NewBean() {\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public String getPropString() {\n");
out.write(" return \"Hello World Again\";\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public Integer getPropInteger( ) {\n");
out.write(" return 22;\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public void otherPrint() {\n");
out.write(" System.out.prin tln(\"otherPrin t()\");\n");
out.write(" }\n");
out.write("\n") ;
out.write(" public void print() {\n");
out.write(" System.out.prin tln(\"NewBean 2 exist!\");\n");
out.write(" }\n");
out.write("}\n" );
out.close();
a = o.newInstance(" NewBean");
a.print();
System.out.prin tln(a.invoke("g etPropString")) ;
System.out.prin tln(a.invoke("g etPropInteger") );
a.invoke("other Print");
a = null;
} catch (Exception e) {
e.printStackTra ce();
}
}
}
*************** ******* File OneBeans.java
import java.lang.refle ct.*;
public abstract class OneBeans {
public abstract void print();
public Object invoke(String methodName, Object[] args)
throws NoSuchMethodExc eption, IllegalAccessEx ception,
InvocationTarge tException, ClassNotFoundEx ception {
Class[] c = {};
return this.getClass() .getMethod(meth odName, c).invoke(this, args);
}
public Object invoke(String methodName)
throws NoSuchMethodExc eption, IllegalAccessEx ception,
InvocationTarge tException, ClassNotFoundEx ception {
Object[] args = {};
return invoke(methodNa me, args);
}
}
*************** ******** File Factory.java
import java.util.HashM ap;
import java.io.PrintWr iter;
import java.io.StringW riter;
import java.io.File;
public class Factory {
private HashMap allClasses;
private String abstractClassNa me;
private String packageName;
private Class abstractClass;
private MyClassLoader classLoader;
public Factory(String abstractClassNa me) throws ClassNotFoundEx ception {
this.abstractCl assName = abstractClassNa me;
this.packageNam e = "";
int lio = abstractClassNa me.lastIndexOf( ".") + 1;
if (lio > 0) {
this.abstractCl assName = abstractClassNa me.substring(li o);
this.packageNam e = abstractClassNa me.substring(0, lio);
}
this.loadClassL oader();
}
private void clearAllClasses () {
try {
allClasses.clea r();
} catch (Exception e) {
}
}
private String getFileName(Str ing className, boolean src) {
String propName = (src) ? "sources.pa th" : "bin.path";
String response = (src) ? "java" : "class";
String packPath = this.getPackage Name().replace( ".","/");
return System.getPrope rty(propName) + "/" + packPath + className + "." + response;
}
private String compile(String srcFile, String binFile) {
File src = new File(srcFile);
File bin = new File(binFile);
int resultCode = 0;
String result = "";
if (src.lastModifi ed() != bin.lastModifie d()) {
System.out.prin tln("Compiling " + srcFile + "...");
StringWriter err = new StringWriter();
PrintWriter errPrinter = new PrintWriter(err );
String args[] = {"-classpath",
System.getPrope rty("java.class .path"),
"-d",
System.getPrope rty("bin.path") ,
"-sourcepath",
System.getPrope rty("sources.pa th"),
srcFile};
resultCode = com.sun.tools.j avac.Main.compi le(args, errPrinter);
errPrinter.clos e();
result = err.toString();
bin.setLastModi fied(src.lastMo dified());
}
return (resultCode == 0) ? null : result;
}
public String getSrcFile(Stri ng className) {
return getFileName(cla ssName, true);
}
public String getBinFile(Stri ng className) {
return getFileName(cla ssName, false);
}
public String getPackageName( ) {
return this.packageNam e;
}
public String getAbstractClas sName() {
return this.abstractCl assName;
}
public String getFullAbstract ClassName() {
return this.packageNam e + this.abstractCl assName;
}
public String getFullClassNam e(String className) {
return this.packageNam e + className;
}
public Class getOneClass(Str ing className) {
return (Class) allClasses.get( className);
}
public OneBeans newInstance(Str ing className)
throws ClassNotFoundEx ception, InstantiationEx ception, IllegalAccessEx ception {
return (OneBeans) this.loadClass( className).newI nstance();
}
public void loadClassLoader () throws ClassNotFoundEx ception {
clearAllClasses ();
allClasses = null;
this.classLoade r = null;
abstractClass = null;
Runtime.getRunt ime().gc();
Runtime.getRunt ime().gc();
allClasses = new HashMap();
this.classLoade r = new MyClassLoader() ;
abstractClass = this.classLoade r.loadOneClass( this.getFullAbs tractClassName( ), true);
}
public Class loadClass(Strin g className) throws ClassNotFoundEx ception {
if (allClasses.con tainsKey(classN ame)) {
return getOneClass(cla ssName);
} else {
String result = compile(this.ge tSrcFile(classN ame), this.getBinFile (className));
if (result == null) {
Class cl = this.classLoade r.loadOneClass( this.getFullCla ssName(classNam e), true);
allClasses.put( className, cl);
return cl;
} else {
System.err.prin tln(result);
return null;
}
}
}
}
class MyClassLoader extends ClassLoader {
public Class loadOneClass(St ring className, boolean resolve) throws ClassNotFoundEx ception {
return this.loadClass( className, resolve);
}
}