phpBB
Statistics
| Revision:

root / trunk / phpBB / includes / captcha / plugins / captcha_abstract.php

History | View | Annotate | Download (8.5 kB)

1 9532 toonarmy
<?php
2 8889 Kellanved
/**
3 8889 Kellanved
*
4 8889 Kellanved
* @package VC
5 9532 toonarmy
* @copyright (c) 2006, 2008 phpBB Group
6 11653 git-gate
* @license http://opensource.org/licenses/gpl-2.0.php GNU General Public License v2
7 8889 Kellanved
*
8 8889 Kellanved
*/
9 8889 Kellanved
10 8889 Kellanved
/**
11 8889 Kellanved
* @ignore
12 8889 Kellanved
*/
13 8889 Kellanved
if (!defined('IN_PHPBB'))
14 8889 Kellanved
{
15 8889 Kellanved
        exit;
16 8889 Kellanved
}
17 8889 Kellanved
18 8889 Kellanved
19 8889 Kellanved
/**
20 9554 acydburn
* This class holds the code shared by the two default 3.0.x CAPTCHAs.
21 9554 acydburn
*
22 9554 acydburn
* @package VC
23 8889 Kellanved
*/
24 11557 git-gate
class phpbb_captcha_plugins_captcha_abstract
25 8889 Kellanved
{
26 9524 Kellanved
        var $confirm_id;
27 9524 Kellanved
        var $confirm_code;
28 9524 Kellanved
        var $code;
29 9524 Kellanved
        var $seed;
30 9626 Kellanved
        var $attempts = 0;
31 9524 Kellanved
        var $type;
32 9672 Kellanved
        var $solved = 0;
33 9576 Kellanved
        var $captcha_vars = false;
34 8889 Kellanved
35 8889 Kellanved
        function init($type)
36 8889 Kellanved
        {
37 8889 Kellanved
                global $config, $db, $user;
38 9554 acydburn
39 8889 Kellanved
                // read input
40 9707 Kellanved
                $this->confirm_id = request_var('confirm_id', '');
41 8889 Kellanved
                $this->confirm_code = request_var('confirm_code', '');
42 9524 Kellanved
                $refresh = request_var('refresh_vc', false) && $config['confirm_refresh'];
43 9554 acydburn
44 8889 Kellanved
                $this->type = (int) $type;
45 9554 acydburn
46 9707 Kellanved
                if (!strlen($this->confirm_id) || !$this->load_code())
47 8889 Kellanved
                {
48 8889 Kellanved
                        // we have no confirm ID, better get ready to display something
49 8889 Kellanved
                        $this->generate_code();
50 8889 Kellanved
                }
51 9524 Kellanved
                else if ($refresh)
52 9524 Kellanved
                {
53 9524 Kellanved
                        $this->regenerate_code();
54 9524 Kellanved
                }
55 8889 Kellanved
        }
56 9554 acydburn
57 8889 Kellanved
        function execute_demo()
58 8889 Kellanved
        {
59 8889 Kellanved
                global $user;
60 9554 acydburn
61 10751 git-gate
                $this->code = gen_rand_string_friendly(mt_rand(CAPTCHA_MIN_CHARS, CAPTCHA_MAX_CHARS));
62 8889 Kellanved
                $this->seed = hexdec(substr(unique_id(), 4, 10));
63 9554 acydburn
64 8889 Kellanved
                // compute $seed % 0x7fffffff
65 8889 Kellanved
                $this->seed -= 0x7fffffff * floor($this->seed / 0x7fffffff);
66 9554 acydburn
67 9524 Kellanved
                $captcha = new captcha();
68 9921 Kellanved
                define('IMAGE_OUTPUT', 1);
69 9524 Kellanved
                $captcha->execute($this->code, $this->seed);
70 8889 Kellanved
        }
71 9554 acydburn
72 8889 Kellanved
        function execute()
73 8889 Kellanved
        {
74 8889 Kellanved
                if (empty($this->code))
75 8889 Kellanved
                {
76 8889 Kellanved
                        if (!$this->load_code())
77 8889 Kellanved
                        {
78 8889 Kellanved
                                // invalid request, bail out
79 8889 Kellanved
                                return false;
80 8889 Kellanved
                        }
81 8889 Kellanved
                }
82 9524 Kellanved
                $captcha = new captcha();
83 9921 Kellanved
                define('IMAGE_OUTPUT', 1);
84 9524 Kellanved
                $captcha->execute($this->code, $this->seed);
85 8889 Kellanved
        }
86 9554 acydburn
87 8889 Kellanved
        function get_template()
88 8889 Kellanved
        {
89 9524 Kellanved
                global $config, $user, $template, $phpEx, $phpbb_root_path;
90 10085 acydburn
91 9869 Kellanved
                if ($this->is_solved())
92 9869 Kellanved
                {
93 9869 Kellanved
                        return false;
94 9869 Kellanved
                }
95 9869 Kellanved
                else
96 9869 Kellanved
                {
97 9996 Kellanved
                        $link = append_sid($phpbb_root_path . 'ucp.' . $phpEx,  'mode=confirm&amp;confirm_id=' . $this->confirm_id . '&amp;type=' . $this->type);
98 10085 acydburn
                        $explain = $user->lang(($this->type != CONFIRM_POST) ? 'CONFIRM_EXPLAIN' : 'POST_CONFIRM_EXPLAIN', '<a href="mailto:' . htmlspecialchars($config['board_contact']) . '">', '</a>');
99 10085 acydburn
100 9869 Kellanved
                        $template->assign_vars(array(
101 9869 Kellanved
                                'CONFIRM_IMAGE_LINK'                => $link,
102 9939 bantu
                                'CONFIRM_IMAGE'                                => '<img src="' . $link . '" />',
103 9939 bantu
                                'CONFIRM_IMG'                                => '<img src="' . $link . '" />',
104 9869 Kellanved
                                'CONFIRM_ID'                                => $this->confirm_id,
105 9869 Kellanved
                                'S_CONFIRM_CODE'                        => true,
106 9869 Kellanved
                                'S_TYPE'                                        => $this->type,
107 9869 Kellanved
                                'S_CONFIRM_REFRESH'                        => ($config['enable_confirm'] && $config['confirm_refresh'] && $this->type == CONFIRM_REG) ? true : false,
108 9869 Kellanved
                                'L_CONFIRM_EXPLAIN'                        => $explain,
109 9869 Kellanved
                        ));
110 9554 acydburn
111 9869 Kellanved
                        return 'captcha_default.html';
112 9869 Kellanved
                }
113 8889 Kellanved
        }
114 9554 acydburn
115 8889 Kellanved
        function get_demo_template($id)
116 8889 Kellanved
        {
117 9524 Kellanved
                global $config, $user, $template, $phpbb_admin_path, $phpEx;
118 9554 acydburn
119 9576 Kellanved
                $variables = '';
120 10085 acydburn
121 9576 Kellanved
                if (is_array($this->captcha_vars))
122 9576 Kellanved
                {
123 9576 Kellanved
                        foreach ($this->captcha_vars as $captcha_var => $template_var)
124 9576 Kellanved
                        {
125 9576 Kellanved
                                $variables .= '&amp;' . rawurlencode($captcha_var) . '=' . request_var($captcha_var, (int) $config[$captcha_var]);
126 9576 Kellanved
                        }
127 9576 Kellanved
                }
128 9554 acydburn
129 8889 Kellanved
                // acp_captcha has a delivery function; let's use it
130 8889 Kellanved
                $template->assign_vars(array(
131 9996 Kellanved
                        'CONFIRM_IMAGE'                => append_sid($phpbb_admin_path . 'index.' . $phpEx, 'captcha_demo=1&amp;mode=visual&amp;i=' . $id . '&amp;select_captcha=' . $this->get_class_name()) . $variables,
132 8889 Kellanved
                        'CONFIRM_ID'                => $this->confirm_id,
133 8889 Kellanved
                ));
134 9554 acydburn
135 9609 Kellanved
                return 'captcha_default_acp_demo.html';
136 8889 Kellanved
        }
137 9554 acydburn
138 8889 Kellanved
        function get_hidden_fields()
139 8889 Kellanved
        {
140 8889 Kellanved
                $hidden_fields = array();
141 9554 acydburn
142 9581 Kellanved
                // this is required for posting.php - otherwise we would forget about the captcha being already solved
143 8889 Kellanved
                if ($this->solved)
144 8889 Kellanved
                {
145 8889 Kellanved
                        $hidden_fields['confirm_code'] = $this->confirm_code;
146 8889 Kellanved
                }
147 8889 Kellanved
                $hidden_fields['confirm_id'] = $this->confirm_id;
148 8889 Kellanved
                return $hidden_fields;
149 8889 Kellanved
        }
150 9554 acydburn
151 9524 Kellanved
        function garbage_collect($type)
152 8889 Kellanved
        {
153 8889 Kellanved
                global $db, $config;
154 8889 Kellanved
155 8889 Kellanved
                $sql = 'SELECT DISTINCT c.session_id
156 9554 acydburn
                        FROM ' . CONFIRM_TABLE . ' c
157 9554 acydburn
                        LEFT JOIN ' . SESSIONS_TABLE . ' s ON (c.session_id = s.session_id)
158 9554 acydburn
                        WHERE s.session_id IS NULL' .
159 9554 acydburn
                                ((empty($type)) ? '' : ' AND c.confirm_type = ' . (int) $type);
160 8889 Kellanved
                $result = $db->sql_query($sql);
161 8889 Kellanved
162 8889 Kellanved
                if ($row = $db->sql_fetchrow($result))
163 8889 Kellanved
                {
164 8889 Kellanved
                        $sql_in = array();
165 8889 Kellanved
                        do
166 8889 Kellanved
                        {
167 8889 Kellanved
                                $sql_in[] = (string) $row['session_id'];
168 8889 Kellanved
                        }
169 8889 Kellanved
                        while ($row = $db->sql_fetchrow($result));
170 8889 Kellanved
171 8889 Kellanved
                        if (sizeof($sql_in))
172 8889 Kellanved
                        {
173 8889 Kellanved
                                $sql = 'DELETE FROM ' . CONFIRM_TABLE . '
174 8889 Kellanved
                                        WHERE ' . $db->sql_in_set('session_id', $sql_in);
175 8889 Kellanved
                                $db->sql_query($sql);
176 8889 Kellanved
                        }
177 8889 Kellanved
                }
178 8889 Kellanved
                $db->sql_freeresult($result);
179 8889 Kellanved
        }
180 9554 acydburn
181 8889 Kellanved
        function uninstall()
182 8889 Kellanved
        {
183 9554 acydburn
                $this->garbage_collect(0);
184 8889 Kellanved
        }
185 9554 acydburn
186 8889 Kellanved
        function install()
187 8889 Kellanved
        {
188 8889 Kellanved
                return;
189 8889 Kellanved
        }
190 9554 acydburn
191 9707 Kellanved
        function validate()
192 8889 Kellanved
        {
193 8889 Kellanved
                global $config, $db, $user;
194 10085 acydburn
195 10558 git-gate
                if (empty($user->lang))
196 10558 git-gate
                {
197 10558 git-gate
                        $user->setup();
198 10558 git-gate
                }
199 10558 git-gate
200 9591 Kellanved
                $error = '';
201 8889 Kellanved
                if (!$this->confirm_id)
202 8889 Kellanved
                {
203 8889 Kellanved
                        $error = $user->lang['CONFIRM_CODE_WRONG'];
204 8889 Kellanved
                }
205 8889 Kellanved
                else
206 8889 Kellanved
                {
207 8889 Kellanved
                        if ($this->check_code())
208 8889 Kellanved
                        {
209 8889 Kellanved
                                $this->solved = true;
210 8889 Kellanved
                        }
211 8889 Kellanved
                        else
212 8889 Kellanved
                        {
213 8889 Kellanved
                                $error = $user->lang['CONFIRM_CODE_WRONG'];
214 8889 Kellanved
                        }
215 8889 Kellanved
                }
216 9554 acydburn
217 8889 Kellanved
                if (strlen($error))
218 8889 Kellanved
                {
219 9554 acydburn
                        // okay, incorrect answer. Let's ask a new question.
220 9626 Kellanved
                        $this->new_attempt();
221 8889 Kellanved
                        return $error;
222 8889 Kellanved
                }
223 8889 Kellanved
                else
224 8889 Kellanved
                {
225 8889 Kellanved
                        return false;
226 8889 Kellanved
                }
227 8889 Kellanved
        }
228 9554 acydburn
229 8889 Kellanved
        /**
230 8889 Kellanved
        * The old way to generate code, suitable for GD and non-GD. Resets the internal state.
231 8889 Kellanved
        */
232 9524 Kellanved
        function generate_code()
233 8889 Kellanved
        {
234 8889 Kellanved
                global $db, $user;
235 9554 acydburn
236 10751 git-gate
                $this->code = gen_rand_string_friendly(mt_rand(CAPTCHA_MIN_CHARS, CAPTCHA_MAX_CHARS));
237 8889 Kellanved
                $this->confirm_id = md5(unique_id($user->ip));
238 8889 Kellanved
                $this->seed = hexdec(substr(unique_id(), 4, 10));
239 9672 Kellanved
                $this->solved = 0;
240 8889 Kellanved
                // compute $seed % 0x7fffffff
241 8889 Kellanved
                $this->seed -= 0x7fffffff * floor($this->seed / 0x7fffffff);
242 8889 Kellanved
243 8889 Kellanved
                $sql = 'INSERT INTO ' . CONFIRM_TABLE . ' ' . $db->sql_build_array('INSERT', array(
244 8889 Kellanved
                                'confirm_id'        => (string) $this->confirm_id,
245 8889 Kellanved
                                'session_id'        => (string) $user->session_id,
246 8889 Kellanved
                                'confirm_type'        => (int) $this->type,
247 8889 Kellanved
                                'code'                        => (string) $this->code,
248 8889 Kellanved
                                'seed'                        => (int) $this->seed)
249 8889 Kellanved
                );
250 8889 Kellanved
                $db->sql_query($sql);
251 8889 Kellanved
        }
252 9554 acydburn
253 8889 Kellanved
        /**
254 9524 Kellanved
        * New Question, if desired.
255 9524 Kellanved
        */
256 9524 Kellanved
        function regenerate_code()
257 9524 Kellanved
        {
258 9524 Kellanved
                global $db, $user;
259 9554 acydburn
260 10751 git-gate
                $this->code = gen_rand_string_friendly(mt_rand(CAPTCHA_MIN_CHARS, CAPTCHA_MAX_CHARS));
261 9524 Kellanved
                $this->seed = hexdec(substr(unique_id(), 4, 10));
262 9672 Kellanved
                $this->solved = 0;
263 9524 Kellanved
                // compute $seed % 0x7fffffff
264 9524 Kellanved
                $this->seed -= 0x7fffffff * floor($this->seed / 0x7fffffff);
265 9554 acydburn
266 9524 Kellanved
                $sql = 'UPDATE ' . CONFIRM_TABLE . ' SET ' . $db->sql_build_array('UPDATE', array(
267 9524 Kellanved
                                'code'                        => (string) $this->code,
268 9524 Kellanved
                                'seed'                        => (int) $this->seed)) . '
269 9524 Kellanved
                                WHERE
270 10085 acydburn
                                confirm_id = \'' . $db->sql_escape($this->confirm_id) . '\'
271 9709 Kellanved
                                        AND session_id = \'' . $db->sql_escape($user->session_id) . '\'';
272 9524 Kellanved
                $db->sql_query($sql);
273 9524 Kellanved
        }
274 9554 acydburn
275 9524 Kellanved
        /**
276 9626 Kellanved
        * New Question, if desired.
277 9626 Kellanved
        */
278 9626 Kellanved
        function new_attempt()
279 9626 Kellanved
        {
280 9626 Kellanved
                global $db, $user;
281 9626 Kellanved
282 10751 git-gate
                $this->code = gen_rand_string_friendly(mt_rand(CAPTCHA_MIN_CHARS, CAPTCHA_MAX_CHARS));
283 9626 Kellanved
                $this->seed = hexdec(substr(unique_id(), 4, 10));
284 9672 Kellanved
                $this->solved = 0;
285 9626 Kellanved
                // compute $seed % 0x7fffffff
286 9626 Kellanved
                $this->seed -= 0x7fffffff * floor($this->seed / 0x7fffffff);
287 9626 Kellanved
288 9626 Kellanved
                $sql = 'UPDATE ' . CONFIRM_TABLE . ' SET ' . $db->sql_build_array('UPDATE', array(
289 9626 Kellanved
                                'code'                        => (string) $this->code,
290 9626 Kellanved
                                'seed'                        => (int) $this->seed)) . '
291 10085 acydburn
                                , attempts = attempts + 1
292 9626 Kellanved
                                WHERE
293 10085 acydburn
                                confirm_id = \'' . $db->sql_escape($this->confirm_id) . '\'
294 9709 Kellanved
                                        AND session_id = \'' . $db->sql_escape($user->session_id) . '\'';
295 9626 Kellanved
                $db->sql_query($sql);
296 9626 Kellanved
        }
297 10085 acydburn
298 9626 Kellanved
        /**
299 9554 acydburn
        * Look up everything we need for painting&checking.
300 8889 Kellanved
        */
301 9524 Kellanved
        function load_code()
302 8889 Kellanved
        {
303 8889 Kellanved
                global $db, $user;
304 9554 acydburn
305 9707 Kellanved
                $sql = 'SELECT code, seed, attempts
306 9554 acydburn
                        FROM ' . CONFIRM_TABLE . "
307 9707 Kellanved
                        WHERE confirm_id = '" . $db->sql_escape($this->confirm_id) . "'
308 9709 Kellanved
                                AND session_id = '" . $db->sql_escape($user->session_id) . "'
309 9554 acydburn
                                AND confirm_type = " . $this->type;
310 8889 Kellanved
                $result = $db->sql_query($sql);
311 8889 Kellanved
                $row = $db->sql_fetchrow($result);
312 8889 Kellanved
                $db->sql_freeresult($result);
313 9554 acydburn
314 8889 Kellanved
                if ($row)
315 8889 Kellanved
                {
316 8889 Kellanved
                        $this->code = $row['code'];
317 8889 Kellanved
                        $this->seed = $row['seed'];
318 9626 Kellanved
                        $this->attempts = $row['attempts'];
319 8889 Kellanved
                        return true;
320 8889 Kellanved
                }
321 9554 acydburn
322 8889 Kellanved
                return false;
323 8889 Kellanved
        }
324 9554 acydburn
325 9524 Kellanved
        function check_code()
326 8889 Kellanved
        {
327 8889 Kellanved
                return (strcasecmp($this->code, $this->confirm_code) === 0);
328 8889 Kellanved
        }
329 9554 acydburn
330 8889 Kellanved
        function get_attempt_count()
331 8889 Kellanved
        {
332 9626 Kellanved
                return $this->attempts;
333 8889 Kellanved
        }
334 9554 acydburn
335 8889 Kellanved
        function reset()
336 8889 Kellanved
        {
337 8889 Kellanved
                global $db, $user;
338 9554 acydburn
339 8889 Kellanved
                $sql = 'DELETE FROM ' . CONFIRM_TABLE . "
340 9554 acydburn
                        WHERE session_id = '" . $db->sql_escape($user->session_id) . "'
341 9554 acydburn
                                AND confirm_type = " . (int) $this->type;
342 8889 Kellanved
                $db->sql_query($sql);
343 9554 acydburn
344 8889 Kellanved
                // we leave the class usable by generating a new question
345 8889 Kellanved
                $this->generate_code();
346 8889 Kellanved
        }
347 10085 acydburn
348 9672 Kellanved
        function is_solved()
349 9672 Kellanved
        {
350 9702 Kellanved
                if (request_var('confirm_code', false) && $this->solved === 0)
351 9672 Kellanved
                {
352 9672 Kellanved
                        $this->validate();
353 9672 Kellanved
                }
354 9672 Kellanved
                return (bool) $this->solved;
355 9672 Kellanved
        }
356 10085 acydburn
357 9975 Kellanved
        /**
358 9975 Kellanved
        *  API function
359 9975 Kellanved
        */
360 9975 Kellanved
        function has_config()
361 9975 Kellanved
        {
362 9975 Kellanved
                return false;
363 9975 Kellanved
        }
364 10085 acydburn
365 8889 Kellanved
}
366 11557 git-gate
367 11557 git-gate
/**
368 11557 git-gate
* Old class name for legacy use. The new class name is auto loadable.
369 11557 git-gate
*/
370 11557 git-gate
class phpbb_default_captcha extends phpbb_captcha_plugins_captcha_abstract
371 11557 git-gate
{
372 11557 git-gate
}