- 论坛徽章:
- 11
|
/***************************************************************************
* Licensed Materials - Property of IBM
*
*
* "Restricted Materials of IBM"
*
*
*
* IBM Informix Client SDK
*
*
* (C) Copyright IBM Corporation 1997, 2004 All rights reserved.
*
*
*
*
*
* Title: proc.c
*
* Description: To execute a stored procedure returning multiple results
*
* The stored procedure executed is -
* PROCEDURE multiReturnProc (i integer)
* RETURNING integer;
* define j integer;
* for j in (1 to 5)
* return i*j with resume;
* end for;
* END PROCEDURE
*
* Because the Informix ODBC driver version 3.3 does not
* yet suport output parameters for stored procedures,
* the way to get return values from a procedure is to
* use SQLBindCol and SQLFetch. This works whether the
* procedure returns a single value or multiple values.
*
*
***************************************************************************
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#ifndef NO_WIN32
#include <io.h>
#include <windows.h>
#include <conio.h>
#endif /*NO_WIN32*/
#include "infxcli.h"
#define ERRMSG_LEN 200
SQLCHAR defDsn[] = "odbc_demo";
SQLINTEGER checkError (SQLRETURN rc,
SQLSMALLINT handleType,
SQLHANDLE handle,
SQLCHAR* errmsg)
{
SQLRETURN retcode = SQL_SUCCESS;
SQLSMALLINT errNum = 1;
SQLCHAR sqlState[6];
SQLINTEGER nativeError;
SQLCHAR errMsg[ERRMSG_LEN];
SQLSMALLINT textLengthPtr;
if ((rc != SQL_SUCCESS) && (rc != SQL_SUCCESS_WITH_INFO))
{
while (retcode != SQL_NO_DATA)
{
retcode = SQLGetDiagRec (handleType, handle, errNum, sqlState, &nativeError, errMsg, ERRMSG_LEN, &textLengthPtr);
if (retcode == SQL_INVALID_HANDLE)
{
fprintf (stderr, "checkError function was called with an invalid handle!!\n");
return 1;
}
if ((retcode == SQL_SUCCESS) || (retcode == SQL_SUCCESS_WITH_INFO))
fprintf (stderr, "ERROR: %d: %s : %s \n", nativeError, sqlState, errMsg);
errNum++;
}
fprintf (stderr, "%s\n", errmsg);
return 1; /* all errors on this handle have been reported */
}
else
return 0; /* no errors to report */
}
int main (long argc,
char* argv[])
{
/* Declare variables
*/
/* Handles */
SQLHDBC hdbc;
SQLHENV henv;
SQLHSTMT hstmt;
/* Miscellaneous variables */
SQLCHAR dsn[20]; /*name of the DSN used for connecting to the database*/
SQLRETURN rc = 0;
SQLINTEGER in;
SQLCHAR* createProcStmt = (SQLCHAR *) "CREATE PROCEDURE multiReturnProc (i integer)\
RETURNING integer;\
define j integer;\
for j in (1 to 5)\
return i*j with resume;\
end for;\
END PROCEDURE;";
SQLCHAR* dropProcStmt = (SQLCHAR *) "DROP PROCEDURE multiReturnProc";
SQLSMALLINT inputParam = 2;
SQLINTEGER retVal = 7, cbRetVal = 0, cbInputParam = 0;
/* STEP 1. Get data source name from command line (or use default)
** Allocate the environment handle and set ODBC version
** Allocate the connection handle
** Establish the database connection
** Allocate the statement handle
*/
/* If(dsn is not explicitly passed in as arg) */
if (argc != 2)
{
/* Use default dsn - odbc_demo */
fprintf (stdout, "\nUsing default DSN : %s\n", defDsn);
strcpy ((char *)dsn, (char *)defDsn);
}
else
{
/* Use specified dsn */
strcpy ((char *)dsn, (char *)argv[1]);
fprintf (stdout, "\nUsing specified DSN : %s\n", dsn);
}
/* Allocate the Environment handle */
rc = SQLAllocHandle (SQL_HANDLE_ENV, SQL_NULL_HANDLE, &henv);
if (rc != SQL_SUCCESS)
{
fprintf (stdout, "Environment Handle Allocation failed\nExiting!!");
return (1);
}
/* Set the ODBC version to 3.0 */
rc = SQLSetEnvAttr (henv, SQL_ATTR_ODBC_VERSION, (SQLPOINTER) SQL_OV_ODBC3, 0);
if (checkError (rc, SQL_HANDLE_ENV, henv, (SQLCHAR *) "Error in Step 1 -- SQLSetEnvAttr failed\nExiting!!"))
return (1);
/* Allocate the connection handle */
rc = SQLAllocHandle (SQL_HANDLE_DBC, henv, &hdbc);
if (checkError (rc, SQL_HANDLE_ENV, henv, (SQLCHAR *) "Error in Step 1 -- Connection Handle Allocation failed\nExiting!!"))
return (1);
/* Establish the database connection */
rc = SQLConnect (hdbc, dsn, SQL_NTS, (SQLCHAR *) "", SQL_NTS, (SQLCHAR *) "", SQL_NTS);
if (checkError (rc, SQL_HANDLE_DBC, hdbc, (SQLCHAR *) "Error in Step 1 -- SQLConnect failed\nExiting!!"))
return (1);
/* Allocate the statement handle */
rc = SQLAllocHandle (SQL_HANDLE_STMT, hdbc, &hstmt );
if (checkError (rc, SQL_HANDLE_DBC, hdbc, (SQLCHAR *) "Error in Step 1 -- Statement Handle Allocation failed\nExiting!!"))
return (1);
fprintf (stdout, "STEP 1 done...connected to database\n");
/* STEP 2. Create the stored procedure in the database
*/
/* Execute the SQL statement to create the stored procedure*/
rc = SQLExecDirect (hstmt, createProcStmt, SQL_NTS);
if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 2 -- SQLExecDirect failed\n"))
goto Exit;
fprintf (stdout, "STEP 2 done...stored procedure created\nExecuting procedure...\n\n");
/* STEP 3. Bind the input parameter
** Execute the procedure
** Bind the result set column (return values)
** Fetch the results
** Display the results
** Close the result set cursor
*/
/* Bind the input parameter */
rc = SQLBindParameter (hstmt, 1, SQL_PARAM_INPUT, SQL_C_SSHORT, SQL_INTEGER, 0, 0, &inputParam, 0, &cbInputParam);
if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 3 -- SQLBindParameter failed\n"))
return (1);
/* Execute the procedure */
rc = SQLExecDirect (hstmt, (SQLCHAR *) "{call multiReturnProc (?)}", SQL_NTS);
if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 3 -- SQLExecDirect failed\n"))
goto Exit;
/* Bind the result set column */
rc = SQLBindCol (hstmt, 1, SQL_C_SLONG, (SQLPOINTER)&retVal, 0, &cbRetVal);
if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 3 -- SQLBindCol failed\n"))
goto Exit;
/* Fetch and display the results */
while (1)
{
rc = SQLFetch (hstmt);
if (rc == SQL_NO_DATA_FOUND)
break;
else if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 3 -- SQLFetch failed\n"))
goto Exit;
/* Display the results */
fprintf (stdout, "Procedure returned %d\n", retVal);
}
/* Close the result set cursor */
rc = SQLCloseCursor (hstmt);
if (checkError (rc, SQL_HANDLE_STMT, hstmt, (SQLCHAR *) "Error in Step 3 -- SQLCloseCursor failed\n"))
goto Exit;
fprintf (stdout, "\nSTEP 3 done...stored procedure executed\n");
Exit:
/* CLEANUP: Drop the stored procedure from the database
** Close the statement handle
** Free the statement handle
** Disconnect from the datasource
** Free the connection and environment handles
** Exit
*/
/* Drop the stored procedure from the database */
SQLExecDirect (hstmt, dropProcStmt, SQL_NTS);
/* Close the statement handle */
SQLFreeStmt (hstmt, SQL_CLOSE);
/* Free the statement handle */
SQLFreeHandle (SQL_HANDLE_STMT, hstmt);
/* Disconnect from the data source */
SQLDisconnect (hdbc);
/* Free the environment handle and the database connection handle */
SQLFreeHandle (SQL_HANDLE_DBC, hdbc);
SQLFreeHandle (SQL_HANDLE_ENV, henv);
fprintf (stdout,"\n\nHit <Enter> to terminate the program...\n\n");
in = getchar ();
return (rc);
} |
|