1 /* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
3 * Copyright (C) 2001-2003, Ximian, Inc.
11 #include <libsoup/soup.h>
13 #include "test-utils.h"
16 static const char *uri = "http://localhost:47524/xmlrpc-server.php";
18 static const char *const value_type[] = {
31 do_xmlrpc (const char *method, GValue *retval, ...)
39 va_start (args, retval);
40 params = soup_value_array_from_args (args);
43 body = soup_xmlrpc_build_method_call (method, params->values,
45 g_value_array_free (params);
49 msg = soup_message_new ("POST", uri);
50 soup_message_set_request (msg, "text/xml", SOUP_MEMORY_TAKE,
52 soup_session_send_message (session, msg);
54 if (debug_level >= 3) {
55 debug_printf (3, "\n%s\n%d %s\n%s\n",
56 msg->request_body->data,
57 msg->status_code, msg->reason_phrase,
58 msg->response_body->data);
61 if (!SOUP_STATUS_IS_SUCCESSFUL (msg->status_code)) {
62 debug_printf (1, "ERROR: %d %s\n", msg->status_code,
68 if (!soup_xmlrpc_parse_method_response (msg->response_body->data,
69 msg->response_body->length,
72 debug_printf (1, "FAULT: %d %s\n", err->code, err->message);
75 debug_printf (1, "ERROR: could not parse response\n");
85 check_xmlrpc (GValue *value, GType type, ...)
89 if (!G_VALUE_HOLDS (value, type)) {
90 debug_printf (1, "ERROR: could not parse response\n");
91 g_value_unset (value);
95 va_start (args, type);
96 SOUP_VALUE_GETV (value, type, args);
105 int i, val, sum, result;
109 debug_printf (1, "sum (array of int -> int): ");
111 ints = g_value_array_new (10);
112 for (i = sum = 0; i < 10; i++) {
114 debug_printf (2, "%s%d", i == 0 ? "[" : ", ", val);
115 soup_value_array_append (ints, G_TYPE_INT, val);
118 debug_printf (2, "] -> ");
120 ok = (do_xmlrpc ("sum", &retval,
121 G_TYPE_VALUE_ARRAY, ints,
123 check_xmlrpc (&retval, G_TYPE_INT, &result));
124 g_value_array_free (ints);
129 debug_printf (2, "%d: ", result);
130 debug_printf (1, "%s\n", result == sum ? "OK!" : "WRONG!");
131 return result == sum;
135 test_countBools (void)
138 int i, trues, falses;
140 int ret_trues, ret_falses;
144 debug_printf (1, "countBools (array of boolean -> struct of ints): ");
146 bools = g_value_array_new (10);
147 for (i = trues = falses = 0; i < 10; i++) {
148 val = rand () > (RAND_MAX / 2);
149 debug_printf (2, "%s%c", i == 0 ? "[" : ", ", val ? 'T' : 'F');
150 soup_value_array_append (bools, G_TYPE_BOOLEAN, val);
156 debug_printf (2, "] -> ");
158 ok = (do_xmlrpc ("countBools", &retval,
159 G_TYPE_VALUE_ARRAY, bools,
161 check_xmlrpc (&retval, G_TYPE_HASH_TABLE, &result));
162 g_value_array_free (bools);
166 if (!soup_value_hash_lookup (result, "true", G_TYPE_INT, &ret_trues)) {
167 debug_printf (1, "NO 'true' value in response\n");
170 if (!soup_value_hash_lookup (result, "false", G_TYPE_INT, &ret_falses)) {
171 debug_printf (1, "NO 'false' value in response\n");
174 g_hash_table_destroy (result);
176 debug_printf (2, "{ true: %d, false: %d } ", ret_trues, ret_falses);
177 ok = (trues == ret_trues) && (falses == ret_falses);
178 debug_printf (1, "%s\n", ok ? "OK!" : "WRONG!");
185 GByteArray *data, *result;
189 gsize digest_len = sizeof (digest);
193 debug_printf (1, "md5sum (base64 -> base64): ");
195 data = g_byte_array_new ();
196 g_byte_array_set_size (data, 256);
197 for (i = 0; i < data->len; i++)
198 data->data[i] = (char)(rand ());
200 checksum = g_checksum_new (G_CHECKSUM_MD5);
201 g_checksum_update (checksum, data->data, data->len);
202 g_checksum_get_digest (checksum, digest, &digest_len);
203 g_checksum_free (checksum);
205 ok = (do_xmlrpc ("md5sum", &retval,
206 SOUP_TYPE_BYTE_ARRAY, data,
208 check_xmlrpc (&retval, SOUP_TYPE_BYTE_ARRAY, &result));
209 g_byte_array_free (data, TRUE);
213 if (result->len != digest_len) {
214 debug_printf (1, "result has WRONG length (%d)\n", result->len);
215 g_byte_array_free (result, TRUE);
219 ok = (memcmp (digest, result->data, digest_len) == 0);
220 debug_printf (1, "%s\n", ok ? "OK!" : "WRONG!");
221 g_byte_array_free (result, TRUE);
226 test_dateChange (void)
228 GHashTable *structval;
229 SoupDate *date, *result;
234 debug_printf (1, "dateChange (struct of time and ints -> time): ");
236 structval = soup_value_hash_new ();
238 date = soup_date_new (1970 + (rand () % 50),
244 soup_value_hash_insert (structval, "date", SOUP_TYPE_DATE, date);
246 if (debug_level >= 2) {
247 timestamp = soup_date_to_string (date, SOUP_DATE_ISO8601_XMLRPC);
248 debug_printf (2, "{ date: %s", timestamp);
253 date->year = 1970 + (rand () % 50);
254 debug_printf (2, ", tm_year: %d", date->year - 1900);
255 soup_value_hash_insert (structval, "tm_year",
256 G_TYPE_INT, date->year - 1900);
259 date->month = 1 + rand () % 12;
260 debug_printf (2, ", tm_mon: %d", date->month - 1);
261 soup_value_hash_insert (structval, "tm_mon",
262 G_TYPE_INT, date->month - 1);
265 date->day = 1 + rand () % 28;
266 debug_printf (2, ", tm_mday: %d", date->day);
267 soup_value_hash_insert (structval, "tm_mday",
268 G_TYPE_INT, date->day);
271 date->hour = rand () % 24;
272 debug_printf (2, ", tm_hour: %d", date->hour);
273 soup_value_hash_insert (structval, "tm_hour",
274 G_TYPE_INT, date->hour);
277 date->minute = rand () % 60;
278 debug_printf (2, ", tm_min: %d", date->minute);
279 soup_value_hash_insert (structval, "tm_min",
280 G_TYPE_INT, date->minute);
283 date->second = rand () % 60;
284 debug_printf (2, ", tm_sec: %d", date->second);
285 soup_value_hash_insert (structval, "tm_sec",
286 G_TYPE_INT, date->second);
289 debug_printf (2, " } -> ");
291 ok = (do_xmlrpc ("dateChange", &retval,
292 G_TYPE_HASH_TABLE, structval,
294 check_xmlrpc (&retval, SOUP_TYPE_DATE, &result));
295 g_hash_table_destroy (structval);
297 soup_date_free (date);
301 if (debug_level >= 2) {
302 timestamp = soup_date_to_string (result, SOUP_DATE_ISO8601_XMLRPC);
303 debug_printf (2, "%s: ", timestamp);
307 ok = ((date->year == result->year) &&
308 (date->month == result->month) &&
309 (date->day == result->day) &&
310 (date->hour == result->hour) &&
311 (date->minute == result->minute) &&
312 (date->second == result->second));
313 soup_date_free (date);
314 soup_date_free (result);
316 debug_printf (1, "%s\n", ok ? "OK!" : "WRONG!");
320 static const char *const echo_strings[] = {
324 "& so is <this>"
326 #define N_ECHO_STRINGS G_N_ELEMENTS (echo_strings)
331 GValueArray *originals, *echoes;
335 debug_printf (1, "echo (array of string -> array of string): ");
337 originals = g_value_array_new (N_ECHO_STRINGS);
338 for (i = 0; i < N_ECHO_STRINGS; i++) {
339 soup_value_array_append (originals, G_TYPE_STRING, echo_strings[i]);
340 debug_printf (2, "%s\"%s\"", i == 0 ? "[" : ", ", echo_strings[i]);
342 debug_printf (2, "] -> ");
344 if (!(do_xmlrpc ("echo", &retval,
345 G_TYPE_VALUE_ARRAY, originals,
347 check_xmlrpc (&retval, G_TYPE_VALUE_ARRAY, &echoes))) {
348 g_value_array_free (originals);
351 g_value_array_free (originals);
353 if (debug_level >= 2) {
354 for (i = 0; i < echoes->n_values; i++) {
355 debug_printf (2, "%s\"%s\"", i == 0 ? "[" : ", ",
356 g_value_get_string (&echoes->values[i]));
358 debug_printf (2, "] -> ");
361 if (echoes->n_values != N_ECHO_STRINGS) {
362 debug_printf (1, " WRONG! Wrong number of return strings");
363 g_value_array_free (echoes);
367 for (i = 0; i < echoes->n_values; i++) {
368 if (strcmp (echo_strings[i], g_value_get_string (&echoes->values[i])) != 0) {
369 debug_printf (1, " WRONG! Mismatch at %d\n", i + 1);
370 g_value_array_free (echoes);
375 debug_printf (1, "OK!\n");
376 g_value_array_free (echoes);
381 main (int argc, char **argv)
383 test_init (argc, argv, NULL);
388 session = soup_test_session_new (SOUP_TYPE_SESSION_SYNC, NULL);
392 if (!test_countBools ())
396 if (!test_dateChange ())
401 soup_session_abort (session);
402 g_object_unref (session);