LCOV - code coverage report
Current view: top level - src/ctlib/unittests - lang_ct_param.c (source / functions) Hit Total Coverage
Test: FreeTDS coverage Lines: 112 181 61.9 %
Date: 2025-01-18 12:13:41 Functions: 2 4 50.0 %

          Line data    Source code
       1             : #include <config.h>
       2             : 
       3             : #include <stdarg.h>
       4             : #include <stdio.h>
       5             : 
       6             : #if HAVE_STDLIB_H
       7             : #include <stdlib.h>
       8             : #endif /* HAVE_STDLIB_H */
       9             : 
      10             : #if HAVE_STRING_H
      11             : #include <string.h>
      12             : #endif /* HAVE_STRING_H */
      13             : 
      14             : #include <ctpublic.h>
      15             : #include "common.h"
      16             : 
      17             : static const char *query =
      18             :         "insert into #ctparam_lang (name,name2,age,cost,bdate,fval) values (@in1, @in2, @in3, @moneyval, @dateval, @floatval)";
      19             : 
      20             : CS_RETCODE ex_servermsg_cb(CS_CONTEXT * context, CS_CONNECTION * connection, CS_SERVERMSG * errmsg);
      21             : CS_RETCODE ex_clientmsg_cb(CS_CONTEXT * context, CS_CONNECTION * connection, CS_CLIENTMSG * errmsg);
      22             : 
      23             : static int insert_test(CS_CONNECTION *conn, CS_COMMAND *cmd, int useNames);
      24             : 
      25             : /* Testing: binding of data via ct_param */
      26             : int
      27           8 : main(int argc, char *argv[])
      28             : {
      29           8 :         int errCode = 0;
      30             :         
      31             :         CS_CONTEXT *ctx;
      32             :         CS_CONNECTION *conn;
      33             :         CS_COMMAND *cmd;
      34           8 :         int verbose = 0;
      35             : 
      36             :         CS_RETCODE ret;
      37             :         CS_CHAR cmdbuf[4096];
      38             : 
      39           8 :         if (argc > 1 && (0 == strcmp(argv[1], "-v")))
      40           0 :                 verbose = 1;
      41             : 
      42           8 :         printf("%s: submit language query with variables using ct_param\n", __FILE__);
      43           8 :         if (verbose) {
      44           0 :                 printf("Trying login\n");
      45             :         }
      46           8 :         ret = try_ctlogin(&ctx, &conn, &cmd, verbose);
      47           8 :         if (ret != CS_SUCCEED) {
      48           0 :                 fprintf(stderr, "Login failed\n");
      49           0 :                 return 1;
      50             :         }
      51             : 
      52           8 :         ct_callback(ctx, NULL, CS_SET, CS_CLIENTMSG_CB, (CS_VOID *) ex_clientmsg_cb);
      53             : 
      54           8 :         ct_callback(ctx, NULL, CS_SET, CS_SERVERMSG_CB, (CS_VOID *) ex_servermsg_cb);
      55             : 
      56           8 :         strcpy(cmdbuf, "create table #ctparam_lang (id numeric identity not null, \
      57             :                 name varchar(30), name2 varchar(20), age int, cost money, bdate datetime, fval float) ");
      58             : 
      59           8 :         ret = run_command(cmd, cmdbuf);
      60             : 
      61           8 :         if (ret != CS_SUCCEED) {
      62           0 :                 fprintf(stderr, "create table failed\n");
      63           0 :                 errCode = 1;
      64           0 :                 goto ERR;
      65             :         }
      66             : 
      67             :         /* test by name */
      68           8 :         errCode = insert_test(conn, cmd, 1);
      69             :         /* if worked, test by position */
      70           8 :         if (0 == errCode)
      71           8 :                 errCode = insert_test(conn, cmd, 0);
      72           8 :         query = "insert into #ctparam_lang (name,name2,age,cost,bdate,fval) values (?, ?, ?, ?, ?, ?)";
      73           8 :         if (0 == errCode)
      74           8 :                 errCode = insert_test(conn, cmd, 0);
      75             : 
      76           8 :         if (verbose && (0 == errCode))
      77           0 :                 printf("lang_ct_param tests successful\n");
      78             : 
      79          16 : ERR:
      80           8 :         if (verbose) {
      81           0 :                 printf("Trying logout\n");
      82             :         }
      83           8 :         ret = try_ctlogout(ctx, conn, cmd, verbose);
      84           8 :         if (ret != CS_SUCCEED) {
      85           0 :                 fprintf(stderr, "Logout failed\n");
      86           0 :                 return 1;
      87             :         }
      88             : 
      89             :         return errCode;
      90             : }
      91             : 
      92             : static int 
      93          24 : insert_test(CS_CONNECTION *conn, CS_COMMAND *cmd, int useNames)
      94             : {
      95             :         CS_CONTEXT *ctx;
      96             : 
      97             :         CS_RETCODE ret;
      98             :         CS_INT res_type;
      99             : 
     100             :         CS_DATAFMT datafmt;
     101             :         CS_DATAFMT srcfmt;
     102             :         CS_DATAFMT destfmt;
     103             :         CS_INT intvar;
     104             :         CS_FLOAT floatvar;
     105             :         CS_MONEY moneyvar;
     106             :         CS_DATEREC datevar;
     107             :         char moneystring[10];
     108             :         char dummy_name[30];
     109             :         char dummy_name2[20];
     110             :         CS_INT destlen;
     111          24 :         CS_INT rowsAffected = -1;
     112          24 :         int rows_found = 0;
     113             : 
     114             :         /* clear table */
     115          24 :         run_command(cmd, "delete #ctparam_lang");
     116             : 
     117             :         /*
     118             :          * Assign values to the variables used for parameter passing.
     119             :          */
     120             : 
     121          24 :         intvar = 2;
     122          24 :         floatvar = 0.12;
     123          24 :         strcpy(dummy_name, "joe blow");
     124          24 :         strcpy(dummy_name2, "");
     125          24 :         strcpy(moneystring, "300.90");
     126             : 
     127             :         /*
     128             :          * Clear and setup the CS_DATAFMT structures used to convert datatypes.
     129             :          */
     130             : 
     131          24 :         memset(&srcfmt, 0, sizeof(CS_DATAFMT));
     132             :         srcfmt.datatype = CS_CHAR_TYPE;
     133          24 :         srcfmt.maxlength = strlen(moneystring);
     134          24 :         srcfmt.precision = 5;
     135          24 :         srcfmt.scale = 2;
     136             :         srcfmt.locale = NULL;
     137             : 
     138          24 :         memset(&destfmt, 0, sizeof(CS_DATAFMT));
     139          24 :         destfmt.datatype = CS_MONEY_TYPE;
     140          24 :         destfmt.maxlength = sizeof(CS_MONEY);
     141          24 :         destfmt.precision = 5;
     142          24 :         destfmt.scale = 2;
     143             :         destfmt.locale = NULL;
     144             : 
     145             :         /*
     146             :          * Convert the string representing the money value
     147             :          * to a CS_MONEY variable. Since this routine does not have the
     148             :          * context handle, we use the property functions to get it.
     149             :          */
     150          24 :         if ((ret = ct_cmd_props(cmd, CS_GET, CS_PARENT_HANDLE, &conn, CS_UNUSED, NULL)) != CS_SUCCEED) {
     151           0 :                 fprintf(stderr, "ct_cmd_props() failed\n");
     152           0 :                 return 1;
     153             :         }
     154          24 :         if ((ret = ct_con_props(conn, CS_GET, CS_PARENT_HANDLE, &ctx, CS_UNUSED, NULL)) != CS_SUCCEED) {
     155           0 :                 fprintf(stderr, "ct_con_props() failed\n");
     156           0 :                 return 1;
     157             :         }
     158          24 :         ret = cs_convert(ctx, &srcfmt, (CS_VOID *) moneystring, &destfmt, &moneyvar, &destlen);
     159          24 :         if (ret != CS_SUCCEED) {
     160           0 :                 fprintf(stderr, "cs_convert() failed\n");
     161           0 :                 return 1;
     162             :         }
     163             : 
     164             :         /*
     165             :          * create the command
     166             :          */
     167          24 :         if ((ret = ct_command(cmd, CS_LANG_CMD, query, strlen(query), 
     168             :                 CS_UNUSED)) != CS_SUCCEED) 
     169             :         {
     170           0 :                 fprintf(stderr, "ct_command(CS_LANG_CMD) failed\n");
     171           0 :                 return 1;
     172             :         }
     173             : 
     174             :         /*
     175             :          * Clear and setup the CS_DATAFMT structure, then pass
     176             :          * each of the parameters for the query.
     177             :          */
     178          24 :         memset(&datafmt, 0, sizeof(datafmt));
     179          24 :         if (useNames)
     180           8 :                 strcpy(datafmt.name, "@in1");
     181             :         else
     182             :                 datafmt.name[0] = 0;
     183          24 :         datafmt.maxlength = 255;
     184          24 :         datafmt.namelen = CS_NULLTERM;
     185             :         datafmt.datatype = CS_CHAR_TYPE;
     186          24 :         datafmt.status = CS_INPUTVALUE;
     187             : 
     188             :         /*
     189             :          * The character string variable is filled in by the RPC so pass NULL
     190             :          * for the data 0 for data length, and -1 for the indicator arguments.
     191             :          */
     192          24 :         ret = ct_param(cmd, &datafmt, dummy_name, strlen(dummy_name), 0);
     193          24 :         if (CS_SUCCEED != ret) {
     194           0 :                 fprintf(stderr, "ct_param(char) failed\n");
     195           0 :                 return 1;
     196             :         }
     197             : 
     198          24 :         if (useNames)
     199           8 :                 strcpy(datafmt.name, "@in2");
     200             :         else
     201          16 :                 datafmt.name[0] = 0;
     202          24 :         datafmt.maxlength = 255;
     203          24 :         datafmt.namelen = CS_NULLTERM;
     204          24 :         datafmt.datatype = CS_CHAR_TYPE;
     205          24 :         datafmt.status = CS_INPUTVALUE;
     206             : 
     207          24 :         ret = ct_param(cmd, &datafmt, dummy_name2, strlen(dummy_name2), 0);
     208          24 :         if (CS_SUCCEED != ret) {
     209           0 :                 fprintf(stderr, "ct_param(char) failed\n");
     210           0 :                 return 1;
     211             :         }
     212             : 
     213          24 :         if (useNames)
     214           8 :                 strcpy(datafmt.name, "@in3");
     215             :         else
     216          16 :                 datafmt.name[0] = 0;
     217          24 :         datafmt.namelen = CS_NULLTERM;
     218          24 :         datafmt.datatype = CS_INT_TYPE;
     219          24 :         datafmt.status = CS_INPUTVALUE;
     220             : 
     221          24 :         ret = ct_param(cmd, &datafmt, (CS_VOID *) & intvar, CS_SIZEOF(CS_INT), 0);
     222          24 :         if (CS_SUCCEED != ret) {
     223           0 :                 fprintf(stderr, "ct_param(int) failed\n");
     224           0 :                 return 1;
     225             :         }
     226             : 
     227          24 :         if (useNames)
     228           8 :                 strcpy(datafmt.name, "@moneyval");
     229             :         else
     230          16 :                 datafmt.name[0] = 0;
     231          24 :         datafmt.namelen = CS_NULLTERM;
     232          24 :         datafmt.datatype = CS_MONEY_TYPE;
     233          24 :         datafmt.status = CS_INPUTVALUE;
     234             : 
     235          24 :         ret = ct_param(cmd, &datafmt, (CS_VOID *) & moneyvar, CS_SIZEOF(CS_MONEY), 0);
     236          24 :         if (CS_SUCCEED != ret) {
     237           0 :                 fprintf(stderr, "ct_param(money) failed\n");
     238           0 :                 return 1;
     239             :         }
     240             : 
     241          24 :         if (useNames)
     242           8 :                 strcpy(datafmt.name, "@dateval");
     243             :         else
     244          16 :                 datafmt.name[0] = 0;
     245          24 :         datafmt.namelen = CS_NULLTERM;
     246          24 :         datafmt.datatype = CS_DATETIME_TYPE;
     247          24 :         datafmt.status = CS_INPUTVALUE;
     248          24 :         memset(&datevar, 0, sizeof(CS_DATEREC));
     249          24 :         datevar.dateyear = 2003;
     250          24 :         datevar.datemonth = 2;
     251          24 :         datevar.datedmonth = 1;
     252             : 
     253          24 :         ret = ct_param(cmd, &datafmt, &datevar, 0, 0);
     254          24 :         if (CS_SUCCEED != ret) {
     255           0 :                 fprintf(stderr, "ct_param(datetime) failed");
     256           0 :                 return 1;
     257             :         }
     258             : 
     259          24 :         if (useNames)
     260           8 :                 strcpy(datafmt.name, "@floatval");
     261             :         else
     262          16 :                 datafmt.name[0] = 0;
     263          24 :         datafmt.namelen = CS_NULLTERM;
     264          24 :         datafmt.datatype = CS_FLOAT_TYPE;
     265          24 :         datafmt.status = CS_INPUTVALUE;
     266             : 
     267          24 :         ret = ct_param(cmd, &datafmt, &floatvar, 0, 0);
     268          24 :         if (CS_SUCCEED != ret) {
     269           0 :                 fprintf(stderr, "ct_param(float) failed");
     270           0 :                 return 1;
     271             :         }
     272             : 
     273             :         /*
     274             :          * Send the command to the server
     275             :          */
     276          24 :         if (ct_send(cmd) != CS_SUCCEED) {
     277           0 :                 fprintf(stderr, "ct_send(CS_LANG_CMD) failed\n");
     278           0 :                 return 1;
     279             :         }
     280             : 
     281             :         /*
     282             :          * Process the results.
     283             :          */
     284          72 :         while ((ret = ct_results(cmd, &res_type)) == CS_SUCCEED) {
     285          48 :                 switch ((int) res_type) {
     286             : 
     287          48 :                 case CS_CMD_SUCCEED:
     288             :                 case CS_CMD_DONE:
     289             :                         {
     290          48 :                                 CS_INT rowsAffected=0;
     291          48 :                                 ct_res_info(cmd, CS_ROW_COUNT, &rowsAffected, CS_UNUSED, NULL);
     292          48 :                                 if (1 != rowsAffected) 
     293           0 :                                         fprintf(stderr, "insert touched %d rows instead of 1\n", rowsAffected);
     294             :                                 else
     295             :                                         rows_found = 1;
     296             :                         }
     297          48 :                         break;
     298             : 
     299           0 :                 case CS_CMD_FAIL:
     300             :                         /*
     301             :                          * The server encountered an error while
     302             :                          * processing our command.
     303             :                          */
     304           0 :                         fprintf(stderr, "ct_results returned CS_CMD_FAIL.\n");
     305           0 :                         break;
     306             : 
     307           0 :                 case CS_STATUS_RESULT:
     308             :                         /*
     309             :                          * The server encountered an error while
     310             :                          * processing our command.
     311             :                          */
     312           0 :                         fprintf(stderr, "ct_results returned CS_STATUS_RESULT.\n");
     313           0 :                         break;
     314             : 
     315           0 :                 default:
     316             :                         /*
     317             :                          * We got something unexpected.
     318             :                          */
     319           0 :                         fprintf(stderr, "ct_results returned unexpected result type %d\n", res_type);
     320           0 :                         return 1;
     321             :                 }
     322             :         }
     323          24 :         if (ret != CS_END_RESULTS) {
     324           0 :                 fprintf(stderr, "ct_results returned unexpected result %d.\n", (int) ret);
     325           0 :                 exit(1);
     326             :         }
     327             : 
     328          24 :         if (!rows_found) {
     329           0 :                 fprintf(stderr, "expected 1 rows inserted, inserted %d.\n", (int) rowsAffected);
     330           0 :                 exit(1);
     331             :         }
     332             : 
     333             :         /* test row inserted */
     334          24 :         ret = run_command(cmd, "if not exists(select * from #ctparam_lang where name = 'joe blow' and name2 is not null and age = 2) select 1");
     335          24 :         if (ret != CS_SUCCEED) {
     336           0 :                 fprintf(stderr, "check row inserted failed\n");
     337           0 :                 exit(1);
     338             :         }
     339             : 
     340             :         return 0;
     341             : }
     342             : 
     343             : CS_RETCODE
     344           0 : ex_clientmsg_cb(CS_CONTEXT * context, CS_CONNECTION * connection, CS_CLIENTMSG * errmsg)
     345             : {
     346           0 :         printf("\nOpen Client Message:\n");
     347           0 :         printf("Message number: LAYER = (%d) ORIGIN = (%d) ", CS_LAYER(errmsg->msgnumber), CS_ORIGIN(errmsg->msgnumber));
     348           0 :         printf("SEVERITY = (%d) NUMBER = (%d)\n", CS_SEVERITY(errmsg->msgnumber), CS_NUMBER(errmsg->msgnumber));
     349           0 :         printf("Message String: %s\n", errmsg->msgstring);
     350           0 :         if (errmsg->osstringlen > 0) {
     351           0 :                 printf("Operating System Error: %s\n", errmsg->osstring);
     352             :         }
     353           0 :         fflush(stdout);
     354             : 
     355           0 :         return CS_SUCCEED;
     356             : }
     357             : 
     358             : CS_RETCODE
     359           0 : ex_servermsg_cb(CS_CONTEXT * context, CS_CONNECTION * connection, CS_SERVERMSG * srvmsg)
     360             : {
     361           0 :         printf("\nServer message:\n");
     362           0 :         printf("Message number: %d, Severity %d, ", srvmsg->msgnumber, srvmsg->severity);
     363           0 :         printf("State %d, Line %d\n", srvmsg->state, srvmsg->line);
     364             : 
     365           0 :         if (srvmsg->svrnlen > 0) {
     366           0 :                 printf("Server '%s'\n", srvmsg->svrname);
     367             :         }
     368             : 
     369           0 :         if (srvmsg->proclen > 0) {
     370           0 :                 printf(" Procedure '%s'\n", srvmsg->proc);
     371             :         }
     372             : 
     373           0 :         printf("Message String: %s\n", srvmsg->text);
     374           0 :         fflush(stdout);
     375             : 
     376           0 :         return CS_SUCCEED;
     377             : }

Generated by: LCOV version 1.13