I haven't had time to put in all I want, but those sections will be updated at some point.
Java is your one-stop shop for creating interactive web content; you can use it both for client side programming in applets that run in the web browser, and for server side programming to create dynamic web content. It is not, however, the ultimate panacea since it can be rather heavyweight for a simple web form and many browsers do not support it or have buggy implementations.
I shall first discuss how to install the necessary tools and then present (in order) servlets, applets and Java Server Pages (JSP). Servlets run on the web server and using them often require access to the server itself. However, with a correctly setup server this need not be the case.
To do this yourself you will need:
Harder to figure out are some of the configuration files. The rough outline is as follows:
# at the top of the load module section
LoadModule jserv_module libexec/mod_jserv.so
# At the top of the AddModule section
AddModule mod_jserv.c
# Include the jserv config file
<IfModule mod_jserv.c>
Include conf/jserv/jserv.conf
</IfModule>
You should also install mod_ssl to enable secure sockets communication with
the web server. Make sure that you compile apache (and modules) with
-DEAPI.
# Where to find java
wrapper.bin=/usr/local/jdk1.2.2/bin/java
# Classpath values
wrapper.classpath=/usr/local/apache/libexec/ApacheJServ.jar
wrapper.classpath=/usr/lib/pgsql/jdbc7.0-1.2.jar
wrapper.classpath=/usr/local/jdk1.2.2/jswdk-1.0.1/lib/servlet.jar
# Servlet zones
zones=root
# Properties file for each zone
root.properties=<server-root>/conf/jserv/zone.properties
check to see that the logging is set up as well.
# Where to find the servlets
repositories=<server-root>/servlets
Here you can set initial parameters for each servlet and make aliases for
servlets.
I will talk about these in more detail when we use them.
The basic idea of writing an applet is to write a class that extends
java.applet.Applet and implement the methods public void
init() to set up your applet, public void start()
to start any actions running that you need and public void
stop() to stop anything you have started. You must then write
an HTML page that contains an <applet ... > tag telling the browser
where to find the applet.
The simple applet HelloWorldApplet displays an
image containing "Hello World". Here's the
source code.
It doesn't do anything but sit in the browser window so all it needs to
implement is the init() method.
A little more interesting is BouncingTextApplet which displays some text bouncing around the display. Here's the source code.
The init() method sets up the user interface - this consists
of getting the text and measuring it, creating Start and Stop buttons
(these just execute the start() and stop()
methods) and getting an off-screen area to draw on so that we can have
flicker-free animation.
The animation needs to run in a separate thread in order to let the browser
have some control over the applet, so the start() method
starts the animation thread, while the stop() method stops it.
The bulk of the work is done by the run() method which moves
the text aroud and the paint() method that draws it.
The last example of an applet, before we talk about servlets, is an SSH client written as a Java applet. It has a complete terminal emulation inteface that allows you to make an SSH connection and then use it as a standard terminal window - so you may run things like pine and emacs and so on, even lynx! It has all the standard VT100 features. There is one small problem: because of security restrictions you can only connect back to the host from which you downloaded the applet, so you must have a shell account on that host. However, suppose you have a shell account on MLUG. Then you can copy these classes to your public_html directory and connect to MLUG via any Java enabled web browser. This can be very convenient if you end up in BFE with only a windoze machine and no ssh client to check your email. It can also be used for remote administration of your own machine if you are running a web server.
The next example rob.servlets.TestServlet belongs to the package "rob.servlets" (note the declaration "package rob.servlets ;" at the beginning of the source file). The class file must be placed in the directory <server-root>/servlets/rob/servlets/ and it is called with URL http://host:port/servlet/rob.servlets.TestServlet
This servlet shows all the information that is available to the servlets when a request is made. The parameters heading is for any additional parameters that were passed in to the servlet with the request. For example if you call the servlet as http://host:port/servlet/rob.servlets.TestServlet?name=value then you will see this listed.
Servlets may be called from HTML pages using either an anchor (which will send a GET request) or a form which can send both GET and POST requests. The page exampleForm.html calls TestServlet with all three methods.
public void doGet(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException
public void doPost(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException
If you don't care about the difference between GET and POST requests, then
you can just implement one, say doGet and then set the other to call it:
public void doPost(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException {
doGet(req, res) ;
}
I only usually bother implementing doPost if the data sent with the request
is more than just "name=value" pairs from a form - for example a file, or a
Java Object sent from an applet.
%xy", where
xy is the two-digit hexadecimal representation of the lower 8-bits
of the character. Suppose you have a form:
<form action=/servlet/rob.servlets.TestServlet method=get>
<input type=text name=textfield>
<input type=hidden name=action value=test
<input type=submit>
</from>
If someone types in "Some text @$#" and clicks the submit button, then
the browser will send the request as
/servlet/rob.servlets.TestServlet?textfield=Some+text+%40%24%23&action=test
This has the base URL, then a '?' and finally the encoded parameters as
name=value separated by '&' symbols.When you receive the response this is exactly what you will see in the browser's URL line.
You can achieve the same request using an anchor: /servlet/rob.servlets.TestServlet?textfield=Some+text+%40%24%23&action=test.
So much for GET requests. If instead the form had said "method=post" in the first line, then the browser would have sent the request as POST /servlet/rob.servlets.TestServlet HTTP/1.0 and then sent the form parameters as a stream of data (still with the same encoding). This is useful if you need to send more data than a GET request can handle, or if you want to send data other than "name=value" pairs.
In case the encoding sounds complicated, you don't have to worry about it. The servlet engine decodes it all and has several methods for you to query the parameters.
The first thing TestServlet does is read initial parameters. The most common use of these are to pass in database information. A servlet also has access to the local filesystem (although typically the servlet engine runs as user "nobody" so files must be world readable for the servlet to read them). Thus, you may also store information in a file that the servlet can read.
When a request is made for TestServlet it reads any parameters sent with the request, eg /servlet/rob.servlets.TestServlet?name=rob will have a parameter of name = rob. Then it queries both the request and the servlet engine for all the information it stores. The reaults are then returned in a web page.
rob.servlets.BouncingTextServlet is a silly servlet that allows you to send some text as a parameter, and then it returns the BouncingTextApplet with the text you gave it.
Call it with /servlet/rob.servlets.BouncingTextServlet?text=value, but you have to make sure that you encode value properly, otherwise some of it may get lost.
This servlet opens an SSH connection to the local host and keeps it running until the user requests that it stop. In order to do this the servlet engine has to hold the network connection open itself - something that would be impossible in a regular CGI script which runs and then terminates.
This example uses the same SSH classes from mindbright that the SSH applet used, but it would be perfectly possible to have written this servlet to create a local ssh process instead, and talk to that directly.
Advantages: less work in writing and returning HTML pages; lower network bandwidth because only the data needs to be transfered, not the whole page.
Disadvantages: more work to set up the applet to display the information and write its GUI; no security in that the applet can't use the browser's SSL connection, but has to create its own network connection.
The second disadvantage is not necessarily bad in that it is easy to add encryption into the applet's network connection, but I don't have any examples that I can show of this right now.
A cool applet by Ryan Thornton (hope this is okay for me to link to it, Ryan).
The principle behind JSP is like that of PHP and ASP pages. The server recognises that it is being asked to return a JSP page and sends it to the JSP engine (Tomcat). Tomcat processes the page and returns the HTML generated. A JSP page may contain any valid HTML together with fragments of Java code. A quick reference for the tags may be found here: http://java.sun.com/products/jsp/tags/11/syntaxref11.html.
JSP are best illustrated by examples (taken from the O'Reilly Servlets book).
<% code fragment %>
<HTML>
<HEAD><TITLE>Hello</TITLE></HEAD>
<BODY>
<H1>
<%
if (request.getParameter("name") == null) {
out.println("Hello World");
}
else {
out.println("Hello, " + request.getParameter("name"));
}
%>
</H1>
</BODY></HTML>
<%= code fragment %>
<HTML>
<HEAD><TITLE>Hello</TITLE></HEAD>
<BODY>
<H1>
<% if (request.getParameter("name") == null) { %>
Hello World
<% } else { %>
Hello, <%= request.getParameter("name") %>
<% } %>
</H1>
</BODY></HTML>
Notice that the scriptlet may be broken by HTML.
<%! declaration %>The difference between this and scriptlets is that scriptlets are executed as the page is processed and can result in text being output, or simply cause some text to be written instead of another text. Declarations are stored and may be called or referred to later. Here is a third version of the same thing: Hello World version 3.
<HTML>
<HEAD><TITLE>Hello</TITLE></HEAD>
<BODY>
<%!
private static final String DEFAULT_NAME = "World!";
private String getName(HttpServletRequest req) {
String name = req.getParameter("name");
if (name == null)
return DEFAULT_NAME;
else
return name;
}
%>
<H1>
Hello, <%= getName(request) %>
</H1>
</BODY>
</HTML>
<%@ include file="relativeURL" %>There's not much to say about this one - it is directly equivalent to PHP's include statement and just dumps in the text from the file (or the text after processing if it is another JSP file.
<%@ page import="java.util.*, java.lang.*" %>
public void setName(String s)
public String getName()
You can use these classes in your JSP page in a transparent manner. Here
is a simple Bean with a property "name":
public class HelloBean {
private String name = "World";
public void setName(String name) {
this.name = name;
}
public String getName() {
return name;
}
}
If you call this class "HelloBean.java", compile it and put it in Tomcat's
classpath, then you can use it with the <jsp:useBean ... > tag, and
get/set its properties with the tags
<jsp:getProperty name="HelloBean" property="name" />
<jsp:setProperty name="HelloBean" property="name" value="Rob" />
Actually setProperty is smarter than that - if the request contains the
property "name", then you can set the corresponding property in the bean
with
<jsp:setProperty name="hello" property="name" />
The "Hello World" page again: Hello World version 4.
<%@ page import = "HelloBean" %>
<jsp:useBean id="hello" beanName="HelloBean" type="HelloBean" scope="request" />
<jsp:setProperty name="hello" property="name" />
<HTML>
<HEAD><TITLE>Hello</TITLE></HEAD>
<BODY>
<H1>
Hello, <%= hello.getName() %>
</H1>
</BODY>
</HTML>