The most effective way to learn a framework is by examining and understanding a non-trivial application that uses it. Learning by just reading API documentation is often slower, since it's harder to see how your applications will work in practice. Any framework that doesn't give you such an example application isn't doing you any favors.
Since .class files are included in the download, there is no initial need to perform a compile before running the application. Once you modify the source, then a compile will be needed in order to see your changes.
(If you have followed these steps below, but still cannot launch the app successfully, just ask for email support. Please include log files, if any, and a description of the problem.)
The example applications aren't small. The tutorial is an alternative for those looking for a quicker introduction, and for those with less familiarity with Java web apps.
For APP_HOME = 'C:\TEMP2\predictions' C:\TEMP2\predictions> dir /b css\ images\ main\ pub\ WEB-INF\ build.xml Error.html ... For APP_HOME = 'C:\myname\myprojects\fish\' C:\myname\myprojects\fish\> dir /b access\ all\ exercise\ images\ main\ translate\ WEB-INF\ webmaster\ build.xml Error.html ...
[APP_HOME]\WEB-INF\datastore\mysql\CreateALL.SQLThe script has been validated against MySQL version 5.5.8. If you want to use a different database other than MySQL, then the script will need to be ported to the new target database. However, you need to be aware that there a number of settings in web.xml that are also sensitive to the database. To avoid problems with those relatively minor settings, you are strongly encouraged to use MySQL during this introduction to WEB4J.
In the CreateALL.SQL script, you may have to replace
DROP DATABASE/CREATE DATABASEwith
DROP SCHEMA/CREATE SCHEMA
The script is run using the mysql client:
[APP_HOME]\WEB-INF\datastore\mysql>C:\mysql\bin\mysql --local-infile=1 -u myname -pmypass < CreateALL.SQL
The above example runs the .SQL script directly from the directory where it resides.
You will need wide permissions in order to run the script.
It's important to note that the user and role tables contain entries suitable only for testing. If you build a 'real' application from this example application, you will need to remove such entries. Note as well that user passwords are protected by being stored in a hashed form. You can enter new user names and passwords only through the application, not by direct manipulation of the tables (see below).
This script sets the default encoding for all tables to UTF-8.
[APP_HOME]\WEB-INF\web.xml
There are a number of web4j settings in the deployment descriptor. When getting started, the only ones you should likely set are:
A captcha is often used on the public web. They're used to prevent bots from creating accounts and putting spam into databases. The Predictions application implements a captcha using:
To use Predictions, you will need to create a recaptcha account. (Don't worry, it only takes a minute.) When you create an account, you will receive two items: a public key and a private key. These keys identify which app is calling the recaptcha server. Inside the Predictions app, you need to do two things with these keys:
It's a bit silly to require junit.jar for a deployment. The reason it's required is because WEB4J loads all classes in your app upon startup, and examines them using reflection. In a production deployment, you would likely remove all JUnit test classes, and there would be no need for junit.jar at all.
Predictions context file: | [APP_HOME]\WEB-INF\tomcat\predict.xml |
Fish and Chips Club context file: | [APP_HOME]\WEB-INF\tomcat\fish.xml |
You must then edit the context file to match your environment. Remember to:
Please edit the context file with care. Any mistake will cause the launch of the app to fail. If you have a problem launching, the cause is almost always with the context file.
The context file specifies:
Here are two examples of a customised version of the context file. Compare them with your version, to see where you need to make changes specific to your own environment.
Important: the docBase attribute of the <Context> tag must point to your APP_HOME.
For predict.xml:
<Context docBase="C:\TEMP2\predictions" reloadable="true"> <Resource name="jdbc/predict" auth="Container" type="javax.sql.DataSource" username="fred" password="****" driverClassName="com.mysql.jdbc.Driver" url="jdbc:mysql://localhost:3306/predict?useServerPrepStmts=false" maxActive="10" maxIdle="5" /> <Realm className="org.apache.catalina.realm.JDBCRealm" connectionURL="jdbc:mysql://localhost:3306/predict" digest="SHA-1" driverName="com.mysql.jdbc.Driver" roleNameCol="Role" userCredCol="Password" userNameCol="LoginName" userRoleTable="userrole" userTable="users" connectionName="fred" connectionPassword="****" debug="99" /> </Context>
For fish.xml:
<Context docBase="C:\bob\projects\fish" reloadable="true"> <Resource name="jdbc/fish" auth="Container" type="javax.sql.DataSource" username="bob" password="****" driverClassName="com.mysql.jdbc.Driver" url="jdbc:mysql://localhost:3306/fish?useServerPrepStmts=false" maxActive="10" maxIdle="5" /> <Resource name="jdbc/fish_translation" auth="Container" type="javax.sql.DataSource" username="bob" password="****" driverClassName="com.mysql.jdbc.Driver" url="jdbc:mysql://localhost:3306/fish_translation" maxActive="10" maxIdle="5" /> <Resource name="jdbc/fish_access" auth="Container" type="javax.sql.DataSource" username="bob" password="****" driverClassName="com.mysql.jdbc.Driver" url="jdbc:mysql://localhost:3306/fish_access" maxActive="10" maxIdle="5" /> <Realm className="org.apache.catalina.realm.JDBCRealm" connectionURL="jdbc:mysql://localhost:3306/fish_access" digest="SHA-1" driverName="com.mysql.jdbc.Driver" roleNameCol="Role" userCredCol="Password" userNameCol="Name" userRoleTable="UserRole" userTable="Users" connectionName="bob" connectionPassword="****" debug="99" /> </Context>
After the above edits are saved, simply copy the context file into the directory named
[TOMCAT_HOME]\conf\Catalina\localhost\
If the above directory doesn't exist, then just create it. If Tomcat is running, then it will deploy the application.
For purposes of comparison, example log files are included, under [APP_HOME]. A successful launch will end with the time it has taken to initialize the app (usually about a second). If you see such a message, then congratulations, you have launched the example application successfully. Hallelujah!
To test the JSP taglib configuration, a simple test page has been provided, called TestTags.jsp. It's located in the root of the web app. Example URLs:
http://localhost:8080/predict/TestTags.jsp http://localhost:8080/fish/TestTags.jsp
http://localhost:8080/predict/ http://localhost:8080/fish/
Predictions will let you view some pages, without needing to login in immediately (in the style of most public web apps). Fish and Chips Club, on the other hand, forces you to login in immediately (in the style of most intranet apps).
Either way, you can log in with user name 'testeD', and password 'testtest'.
It's important that you understand the mechanics of the login mechanism, so that you don't bookmark the wrong item. That is, you're not supposed to bookmark the login page itself. It's natural to find this confusing. Rather, you're supposed to bookmark the home page (or some other page you are interested in). Then, when you navigate to that bookmark, and you're already logged in, then you won't be bothered with a second, unnecessary login. But, if you are not logged in, then a security-constraint defined in web.xml which protects that URL will be activated, and you will be asked to provide a user name and password in the usual way.
This kind of behavior is defined by the servlet specification's form-based login mechanism. Once you understand this mechanism, you can see that attempting to bookmark the Login.jsp page itself does not make sense: after successful login, Tomcat would not know where you 'really' wanted to go.
The Predictions example app is pretty simple.
The Fish and Chips example app has distinct modules. Users can access the various modules only if they have been assigned the proper role. (The user name mentioned in the previous section has wide open permissions.) Here are the links to the main page in each module. These links are valid for the default Tomcat port 8080, and with 'fish' as the context path. Please amend as needed.
The startup time is short - usually under a second. When you have configured Tomcat's <Context> as described above, where the context is mapped directly to the source code root directory, then you can see your changes reflected quickly, without an extended waiting period.
You can also use the WEB4J Developer Tools to speed up your development. (The Log Viewer is particularly useful, but the other tools are nothing to get excited about.)
In the beginning, adding a new user will seem unnecessarily painful. There is some inconvenience, but there's a reason for the inconvenience. The whole idea of an example application is to mimic what a 'real' application might do.
To add a new user, navigate to the Access Control module:
http://localhost:8080/fish/access/user/UserAction.list
Login as 'testeD', as described above. (This user has wide privileges.)
You add a new user in two steps:
When a new user is added, they always receive the default password
'changemetosomethingalotmoreconvenienttotype'This password is intentionally inconvenient, so that the user will be motivated to change it. After login, any user can change their password at any time by navigating to the Preferences screen. (This is simply an example of a particular password policy. Many others are possible.)
Tomcat Manager requires login. You need to add an entry to [TOMCAT_HOME]\conf\tomcat-users.xml, such that a user has the role of 'manager'. Here is an example entry:
<?xml version='1.0' encoding='utf-8'?> <tomcat-users> <role rolename="manager"/> <user username="blah" password="blah" roles="manager"/> </tomcat-users>The tool is accessed using :
http://localhost:8080/manager/html/list