Line data Source code
1 : #include "common.h"
2 : #include <assert.h>
3 :
4 : /* Test compute results */
5 :
6 : /*
7 : * This it's quite important cause it test different result types
8 : * mssql odbc have also some extension not supported by FreeTDS
9 : * and declared in odbcss.h
10 : */
11 :
12 : static char col1[256], col2[256];
13 : static SQLLEN ind1, ind2;
14 :
15 : static int main_line;
16 :
17 : static void
18 128 : TestName(SQLSMALLINT index, const char *expected_name)
19 : {
20 : SQLTCHAR name[128];
21 : char buf[256];
22 : SQLSMALLINT len, type;
23 :
24 : #define NAME_TEST \
25 : do { \
26 : if (strcmp(C(name), expected_name) != 0) \
27 : { \
28 : sprintf(buf, "line %d: wrong name in column %d expected '%s' got '%s'", \
29 : main_line, index, expected_name, C(name)); \
30 : ODBC_REPORT_ERROR(buf); \
31 : } \
32 : } while(0)
33 :
34 : /* retrieve with SQLDescribeCol */
35 128 : CHKDescribeCol(index, name, TDS_VECTOR_SIZE(name), &len, &type, NULL, NULL, NULL, "S");
36 128 : NAME_TEST;
37 :
38 : /* retrieve with SQLColAttribute */
39 128 : CHKColAttribute(index, SQL_DESC_NAME, name, TDS_VECTOR_SIZE(name), &len, NULL, "S");
40 128 : if (odbc_db_is_microsoft())
41 96 : NAME_TEST;
42 128 : CHKColAttribute(index, SQL_DESC_LABEL, name, TDS_VECTOR_SIZE(name), &len, NULL, "S");
43 128 : NAME_TEST;
44 128 : }
45 :
46 : static void
47 128 : CheckFetch(const char *c1name, const char *c1, const char *c2)
48 : {
49 128 : int error = 0;
50 :
51 128 : TestName(1, c1name);
52 :
53 128 : CHKFetch("S");
54 :
55 128 : if (strlen(c1) != ind1 || strcmp(c1, col1) != 0) {
56 0 : fprintf(stderr, "%s:%d: Column 1 error '%s' (%d) expected '%s' (%d)\n", __FILE__, main_line, col1, (int) ind1, c1,
57 : (int) strlen(c1));
58 0 : error = 1;
59 : }
60 :
61 128 : if (strlen(c2) != ind2 || strcmp(c2, col2) != 0) {
62 0 : fprintf(stderr, "%s:%d: Column 2 error '%s' (%d) expected '%s' (%d)\n", __FILE__, main_line, col2, (int) ind2, c2,
63 : (int) strlen(c2));
64 0 : error = 1;
65 : }
66 :
67 128 : if (error)
68 0 : exit(1);
69 128 : }
70 :
71 : #define CheckFetch main_line = __LINE__; CheckFetch
72 :
73 10 : TEST_MAIN()
74 : {
75 10 : odbc_connect();
76 :
77 : /* MSSQL 2012+, compute not supported */
78 10 : if (odbc_db_is_microsoft() && odbc_db_version_int() >= 0x0b000000u) {
79 2 : odbc_disconnect();
80 2 : return 0;
81 : }
82 :
83 8 : odbc_command("create table #tmp1 (c varchar(20), i int)");
84 8 : odbc_command("insert into #tmp1 values('pippo', 12)");
85 8 : odbc_command("insert into #tmp1 values('pippo', 34)");
86 8 : odbc_command("insert into #tmp1 values('pluto', 1)");
87 8 : odbc_command("insert into #tmp1 values('pluto', 2)");
88 8 : odbc_command("insert into #tmp1 values('pluto', 3)");
89 :
90 :
91 : /*
92 : * TODO skip rows/column on compute (compute.c)
93 : * TODO check rows/column after moreresults after compute
94 : */
95 :
96 :
97 : /* select * from #tmp1 compute sum(i) */
98 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
99 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
100 8 : odbc_command("select * from #tmp1 order by c, i compute sum(i)");
101 8 : CheckFetch("c", "pippo", "12");
102 8 : CheckFetch("c", "pippo", "34");
103 8 : CheckFetch("c", "pluto", "1");
104 8 : CheckFetch("c", "pluto", "2");
105 8 : CheckFetch("c", "pluto", "3");
106 8 : CHKFetch("No");
107 8 : CHKMoreResults("S");
108 :
109 : /* why I need to rebind ?? ms bug of feature ?? */
110 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
111 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
112 8 : col2[0] = '@';
113 8 : CheckFetch("sum", "52", "@");
114 8 : CHKFetch("No");
115 8 : CHKMoreResults("No");
116 :
117 :
118 :
119 :
120 : /* select * from #tmp1 order by c compute sum(i) by c */
121 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
122 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
123 8 : odbc_command("select c as mao, i from #tmp1 order by c, i compute sum(i) by c compute max(i)");
124 8 : CheckFetch("mao", "pippo", "12");
125 8 : CheckFetch("mao", "pippo", "34");
126 8 : CHKFetch("No");
127 8 : CHKMoreResults("S");
128 :
129 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
130 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
131 8 : strcpy(col2, "##");
132 8 : CheckFetch("sum", "46", "##");
133 8 : CHKFetch("No");
134 8 : CHKMoreResults("S");
135 :
136 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
137 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
138 8 : CheckFetch("mao", "pluto", "1");
139 8 : CheckFetch("mao", "pluto", "2");
140 8 : CheckFetch("mao", "pluto", "3");
141 8 : CHKFetch("No");
142 8 : CHKMoreResults("S");
143 :
144 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
145 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
146 8 : strcpy(col2, "%");
147 8 : CheckFetch("sum", "6", "%");
148 8 : CHKFetch("No");
149 8 : CHKMoreResults("S");
150 :
151 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
152 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
153 8 : strcpy(col2, "&");
154 8 : CheckFetch("max", "34", "&");
155 8 : CHKFetch("No");
156 8 : CHKMoreResults("No");
157 :
158 :
159 :
160 : /* test skip recordset with computed rows */
161 :
162 : /* select * from #tmp1 where i = 2 compute min(i) */
163 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
164 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
165 8 : odbc_command("select * from #tmp1 where i = 2 or i = 34 order by c, i compute min(i) by c");
166 8 : CheckFetch("c", "pippo", "34");
167 8 : CHKFetch("No");
168 8 : CHKMoreResults("S");
169 :
170 : /* here just skip results, before a row */
171 8 : CHKMoreResults("S");
172 :
173 8 : SQLBindCol(odbc_stmt, 1, SQL_C_CHAR, col1, sizeof(col1), &ind1);
174 8 : SQLBindCol(odbc_stmt, 2, SQL_C_CHAR, col2, sizeof(col2), &ind2);
175 8 : CheckFetch("c", "pluto", "2");
176 8 : CHKFetch("No");
177 8 : CHKMoreResults("S");
178 :
179 : /* here just skip results, before done */
180 8 : CHKMoreResults("No");
181 :
182 :
183 8 : odbc_disconnect();
184 8 : return 0;
185 : }
|