1 /* vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
2 *
3 * Gearmand client and server library.
4 *
5 * Copyright (C) 2011 Data Differential, http://datadifferential.com/
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions are
10 * met:
11 *
12 * * Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 *
15 * * Redistributions in binary form must reproduce the above
16 * copyright notice, this list of conditions and the following disclaimer
17 * in the documentation and/or other materials provided with the
18 * distribution.
19 *
20 * * The names of its contributors may not be used to endorse or
21 * promote products derived from this software without specific prior
22 * written permission.
23 *
24 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
25 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
26 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
27 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
28 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
29 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
30 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
31 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
32 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
34 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 *
36 */
37
38 #include "gear_config.h"
39
40 #include <libtest/test.hpp>
41
42 using namespace libtest;
43
44 #include <cstring>
45 #include <cassert>
46
47 #include <libgearman/gearman.h>
48
49 #include <tests/basic.h>
50 #include <tests/context.h>
51 #include <tests/start_worker.h>
52
53 #include "libgearman/client.hpp"
54 using namespace org::gearmand;
55
56 #include "tests/workers/v2/called.h"
57
58 #ifndef __INTEL_COMPILER
59 #pragma GCC diagnostic ignored "-Wold-style-cast"
60 #endif
61
client_echo_fail_test(void * object)62 test_return_t client_echo_fail_test(void *object)
63 {
64 Context *test= (Context *)object;
65 test_truth(test);
66
67 libgearman::Client client(in_port_t(20));
68
69 gearman_return_t rc= gearman_client_echo(&client, test_literal_param("This should never work"));
70 test_true(gearman_failed(rc));
71
72 return TEST_SUCCESS;
73 }
74
client_echo_test(void * object)75 test_return_t client_echo_test(void *object)
76 {
77 Context *test= (Context *)object;
78 test_truth(test);
79
80 libgearman::Client client(test->port());
81
82 ASSERT_EQ(gearman_client_echo(&client, test_literal_param("This is my echo test")), GEARMAN_SUCCESS);
83
84 return TEST_SUCCESS;
85 }
86
worker_echo_test(void * object)87 test_return_t worker_echo_test(void *object)
88 {
89 Context *test= (Context *)object;
90 test_truth(test);
91
92 gearman_worker_st *worker= test->worker;
93 test_truth(worker);
94
95 ASSERT_EQ(gearman_worker_echo(worker, test_literal_param("This is my echo test")),
96 GEARMAN_SUCCESS);
97
98 return TEST_SUCCESS;
99 }
100
queue_clean(void * object)101 test_return_t queue_clean(void *object)
102 {
103 Context *test= (Context *)object;
104 test_truth(test);
105 gearman_worker_st *worker= test->worker;
106 test_truth(worker);
107
108 gearman_worker_set_timeout(worker, 3000);
109
110 Called called;
111 gearman_function_t counter_function= gearman_function_create(called_worker);
112 ASSERT_EQ(gearman_worker_define_function(worker,
113 test->worker_function_name(), strlen(test->worker_function_name()),
114 counter_function,
115 5, &called), GEARMAN_SUCCESS);
116
117 // Clean out any jobs that might still be in the queue from failed tests.
118 while (GEARMAN_SUCCESS == gearman_worker_work(worker)) {};
119
120 return TEST_SUCCESS;
121 }
122
queue_add(void * object)123 test_return_t queue_add(void *object)
124 {
125 Context *test= (Context *)object;
126 test_truth(test);
127
128 test->run_worker= false;
129
130 libgearman::Client client(test->port());
131
132 {
133 gearman_return_t rc= gearman_client_echo(&client, test_literal_param("echo test message"));
134 ASSERT_EQ(rc, GEARMAN_SUCCESS);
135 }
136
137 {
138 gearman_job_handle_t job_handle= {};
139 gearman_return_t ret= gearman_client_do_background(&client, test->worker_function_name(), NULL,
140 test->worker_function_name(), strlen(test->worker_function_name()),
141 job_handle);
142 ASSERT_EQ(ret, GEARMAN_SUCCESS);
143 test_truth(job_handle[0]);
144
145 gearman_return_t rc;
146 do {
147 rc= gearman_client_job_status(&client, job_handle, NULL, NULL, NULL, NULL);
148 test_true(rc != GEARMAN_IN_PROGRESS);
149 } while (gearman_continue(rc) and rc != GEARMAN_JOB_EXISTS); // We need to exit on these values since the job will never run
150 test_true(rc == GEARMAN_JOB_EXISTS or rc == GEARMAN_SUCCESS);
151 }
152
153 test->run_worker= true;
154
155 return TEST_SUCCESS;
156 }
157
queue_worker(void * object)158 test_return_t queue_worker(void *object)
159 {
160 Context *test= (Context *)object;
161 test_truth(test);
162
163 // Setup job
164 ASSERT_EQ(TEST_SUCCESS, queue_add(object));
165
166 gearman_worker_st *worker= test->worker;
167 test_truth(worker);
168
169 test_true(test->run_worker);
170
171 Called counter;
172 gearman_function_t counter_function= gearman_function_create(called_worker);
173 ASSERT_EQ(gearman_worker_define_function(worker,
174 test->worker_function_name(), strlen(test->worker_function_name()),
175 counter_function,
176 0, &counter), GEARMAN_SUCCESS);
177
178 gearman_return_t rc= gearman_worker_work(worker);
179 ASSERT_EQ(rc, GEARMAN_SUCCESS);
180
181 test_truth(counter.count());
182
183 return TEST_SUCCESS;
184 }
185
186 #define NUMBER_OF_WORKERS 10
187 #define NUMBER_OF_JOBS 40
188 #define JOB_SIZE 100
lp_734663(void * object)189 test_return_t lp_734663(void *object)
190 {
191 Context *test= (Context *)object;
192 test_truth(test);
193
194 const char *worker_function_name= "drizzle_queue_test";
195
196 uint8_t value[JOB_SIZE]= { 'x' };
197 memset(&value, 'x', sizeof(value));
198
199 libgearman::Client client(test->port());
200
201 ASSERT_EQ(gearman_client_echo(&client, value, sizeof(value)), GEARMAN_SUCCESS);
202
203 for (uint32_t x= 0; x < NUMBER_OF_JOBS; x++)
204 {
205 gearman_job_handle_t job_handle= {};
206 ASSERT_EQ(gearman_client_do_background(&client, worker_function_name, NULL, value, sizeof(value), job_handle), GEARMAN_SUCCESS);
207 test_truth(job_handle[0]);
208 }
209
210 struct worker_handle_st *worker_handle[NUMBER_OF_WORKERS];
211
212 Called called;
213 gearman_function_t counter_function_fn= gearman_function_create(called_worker);
214 for (uint32_t x= 0; x < NUMBER_OF_WORKERS; x++)
215 {
216 worker_handle[x]= test_worker_start(test->port(), NULL, worker_function_name, counter_function_fn, &called, gearman_worker_options_t());
217 test_true(worker_handle[x]);
218 }
219
220 while (called.count() < NUMBER_OF_JOBS)
221 {
222 libtest::dream(0, static_cast<long>(gearman_timeout(&client) *1000));
223 }
224
225 for (uint32_t x= 0; x < NUMBER_OF_WORKERS; x++)
226 {
227 worker_handle[x]->shutdown();
228 }
229
230 for (uint32_t x= 0; x < NUMBER_OF_WORKERS; x++)
231 {
232 delete worker_handle[x];
233 }
234
235 return TEST_SUCCESS;
236 }
237