48
Guy Bowerman IBM Information Management Session: I10 Wed, October 4, 2006 • 11:00 a.m. – 12:00 a.m. Platform: Informix Java and IDS: Part 2 - JSP

Guy Bowerman IBM Information Management Session: I10 Wed, October 4, 2006 11:00 a.m. – 12:00 a.m. Platform: Informix Java and IDS: Part 2 - JSP

Embed Size (px)

Citation preview

Guy BowermanIBM Information Management

Session: I10

Wed, October 4, 2006 • 11:00 a.m. – 12:00 a.m.

Platform: Informix

Java and IDS: Part 2 - JSP

2

Agenda

• JSP vs. PHP vs. ASP vs. ???

• Configuring Apache Tomcat 5.x for IDS

• JSP Example – Simple Select

• Authentication & Sessions

• Pagination – Cursor-less cursors

• Inserting & Streaming Byte Data

• JSP Connection Pool

• AJAX Made Simple

3

JSP vs. PHP vs. ASP vs. ???

• JSP• Variety of ready-made libraries, beans• Platform independence• Reliance on JVM

• PHP • Scalability• Increasing popularity

• ASP• Limited to VBScript/COM• Windows or Windows• Browser incompatibilities

• Consider Tapestry/Cocoon vs. Rails etc…

4

Apache Tomcat 5.x & Informix JDBC

Configuration Install Tomcat Copy ifx*.jar to $CATALINA_HOME/common/lib/ Restart Tomcat – Done!

Create new applications under $CATALINA_HOME/webapps/.

Create a WEB-INF directory in application dir, e.g:

$CATALINA_HOME/webapps/jspdemo/WEB-INF

5

JSP Application Directory Layout

• *.html, *.jsp, etc..

• /WEB-INF/web.xml

• Web Application Deployment Descriptor• /WEB-INF/classes/

• Java class files required by application.• /WEB-INF/lib/

• JAR files used by application.

6

JSP Example – Simple Select

$CATALINA_HOME/webapps/jspdemo/demo1.jsp:

<%@ page import="java.sql.*" errorPage="error.jsp"%>

<head> <title>JSP Demo 1</title> </head>

<body> <ul> <h3>Customers by city</h3><br/> <% // initialize Informix JDBC driver Class.forName("com.informix.jdbc.IfxDriver"); ….

7

Connect and Create Statement

… // connection URL String url = "jdbc:informixsqli://mymachine:1526/stores_demo” + “:INFORMIXSERVER=ol_myserver";

// get database connection Connection conn = DriverManager.getConnection(url, "informix", “mypasswd");

// create statement and execute query Statement stmt = conn.createStatement(); ResultSet rs = stmt.executeQuery( "select city, company from customer order by 1,2");%>…

8

JSP Example – Display Results

<table border=1><% // process result set while (rs.next()) { %> <tr> <td><b><%=rs.getString(1)%></b></td> <td><%=rs.getString(2)%></td> </tr><% } %></table>

9

JSP Example – Close Objects

<% // close ResultSet and Statement objectsrs.close();stmt.close();

// close connectionconn.close(); %></ul></body>

10

Error Handlingerror.jsp:<%@ page language="java" isErrorPage="true"%><head><title>An error has occurred</title></head><body>

<center><h1>Oops</h1> </center><br></br><ul> <font size=+1>Something bad happened...<br></br> <ul> <font color="red"><%=exception.toString()%></font> </ul><br>Try to stay calm, I'm sure there is a rational explanation.</br></font></ul>

</body>

11

JSP Example - Output

12

Authentication & Sessions

13

JSP Authentication Options

• Handle your own authentication

• Use a standard Tomcat Realm• JDBCRealm• DataSourceRealm• JNDIRealm (LDAP based authentication)• MemoryRealm (conf/tomcat-users.xml). • JAASRealm

• Implement your own Realm plug-in

14

Implementing a JDBCRealm

• Write a login page

• Write a login error page

• Create a user table

• Create a user roles table

• Add a Realm definition to server.xml

• Add security-constraint, login-config and security-role definitions to WEB-INF/web.xml

15

Tomcat Realm login page

<head><title>Authentication Page</title></head><body><center><h2>Please log in to view the customer database</h2><br/><br/><form method="POST" action="j_security_check"> <table><tr><td>Username: <input type="text" size="15" maxlength="32"

name="j_username"> </td></tr><tr><td> Password: <input type="password" size="15" maxlength="32"

name="j_password"> </td></tr><tr> <td><input value="Login" type="submit">&nbsp;&nbsp;&nbsp; <input value="Clear" type="reset"></td> </tr></table></form></center></body>

16

Tomcat Realm Login Error Page

<head><title>Authentication Error!</title></head><body><center><h1>Access Denied!</h1><br/><br/><a href="javascript:history.back(1)">Tryagain?</a></center>

</body>

17

JDBCRealm User Tables

Make sure your database is logged!

create table users(username varchar(32) unique, password varchar(32)); create table roles(username varchar(32), rolename varchar(32));insert into users values("guyb", "test");insert into users values("user2", "test2");insert into roles values("guyb", "admin");insert into roles values("guyb", "manager");insert into roles values("user2", "custAdmin");

18

Define JDBCRealm in conf/server.xml

<!-- Comment out the old Realm definition -->

<Realm className="org.apache.catalina.realm.JDBCRealm" driverName="com.informix.jdbc.IfxDriver" connectionURL= "jdbc:informixsqli://mymachine:1526/stores_demo:INFORMIXSERVER=ol_myserver"; connectionName="informix" connectionPassword="mypasswd"

userTable="users" userNameCol="username" userCredCol="password"

userRoleTable="roles" roleNameCol="rolename"/>

19

Add security-constraint to WEB-INF/web.xml

<security-constraint><web-resource-collection><web-resource-name>Authorization Test</web-resource-name><description>custAdmin role</description><url-pattern>/*</url-pattern><http-method>GET</http-method><http-method>POST</http-method><http-method>PUT</http-method><http-method>DELETE</http-method></web-resource-collection><auth-constraint> <description>These roles allowed</description> <role-name>custAdmin</role-name></auth-constraint>

</security-constraint>

20

Add login-config and security-role to web.xml

<login-config><auth-method>FORM</auth-method><realm-name>Protected Area</realm-name><form-login-config> <form-login-page>/login.jsp</form-login-page> <form-error-page>/loginerror.jsp</form-error-page>

</form-login-config></login-config>

<security-role><description>custAdmin role only</description><role-name>custAdmin</role-name>

</security-role>

21

Session Management

• Once logged in, access user name with request.getUserPrincipal().getName(), e.g.

<h3>Hello <%=request.getUserPrincipal().getName()%></h3>

• Tomcat provides a “session” object, e.g.

session.setAttribute("userName“, request.getUserPrincipal().getName());

session.setAttribute("loggedIn", "1");

if (session.getAttribute("loggedIn“).equals("1") { … }

22

Pagination – Cursor-less Cursors

23

Pagination

Problem

• Display output in pages, 10 rows at a time, with next and previous buttons.

Solution

• Use the IDS 10.0 SELECT SKIP offset option with FIRST e.g.select SKIP 20 FIRST 10 col1, col2 from tab1

• Keep a count of rows and pass the count as a parameter to the JSP program. Use parameter to dynamically generate the next SKIP value

24

Uploading and Downloading Binary Files

25

Inserting Binary Files

Problem

• Insert binary files from a browser into an Informix database

Solution

• Use the Jakarta Commons FileUpload Package with the PreparedStatement.setBinaryStream() Method

26

Inserting Binary File – HTML Upload Form

<form action="docupload.jsp" method="post" enctype="multipart/form-data">

<input type="file" name="docfile"/><input type="submit" name="Action" value="Upload"/>

</form>

27

Inserting Binary File – Get FileInputStream<%@ page import="org.apache.commons.fileupload.*, java.io.*

%> DiskFileUpload dfu = new DiskFileUpload();

List fileItems = dfu.parseRequest(request);Iterator itr = fileItems.iterator();FileInputStream docstream = null;

dfu.setSizeMax(10000000); // throw exception if > 10 Mb while(itr.hasNext()) { FileItem fi = (FileItem) itr.next(); if (!fi.isFormField()) { // only process files here, not form

fields docfilename = fi.getName();

docsize = fi.getSize(); docstream = (FileInputStream) fi.getInputStream(); }

28

Inserting Binary File – Insert into Table

if (docsize > 0) { // insert into document table

String sqlStr = "insert into document values("'" + docfilename + "',?)“

PreparedStatement pstmt = conn.prepareStatement(sqlStr);

pstmt.setBinaryStream(1, docstream, (int) docsize); pstmt.executeUpdate(); pstmt.close();}

29

Downloading Binary Files

Problem

• Select a binary file from a database and stream it to the browser

Solution

• Set content type to APPLICATION/OCTET-STREAM

• Use the ResultSet.getBinaryStream() method

30

Downloading Binary Files

<%@ page import="java.sql.*, java.io.*, " errorPage="error.jsp"%><% // Important – do not print linefeeds or text before streaming file..… String sqlStr = "select docdata from document where filename = "

+ docfilename;ResultSet rs = stmt.executeQuery(sqlStr);rs.next();

// set content typeresponse.setContentType("APPLICATION/OCTET-STREAM");response.setHeader("Content-Disposition", "attachment; filename=\"" + filename + "\"");

FileInputStream fileData = (FileInputStream) rs.getBinaryStream(1);

// stream file to browserwhile ((i = fileData.read()) != -1) out.write(i);out.close();

%>

31

JSP Connection Pools

• JSP applications can be slowed down by frequent connects/disconnects

• Apache Tomcat comes with Jakarta Commons Database Connection Pool (commons-dbcp)

• Straightforward to configure and use for most database systems

32

Creating an Informix JSP Connection Pool

• Add a Context entry to conf/server.xml

• Add a Resource reference to WEB-INF/web.xml

• In application initialize Context and get DataSource from Context.

• Get Connection object from DataSource

33

Connection Pool Example – Server.xml

Add Context entry to $CATALINA_HOME/conf/server.xml…

<Context path="/jspdemo" docBase=“jspdemo" debug="0" reloadable="true" crossContext="true"> <Resource name="jdbc/jspdemo" auth="Container" type="javax.sql.DataSource" maxActive="20" maxIdle="10" maxWait="1000" username="informix" password=“mypasswd" driverClassName="com.informix.jdbc.IfxDriver“ url="jdbc:informix-sqli://mymachine:1526/stores_demo:INFORMIXSERVER=ol_myserver"/>

</Context>….

</Host>

34

Connection Pool Example – Web.xml

Add Resource reference to: $CATALINA_HOME/webapps/myapp/WEB-INF/web.xml

<?xml version="1.0" encoding="ISO-8859-1"?><web-app xmlns=http://java.sun.com/xml/ns/j2ee xmlns:xsi=http://www.w3.org/2001/XMLSchema-instance xsi:schemaLocation=http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd version="2.4">

<resource-ref> <description>Informix Datasource example</description> <res-ref-name>jdbc/jspdemo</res-ref-name> <res-type>javax.sql.DataSource</res-type> <res-auth>Container</res-auth></resource-ref>

</web-app>

35

Connection Pool – Application Changes

<%@ page import="java.sql.*,javax.naming.*,javax.sql.*" errorPage="error.jsp"%>

…<%

// get database connectionContext initContext = new InitialContext();Context envContext = (Context) initContext.lookup("java:/comp/env");DataSource ds = (DataSource) envContext.lookup("jdbc/jspdemo");Connection conn = ds.getConnection();// replaces:// Connection conn = DriverManager.getConnection(url, user, passwd);…

36

What is AJAX?

• Asynchronous JavaScript and XML

• Dynamically update parts of an HTML page by means of JavaScript calls to server routines

37

AJAX Made Simple

38

AJAX Components

• JavaScript function to call server routine via a browser independent XMLHttpRequest object

• JavaScript processResponse() function to handle response from server and update page

• Server routine to display updated data

39

AJAX Example – Triggering the Update

Give an ID to the section of the page to update – in this case anHTML table column – the AJAX update is triggered here by movingthe mouse over the column (onMouseOver)

<tr> <td><b><%=city%></b></td> <td id="customer<%=custno%>"> <a href="javascript:custContact(<%=custno%>)" onMouseOver="javascript:custContact(<%=custno%>)">

<%=company%></a> </td> </tr>

40

AJAX Example – XMLHttpRequest Object

<script language="Javascript" type="text/javascript"><!--function createRequestObject() { // return appropriate request object for browser (Mozilla/IE) if (window.ActiveXObject) return new

ActiveXObject("Microsoft.XMLHTTP"); else return new XMLHttpRequest();}

var xmlHttp = createRequestObject();

41

AJAX Example – Call Server Routines

var elementId = ''; // AJAX call to display contact details for a customer

function custContact(cust) { elementId = 'customer' + cust; xmlHttp.open('get', 'ccity_serv.jsp?cust=' + cust); xmlHttp.onreadystatechange = processResponse; xmlHttp.send(null);}

// AJAX call to revert display to company namefunction closeContact(cust) { elementId = 'customer' + cust; xmlHttp.open('get', 'ccity_serv.jsp?closeCust=' + cust); xmlHttp.onreadystatechange = processResponse; xmlHttp.send(null);}

42

AJAX Example – Process Response

// set ID tag to output from AJAX requestfunction processResponse() { if (xmlHttp.readyState == 4) { if (xmlHttp.status == 200) document.getElementById(elementId).innerHTML =

xmlHttp.responseText; else document.getElementById(elementId).innerHTML = '<font color="red">Error: ' + xmlHttp.status + '</font>'; }}

--></script>

43

AJAX Example – Server Routines

The server routines only display the HTML required to update

the section of the page specified by the ID tag..

String cust = request.getParameter("cust"),

closeCust = request.getParameter("closeCust");

if (cust != null) {

… // execute select stmt to get contact details and display a table

}

else if (closeCust != null) {…// execute select stmt to get company name and display it

}

44

AJAX Server Routine - Cust

if (cust != null) { rs = stmt.executeQuery("select fname, lname, company, " + " address1, address2, city, state, zipcode from customer where " + "customer_num = " + cust); rs.next(); String comp = rs.getString("company").trim();%> <table><tr><td> <table border=1><tr><td bgcolor="pink"><font size=+1> <%=rs.getString("fname")%> <%=rs.getString("lname").trim()

%>,<br/> <%=comp%>,<br/> <%=rs.getString("address1").trim()%>,<br/> …

45

AJAX Server Routine - Cust

<% if (rs.getString("address2") != null) {%> <%=rs.getString("address2").trim()%>,<br/><% } %> <%=rs.getString("city")%><%=rs.getString("state")%> <%=rs.getString("zipcode")%></font> </td></tr></table></td><td> <a href="javascript:closeContact(<%=cust%>)" onMouseOver="javascript:closeContact(<%=cust%>)">

Close</a></td></tr> </table><%

}

46

AJAX Server Routine - closeCust

// re-display the original HTML showing customer name else if (closeCust != null) { rs = stmt.executeQuery("select company from customer where "

+ "customer_num = " + closeCust); rs.next(); String comp = rs.getString("company").trim();%> <a href="javascript:custContact(<%=closeCust%>)" onMouseOver="javascript:custContact(<%=closeCust%>)">

<%=comp%></a><% }

47

Questions

48

Guy BowermanIBM Information Management

[email protected]

Session I10Java and IDS: Part 2 - JSP