Guild Companies, Inc.  
 
Midrange Programmer - How-To Advice & Free Code
OS/400 Edition
Volume 1, Number 5 - March 14, 2002

Call iSeries Programs Using SQL

by Kevin Vandever

[The code for this article is available for download.]

Though RPG applications once reigned as the center of our development efforts, they have since been relegated to the role of legacy apps, as our attention has turned toward other platforms and other technologies. The fact remains, however, that our most vital business rules still exist inside those RPG apps. So how do you get to those apps from the outside world? Well, one way is to call them using SQL. This article will explain how to do just that.

Why SQL?

So what's so special about SQL? SQL is the universal language used to access data from most, if not all, relational databases in existence today. This includes Oracle, Access, SQL Server, and DB2, the native database for the iSeries. High-level languages such as Java, Visual Basic, and C++ are able to access relational databases by loading a database driver (JDBC or ODBC, depending on the language) and embedding SQL statements to work with that driver.

One of the features of SQL is the stored procedure. A stored procedure is nothing more than a program that is created and stored as part of the database and accessed via SQL. This program can be created using SQL statements, but it doesn't have to be. And that's where RPG comes in. DB2 on the iSeries allows stored procedures to be created in any language that runs on the iSeries. So you can create a stored procedure from an ILE RPG program and call that program using the SQL call statement from other platforms. Let's talk a little more about creating a stored procedure from an RPG program.

Stored Procedures

It is not my intent in this article to fully explain stored procedures. I will do that in a future article. What I want to do here is show you how easy it is to turn an RPG program into a stored procedure. The first thing you need to do is to start an interactive SQL session on your iSeries. You can do this typing STRSQL on the command line. (You can also enter SQL statements interactively using Operations Navigator, but I will use STRSQL for the purposes of this article.) Now that you have an interactive SQL session, you are now ready to create a stored procedure. Type the following command and press F4 to prompt:

CREATE PROCEDURE

A screen that looks much like the one in the following figure should appear:

Type a name for your stored procedure and a library to place it in. The next parameter.RESULT SETS, allows you to state the maximum number of result sets that will be returned from this procedure. For my purpose in this exercise, I leave this field blank; however, depending on how you are calling this stored procedure and what you are trying to accomplish, you may want to set a maximum number. The next parameter, Language, is the language in which this stored procedure was written. Notice all the wonderful options available to you. You could choose any of them, but for this example I want to use RPGLE. The last option on this first screen is the parameter style. I stated that I wanted a general parameter style option. As you can see, depending on what you are passing and the language you are passing to, you may want to enter a different option here.I will explain more about parameter styles, as well as all the available options, in the next issue when I cover stored procedures in more detail. Press Enter to get to the second screen, shown here:

The first thing you do on this screen is enter the name of the external program you are going to call. In my example, it is an RPG program (as stated on the previous screen) called CUSTCHECK, and it resides in a library called NEXSOURCE. The next parameter, IS DETERMINISTIC, is pretty cool. It specifies whether or not the procedure will always return the same result from repeated calls containing the same input values. If the answer is yes, DB2 will cache the results and the next time a call is made using the same input parameters, the result will be returned to the caller without the external program ever being called. Since my external program checks the validity of a customer ID passed to it, I want it always checked and therefore answer N to this parameter.

Next I specify whether or not I want the external program called when my input parameters are null. I leave the last parameter, SPECIFIC, blank. You use this parameter if you want a specific name for your procedure. The interesting part is that this name has to be the same as the procedure name, so I have never really figured out why to use this parameter. Anyway, press Enter one more time to get a screen like the one shown here:

This is where you enter your input and output parameters. My RPG program contains two parameters in the *ENTRY PLIST. The first parameter will contain the customer ID passed to the program. The second parameter will not contain anything coming into the program, but it will be set to 1 or 0, depending on whether or not the customer is valid. So when setting my parameters in the stored procedure, I not only match the data type of the parms in my RPG, I want to match usage as well. This is important even though RPG doesn't care whether you use parameters as input, output, or both. Press Enter and--presto!--you have created a stored procedure from an RPG program. The cool thing is that you can now call this program using an SQL call from another language on a different platform, and you haven't stopped its ability to call it as you always have inside your iSeries application.

Let's take a look at how to call the stored procedure you just created from another language.

A Java Example

In this example, I am going to use JDBC as my database driver and Java as my language, but the concept works the same for the ODBC driver and languages such as Visual Basic and C++; you basically register the database driver, connect to a database, prepare your SQL statement, and then execute that statement. Then, depending on whether you are expecting a return value, you get that value and do what you will with it.

Take a look at my Java source code (staticSqlCall). In this program, I pass in a customer ID from the command line and that customer ID is used as the input parameter to my stored procedure. After I call the stored procedure, I get the output parameter and, depending on the value, display a message to the screen stating whether or not the customer ID passed was valid. Let's take a look at the SQL-related lines in the Java app. Skip down to the block of code contained within the border of asterisks. The first thing I do is create a Connection object called con. Next I create a String called url and set it to jdbc:as400://, followed by the machine's IP address. Next I register the driver using the registerDriver method in the DriverManager class.

Now I'm ready to instantiate my connection object with a connection to my iSeries database. I do this by using the getConnection method in the DriverManager class, passing my url string along with a valid user ID and password. For the purpose of illustration, I have hard coded the user ID and password, but in a production environment you would want to retrieve that information from some secure storage area such as a database file or LDAP directory. Now that I have connected to the database, I am ready to build my SQL statement.

In my example, I am going to use the CallableStatement class. The first thing I do is create a new CallableStatement object. I called it sqlCall. Now, using the prepareCall method from my connection object, I instantiate the sqlCall with the actual CALL statement that I will use. The question marks (?) represent the parameters that the stored procedure contains. The sqlCall object is now ready to go. We just have to fill in the question marks. Remember we had one input parameter and one output parameter? It is important to remember this here because it will determine how you deal with each parameter. For the input parameter, I use the setString method from the sqlCall object to set the first parameter to the string (args[0]) that I entered on the command line. The setString method accepts the parameter number, in this case 1, and the String that will be passed to the stored procedure. The setString method is used because the parameter is of CHAR data type. If it were another data type, a different SET method would be used. Now that the input parameter is set, it is time to register the output parameter.

I do this using the registerOutParameter method in my sqlCall object. This method accepts the parameter number and the fully qualified expected data type. The input parameter has been set and the output parameter registered so that the sqlCall object now knows what the question marks really represent. The next thing to do is call the stored procedure, and I do this using the execute method contained in my sqlCall object. This method accepts no parameters; rather, it executes this sqlCall object, which we just spent the last few statements defining. The next thing I do is retrieve my output parameter. This is done using the getBoolean method in my sqlCall object. The getBoolean method accepts the parameter number as input and its return value is a Boolean true or false. The getBoolean method is used because that is the method used to retrieve SMALLINT data types. If the output parameter were CHAR, the getString method would have been used instead. Now that I have the value contained in my output parameter, I can perform an IF test and tell the user whether or not the customer ID keyed on the command line was valid. The last two method calls are used to close the sqlCall object and disconnect the database connection, respectively. To run the application, type the following from your DOS command line, Qshell command line on the iSeries, the CODE/400 command shell or any other environment you might use:

java staticSqlCall 00000001

The 00000001 represents the customer ID that you want to validate. Don’t worry, if you forget to type the parameter, the java application will ask you to try again. Also, I’ve included a sample RPG program with the downloadable code for this article that you can use with the java application to test out this technique.

iSeries Applications Extended

This article was not meant to discuss the specifics of Java (for that, check out my article "Java Concepts for iSeries Programmers"), nor was it meant to be a tutorial on JDBC or the IBM Toolbox for Java, or to touch on the inner workings of stored procedures (tune in later for that one). It was, however, meant to show you how to make your RPG and other iSeries programs accessible from just about anywhere within your IT infrastructure, using a standard database driver and SQL. So design away and do so happily, knowing that your iSeries programs are just a call away.

Sponsored By
TRAMENCO

Introducing a New Source for Training and Mentoring. Follow this link to a vital new source for how-to technical information: www.tramenco.com.

Unlike companies that offer training as an afterthought, The Training and Mentoring Company (Tramenco) is dedicated to just one thing: Advancing your career by giving you the skills you need to solve real-world business problems.

You get the best information from the world's leading experts--Howard Arner, Kelly Conklin, Don Denoncourt, Susan Gantner, Skip Marchesani, Glen Marchesani, Shannon O'Donnell, Craig Pelke, and Richard Shaler.

Choose from a menu of training options to fit your needs: onsite seminars, public seminars, mentoring, consulting, books, CBTs, and Web-based training.

And make plans to attend the 2002 iSeries Connection Conference, the multi-day, multi-track conference that was the only sold-out iSeries training event this year, co-sponsored by the Education Connection and Tramenco.

For more information about Tramenco's career enhancing opportunities, call (800) 421-8031 or go to www.tramenco.com.

THIS ISSUE
SPONSORED BY:
mrc
Client Server Dev.
COMMON
Aldon Computer Group
Profound Logic Software
Tramenco
BACK ISSUES
TABLE OF CONTENTS
Displaying Static HTML Pages from the iSeries
ILE Static Binding
JSP Server-Side Error Handling, Part 2
Getting Started with Qshell Scripts
Introduction to Communications Console and CODE/400's Code/Editor
Call iSeries Programs Using SQL
  Newsletters | Subscribe | Advertise | About Us | Contact | Search | Home  
  Last Updated: 2/13/02
Copyright © 1996-2008 Guild Companies, Inc. All Rights Reserved.