Sunday, December 26, 2010

Tomcat Oracle JDBC Connection using JNDI Resource

This post will cover connecting your Tomcat web application to Oracle via JDBC using Tomcat's JNDI emulation ability.

We'll be creating this example using Tomcat 6.0.29 on CentOS 5.5

In our example, we'll create a connection for an application in the Tomcat/webapps/ROOT directory.

We'll also do the same for an application in a directory other than ROOT (e.g. Tomcat/webapps/myapp).

In our examples below, I have installed Tomcat at /usr/share/apache-tomcat-6.0.29.

Adjust this to your Tomcat installation as required.

First, let's create a simple test table in Oracle.

CREATE TABLE  DEMO_CUSTOMERS 
   (    CUSTOMER_ID NUMBER, 
    CUST_FIRST_NAME VARCHAR2(20), 
    CUST_LAST_NAME VARCHAR2(20) 
    
   )

Now, let's populate it with some data.

INSERT INTO DEMO_CUSTOMERS VALUES (1, 'John ', 'Dulles');
INSERT INTO DEMO_CUSTOMERS VALUES (2, 'William ', 'Hartsfield');
INSERT INTO DEMO_CUSTOMERS VALUES (3, 'Edward', 'Logan');
INSERT INTO DEMO_CUSTOMERS VALUES (4, 'Edward "Butch"', 'OHAare');
INSERT INTO DEMO_CUSTOMERS VALUES (5, 'Fiorello', 'Lambert');
INSERT INTO DEMO_CUSTOMERS VALUES (6, 'Albert', 'Hartsfield');
INSERT INTO DEMO_CUSTOMERS VALUES (7, 'Eugene', 'Bradley');


1. Download the required drivers

You will need to download the required Oracle JDBC drivers from the OTN

Both ojdbc6.jar and ojdbc14.jar will work for this example.

Additionally, since I will be using JSP Standard Tag Library (or JSTL), I will also need to download standard.jar and jstl.jar, which you can download here.


2. Move the drivers above to: /usr/share/apache-tomcat-6.0.29/lib

[root@sv2 ~]# mv ojdbc14.jar /usr/share/apache-tomcat-6.0.29/lib/ojdbc14.jar
[root@sv2 ~]# mv standard.jar /usr/share/apache-tomcat-6.0.29/lib/standard.jar
[root@sv2 ~]# mv jstl.jar /usr/share/apache-tomcat-6.0.29/lib/jstl.jar

By placing the drivers in the TOMCAT_HOME/lib directory, we are making them available to all applications.

3. Create the JDBC JNDI resource for our default context 

Since we are using the ROOT directory, we will be using /usr/share/apache-tomcat-6.0.29/conf/context.xml.

Add the following:

<Resource name="jdbc/oradb"
          auth="Container"
          type="javax.sql.DataSource"
          driverClassName="oracle.jdbc.OracleDriver"
          url="jdbc:oracle:thin:@host:1521:sid"
          username="username"
          password="password"
          maxActive="20"
          maxIdle="30"
          maxWait="-1"
/>

Replace the url, username, and password above with your own.

I've used 'oradb' as my resource name. You can use whatever you like.

For an explanation of maxActive, maxIdle, and maxWait, and other attributes, please see the Context Configuration section of the Tomcat JNDI Datasource HOW-TO


4. Add a Resource-Ref to our web.xml file. 

Again, we are using the ROOT directory so we'll add our resource-ref to /usr/share/apache-tomcat-6.0.29/webapps/ROOT/WEB-INF/web.xml


jdbc/oradb
javax.sql.DataSource
Container

5. Create a JSP page to test our set up. 

I'll call the file mytest.jsp and place it into the ROOT directory (/usr/share/apache-tomcat-6.0.29/webapps/ROOT)


<%@ taglib uri="http://java.sun.com/jsp/jstl/sql" prefix="sql" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>

  <html>
  <head>

    
       select * from DEMO_CUSTOMERS
    

  </head>
  <body>
    <h1>Testing JDBC JINDI Oracle</h1>
    <table width='500' border='1'>
      <tr>
        <th align='left'>Customer Id</th>
        <th align='left'>Customer First Name</th>
        <th align='left'>Customer Last Name</th>
      </tr>
      <c:forEach var="democusts" items="${democusts.rows}">
        <tr>
           <td> ${democusts.CUSTOMER_ID}</td>
           <td> ${democusts.CUST_FIRST_NAME} </td>
           <td> ${democusts.CUST_LAST_NAME} </td>
       </tr>
      </c:forEach>
    </table>
  </body>
  </html>


Now start (or restart) Tomcat to allow it to read the changes to our configuration files

[root@sv2 ~]# service tomcat start
Using CATALINA_BASE:   /usr/share/apache-tomcat-6.0.29
Using CATALINA_HOME:   /usr/share/apache-tomcat-6.0.29
Using CATALINA_TMPDIR: /usr/share/apache-tomcat-6.0.29/temp
Using JRE_HOME:        /usr/java/jdk1.6.0_23
Using CLASSPATH:       /usr/share/apache-tomcat-6.0.29/bin/bootstrap.jar 


We can now navigate to http://YourDomain.com:8080/mytest.jsp and we should see the following:




6. Locations when using directory outside of ROOT. 

If you web application does not live in the ROOT directory, you can apply the above to using the following locations within your application.

For an application called "MyApp", for example, you could use the following locations.

JDBC JNDI Resource: Webapps>MyApp>META-INF/context.xml

Resource-Ref: Webapps>MyApp>WEB-INF/web.xml

Drivers: Webapps>MyApp>WEB-INF/lib/{ojdbc14.jar, standard.jar, jstl.jar}

If any of the directories or files above do not exist, you will need to create them.

Again, you can leave the drivers under Tomcat/lib if you want them to be available to all applications.


For more information, see Apache Tomcat JNDI Datasource HOW-TO


Related Posts:
Install Tomcat 6 on CentOS
Tomcat Manager Password
Tomcat Custom 404 Page

Thursday, December 23, 2010

Install GlassFish 3 on CentOS

This post will cover installing GlassFish 3.0.1 on CentOS 5.x.

We'll also see how to run GlassFish as a service, how to access the Admin Console, and how to run GlassFish under a minimally privileged user.

GlassFish 3.0.1 is available two editions.

GlassFish Server Open Source Edition 3.0.1 (free) and Oracle GlassFish Server 3.0.1 (supported and requires paid subscription).

I installed both using the same process below on CentOS 5.5.

This post is intended to get a basic installation of GlassFish 3.0.1 up and running. Please consult the documentation.

If you do not already have the Java Development Kit (JDK) installed on your machine, you will need to download and install the required JDK for your platform.

If you do have the JDK installed, you can skip to: Step 2: Download and Install the GlassFish 3.0.1 Server:


Step 1: Install the JDK

You can download the JDK here: http://www.oracle.com/technetwork/java/javase/downloads/index.html

I'm using the latest, which is JDK 6, update 24. The JDK is specific to 32 and 64 bit versions.

My CentOS box is 64 bit, so I'll need: jdk-6u24-linux-x64.bin.

If you are on 32 bit, you'll need: jdk-6u24-linux-i586.bin

Download the appropriate JDK and save it to a directory. I'm saving it to /root.

Move (mv) or copy (cp) the file to the /opt directory:

[root@sv2 ~]# mv jdk-6u24-linux-x64.bin /opt/jdk-6u24-linux-x64.bin

Create the directory /usr/java.

[root@sv2 ~]# mkdir /usr/java

Change to the /usr/java directory we created and install the JDK using 'sh /opt/jdk-6u24-linux-x64.bin'

[root@sv2 ~]# cd /usr/java
[root@sv2 java]# sh /opt/jdk-6u24-linux-x64.bin


Set the JAVA_HOME path. This is where we installed the JDK above.

To do this for your current session, you can issue the following:

[root@sv2 java]# JAVA_HOME=/usr/java/jdk1.6.0_24
[root@sv2 java]# export JAVA_HOME
[root@sv2 java]# PATH=$JAVA_HOME/bin:$PATH
[root@sv2 java]# export PATH

To set the JAVA_HOME for users, we add this to the user ~/.bashrc or ~/.bash_profile of the user. We can also add it /etc/profile and then source it to give to all users.

JAVA_HOME=/usr/java/jdk1.6.0_24 
export JAVA_HOME 
PATH=$JAVA_HOME/bin:$PATH 
export PATH

Once you have added the above to ~/.bash_profile or ~/.bashrc, you should log out, then log back in and check that the JAVA_HOME is set correctly.

[root@sv2 ~]#  echo $JAVA_HOME
/usr/java/jdk1.6.0_24



Step 2: Download and Install the GlassFish 3.0.1 Server:

You can download both the GlassFish Server Open Source Edition 3.0.1 and Oracle GlassFish Server 3.0.1 at http://glassfish.java.net/

Once you have downloaded the desired file, move (mv) or copy (cp) the file to /usr/share/glassfish-3.0.1.zip (or /usr/share/ogs-3.0.1.zip for Oracle GlassFish).

[root@sv2 ~]# mv glassfish-3.0.1.zip /usr/share/glassfish-3.0.1.zip

Change to the /usr/share directory and unzip the file:

[root@sv2 ~]# cd /usr/share
[root@sv2 share]# unzip -q glassfish-3.0.1.zip

The unzip will create the following directory: /usr/share/glassfishv3

Note: Both GlassFish editions will create the same directory when unzipped: glassfishv3

At this point, we should be able to start and stop GlassFish using:

/usr/share/glassfishv3/glassfish/bin/asadmin start-domain domain1

and

/usr/share/glassfishv3/glassfish/bin/asadmin stop-domain domain1

Start GlassFish:

[root@sv2 share]# /usr/share/glassfishv3/glassfish/bin/asadmin start-domain domain1
Waiting for DAS to start ...
Started domain: domain1
Domain location: /usr/share/glassfishv3/glassfish/domains/domain1
Log file: /usr/share/glassfishv3/glassfish/domains/domain1/logs/server.log
Admin port for the domain: 4848
Command start-domain executed successfully.
[root@sv2 share]#

Stop GlassFish:

[root@sv2 share]# /usr/share/glassfishv3/glassfish/bin/asadmin stop-domain domain1
Waiting for the domain to stop ....
Command stop-domain executed successfully.
[root@sv2 share]#

Note: If you did not set the JAVA_HOME and PATH for the user you are logged in as, or for your current session, when you attempt to start the GlassFish server it will complain it cannot find Java with the following:

error: /usr/share/glassfishv3/glassfish/bin/asadmin: line 19: exec: java: not found



Step 3: Running GlassFish as a Service.

To run GlassFish as a service and enable start up at boot, we'll now create a Start/Stop/Restart script.

We'll create the script as /etc/init.d/glassfish, make the script executable, and then add our new glassfish service to chkconfig.

Create our glassfish script:

[root@sv2 ~]# cd /etc/init.d
[root@sv2 init.d]# vi glassfish

#!/bin/bash
# description: Glassfish Start Stop Restart
# processname: glassfish
# chkconfig: 234 20 80
JAVA_HOME=/usr/java/jdk1.6.0_24
export JAVA_HOME
PATH=$JAVA_HOME/bin:$PATH
export PATH
GLASSFISH_HOME=/usr/share/glassfishv3/glassfish

case $1 in
start)
sh $GLASSFISH_HOME/bin/asadmin start-domain domain1
;;
stop)
sh $GLASSFISH_HOME/bin/asadmin stop-domain domain1
;;
restart)
sh $GLASSFISH_HOME/bin/asadmin stop-domain domain1
sh $GLASSFISH_HOME/bin/asadmin start-domain domain1
;;
esac
exit 0


If you do not set the JAVA_HOME and PATH in the GlassFish script, when you attempt to start the GlassFish server it will complain it cannot find Java with the following:

error: /usr/share/glassfishv3/glassfish/bin/asadmin: line 19: exec: java: not found

Now, make the script executable and add it to our chkconfig so it starts at boot.

[root@sv2 init.d]# chmod 755 glassfish
[root@sv2 init.d]# chkconfig --add glassfish
[root@sv2 init.d]# chkconfig --level 234 glassfish on


We should now be able to Start, Stop, and Restart GlassFish as a service.

Start GlassFish:

[root@sv2 init.d]# service glassfish start
Waiting for DAS to start .....
Started domain: domain1
Domain location: /usr/share/glassfishv3/glassfish/domains/domain1
Log file: /usr/share/glassfishv3/glassfish/domains/domain1/logs/server.log
Admin port for the domain: 4848
Command start-domain executed successfully.

Stop GlassFish:

[root@sv2 init.d]# service glassfish stop
Waiting for the domain to stop ....
Command stop-domain executed successfully.


Step 4: Access GlassFish Admin Console.

You should now be able to access the GlassFish Admin Console at:

http://yourdomain.com:4848 or http://yourip:4848



On accessing the GlassFish Admin Console for the first time, you will find that no user name or password is required.

Previous to 3.0.1, a default password 'adminadmin' was used.

You can set (or change) the admin password within the GlassFish Admin console.

1. Click "Enterprise Server" on the tree.

2. Click the Administrator Password tab.

3. Enter and confirm your password and click Save.


The first password save will create a file,.asadminpass, in the home directory of the user you are running the service under.

Alternatively, you can set the admin password via the CLI using.

[root@sv2 bin]# $GLASSFISH_HOME/bin/asadmin change-admin-password
Enter admin user name [default: admin]>
Enter admin password>
Enter new admin password>
Enter new admin password again>

Command change-admin-password executed successfully.
[root@sv2 bin]#

Note: to make using the CLI easier, I've added the following lines to my ~/.bashrc (or ~/.bash_profile):

GLASSFISH_HOME=/usr/share/glassfishv3/glassfish
export GLASSFISH_HOME

So your ~/.bashrc or ~/.bash_profile will look like this:

JAVA_HOME=/usr/java/jdk1.6.0_24
export JAVA_HOME
PATH=$JAVA_HOME/bin:$PATH
export PATH
GLASSFISH_HOME=/usr/share/glassfishv3/glassfish
export GLASSFISH_HOME


As you can see above, I can now use $GLASSFISH_HOME rather than the full path of /usr/share/glassfishv3/glassfish.


Step 5: Running GlassFish with Minimally Privileged (non-root) User.


Since I am installing this on my development machine, I am running GlassFish as root above.

In production, you will want to run GlassFish as a non-root user with minimal privileges.

To do this, we can need to the following.

1. Create the user, glassfish, who will own the files.

Create the new group, glassfish, and add the user glassfish to the group:

[root@sv2 ~]# groupadd glassfish
[root@sv2 ~]# useradd -s /bin/bash -g glassfish glassfish


2. Change ownership of the GlassFish files to the user glassfish we created.

We'll change ownership of the files under /usr/share/glassfishv3 from root to the user glassfish we created above:

[root@sv2 ~]# chown -Rf glassfish.glassfish /usr/share/glassfishv3/


3. Update our glassfish script.

Finally, we update the glassfish start/stop/restart script we created above so we su to user glassfish:

#!bin/bash
# description: Glassfish Start Stop Restart
# processname: glassfish
# chkconfig: 234 20 80
JAVA_HOME=/usr/java/jdk1.6.0_24
export JAVA_HOME
PATH=$JAVA_HOME/bin:$PATH
export PATH
GLASSFISH_HOME=/usr/share/glassfishv3/glassfish
GLASSFISH_USER=glassfish

case $1 in
start)
su $GLASSFISH_USER -c "$GLASSFISH_HOME/bin/asadmin start-domain domain1"
;;
stop)
su $GLASSFISH_USER -c "$GLASSFISH_HOME/bin/asadmin stop-domain domain1"
;;
restart)
su $GLASSFISH_USER -c "$GLASSFISH_HOME/bin/asadmin stop-domain domain1"
su $GLASSFISH_USER -c "$GLASSFISH_HOME/bin/asadmin start-domain domain1"
;;
esac
exit 0


Step 6: Running GlassFish on Port 80 as Non-Root User.

To run services below port 1024 as user other than root, you will need to use port forwarding.

You can do this by adding the following to your IP tables:

[root@sv2 ~]# iptables -t nat -A PREROUTING -p tcp -m tcp --dport 80 -j REDIRECT --to-ports 8080
[root@sv2 ~]# iptables -t nat -A PREROUTING -p udp -m udp --dport 80 -j REDIRECT --to-ports 8080


Note: GlassFish 3.1 has now been released. For GlassFish 3.1 installation, you can view my tutorial here:
http://www.davidghedini.com/pg/entry/install_glassfish_3_1_on
It is basically the same procedure as GlassFish 3.0.1, with some minor changes.


GlassFish Quick Start Guide

http://glassfish.java.net/

Oracle GlassFish Docs