Step 5: Process the results of the command

Applications call ct_results repeatedly to handle the results returned by the server. Almost all Client-Library programs process results by executing a loop controlled by ct_results return status. Inside the loop, a switch takes place on the current type of result. Different types of results require different types of processing.

The results-processing model used in the example is based on this pseudocode:

while ct_results returns CS_SUCCEED
         switch on result_type
             case row results
                 for each column:
                     ct_bind
                 end for
                 while ct_fetch is returning rows
                     process each row
                 end while
                 check ct_fetch’s final return code
             end case row results
             case command done ....
             case command failed ....
             case other result type....
             ... raise an error ...
         end switch
 end while
 check ct_results’ final return code

NoteSybase strongly recommends that you use this type of program structure, even in the case of a simple language command. In more complex programs, you cannot predict the number and type of result sets that an application will receive in response to a command. Code that calls ct_results in a loop is also easier to maintain, enhance, or reuse, since the results-handling logic is centralized.

ct_results sets up results for processing and sets the return parameter result_type to indicate the type of result data that is available for processing.

If the select statement sent by firstapp.c executes successfully on the server, the sample program receives result types of CS_ROW_RESULT and CS_CMD_DONE, in that order. If the statement does not execute successfully on the server, the program receives a result type of CS_CMD_FAIL.

Because this program is so simple, most result types are not included as cases in the result_type switch. However, the code does raise an error for unexpected values of result_type. Code this check into your program’s results loop—the error raised may help you trap coding bugs early in the development cycle.

For row results, typically the number of columns in the result set is determined and then used to control a loop in which result items are bound to program variables. An application can call ct_res_info to get the number of result columns and ct_describe to get a description of each column. However, in firstapp.c, these calls are not necessary because the example was coded with knowledge of how many columns were selected and their format.

ct_bind binds a result item to a program variable. Binding creates an association between a result item and a program data space.

ct_fetch fetches result data. In the example, since binding has been specified and the count field in the CS_DATAFMT structure for each column is set to 1, each ct_fetch call copies one row of data into program data space. As each row is fetched, the sample program prints it.

ct_fetch is called until there are no more rows, then the sample program checks ct_fetch’s final return code to find out whether the loop terminated normally or because of failure.

For information on the other result types that an application can receive, see Chapter 6, “Writing Results-Handling Code.”