Você está na página 1de 30

Use Apache Derby in your OpenLaszlo

applications, Part 2: Storing and embedding data


Skill Level: Intermediate

Tyler Anderson (tyleranderson5@yahoo.com)


Freelance Writer
Stexar Corp.

25 Apr 2006

Since OpenLaszlo's open source announcement, many developers have been using
OpenLaszlo to create user-friendly rich Internet applications. Many of these
applications require a database solution to have dynamic data fed to them. Because
OpenLaszlo runs on Apache Tomcat by default, which supports JavaServer Pages
(JSP) and Java™ servlets, Apache Derby is an excellent database to use; it can be
embedded in Java applications since it's pure Java. In this tutorial, you'll build a
management interface to the online shopping console created in Part 1. You'll also
allow orders to be written to the database and enable management to edit, delete,
and add new items to the database via the OpenLaszlo user interface (UI).

Section 1. Before you start


Learn how rich UIs built with OpenLaszlo can use Apache Derby as their back-end
database. The OpenLaszlo LZX markup language can use scripts written in several
different languages to source the data used within OpenLaszlo applications. This
tutorial focuses on the use of JSP, a standard Java-based scripting language
supported by the out-of-the-box distribution of the OpenLaszlo application server.
You'll test the system on the standard OpenLaszlo environment that includes
OpenLaszlo running on Apache Tomcat with the Derby database being accessed via
the Derby Network Server.

About this series


This two-part tutorial series documents the steps of how to build an OpenLaszlo
application with Apache Derby as the back-end database. You use an example
application -- an online grocery store that home consumers can connect to and order
items from -- which exemplifies the strengths of using Derby in such a situation. The

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 1 of 30
developerWorks® ibm.com/developerWorks

grocery store's employees can look up existing orders and modify stock. Derby is
important here, because it's used to supply items for display to home consumers
browsing the online grocery store and to update the stock count of purchased items.
When the Derby database is updated with more stock or more items, the results are
reflected in the online storefront built using OpenLaszlo.

Part 1 focused on reading a Derby database to feed data into an OpenLaszlo


application. This installment extends the example application by adding a manager's
interface into the storefront to enable an online store's employee to update stock and
add or remove items. Ultimately, you'll learn how to insert, update, and delete data
from the Derby database using the OpenLaszlo markup language. Finally, you'll
deploy the OpenLaszlo Web application on Tomcat, completing the example.

About this tutorial


In this tutorial, you'll extend the application created in Part 1 by adding the ability to
write data back to Derby. Now you'll save orders made from Part 1 in the database,
making the order visible to the grocery store's employees. Thus, the employees will
be able to look up current orders and modify stock as well as add, edit, and delete
items.

System requirements
You need the following tools to follow along with this tutorial:

OpenLaszlo -- This tutorial uses the latest version of OpenLaszlo, version 3.1.
Download OpenLaszlo 3.1, and get installation instructions for your operating
system.

Apache Derby -- Download Apache Derby, ensuring that the .jar files you receive
are added to your CLASSPATH.

IBM DB2® drivers -- Download IBM Cloudscape™ (IBM DB2 JDBC Universal
Driver, for Cloudscape/Derby) to connect to Derby. Make sure to add the drivers to
your CLASSPATH.

Java SDK -- OpenLaszlo, Apache Derby, and the DB2 drivers require the Java
platform. This tutorial uses Java 1.4.2_09; however, any version later than this
should suffice. Download the Java SDK from Sun Microsystems.

This tutorial was written on a Microsoft® Windows® operating system, but the
differences should be minimal, if any, if you're using a different operating system,
such as Linux®.

Storing and embedding data


Page 2 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

Section 2. Overview
Now that you've conquered Part 1 of this series, you're ready to take on Part 2. In
this tutorial, the database needs some changes and a new table.

Modify the database


Since you'll be saving orders in this part of the tutorial series, you need to make a
couple of changes to the database. The first change involves adding a new stock
field to the shoppingitems table. This field holds the quantity of the item on hand and
for sale through the online grocery store.

The next change requires a new table, the shoppingorders table. New orders get
saved in this table via the UI. This table holds four fields: an order ID, the name, the
description, and the price of the product ordered. Next, you'll make these changes
using Derby's ij tool.

Create the orders table


Now you'll recreate the shoppingitems table to incorporate the new changes and
create the new shoppingorders table. Start the ij tool as you did back in Part 1, and
type the following, shown in Listing 1.

Listing 1. Deleting and recreating the shoppingitems table

drop table shoppingitems;


create table shoppingitems (itemid integer not null generated
always as identity
(start with 1, increment by 1),
name varchar(50),
description varchar(255),
price integer,
stock integer);

First you delete the old table so you can recreate it with the new stock field. Now
create the new table, shown in Listing 2.

Listing 2. Creating the shoppingorders table

create table shoppingorders (orderid integer not null generated


always as identity
(start with 1, increment by 1),
name varchar(50),
description varchar(255),
price integer);

This creates the new shoppingorders table. Now when orders get created, you store

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 3 of 30
developerWorks® ibm.com/developerWorks

the name, description, and price information in this table.

Initialize the orders table


To help test your software, you need to initialize the new tables with data. Type the
following, shown in Listing 3, to initialize the shoppingitems table.

Listing 3. Initializing the shoppingitems table

insert into shoppingitems (name, description, price,stock) values


('Bread','Yummy whole wheat bread',3,5),
('Tomato Soup','Expensive tomato soup',10,5),
('Super Watermelon','This is a magical super watermelon. It can feed a million families
because of its mystical powers, hence the large price. Who would not want such a
melon?',23498,5);

On to the shoppingorders table, shown in Listing 4.

Listing 4. Initializing the shoppingorders table

insert into shoppingorders (name, description, price) values


('Bread','Yummy whole wheat bread',3),
('Tomato Soup','Expensive tomato soup',10),
('Super Watermelon','This is a magical super watermelon. It can feed a million families
because of its mystical powers, hence the large price. Who would not want such a
melon?',23498);

With the tables initialized, let's move on to building the application, beginning with
saving orders.

Section 3. Save orders


Back in Part 1, you were able to extract items from a Derby database and display
the items in the grocery store. This time you'll go further and save orders in the
shoppingorders table.

Dynamic queries using REST


Also, in Part 1 the data set was hardcoded, meaning that you couldn't modify the
data returned and resend requests to the JSP script. That'll change now, since you
need to be able to make dynamic requests to send commands to your JSP script
and update the database. In this way, declaring a data set is much simpler, too.
Declare the items data set as follows:

<dataset name="items" />

Storing and embedding data


Page 4 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

You'll use this paramaterless data set to make dynamic requests. Let's move on to
how to prepare and send a request.

Prepare a request
With the data set declared, you're ready to prepare the request and communicate
with your JSP scripts. To do so, create a method, sendRequest, with parameters
that set up the data set and send off the request, as shown in Listing 5.

Listing 5. Creating the sendRequest method

<method name="sendRequest"
args="src, queryType, args"><![CDATA[
Debug.write(
"sendRequest",
"src", src,
"queryType", queryType,
"args", args,
"items", items);
items.setQueryType(queryType);
items.setSrc(src);
items.cacheable = false;
items.setQueryParams(null);
items.setQueryParams(args);
items.doRequest();
]]>
</method>

This method takes three parameters:

• src specifies the URL to the JSP script that you'll make the request to.
• queryType specifies the HTTP request type, either GET or POST. You'll
use both methods in this tutorial; therefore the sendRequest method is
parameterized here.
• args specifies the arguments to pass to the script, which you'll use in
deleting items from the database.

Make the request


When the application first loads, the empty data set needs to be intialized. You'll do
this in the customer storefront as demonstrated in Part 1:

<canvas title="Online Shopping" debug="true"


oninit="query(null)">
The oninit event executes when the canvas is first initialized. You use this method
to send a request to the items.jsp script from Part 1 to retrieve the item data for the
storefront. Create the query method, as shown in Listing 6.

Listing 6. Querying the database

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 5 of 30
developerWorks® ibm.com/developerWorks

<method name="query" args="parameters"><![CDATA[


this.sendRequest(
this.serviceURL,
"GET",
parameters);
]]>
</method>

This method calls the sendRequest method, passing the serviceURL as the URL
to query and fetch the items from the database. Declare the serviceURL attribute,
as shown below:

<attribute name="serviceURL"
type="string"
value="../items.jsp"/>
The prefix ../ refers to the script one directory down, allowing both the customer
and management consoles to access it. That completes the code for querying the
items from the database; however, for easier debugging, you need to hook into the
ondata event for when the items' data set receives its data from the JSP script.
Create the ondata method, as shown in Listing 7.

Listing 7. Creating the ondata event and writing data to the debugger

<method event="ondata" reference="items"><![CDATA[


Debug.write(
"ondata",
"items", items,
"data", items.data);
]]>
</method>

The reference attribute in the method tag specifies which object to hook into
when listening to ondata events. When the data comes back, it'll be written to the
debugger so you can verify correct functionality of your OpenLaszlo application.

Use JavaScript in the request


You'll use JavaScript for getter methods from the file you include that contains the
form for ordering grocery items. You need to create four JavaScript functions for the
client storefront, shown in Listing 8.

Listing 8. Getter methods for retrieving data to send in the request and send
confirmation of a sent order

<script>
...
function getItemid() {
return this.item.getText();
}
function getDesc() {
return this.description.getText();
}
function getPrice() {

Storing and embedding data


Page 6 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

return this.price.getText();
}
function setOrderText() {
this.order.setText('Thank you for your order! It will arrive in 1 to 2 hours.');
}
...
</script>

The first function, getItemid, retrieves the text being displayed in the combobox.
The next one, the getDesc function, retrieves the text in the description, and the
getPrice function retrieves the price. You'll use the setOrderText function to
display a visual confirmation that the Order button was pressed and that the order
request was sent to the database.

Submit the request


To submit orders, you only need to change the function that the Order button
currently references upon firing an onclick method. Modify the Order button as
follows:

<button text="Order" isdefault="true" x="282"


onclick="canvas.submitOrder();"/>
The button now calls submitOrder. The method that formulates the request to
send it to a script will save the order information into the database. Create this
submitOrder method, as shown in Listing 9.

Listing 9. Submitting an order

<method name="submitOrder" ><![CDATA[


Debug.write("SUBMITTING ORDER");
sendRequest(this.submitURL,
"POST",
{"name" : getItemid(),
"desc" : getDesc(),
"price" : getPrice()});
setOrderText();
]]>
</method>

First, you communicate to the debugger window that an order is being submitted.
Then you send the request by calling the sendRequest method, which sends the
submitURL, shown below. Next, you indicate the type of query by sending POST as
the transmission method, due to the obvious side effects of writing to the database.
The arguments you send to the request are the name, description, and price of the
item being ordered.

<attribute name="submitURL"
type="string"
value="submit.jsp"/>

Save the order to the database

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 7 of 30
developerWorks® ibm.com/developerWorks

You now need to write the submit.jsp script that will receive the name, desc, and
price values in the POST request, and write them to the database. That's all it takes
to send a dynamic request via POST to a JSP script to make appropriate database
modifications. With this functionality in place, you'll use your JSP script to write the
passed values to the database. First, however, you need to start the script, shown in
Listing 10.

Listing 10. Saving the submitted order to the database

<%@ page import='java.io.*' %>


<%@ page import='java.util.*' %>
<%@ page import='java.sql.*' %>
<%@ page import='com.ibm.db2.jcc.DB2Driver' %>
<%
if(!request.getParameter("name").equals("") &&
!request.getParameter("desc").equals("") &&
!request.getParameter("price").equals("")){
Driver driver = null;
try {
driver = (Driver)
(DB2Driver.class).newInstance();
} catch(Exception e) {
throw new IllegalArgumentException("Unable to load, " +
"instantiate, or register "+
"driver " + driver +
": "+e.getMessage());
}

First, you import class dependencies, and then you make sure that the needed
parameters to make the request work have been set and passed by your
OpenLaszlo application, as expected. Next, you instantiate the drive and get ready
to make a request. Connect to the database and insert the order into the database,
shown in Listing 11.

Listing 11. Inserting orders into the database

try {
Properties prop = new Properties();
prop.put("user", "shopuser");
prop.put("password", "shoppass");
Connection conn = driver.
connect("jdbc:derby:net://localhost:1527/SHOPPING;",
prop);
String sql = "insert into shoppingorders (name, description,"+
" price) values (?, ?, ?)";
PreparedStatement statement = conn.prepareStatement(sql);
statement.setString(1, request.getParameter("name"));
statement.setString(2, request.getParameter("desc"));
statement.setInt(3, Integer.parseInt
(request.getParameter("price")));
statement.execute();
} catch(Throwable e) {
e.printStackTrace();
System.out.println(e.getMessage());
System.out.println("Error executing query");
}
}
%>
<jsp:forward page="../items.jsp" />

Storing and embedding data


Page 8 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

First, you set up and connect to the database, as you did in Part 1 of this series.
Then you create the SQL that you'll use to insert the row into the database. You set
each of the unknown ? values in the sql String and then execute the query. If an
error occurs, you'll display it in the server output. The last line redirects the page to
the items.jsp page to reload the items data set in case changes have been made.
Figure 1 shows an executed order.

Figure 1. Executing an order

You can see in the debugger shown in Figure 1 that the order was sent out and the
latest database data was returned. In the last two sections of this tutorial you'll
create the manager's interface, starting with viewing orders.

Section 4. View orders


The manager's interface involves creating a tabbed UI, thus allowing the current

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 9 of 30
developerWorks® ibm.com/developerWorks

items on screen to be focused on the current task at hand and causing less
distraction for the employees. In this section you'll create the tabbed layout and learn
how to view placed orders.

Create a tabbed layout


Tabbed layouts are great ways to tidy a UI. Start by creating the three .lzx files you
need for this section of the grocery store: manage.lzx, addEditDeleteItems.lzx, and
viewOrders.lzx. In the last two files, define them as shown:

<form>
</form>
You'll fill them in with more data later. Now start on the manage.lzx file by declaring
its canvas:

<canvas title="Manager's Page" debug="true"


oninit="query(null)">
<include href="lz" />
<simplelayout axis="y"/>
This declaration is nearly identical to the one for the client interface, except that here
you include a dependency for using the tabbed layout. Now declare the orders as a
hardcoded data set that goes directly to the orders.jsp to obtain the current list of
orders, shown here:

<dataset name="orders"
request="true" type="http"
src="orders.jsp"/>
You'll define the orders.jsp script later in this section. Next create the tabbed layout
for your view, as shown in Listing 12.

Listing 12. The title and tabs for creating the tabbed layout

<text fontsize="20">Welcome, Grocery Store Manager!</text>


<menuseparator width="600" height="6"/>
<basetabs x="10" y="10" tabclass="tab">
<basetabpane text="Items">
<include href="addEditDeleteItems.lzx" />
</basetabpane>
<basetabpane text="View Orders">
<include href="viewOrders.lzx" />
</basetabpane>
</basetabs>

First, you create the title and menu separator, followed by the tabbed layout
declaration. You can set the title of a tab using the text attribute in the
basetabpane tag. The contents of each tab are placed inside the
<basetabpane...> </basetabpane> tags where you include the other files that
you've created. Now you need to define the viewOrders.lzx form where you'll be able
to view the currently placed orders in the management UI.

Storing and embedding data


Page 10 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

View orders using a grid layout


This form will display the ordered items in a simple grid. Define the viewOrders.lzx
file, as shown in Listing 13.

Listing 13. Viewing orders

<form>
<simplelayout axis="y"/>
<grid datapath="orders:/shopping" contentdatapath="order">
<gridcolumn showheader="false" width="50">
<view bgcolor="#CCCCCC" width="${parent.width}"
placement="header"
height="${parent.immediateparent.height-1}"/>
<text datapath="position()"/>
</gridcolumn>
<gridcolumn width="200"> Name
<text datapath="@name"/>
</gridcolumn>
<gridcolumn width="200"> Price
<text datapath="@price"/>
</gridcolumn>
</grid>
</form>

This form is shown as a table that displays data contained in the orders data set in
the grid tag. A gridcolumn tag displays a column of data, with the first column
showing line numbers by setting its text attribute's data path to position(). The
next two gridcolumn tags display the name and price values, respectively.
Preview the form, shown in Figure 2.

Figure 2. Viewing the ordered items

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 11 of 30
developerWorks® ibm.com/developerWorks

Next, define the orders.jsp script that returns the ordered item data from the
database.

Gather and format order data


With the form ready and in place, now you just need to define the orders.jsp file to
return order data back to the UI. Use the script shown in Listing 10 and Listing 11 as
a template, since you'll only be modifying the code in between the last catch
statement and the statement creating the Connection object to the database. The
code for retrieving orders from the database is shown in Listing 14.

Listing 14. Querying the database and returning orders

...
String sql = "select * from shoppingorders";
PreparedStatement statement = conn.prepareStatement(sql);

Storing and embedding data


Page 12 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

ResultSet results = statement.executeQuery();


String name, desc, price;
int id = 1;
out.write("<shopping>\n");
while(results.next()){
out.write(" <order ");
name = results.getString("name");
desc = results.getString("description");
price = results.getString("price");
out.write(" id='" + id + "'");
out.write(" name='" + name + "'");
out.write(" description='" + desc + "'");
out.write(" price='" + price + "'");
out.write(" />\n");
id++;
}
out.write("</shopping>\n");
...

Notice here that the ID, name, description, and price attributes need to be
inside the order tag due to the way they are referenced by the grid. Next, in the final
section, you'll complete the management section of the online grocery store
application by implementing code for the items tab.

Section 5. Manage orders


With the tabbed layout in place, your next step is to create the form for the tab that
manages the items stored in the database. Here you'll add functionality to delete,
update or edit, and add new items to the database.

Set up dynamic queries


First you need to add functionality as you did to the customer interface that uses
dynamic queries. This time will be a little different since you have to add in the
stock variable. Create the JavaScript declaration with the getData function inside
it, as shown in Listing 15.

Listing 15. Creating the getData function

<script><![CDATA[
function getData(itemid) {
datapath = 'items:/shopping/item[' + itemid + ']';
this.description.setDatapath(datapath);
this.price.setDatapath(datapath);
this.name.setDatapath(datapath);
this.stock.setDatapath(datapath);
Debug.write(datapath);
}
]]>
</script>

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 13 of 30
developerWorks® ibm.com/developerWorks

This function retrieves the item from the value of the current data set based on the
value passed to it from the combobox object. Next, declare the dataset, shown in
Listing 16.

Listing 16. Declaring the dataset

<dataset name="items" />


<attribute name="itemsURL"
type="string"
value="../items.jsp"/>

Here you also declare the URL from which to retrieve the item data. Next, add the
query method as you did for the customer interface, shown in Listing 17.

Listing 17. Sending a request to retrieve item data

<method name="query" args="parameters"><![CDATA[


this.sendRequest(
this.itemsURL,
"GET",
parameters);
]]>
</method>

Now declare the sendRequest method (see Listing 18).

Listing 18. Creating the sendRequest method

<method name="sendRequest"
args="src, queryType, args"><![CDATA[
Debug.write(
"sendRequest",
"src", src,
"queryType", queryType,
"args", args,
"items", items);
items.setQueryType(queryType);
items.setSrc(src);
items.cacheable = false;
items.setQueryParams(null);
items.setQueryParams(args);
items.doRequest();
]]>
</method>

Like before, this method writes to the debugger the data sent to it, sets the
parameters of the items data set, and sends the request off to the desired URL
contained in the src parameter. Now create the ondata method, shown in Listing
19.

Listing 19. Hooking into the ondata event

<method event="ondata" reference="items"><![CDATA[


Debug.write(
"ondata",
"items", items,

Storing and embedding data


Page 14 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

"data", items.data);
]]>
</method>

This method gets called when the data from the items.doRequest() call in
Listing 18 returns with data. Now you'll create the form for managing the items.

Create the form


The management form will allow you to add, edit, or delete items from the Derby
database -- all from a handy OpenLaszlo UI. Place this form in the
addEditDeleteItems.lzx function, shown in Listing 20.

Listing 20. Creating a form to manage database item data

<form>
<simplelayout axis="y"/>
<view x="50" height="30">
<text text="Add, Edit or Delete Items" fontstyle="bold"
fontsize="17" height="30" />
</view>
<view x="80" height="30">
<text x="0" text="Item:" fontstyle="bold" width="100"/>
<combobox x="100" yoffset="17" defaulttext="Choose an item ..."
width="240" editable="false" id="item" height="17">
<textlistitem datapath="items:/shopping/item"
text="$path{'name/text()'}" id="itemid"
value="$path{'id/text()'}"
onselect="getData(this.getValue())"/>
</combobox>
</view>
<view x="80" height="30">
<text text="Name:" fontstyle="bold" x="0" width="100" height="17"/>
<edittext id="name" x="100" width="240"
text="$path{'name/text()'}"/>
</view>
<view x="80" height="100">
<text text="Description:" fontstyle="bold" x="0" width="100"
height="100"/>
<edittext id="description" x="100" width="240" height="96"
text="$path{'description/text()'}" multiline="true"/>
</view>
<view x="80" height="30">
<text text="Price:" fontstyle="bold" x="0" width="100"
height="17"/>
<edittext id="price" x="100" width="240"
text="$path{'price/text()'}"/>
</view>
<view x="80" height="30">
<text text="Stock:" fontstyle="bold" x="0" width="100"
height="17"/>
<edittext id="stock" x="100" width="240"
text="$path{'stock/text()'}"/>
</view>
<view x="80" height="0">
<simplelayout axis="y"/>
<button text="Update" isdefault="true" x="50"
onclick="canvas.update()"/>

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 15 of 30
developerWorks® ibm.com/developerWorks

<button text="Delete" isdefault="true" x="50"


onclick="canvas.remove()"/>
</view>
<view x="80" height="30">
<simplelayout axis="y"/>
<button text="Add New" isdefault="true" x="200"
onclick="canvas.addNew()"/>
<button id="save" text="Save" isdefault="true" x="200"
onclick="canvas.save()" enabled="false"/>
</view>
</form>

Notice that it's somewhat similar to the form you created for the customer interface,
except that you use editable text boxes rather than just labels. This is so that you
can edit them and then save the data back to the database. A box for the stock is
also added for editing the amount of stock on hand. The last two view boxes hold the
buttons you press to initiate calls to the database. Clicking the Update button
updates the item in the database with the name in the combobox to the name in the
textbox and replaces the description, price, and stock values with the ones in the
text boxes. Clicking the Delete button removes the item in the database whose
name matches the name in the combobox. Also, the Save button is initially disabled;
clicking the Add New button enables it, while also clearing the data in the text
boxes, allowing you to enter new data. The new data will be saved in the database
as a new record upon clicking the Save button, returning the Save button to its
disabled state. Preview this form in Figure 3.

Figure 3. The item management form

Storing and embedding data


Page 16 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

Figure 3 shows the Tomato Soup item being edited. The rest of this section creates
the code behind all of this management functionality, beginning with removing items.

Remove items
Here you implement the method called by clicking the Remove button, the remove
method. (See Listing 21.)

Listing 21. Defining the remove method

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 17 of 30
developerWorks® ibm.com/developerWorks

<method name="remove"><![CDATA[
Debug.write("THE NAME TO DELETE",getItemid());
sendRequest(this.deleteURL,
"POST",
{"name" : getItemid()});
]]>
</method>

This sends a request to the deleteURL, shown below. Note as well the
delete.jsp value, which takes the parameter sent in (the name of the item) and
removes it from the database.

<attribute name="deleteURL"
type="string"
value="delete.jsp"/>
You'll define the contents of the delete.jsp script next.

Remove selected items from the database


If everything goes as expected, you'll receive the name in the request to remove an
item from the database. Define the delete.jsp script that takes this parameter and
removes the associated record from the database, as shown in Listing 22.

Listing 22. Removing an item from the database

...
if(!request.getParameter("name").equals("")){
...
Connection conn = driver.
connect("jdbc:derby:net://localhost:1527/SHOPPING;",
prop);
String sql = "delete from shoppingitems where "+
"name='"+request.getParameter("name")+"'";
PreparedStatement statement = conn.prepareStatement(sql);
statement.execute();
...
%>
<jsp:forward page="../items.jsp" />

This script follows the same template as the other JSP scripts, with the changes
noted in boldface. First, check that the name parameter was sent as expected. If so,
an SQL statement is set up that removes the matching item from the database. At
the end, a redirect is sent so that your application receives the latest list of items in
the database. Figure 4 shows an item being deleted.

Figure 4. Deleting an item

Storing and embedding data


Page 18 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

Notice the command to delete the Bread item showing in the debugger. The deleted
item is no longer in the combobox. Next, you'll add functionality to update and edit
items.

Update and edit items


Before updating items, you need some JavaScript help in getting the data for the
request from the text boxes in the form. These methods are shown in Listing 23.

Listing 23. JavaScript getter methods to help with the request

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 19 of 30
developerWorks® ibm.com/developerWorks

<script>
...
function getItemid() {
return this.item.getText();
}
function getName() {
return this.name.getText();
}
function getDesc() {
return this.description.getText();
}
function getPrice() {
return this.price.getText();
}
function getStock() {
return this.stock.getText();
}
...
</script>

You've essentially created five methods to retrieve the currently shown text in each
of the four editable text boxes and the combobox (getItemid). Next, define the
update method, called by pressing the Update button (see Listing 24).

Listing 24. Defining the update method

<method name="update" ><![CDATA[


Debug.write("UPDATING");
sendRequest(this.updateURL,
"POST",
{"nameBefore" : getItemid(),
"nameAfter" : getName(),
"desc" : getDesc(),
"price" : getPrice(),
"stock" : getStock()});
]]>
</method>

This method calls the sendRequest method, sending the updateURL, shown
below, as a parameter as well as the five parameters needed for the request.

<attribute name="updateURL"
type="string"
value="update.jsp"/>

Save updated data in the database


After the Update button is clicked, the request should make its way to the update.jsp
script. This file will take the data and update the record whose name matches the
beforeName parameter, shown in Listing 25.

Listing 25. Updating a record in the database

...
if(!request.getParameter("nameBefore").equals("") &&
!request.getParameter("nameAfter").equals("") &&
!request.getParameter("desc").equals("") &&
!request.getParameter("price").equals("") &&

Storing and embedding data


Page 20 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

!request.getParameter("stock").equals("")){
...
Connection conn = driver.
connect("jdbc:derby:net://localhost:1527/SHOPPING;",
prop);
String sql = "update shoppingitems set name=?, description=?,"+
" price=?, stock=? where name=?";
PreparedStatement statement = conn.prepareStatement(sql);
statement.setString(1, request.getParameter("nameAfter"));
statement.setString(2, request.getParameter("desc"));
statement.setInt(3, Integer.parseInt
(request.getParameter("price")));
statement.setInt(4, Integer.parseInt
(request.getParameter("stock")));
statement.setString(5, request.getParameter("nameBefore"));
statement.execute();
...
%>
<jsp:forward page="../items.jsp" />

After making sure that the five necessary parameters for an update request are
received, you create the SQL statement. Then you set each of the five unknowns,
searching for the record whose name matches the nameBefore parameter and
replacing its name with the nameAfter parameter. Its description, price, and stock
also get replaced with the desc, price, and stock parameters, respectively.
Finally, the redirect retrieves this latest information for your application from the
items.jsp script. In Figure 5, an item is shown being updated.

Figure 5. Updating item data

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 21 of 30
developerWorks® ibm.com/developerWorks

Add new items


Adding new items is essential to the interface, allowing the online grocery to add
new items as they come on the market. First, create the addNew method that
readies the form for adding a new item, as shown in Listing 26.

Listing 26. Creating the addNew method

<method name="addNew" ><![CDATA[

Storing and embedding data


Page 22 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

// add code to update the database


Debug.write("ADDING A NEW RECORD");
enableSave();
readyTextBoxes();
]]>
</method>

This method enables the Save button and readies the four text boxes for you to type
in new data to save in the database. These are the three JavaScript functions that
will aide you in your task, shown in Listing 27.

Listing 27. JavaScript functions to prepare the form for saving new data

<script>
...
function readyTextBoxes() {
datapath = 'items:/shopping';
this.description.setDatapath(datapath);
this.price.setDatapath(datapath);
this.name.setDatapath(datapath);
this.stock.setDatapath(datapath);
this.description.setText('');
this.price.setText('');
this.name.setText('');
this.stock.setText('');
}
function enableSave(bool) {
this.save.setAttribute("enabled", true);
}
function disableSave(bool) {
this.save.setAttribute("enabled", false);
}
...
</script>

The readyTextBoxes function empties the text boxes, while the enableSave and
disableSave functions enable and disable the Save button, respectively. Next,
define the save method, called upon by clicking the Save button, shown in Listing
28.

Listing 28. Sending a save request

<method name="save" ><![CDATA[


Debug.write("SAVING");
disableSave();
sendRequest(this.saveURL,
"POST",
{"name" : getName(),
"desc" : getDesc(),
"price" : getPrice(),
"stock" : getStock()});
]]>
</method>

This method disables the Save button and then calls the sendRequest method,
sending the request to the saveURL attribute, shown below, along with four
parameters: the name, description, price, and stock of the new item being added to
the database.

<attribute name="saveURL"

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 23 of 30
developerWorks® ibm.com/developerWorks

type="string"
value="save.jsp"/>
Take a look at Figure 6, which shows the Add New button being clicked.

Figure 6. Adding a new item

Next, you'll implement the save.jsp script.

Save new item data in the database


Saving new data to the database will allow your customers to order new things.

Storing and embedding data


Page 24 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

Define the save.jsp script, as shown in Listing 29.

Listing 29. Saving the new item in the database

...
if(!request.getParameter("name").equals("") &&
!request.getParameter("desc").equals("") &&
!request.getParameter("price").equals("") &&
!request.getParameter("stock").equals("")){
...
Connection conn = driver.
connect("jdbc:derby:net://localhost:1527/SHOPPING;",
prop);
String sql = "insert into shoppingitems (name, description, "+
"price, stock) values (?, ?, ?, ?)";
PreparedStatement statement = conn.prepareStatement(sql);
statement.setString(1, request.getParameter("name"));
statement.setString(2, request.getParameter("desc"));
statement.setInt(3, Integer.parseInt
(request.getParameter("price")));
statement.setInt(4, Integer.parseInt
(request.getParameter("stock")));
statement.execute();
...
%>
<jsp:forward page="../items.jsp" />

If the four necessary parameters were sent to the script, name, desc, price, and
stock, then the new item will be inserted into the database. You do so by creating a
SQL statement describing the data of the new item that you want to be inserted into
the database. Then you execute the script and redirect to the items.jsp script, which
returns the latest data in the database. Figure 7 demonstrates saving a new item in
the database.

Figure 7. Saving a new item in the database

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 25 of 30
developerWorks® ibm.com/developerWorks

There you go! Now you have a great start to a fully functional storefront built using
OpenLaszlo and a Derby database.

Section 6. Summary
Now you're an OpenLaszlo expert! You can even communicate with a database,

Storing and embedding data


Page 26 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

increasing your capabilities as an OpenLaszlo developer. There are plenty of


opportunities for you to progress and refine your OpenLaszlo skills, too, so check out
the Resources section for links where you can get involved in OpenLaszlo projects.

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 27 of 30
developerWorks® ibm.com/developerWorks

Downloads
Description Name Size Download method
Part 2 source code derbylaszlo2source.zip
9KB HTTP

Information about download methods

Storing and embedding data


Page 28 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.
ibm.com/developerWorks developerWorks®

Resources
Learn
• Read Part 1 of this series.
• Read the the tutorial "Deploy OpenLaszlo apps on Apache Geronimo with
Tomcat" (developerWorks, March 2006).
• Join the OpenLaszlo rave at laszlosystems.com and openlaszlo.org.
• Get instructions for installing OpenLaszlo.
• Take a look at this OpenLaszlo LZX reference book.
• Get OpenLaszlo documentation.
• Get more documentation from OpenLaszlo's wiki.
• Visit Don Hopkin's Web site, an excellent OpenLaszlo resource (browse topics
on left panel).
• View Apache Derby documentation both at Apache.org and on the
developerWorks site..
• Check out The SQL language reference from IBM for good SQL documentation.
• Visit the developerWorks Open source zone for extensive how-to information,
tools, and project updates to help you develop with open source technologies
and use them with IBM's products.
• Visit the Apache Derby Project Web site.
• Check out the developerWorks Apache Derby project area for articles, tutorials,
and other resources to help you get started with Derby today.
• Browse all the Apache articles and free Apache tutorials available in the
developerWorks Open source zone.
• Browse for books on these and other technical topics at the Safari bookstore.
Get products and technologies
• Try out the Eclipse IDE for OpenLaszlo.
• Download the Apache Derby 10.1.2.1 release.
Discuss
• Get involved in the developerWorks community by participating in
developerWorks blogs.

About the author


Tyler Anderson

Storing and embedding data


© Copyright IBM Corporation 1994, 2007. All rights reserved. Page 29 of 30
developerWorks® ibm.com/developerWorks

Tyler Anderson formerly worked for DPMG.com, an SEO company, for whom he
wrote proprietary SEO software. He graduated with a degree in computer science
from Brigham Young University in 2004 and has just graduated with a Master of
Science degree in computer engineering in December 2005, also from Brigham
Young University. He is currently an engineer for Stexar Corp., based in Beaverton,
Oregon. You can reach Tyler at tyleranderson5@yahoo.com.

Storing and embedding data


Page 30 of 30 © Copyright IBM Corporation 1994, 2007. All rights reserved.

Você também pode gostar