In this chapter, you will learn
Stored procedures are used to encapsulate multiple SQL statements with flow logic. They are database objects that serve as sub-routines to applications. SQL procedures are defined in a database using the CREATE PROCEDURE
statement. This chapter introduces the syntax of the CREATE PROCEDURE
statement and uses examples to illustrate how to create simple SQL procedures.
The CREATE PROCEDURE
statement defines a procedure in the database. The clauses define the name and parameters as well as the procedure body consisting of one or more SQL PL statements. Figure 2.1 describes the syntax of the CREATE PROCEDURE
statement and the clauses that apply to SQL procedures.
Example 2.1. CREATE PROCEDURE
statement syntax for DB2 UDB LUW.
>>-CREATE PROCEDURE--procedure-name-----------------------------> >--+----------------------------------------------------+--*----> '-(--+------------------------------------------+--)-' | .-,------------------------------------. | | V .-IN----. | | '---+-------+--parameter-name--data-type-+-' +-OUT---+ '-INOUT-' >--+--------------------------+--*-------------------------------> '-SPECIFIC--specific-name--' .-DYNAMIC RESULT SETS 0--------. .-MODIFIES SQL DATA-. >--+------------------------------+--*--+-------------------+---> '-DYNAMIC RESULT SETS--integer-' +-CONTAINS SQL------+ '-READS SQL DATA----' .-NOT DETERMINISTIC-. .-CALLED ON NULL INPUT-. >--*--+-------------------+--*--+----------------------+--*-----> '-DETERMINISTIC-----' .-INHERIT SPECIAL REGISTERS-. .-OLD SAVEPOINT LEVEL-. >--+---------------------------+--*--+---------------------+----> '-NEW SAVEPOINT LEVEL-' .-LANGUAGE SQL-. .-EXTERNAL ACTION----. >--*--+--------------+--*--+--------------------+--*------------> '-NO EXTERNAL ACTION-' >--+------------------------------+--*--------------------------> '-PARAMETER CCSID--+-ASCII---+-' '-UNICODE-' >--| SQL-procedure-body |-------------------------------------->< SQL-procedure-body: |---SQL-procedure-statement-------------------------------------|
When you issue the CREATE PROCEDURE
statement, DB2 defines the procedure in the database and makes entries in the catalog tables to record the existence of the procedure.
The procedure name specifies the procedure being defined. The name is an SQL identifier that can be a maximum of 128 characters. It must begin with a letter and may be followed by additional letters, digits, or the underscore character “_”
.
These are examples of valid procedure names:
UPDATE_EMPLOYEE_SALARY READEMP
These examples are of unqualified procedure names. When a procedure name is unqualified, the procedure schema is determined by the CURRENT SCHEMA
special register. The DB2 special register will be discussed later in this chapter. By default, the CURRENT SCHEMA
is the authorization ID of the current user. Procedure names may also be qualified by a schema name explicitly. These are examples of valid qualified procedure names:
HRAPP.UPDATE_EMPLOYEE_SALARY DB2ADMIN.READEMP
Similar to the procedure name, the schema name is an SQL identifier with a maximum of 128 characters or 10 characters on iSeries. The schema name cannot begin with SYS
.
The qualified procedure name does not necessarily need to be unique in the database. The combination of qualified procedure name and number of parameters (procedure signature), however, must uniquely identify a procedure. This topic will be discussed in more detail in the following section.
The SPECIFIC
clause is important when there is a requirement to define procedures with the same name but with a different number of parameters. To fully understand the purpose of this clause, we must discuss parameters.
The parameters for a procedure are defined in the CREATE PROCEDURE
statement. The definition of each parameter consists of three parts:
Mode. defines whether the parameter is an input (IN
), output (OUT
), or both (INOUT
).
Parameter name. specifies the name of the parameter. It is recommended that all parameter variables be prefixed with p_
. This is discussed in detail in the “Variables” section of this chapter.
Data type. is the SQL data type and size, if applicable, for this parameter.
The list of parameters is enclosed in parentheses “( )”, and each parameter definition is delimited by a comma “,”
.
Figure 2.2 is an example of a partial CREATE PROCEDURE
statement that defines the procedure and its parameters.
Example 2.2. Defining procedure parameters.
CREATE PROCEDURE update_employee_salary ( IN P_EMPID INTEGER , IN P_PERCENTINCR DECIMAL(4,2) , INOUT P_EMPCOUNT INTEGER , OUT P_UPDATED_SALARY DECIMAL(5,2)) . . .
A procedure may be defined without any parameters, and the parentheses can be omitted, as in this example:
CREATE PROCEDURE increase_salary LANGUAGE SQL BEGIN . . .
To allow back-level DB2 support, parentheses may be coded in the CREATE PROCEDURE
statement.
CREATE PROCEDURE increase_salary() LANGUAGE SQL BEGIN . . .
On LUW and iSeries, it is possible to define multiple procedures with the same qualified name but different numbers of parameters. This is called overloading, and the procedures are referred to as overloaded procedures. Figures 2.3 and 2.4 show examples of overloaded procedures. zSeries does not support overloaded procedures. Therefore, examples run in zSeries have to be created with different procedure names.
Example 2.3. Procedure sum with three parameters.
CREATE PROCEDURE sum( IN p_a INTEGER , IN p_b INTEGER , OUT p_s INTEGER) LANGUAGE SQL SPECIFIC sum_ab -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN SET p_s = p_a + p_b; END
Example 2.4. Procedure sum with four parameters.
CREATE PROCEDURE sum( IN p_a INTEGER , IN p_b INTEGER , IN p_c INTEGER , OUT p_s INTEGER) LANGUAGE SQL SPECIFIC sum_abc -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN SET p_s = p_a + p_b + p_c; END
In the examples, two procedures have the same name, sum
. The first procedure has three parameters, and the second has four parameters. When sum
is called, DB2 determines which version of the procedure to execute based on the number of parameters. Note that each procedure is defined with a unique specific name. Specific names will be discussed in the next section.
The following statement can be used to invoke the SQL procedure:
CALL sum(100,200,?)
This call results in the sum
procedure in Figure 2.3 to be executed because there are three parameters. Note that because the third parameter is an output parameter, a “?
” must be specified in its place.
Executing the following statement invokes the sum
procedure in Figure 2.4 because there are four parameters.
CALL sum(100,200,300,?)
If you attempt to call a procedure where there is no procedure defined in the database with the same number of parameters, an error occurs, as in this example:
CALL sum(100,200,300,400,?)
This call fails because a procedure named sum
with five parameters does not exist.
SPECIFIC
is an optional clause that defines a unique name for a procedure. Specific names are particularly useful when there are multiple procedures defined with the same name but have a different number of parameters (also known as overloaded procedures, as discussed in the previous section). In this case, each procedure would be given a different specific name which would be used to drop or comment on the stored procedure. Attempting to drop an overloaded procedure using only the procedure name would result in ambiguity and error.
The following example illustrates the use of SPECIFIC
name when two procedures with the same name are defined. Consider the two sum
procedures defined in Figures 2.3 and 2.4.
To drop the procedure sum
, issue the following DROP PROCEDURE
statement:
DROP PROCEDURE sum
This statement fails with SQLCODE -476
(SQLSTATE 42725
) because the procedure is ambiguous. DB2 cannot determine which of the two procedures called sum
should be dropped. To drop a particular version of the sum
procedure, you must either specify the procedure parameters with the DROP PROCEDURE
statement or use the DROP SPECIFIC PROCEDURE
statement. These valid statements drop the procedure:
DROP PROCEDURE sum(INTEGER,INTEGER,INTEGER) DROP SPECIFIC PROCEDURE sum_ab
By using DROP SPECIFIC PROCEDURE
, DB2 knows that it should drop the procedure with the specific name sum_ab
. The specific name can also be used with the COMMENT ON
statement, as in this example:
COMMENT ON SPECIFIC PROCEDURE sum_abc IS 'THIS IS THE 3 PARM VERSION OF THE PROCEDURE'
The specific name is an SQL identifier with a maximum length of 18 characters on LUW and 128 characters on iSeries. The name can be unqualified or qualified by a schema name. If it is qualified, it must use the same schema name as the procedure name. The specific name can be the same name as its procedure name. The qualified specific name must be unique among specific procedure names.
In LUW, if the specific name is not explicitly specified when creating a procedure, DB2 generates a unique name for the procedure. The generated unique name consists of SQL and a character timestamp:
SQLyymmddhhmmsshhn
On iSeries, if the specific name is not specified, DB2 uses the procedure name as the specific name. If a procedure already exists with that specific name, a unique name is generated using a portion of the procedure name and a sequence number.
The DYNAMIC RESULT SETS
clause specifies the maximum number of result sets you are returning. Handling result sets is explained in detail in Chapter 5, “Understanding and Using Cursors and Result Sets,” and Chapter 8, “Nested SQL Procedures.”
The SQL data access indication clause restricts the type of SQL statements that can be executed by the procedure. The default, MODIFIES SQL DATA
, is the least restrictive and indicates that any supported SQL statements can be executed.
When CONTAINS SQL
is specified, then only statements that do not read or modify data are allowed in the procedure. Examples of such statements are PREPARE
, the SET
special register, and SQL control statements.
READS SQL DATA
can be specified if the procedure contains only statements that do not modify SQL data. Refer to the SQL Reference of the corresponding platform for statements allowed in the SQL procedure for each access indicator.
This clause allows you to specify the procedure as DETERMINISTIC
if it returns the same results for each invocation of identical input parameters. You can also specify NOT DETERMINISTIC
, the default, if the results depend on the input values and/or other values which may change, such as the current date or time. Identifying a procedure as DETERMINISTIC
allows DB2 to perform additional optimizations to improve performance because DB2 can just call it once, cache the result, and reuse it.
This clause indicates that the procedure will always be called even if its input parameters are null. This behavior is the default, and is the only value that can be specified. This clause is optional and is usually left out.
Special registers are memory registers that allow DB2 to provide information to an application about its environment. Refer to the section “DB2 Special Registers” for more information.
INHERIT SPECIAL REGISTERS
is an optional clause and indicates that updateable special registers in the procedure will inherit their initial values from the environment of the invoking statement. Special register inheritance is the default behavior on all platforms.
This clause is available only in LUW and iSeries. A save point level refers to the scope of reference for any save point related statements. All save point names in the same save point level must be unique.
The OLD SAVEPOINT LEVEL
means that any SAVEPOINT
statements issued within the procedure are created in the same save point level as the caller of the procedure. Thus, any save point created inside the stored procedure must not have the same name as those defined at the caller. This is the default behavior.
The NEW SAVEPOINT LEVEL
, on the other hand, creates a new save point level when the stored procedure is called. Any save points set within the procedure are created at a level that is nested deeper than the level at which this procedure was invoked. Therefore, names of any new save point set within the procedure will not conflict with any existing save points.
You can also make stored procedure calls from inline SQL such as SQL functions, triggers, and stand-alone code. Such a procedure will be executed as if it were created in the NEW SAVEPOINT LEVEL
mode even if the OLD SAVEPOINT LEVEL
was specified.
Save points are discussed in more detail in Chapter 10, “Leveraging DB2 Application Development Features.”
LANGUAGE SQL
identifies this procedure as an SQL procedure, and indicates that the body of the procedure will be specified in the CREATE PROCEDURE
statement body. LANGUAGE SQL
is an optional clause for LUW. For iSeries and zSeries, LANGUAGE SQL
must be specified. Furthermore, on iSeries, it must be specified as the first clause.
The LANGUAGE
keyword is required when creating procedures in other languages such as Java or C.
This clause is only available on LUW. If the SQL procedure takes some action that changes the state of an object not managed by DB2, specify the EXTERNAL ACTION
. Otherwise, use NO EXTERNAL ACTION
so that DB2 can use certain optimizations that assume the procedure has no external impact.
CCSID stands for Coded Character Set ID. This clause specifies the encoding scheme used for all string data passed into and out of the stored procedure for LUW and zSeries. Possible values are ASCII, UNICODE
, and EBCDIC
(for zSeries only).
On iSeries, the specification of the CCSID is at a more granular level. You specify the CCSID for each string parameter of the procedure (CHAR
, VARCHAR
, CLOB
, GRAPHIC
, VARGRAPHIC
, and DBCLOB
). There are numerous options for specifying CCSID on iSeries. Refer to the iSeries SQL Reference for a listing of valid CCSIDs and the allowed conversions between these CCSIDs.
On zSeries, the CCSID can be specified at either the parameter level, the subsystem level in the field DEF ENCODING SCHEME
on installation panel DSNTIPF, or at the SQL procedure level. The default is the value specified at the parameter level or the subsystem level. If specified at both the parameter level and the SQL procedure, they must be the same CCSID value for all parameters.
For SQL procedures, the logic of the procedure is contained in the SQL procedure body of the CREATE PROCEDURE
statement. The SQL procedure body can consist of a single SQL statement or several SQL statements in the form of a compound SQL statement. The next section explains the details of writing the SQL procedure body.
The SQL procedure body can consist of a single SQL statement or, more typically, a compound SQL statement consisting of a BEGIN/END
block with multiple statements within it. The compound statement consists of various declarations followed by SQL procedure statements. All declarations must be specified first followed by SQL procedural statements. The syntax diagram in Figure 2.5 shows the required order of declarations.
Example 2.5. Compound statement syntax diagram.
.-NOT ATOMIC--. >>-+---------+--BEGIN----+-------------+------------------------> '-label:--' '-ATOMIC------' >-----+-----------------------------------------------+---------> | .------------------------------------------. | | V | | '-----+-| SQL-variable-declaration |-+---;---+--' +-| condition-declaration |----+ '-| return-codes-declaration |-' >--+----------------------------------+-------------------------> | .------------------------------. | | V | | '---| statement-declaration |--;-+-' >-----+--------------------------------------+-------------------> | .--------------------------------. | | V | | '----DECLARE-CURSOR-statement--;----+--' >-----+-------------------------------------+--------------------> | .-------------------------------. | | V | | '----| handler-declaration |--;----+--' .-------------------------------. V | >--------SQL-procedure-statement--;---+---END--+--------+------>< '-label--'
Variable declarations are discussed later in this chapter. Compound statements are discussed in Chapter 4, “Using Flow of Control Statements.” Cursor declarations are discussed in Chapter 5, “Understanding and Using Cursors and Result Sets.” Condition handlers are discussed in Chapter 6, “Condition Handling.” Statement declarations, available in LUW, are discussed in Chapter 7, “Working with Dynamic SQL.”
It is always good practice to include comments in programs. DB2 allows two styles of comments:
When two dashes are specified, any text following them is treated as a comment. This style is typically used to comment on a specific variable declaration or statement. It can be used on any line of the CREATE PROCEDURE
statement and terminates with the newline character.
/* */
are C-style comments. The /*
begins a comment and */
ends the comment. There may be multiple lines of comments between the delimiters. This style can be used in the body of an SQL procedure only.
Figure 2.6 are examples of comments used in an SQL procedure.
Example 2.6. Sample comments.
CREATE PROCEDURE proc_with_comments ( IN aaa INTEGER , OUT bbb INTEGER ) LANGUAGE SQL SPECIFIC proc_with_comments -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN /* Variables */ DECLARE v_total INTEGER DEFAULT 0; SELECT 1 INTO v_total FROM SYSIBM.SYSDUMMY1; END
The DECLARE
statement is used to define variables within a compound SQL statement (see Figure 2.7). Each variable declaration consists of a name for the variable, a DB2 data type, and optionally a default value.
Example 2.7. Defining variables.
CREATE PROCEDURE proc_with_variables (IN p_empno VARCHAR(6)) LANGUAGE SQL SPECIFIC proc_with_vars -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN DECLARE v_empno VARCHAR(6); DECLARE v_total, v_count INTEGER DEFAULT 0; SELECT empno INTO v_empno FROM employee WHERE empno = p_empno ; END
Variable declarations must be specified at the beginning of a BEGIN
/END
block before any SQL procedural statements are defined. The CREATE PROCEDURE
statement will fail if a DECLARE
is found anywhere else.
You should ensure that the variables defined in your procedure are different from column names of tables that will be referenced in the procedure. Such a declaration is allowed but only causes confusion. It is recommended that you define a naming convention for your procedures that clearly differentiates variables and columns. In this book, the convention is to precede variables with a prefix of v_
and precede procedures parameters with a prefix of p_
to differentiate them from possible column names.
When variables are declared, they are initialized as NULL
unless the DEFAULT
clause is used to initialize the variable to a value. In Figure 2.7 the value of v_empno
is null until it is set within the procedure body. The integer variables v_total
and v_count
are initialized to zero in the declaration.
As in any programming language, you can initialize or set variables. There are several ways to set variables in SQL procedures, and they are demonstrated in Figure 2.8.
Example 2.8. Setting variables.
CREATE PROCEDURE set_variables () LANGUAGE SQL SPECIFIC set_variables -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN DECLARE v_rcount INTEGER; DECLARE v_max DECIMAL(9,2); DECLARE v_adate,v_another DATE; DECLARE v_total INTEGER DEFAULT 0; -- (1) SET v_total = v_total + 1; -- (2) SELECT MAX(salary) INTO v_max FROM employee; -- (3) VALUES CURRENT DATE INTO v_adate; -- (4) SELECT CURRENT DATE, CURRENT DATE INTO v_adate, v_another FROM SYSIBM.SYSDUMMY1; -- (5) END
When declaring a variable, you can specify a default value using the DEFAULT
clause as in Line (1).
Line (2) shows that a SET
can be used to set a single variable.
Variables can also be set by executing a SELECT
or FETCH
statement in combination with INTO
as shown in (3). Details on using FETCH
can be found in Chapter 4, “Understanding and Using Cursors and Result Sets.”
Lines (4) and (5) show how the VALUES INTO
statement can be used to evaluate a function or special register and assign the value to a variable. Special registers are discussed in more detail in the next section.
Recall that special registers are memory registers that allow DB2 to provide information to an application about its environment. They can be referenced in SQL statements. The most commonly used special registers are
CURRENT DATE
. A date based on the time-of-day clock at the database server. If this register is referenced more than once in a single statement, the value returned will be the same for all references. This is a non-updateable register.
CURRENT ISOLATION
(LUW only). Identifies the isolation level for any dynamic SQL statements issued within the current session.
CURRENT LOCK TIMEOUT
(LUW only). Specifies the number of seconds that an application will wait to obtain a lock. This is an updateable register.
CURRENT PATH
. Identifies the SQL path used to resolve procedure, functions, and data type references for dynamically prepared SQL statements. The value of the CURRENT PATH
special register is a list of one or more schema names. This is an updateable register.
CURRENT PACKAGE PATH
(LUW and zSeries only). Identifies the path to be used when resolving references to packages. This is an updateable register.
CURRENT SCHEMA
. I
dentifies the schema name used to qualify unqualified database objects in dynamic SQL statements. The default value is the authorization ID of the current user or the value of CURRENT SQLID
on zSeries. This special register can be modified using the SET CURRENT SCHEMA
statement. This is an updateable register.
CURRENT TIME
. A time based on the time-of-day clock at the database server. If this register is referenced more than once in a single statement, the value returned will be the same for all references. This is a non-updateable register.
CURRENT TIMESTAMP
. A timestamp based on the time-of-day clock at the database server. If this register is referenced more than once in a single statement, the value returned will be the same for all references. This is a non-updateable register.
USER
. Specifies the runtime authorization ID used to connect to the database. This is a non-updateable register.
SESSION_USER
(LUW only). Specifies the authorization ID to be used for the current session. This is a synonym for the USER
special register. This is a non-updateable register.
SYSTEM_USER
(LUW only). Specifies the authorization ID of the user who connected to the database. This is a non-updateable register.
Special registers can be categorized as updateable and non-updateable. For example, CURRENT SCHEMA
and CURRENT PATH
are both updateable registers. CURRENT TIMESTAMP
is an example of a non-updateable register. To obtain the value of the register, use the SELECT
statement as shown:
SELECT CURRENT SCHEMA FROM SYSIBM.SYSDUMMY1;
Use the SET
command to update the updateable registers such as the current schema:
SET CURRENT SCHEMA = DB2ADMIN
When invoking SQL procedures with unqualified names, the CURRENT PATH
special register is used to resolve the requested SQL procedure. The path is a list of schemas which DB2 searches to locate a procedure. To obtain the CURRENT PATH
special register, connect to the database and simply issue this command
SELECT CURRENT PATH FROM SYSIBM.SYSDUMMY1;
The default setting for the PATH
register in LUW looks like
"SYSIBM", "SYSFUN", "SYSPROC", "DB2ADMIN"
The default PATH
is made up of system schemas followed by the current user connected to the database. On LUW, SYSIBM
, SYSFUN
, and SYSPROC
are the system schemas. With the previously shown PATH
, DB2 first searches for the procedure in schema SYSIBM
, then SYSFUN
, then SYSPROC
, and lastly DB2ADMIN
. If there are overloaded procedures in both SYSPROC
and DB2ADMIN
, the SYSPROC
one will be used. Sometimes you might want to use the DB2ADMIN
procedure instead. In that case, set the CURRENT PATH
to customize the search order of the schemas:
SET CURRENT PATH = DB2ADMIN,SYSIBM,SYSFUN,SYSPROC
Figure 2.9 shows the use of several special registers.
Example 2.9. Using special registers.
CREATE PROCEDURE registersample ( OUT p_start TIMESTAMP , OUT p_end TIMESTAMP , OUT p_c1 TIMESTAMP , OUT p_c2 TIME , OUT p_user CHAR(20)) LANGUAGE SQL SPECIFIC registersample -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN CREATE TABLE datetab (c1 TIMESTAMP,c2 TIME,c3 DATE); VALUES CURRENT TIMESTAMP INTO p_start; -- (1) INSERT INTO datetab VALUES( CURRENT TIMESTAMP , CURRENT TIME , CURRENT DATE + 3 DAYS); -- (2) SELECT c1,c2 INTO p_c1,p_c2 FROM datetab; VALUES CURRENT TIMESTAMP INTO p_end; SET p_user = USER; -- (3) DROP TABLE datetab; END
The procedure registersample
creates a table, datetab
, to demonstrate how special registers are used with SQL statements. This table is dropped at the end so that the procedure can be run repeatedly.
On Line (1), the values statement is used to set the variable p_start
to the current timestamp.
Line (2) shows several special registers being used within a single SQL statement to retrieve the date or time. Here, the time portion of the CURRENT TIMESTAMP
special register will be the same as the value of the CURRENT TIME
special register, and date portion of the CURRENT TIMESTAMP
special register will be the same as the value of CURRENT DATE
. This statement also demonstrates the use of built-in functions. Column c3
will receive a date that is three days from the current date. You can find more details on using built-in functions such as DATE
, TIME
, and TIMESTAMP
in the DB2 SQL Reference.
The p_user
variable is set to the authorization ID of the currently connected user on Line (3).
The following list includes other special registers that are available. More information about them can be found in the DB2 SQL Reference for the corresponding platform.
CURRENT APPLICATION ENCODING SCHEME
(zSeries only). Specifies which encoding scheme is to be used for dynamic statements. It allows an application to indicate the encoding scheme that is used to process data. This is an updatable register.
CURRENT DBPARTITIONNUM
(LUW only). Specifies an INTEGER
value that identifies the coordinator node number for the statement. This is a non-updateable register.
CURRENT DEFAULT TRANSFORM GROUP
(LUW only). Identifies the name of a transform group used by dynamic SQL statements for exchanging user-defined structured type values with host programs. This is an updateable register.
CURRENT DEGREE
(LUW and zSeries only). Specifies the degree of intra-partition parallelism for the execution of dynamic SQL statements. This is an updateable register.
CURRENT EXPLAIN MODE
(LUW only). Holds a value that controls the behavior of the Explain facility. This is an updateable register.
CURRENT EXPLAIN SNAPSHOT
(LUW only). Holds a value that controls behavior of the Explain Snapshot facility. This is an updateable register.
CURRENT LOCALE LC_CTYPE
(zSeries only). Specifies the LC_CTYPE
locale that will be used to execute SQL statements which use a built-in function that references a locale. This is an updatable register.
CURRENT MAINTAINED TABLE TYPES FOR OPTIMIZATION
(LUW and zSeries only). Specifies the types of tables that can be considered for optimization when dynamic SQL queries are processed. This is an updateable register.
CURRENT MEMBER
(zSeries only). Specifies the member name of a current DB2 data sharing member on which a statement is executing. This is a non-updatable register.
CURRENT OPTIMIZATION HINT
(zSeries only). Specifies the user-defined optimization hint that DB2 should use to generate the access path for dynamic statements. This is an updateable register.
CURRENT PRECISION
(zSeries only). Specifies the rules to be used when both operands in a decimal operation have precisions of 15 or less. This is an updatable register.
CURRENT QUERY OPTIMIZATION
(LUW only). Specifies the query optimization level used when binding dynamic SQL statements. This is an updateable register.
CURRENT REFRESH AGE
(LUW and zSeries only). Specifies the maximum duration that a cached data object, such as a materialized query table, can be used for dynamic queries before it must be refreshed. This is an updateable register.
CURRENT RULES
(zSeries only). Specifies whether certain SQL statements are executed in accordance with DB2 rules or the rules of the SQL standard. This is an updatable register.
CURRENT SERVER
. Specifies the name of the database to which the application is connected. This is a non-updateable register.
CURRENT TIMEZONE
. Specifies the difference between UTC (Coordinated Universal Time) and local time at the application server. This is a non-updateable register.
CLIENT ACCTNG
(LUW and zSeries only). Specifies the accounting string for the client connection. On zSeries, use CURRENT CLIENT_ACCTNG
. This is an updateable register.
CLIENT APPLNAME
(LUW and zSeries only). Specifies the client application name. On zSeries, use CURRENT CLIENT_APPLNAME
. This is an updateable register.
CLIENT USERID
(LUW and zSeries only). Specifies the client user ID. On zSeries, use CURRENT CLIENT_USERID
. This is an updateable register.
CLIENT WRKSTNNAME
(LUW and zSeries only). Specifies the client workstation name. On zSeries, use CURRENT CLIENT_WRKSTNNAME
. This is an updateable register.
A detailed example is presented in this section to demonstrate all the basic features discussed thus far. The procedure in Figure 2.10 inserts a row into the employee table of the SAMPLE database. If you have not created the SAMPLE database, see Appendix A, “Getting Started with DB2.” We recommend that you create this database because most examples in this book make use of it to demonstrate concepts.
Example 2.10. add_new_employee procedure
CREATE PROCEDURE add_new_employee ( IN p_empno VARCHAR(6) -- (1) , IN p_firstnme CHAR(12) , IN p_midinit CHAR(1) , IN p_lastname VARCHAR(15) , IN p_deptname VARCHAR(30) , IN p_edlevel SMALLINT , OUT p_status VARCHAR(100) , OUT p_ts TIMESTAMP) LANGUAGE SQL SPECIFIC add_new_employee -- applies to LUW and iSeries -- WLM ENVIRONMENT <env> -- applies to zSeries BEGIN DECLARE v_deptno CHAR(3) DEFAULT ' '; -- (2) DECLARE v_create_ts TIMESTAMP; -- (3) SET v_create_ts = CURRENT TIMESTAMP; /* Get the corresponding department number */ SELECT deptno INTO v_deptno -- (4) FROM department WHERE deptname = p_deptname; /* Insert new employee into table */ -- (5) INSERT INTO employee ( empno , firstnme , midinit , lastname , workdept , hiredate , edlevel) VALUES ( p_empno , p_firstnme , p_midinit , p_lastname , v_deptno , DATE(v_create_ts) , p_edlevel ); SET p_status = 'Employee added'; -- (6) SET p_ts = v_create_ts; -- (7) END
The parameter list shown in Line (1) defines input and output variables to the procedures. The input parameters represent column values that will be inserted into the Employee table. Note that the p_
prefix is used for each variable to differentiate variables from column names. The output parameters are used to return a status and the TIMESTAMP
of the execution of the procedure.
Line (2) declares the v_deptno
variable to hold the department number retrieved from the Department table. v_deptno
is initialized to ’ ’.
Line (3) declares the v_create_ts
variable to hold the TIMESTAMP
of execution of the procedure. To ensure that the same value of hiredate
is used to insert into the Employee table, the CURRENT TIMESTAMP
register is retrieved only once in the procedure.
To look up the department number in the Department table, a SELECT
statement shown in Line (4) is used to retrieve deptno
and saved in v_deptno
.
Line (5) inserts into the Employee table using parameter values v_deptno
and v_create_ts
. The value of v_create_ts
, which is of type TIMESTAMP
, must be cast to DATE
using the DATE
casting function.
On Lines (6) and (7), the output parameters p_status
and p_ts
are set.
To execute the add_new_employee
procedure on LUW, enter the following in CLP:
CALL add_new_employee('123456','ROBERT','K','ALEXANDER','PLANNING',1,?,?)
The output of this call is
P_STATUS: Employee added P_TS: 2002-09-29 17:19:10.927001 "ADD_NEW_EMPLOYEE" RETURN_STATUS: "0"
The results of many examples in the book are shown using the CLP on LUW. The output will vary based on the operating system. For example, if you are using the Run an SQL Script window of the iSeries Navigator, the output from the call above would be
Output Parameter #7 = Employee added Output Parameter #8 = 2002-09-29 17:19:10.927001 Statement ran successfully (591 ms)
The CREATE PROCEDURE
statement syntax for DB2 UDB for iSeries is very similar to the CREATE PROCEDURE
statement syntax for DB2 UDB for distributed platforms shown in Figure 2.1. In iSeries, the following is true:
The LANGUAGE SQL
clause is mandatory and must be listed right after the parameter declaration in the procedure.
The PARAMETER CCSID
clause is not supported, but specification of the encoding scheme can be specified with the data type of the parameters.
An option to specify whether the procedure runs FENCED
or NOT FENCED
is supported for compatibility with other products in the DB2 family.
A COMMIT ON RETURN
clause can be specified to commit a transaction when returning from a SQL procedure.
An optional SET OPTION
clause is supported to specify precompile options.
For completeness, Figure 2.11 shows the syntax diagram for the iSeries CREATE PROCEDURE
statement, followed by a more detailed explanation of some of the clauses.
Example 2.11. CREATE PROCEDURE
statement syntax for DB2 UDB for iSeries.
>>-CREATE PROCEDURE---procedure-name ---------------------------> >--+----------------------------------------------------------+-> '--(--+----------------------------------------------+--)--'-> | .-,---------------------------------------. | | V .-IN----. | | '----+-------+---parameter-name--data-type---+-' +-OUT---+ '-INOUT-' >--LANGUAGE SQL-----------------------------------------------+-> .-NOT DETERMINISTIC--. .-MODIFIES SQL DATA--. >--+--------------------+-----+--------------------+------------> '-DETERMINISTIC------' +-CONTAINS SQL-------+ '-READS SQL DATA-----' .-CALLED ON NULL INPUT-. >--+----------------------+-----+--------------------------+----> '-SPECIFIC--specific-name--' .-DYNAMIC RESULT SETS 0---------. .-FENCED-----. >--+-------------------------------+-----+------------+---------> '-DYNAMIC RESULT SETS--integer--' '-NOT FENCED-' .-COMMIT ON RETURN NO--. .-OLD SAVEPOINT LEVEL-. >--+----------------------+-----+---------------------+---------> '-COMMIT ON RETURN YES-' '-NEW SAVEPOINT LEVEL-' .-INHERIT SPECIAL RESGISTERS-. >--+----------------------------+-------------------------------> >--+---------------------+---SQL-routine-body------------------>< '-SET OPTION-statement-'
This option is provided only for compatibility with other products in the DB2 family and is not used by SQL procedures in DB2 UDB for iSeries.
This clause can be specified to tell the database manager to commit the transaction when returning from the SQL procedure call. The default value is NO
. If a value of YES
is specified, the transaction is committed only upon successful completion of the procedure. If an error is encountered, a COMMIT
is not issued.
The SET OPTION
statement is used to specify processing options that will be used to create the procedure. For example, a procedure can be created for debug by specifying the following:
SET OPTION DBGVIEW = *SOURCE
DBGVIEW
identifies that debug information is to be provided by the compiler. The *SOURCE
specifies that the compiled object is to be debugged using the program source code.
Chapter 12, “Performance Tuning,” discusses the SET OPTION
statement in more detail. For a complete list of options, refer to the SET OPTION
statement information found in the Statements chapter of the DB2 UDB for iSeries SQL Reference.
In DB2 UDB for zSeries, the CREATE PROCEDURE
statement defines a procedure in the DB2 subsystem. Figure 2.12 shows the syntax diagram of such a statement. It is very similar to the syntax shown in Figure 2.1 for DB2 for LUW. In zSeries, the following is true:
The SPECIFIC, SAVEPOINT LEVEL
, and EXTERNAL ACTION
clauses are not part of the syntax.
PARAMETER CCSID
has an extra possible value of EBCDIC
. In addition, the CCSID
clause can be included with each stored procedure parameter.
The FENCED
clause is the default value and an optional clause. There is no NOT FENCED
option.
A COMMIT ON RETURN
clause can be specified to commit a transaction when returning from an SQL procedure.
Example 2.12. CREATE PROCEDURE statement syntax in DB2 UDB for zSeries.
>>-CREATE PROCEDURE---------------------------------------------> >----procedure-name--(--+----------------------------------------------+---)-> | .-,----------------------------------------. | | V .-IN-----. | | '----+-------+---parameter-name--data-type---+-' +-OUT---+ '-INOUT-' .-DYNAMIC RESULT SETS 0--------. .-MODIFIES SQL DATA-. >--+------------------------------+--*--+-------------------+---> '-DYNAMIC RESULT SETS--integer-' +-CONTAINS SQL------+ '-READS SQL DATA----' .-NOT DETERMINISTIC-. .-CALLED ON NULL INPUT-. >--*--+-------------------+--*--+----------------------+--*-----> '-DETERMINISTIC-----' .-INHERIT SPECIAL REGISTERS-. >--+---------------------------+--*-------LANGUAGE SQL----------> '-DEFAULT SPECIAL REGISTERS-' .-FENCED-. .-NO DBINFO-. >--+------------------------------+---+--------+---+-----------+-> '-PARAMETER CCSID--+-ASCII---+-' '-EBCDIC -' '-UNICODE-' .-NO COLLID ------------. >--+-----------------------+---+-------------------------------+-> '-COLLID Collection-Id -' '-WLM ENVIRONMENT--+--name----+-' '-(name,*)-' .-ASUTIME NO LIMIT ------. .-STAY RESIDENT NO--. >--+------------------------+----+-------------------+-----------> '-ASUTIME LIMIT integer--' +-STAY RESIDENT YES-' .-PROGRAM TYPE MAIN--. .-SECURITY DB2-----. >--+--------------------+----+------------------+----------------> '-PROGRAM TYPE SUB---' +-SECURITY USER ---+ '-SECURITY DEFINER-' .-COMMIT ON RETURN NO---. >--+-------------------------------+----+-----------------------+-> '-RUN OPTIONS run time options--' '-COMMIT ON RETURN YES--' .-STOP AFTER SYSTEM DEFAULT FAILURES --. >--+--------------------------------------+----------------------> +-STOP AFTER integer FAILURES ---------+ '-CONTINUE AFTER FAILURE---------------' >-----| SQL-procedure-body |------------------------------------>< SQL-procedure-body: |---SQL-procedure-statement-------------------------------------|
This option specifies that the SQL procedure runs in an external address space to prevent user programs from corrupting the DB2 engine storage. This clause is optional and is the default value in DB2 UDB for zSeries. There is no NOT FENCED
option. Note that SQL procedures created in DB2 UDB for LUW are all UNFENCED
; this is the default and the only behavior.
NO DBINFO
indicates that specific internal information known to DB2 will not be passed to the SQL procedure. NO DBINFO
is the default for SQL procedures.
NO COLLID
indicates that the package collection for the SQL procedure is the same as the package collection of the calling program. COLLID collection-id
provides the collection ID to be used for the SQL procedure.
This option identifies the Workload Manager (WLM) environment where the SQL procedure is to run if defined as a WLM-established SQL procedure. If WLM ENVIRONMENT
is not specified, the default WLM environment specified at installation time is used.
This option indicates whether the SQL procedure will use unlimited processor time for a single invocation of an SQL procedure (NOLIMIT
) or a specific amount of processor time (LIMIT
integer).
This option specifies whether the SQL procedure will run as a subroutine (SUB
) or as a main program (MAIN
).
This option indicates how the SQL procedure interacts with an external security product to control access to non-SQL resources. Possible values include the following:
DB2
. The SQL procedure does not require a special external security environment. If it accesses resources that an external security product protects, the access is performed using the authorization ID associated with the SQL procedure address space. DB2
is the default.
USER
. An external security environment should be established for the SQL procedure. If the SQL procedure accesses resources that the external security product protects, the access is performed using the authorization ID of the user who invoked the SQL procedure.
DEFINER
. An external security environment should be established for the SQL procedure. If the SQL procedure accesses resources that the external security product protects, the access is performed using the authorization ID of the owner of the SQL procedure.
This option indicates the Language Environment runtime options that are to be used for the SQL procedure.
This option indicates whether a COMMIT
is automatically issued upon return from the SQL procedure, regardless of whether a COMMIT
or ROLLBACK
is explicitly coded in the SQL procedure. NO
is the default.
This option indicates whether the SQL procedure is to be put in a stopped state after some number of failures. Possible values include the following:
STOP AFTER SYSTEM DEFAULT FAILURES
. The value of field MAX ABEND COUNT
on installation panel DSNTIPX is used to determine the number of failures allowed before placing the SQL procedure in stopped state. This is the default.
STOP AFTER
nn
FAILURES
. Indicates that after nn failures, the SQL procedure should be placed in a stopped state. The value nn can be an integer from 1 to 32767.
CONTINUE AFTER FAILURE
. Specifies that this SQL procedure should not be placed in a stopped state after any failure.
SQL procedures are defined using the CREATE PROCEDURE
statement. The statement defines the name, the parameters, and several other properties of the procedure.
The SQL procedure logic is defined in the procedure body of the CREATE PROCEDURE
statement. The body is typically a compound statement consisting of declarations followed by procedural statements. The DECLARE
statement is used to declare variables, their data type, and optionally, a default value. Statements such as SET
, SELECT...INTO
, and VALUES
can also be used to assign values to variables.
This chapter demonstrated creation of simple procedures with some basic procedural statements. Other SQL PL statements will be discussed in detail in the rest of this book.
18.227.134.232