deprecation="on"
optimize="off"
includes="sample/**"
- excludes="sample/hotswap/**">
+ excludes="sample/hotswap/**,sample/evolve/sample/**">
<classpath refid="classpath"/>
</javac>
+
+ <copy file="sample/vector/Test.j"
+ todir="${build.classes.dir}/sample/vector"/>
+
+ <javac srcdir="${basedir}/sample/evolve"
+ destdir="${build.classes.dir}/sample/evolve/"
+ debug="on"
+ deprecation="on"
+ optimize="off"
+ includes="sample/**">
+ <classpath refid="classpath"/>
+ </javac>
+ <copy todir="${build.classes.dir}/sample/evolve">
+ <fileset dir="sample/evolve"/>
+ </copy>
+ <copy file="${build.classes.dir}/sample/evolve/WebPage.class"
+ tofile="${build.classes.dir}/sample/evolve/WebPage.class.0"/>
+ <copy file="${build.classes.dir}/sample/evolve/sample/evolve/WebPage.class"
+ tofile="${build.classes.dir}/sample/evolve/WebPage.class.1"/>
+
<javac srcdir="${basedir}/sample/hotswap"
destdir="${build.classes.dir}"
debug="on"
includes="*">
<classpath refid="classpath"/>
</javac>
- <copy file="sample/vector/Test.j"
- todir="${build.classes.dir}/sample/vector"/>
- <copy todir="${build.classes.dir}/sample/evolve">
- <fileset dir="sample/evolve"/>
- </copy>
<echo>To run the sample programs without ant, change the current directory
to ${build.classes.dir}.</echo>
</target>
* server overwrites WebPage.class (class file) and calls update()\r
* in VersionManager so that WebPage.class is loaded into the JVM\r
* again. The new contents of WebPage.class are copied from\r
- * either WebPage.class.0 or WebPage.class.1.\r
+ * either sample/evolve/WebPage.class\r
+ * or sample/evolve/sample/evolve/WebPage.class.\r
*/\r
public class DemoServer extends Webserver {\r
\r
* show() on the created object.\r
*/\r
\r
-// WebPage.class.0\r
public class WebPage {\r
public void show(OutputStreamWriter out) throws IOException {\r
Calendar c = new GregorianCalendar();\r
out.write("<P><A HREF=\"demo.html\">Return to the home page.</A>");\r
}\r
}\r
-/*\r
-// WebPage.class.1\r
-public class WebPage {\r
- public void show(OutputStreamWriter out) throws IOException {\r
- out.write("<H2>Current Time:</H2>");\r
- Calendar c = new GregorianCalendar();\r
- out.write("<CENTER><H3><FONT color=\"blue\">");\r
- out.write(c.getTime().toString());\r
- out.write("</FONT></H3></CENTER><HR>");\r
- out.write("<P><A HREF=\"demo.html\">Return to the home page.</A>");\r
- }\r
-}\r
-*/\r
\r
<P>Web server: <A HREF="DemoServer.java"><code>DemoServer.java</code></A>\r
\r
-<P>WebPage: <A HREF="WebPage.java"><code>WebPage.java</code></A>\r
+<P>WebPage: <A HREF="WebPage.java"><code>WebPage.java</code></A> and\r
+another <A HREF="sample/evolve/WebPage.java"><code>WebPage.java</code></A>\r
\r
<P>Class loader: <A HREF="DemoLoader.java"><code>DemoLoader.java</code></A>,\r
<A HREF="Evolution.java"><code>Evolution.java</code></A>, and\r
--- /dev/null
+package sample.evolve;\r
+\r
+import java.io.*;\r
+import java.util.*;\r
+\r
+/**\r
+ * Updatable class. DemoServer instantiates this class and calls\r
+ * show() on the created object.\r
+ */\r
+\r
+public class WebPage {\r
+ public void show(OutputStreamWriter out) throws IOException {\r
+ out.write("<H2>Current Time:</H2>");\r
+ Calendar c = new GregorianCalendar();\r
+ out.write("<CENTER><H3><FONT color=\"blue\">");\r
+ out.write(c.getTime().toString());\r
+ out.write("</FONT></H3></CENTER><HR>");\r
+ out.write("<P><A HREF=\"demo.html\">Return to the home page.</A>");\r
+ }\r
+}\r
<h2>Instructions</h2>\r
\r
<p>1. Compile <code>sample/evolve/*.java</code>.\r
- Copy <code>WebPage.class</code> to <code>WebPage.class.0</code>.\r
\r
-<p>2. Edit <code>Webpage.java</code>, compile it,\r
- and copy <code>WebPage.class</code> to <code>WebPage.class.1</code>.\r
-<br><code>WebPage.class.0</code> and\r
- <code>WebPage.class.1</code> are used\r
- for changing the contents of <code>WebPage.class</code> during\r
- the demo.\r
+<p>2. change the current directory to <code>sample/evolve</code><br>\r
+and compile there <code>sample/evolve/WebPage.java</code><br>\r
+(i.e. compile <code>sample/evolve/sample/evolve/WebPage.java</code>).\r
+\r
+<p>The two versions of <code>WebPage.class</code> are used<br>\r
+for changing the contents of <code>WebPage.class</code> during\r
+the demo.\r
\r
<p>3. Run the server on the local host (where your web browser is running):\r
\r
version of that class during runtime. Thus, you cannot alter
the definition of a class after the JVM loads it.
However, the JPDA (Java Platform Debugger Architecture) provides
-limited ability for reloading a class. See "HotSwap" of JPDA for details.
+limited ability for reloading a class.
+See <a href="#hotswap">Section 3.6</a>.
</ul>
<p>If the same class file is loaded by two distinct class loaders,
<p><br>
+<a name="hotswap">
+<h3>3.6 Reloading a class at runtime</h3></a>
+
+<p>If the JVM is launched with the JPDA (Java Platform Debugger
+Architecture) enabled, a class is dynamically reloadable. After the
+JVM loads a class, the old version of the class definition can be
+unloaded and a new one can be reloaded again. That is, the definition
+of that class can be dynamically modified during runtime. However,
+the new class definition must be somewhat compatible to the old one.
+<em>The JVM does not allow schema changes between the two versions.</em>
+They have the same set of methods and fields.
+
+<p>Javassist provides a convenient class for reloading a class at runtime.
+For more information, see the API documentation of
+<code>javassist.tool.HotSwapper</code>.
+
+<p><br>
+
<a href="tutorial2.html">Next page</a>
<hr>