Completed
Push — master ( 5482c8...c9885e )
by MeWebStudio - Muharrem
08:52
created

Captcha::check_api()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 2
dl 0
loc 4
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace Mews\Captcha;
4
5
/**
6
 * Laravel 5 Captcha package
7
 *
8
 * @copyright Copyright (c) 2015 MeWebStudio
9
 * @version 2.x
10
 * @author Muharrem ERİN
11
 * @contact [email protected]
12
 * @web http://www.mewebstudio.com
13
 * @date 2015-04-03
14
 * @license http://www.opensource.org/licenses/mit-license.php The MIT License
15
 */
16
17
use Exception;
18
use Illuminate\Config\Repository;
19
use Illuminate\Hashing\BcryptHasher as Hasher;
20
use Illuminate\Filesystem\Filesystem;
21
use Illuminate\Support\Facades\Crypt;
22
use Illuminate\Support\Str;
23
use Intervention\Image\ImageManager;
24
use Illuminate\Session\Store as Session;
25
26
/**
27
 * Class Captcha
28
 * @package Mews\Captcha
29
 */
30
class Captcha
31
{
32
33
    /**
34
     * @var Filesystem
35
     */
36
    protected $files;
37
38
    /**
39
     * @var Repository
40
     */
41
    protected $config;
42
43
    /**
44
     * @var ImageManager
45
     */
46
    protected $imageManager;
47
48
    /**
49
     * @var Session
50
     */
51
    protected $session;
52
53
    /**
54
     * @var Hasher
55
     */
56
    protected $hasher;
57
58
    /**
59
     * @var Str
60
     */
61
    protected $str;
62
63
    /**
64
     * @var ImageManager->canvas
65
     */
66
    protected $canvas;
67
68
    /**
69
     * @var ImageManager->image
70
     */
71
    protected $image;
72
73
    /**
74
     * @var array
75
     */
76
    protected $backgrounds = [];
77
78
    /**
79
     * @var array
80
     */
81
    protected $fonts = [];
82
83
    /**
84
     * @var array
85
     */
86
    protected $fontColors = [];
87
88
    /**
89
     * @var int
90
     */
91
    protected $length = 5;
92
93
    /**
94
     * @var int
95
     */
96
    protected $width = 120;
97
98
    /**
99
     * @var int
100
     */
101
    protected $height = 36;
102
103
    /**
104
     * @var int
105
     */
106
    protected $angle = 15;
107
108
    /**
109
     * @var int
110
     */
111
    protected $lines = 3;
112
113
    /**
114
     * @var string
115
     */
116
    protected $characters;
117
118
    /**
119
     * @var string
120
     */
121
    protected $text;
122
123
    /**
124
     * @var int
125
     */
126
    protected $contrast = 0;
127
128
    /**
129
     * @var int
130
     */
131
    protected $quality = 90;
132
133
    /**
134
     * @var int
135
     */
136
    protected $sharpen = 0;
137
138
    /**
139
     * @var int
140
     */
141
    protected $blur = 0;
142
143
    /**
144
     * @var bool
145
     */
146
    protected $bgImage = true;
147
148
    /**
149
     * @var string
150
     */
151
    protected $bgColor = '#ffffff';
152
153
    /**
154
     * @var bool
155
     */
156
    protected $invert = false;
157
158
    /**
159
     * @var bool
160
     */
161
    protected $sensitive = false;
162
163
    /**
164
     * @var int
165
     */
166
    protected $textLeftPadding = 4;
167
168
    /**
169
     * Constructor
170
     *
171
     * @param Filesystem $files
172
     * @param Repository $config
173
     * @param ImageManager $imageManager
174
     * @param Session $session
175
     * @param Hasher $hasher
176
     * @param Str $str
177
     * @throws Exception
178
     * @internal param Validator $validator
179
     */
180
    public function __construct(
181
        Filesystem $files,
182
        Repository $config,
183
        ImageManager $imageManager,
184
        Session $session,
185
        Hasher $hasher,
186
        Str $str
187
    )
188
    {
189
        $this->files = $files;
190
        $this->config = $config;
191
        $this->imageManager = $imageManager;
192
        $this->session = $session;
193
        $this->hasher = $hasher;
194
        $this->str = $str;
195
        $this->characters = config('captcha.characters','2346789abcdefghjmnpqrtuxyzABCDEFGHJMNPQRTUXYZ');
196
    }
197
198
    /**
199
     * @param string $config
200
     * @return void
201
     */
202
    protected function configure($config)
203
    {
204
        if ($this->config->has('captcha.' . $config))
205
        {
206
            foreach($this->config->get('captcha.' . $config) as $key => $val)
207
            {
208
                $this->{$key} = $val;
209
            }
210
        }
211
    }
212
213
    /**
214
     * Create captcha image
215
     *
216
     * @param string $config
217
     * @param boolean $api
218
     * @return ImageManager->response
0 ignored issues
show
Documentation introduced by
The doc-type ImageManager->response could not be parsed: Unknown type name "ImageManager-" at position 0. (view supported doc-types)

This check marks PHPDoc comments that could not be parsed by our parser. To see which comment annotations we can parse, please refer to our documentation on supported doc-types.

Loading history...
219
     */
220
    public function create($config = 'default', $api = false)
221
    {
222
        $this->backgrounds = $this->files->files(__DIR__ . '/../assets/backgrounds');
223
        $this->fonts = $this->files->files(__DIR__ . '/../assets/fonts');
224
        
225
        if (app()->version() >= 5.5){
226
            $this->fonts = array_map(function($file) {
227
                return $file->getPathName();
228
            }, $this->fonts);
229
        }
230
        
231
        $this->fonts = array_values($this->fonts); //reset fonts array index
232
233
        $this->configure($config);
234
235
        $generator = $this->generate();
236
        $this->text = $generator['value'];
237
238
        $this->canvas = $this->imageManager->canvas(
239
            $this->width,
240
            $this->height,
241
            $this->bgColor
242
        );
243
244
        if ($this->bgImage)
245
        {
246
            $this->image = $this->imageManager->make($this->background())->resize(
247
                $this->width,
248
                $this->height
249
            );
250
            $this->canvas->insert($this->image);
251
        }
252
        else
253
        {
254
            $this->image = $this->canvas;
255
        }
256
257
        if ($this->contrast != 0)
258
        {
259
            $this->image->contrast($this->contrast);
260
        }
261
262
        $this->text();
263
264
        $this->lines();
265
266
        if ($this->sharpen)
267
        {
268
            $this->image->sharpen($this->sharpen);
269
        }
270
        if ($this->invert)
271
        {
272
            $this->image->invert($this->invert);
273
        }
274
        if ($this->blur)
275
        {
276
            $this->image->blur($this->blur);
277
        }
278
279
        return $api ? [
280
	        'sensitive' => $generator['sensitive'],
281
	        'key'       => $generator['key'],
282
        	'img'       => $this->image->encode('data-url')->encoded
283
        ] : $this->image->response('png', $this->quality);
284
    }
285
286
    /**
287
     * Image backgrounds
288
     *
289
     * @return string
290
     */
291
    protected function background()
292
    {
293
        return $this->backgrounds[rand(0, count($this->backgrounds) - 1)];
294
    }
295
296
    /**
297
     * Generate captcha text
298
     *
299
     * @return string
300
     */
301
    protected function generate()
302
    {
303
        $characters = str_split($this->characters);
304
305
        $bag = '';
306
        for($i = 0; $i < $this->length; $i++)
307
        {
308
            $bag .= $characters[rand(0, count($characters) - 1)];
309
        }
310
311
        $bag = $this->sensitive ? $bag : $this->str->lower($bag);
312
313
        $hash = $this->hasher->make($bag);
314
        $this->session->put('captcha', [
315
            'sensitive' => $this->sensitive,
316
            'key'       => $hash
317
        ]);
318
319
        return [
320
        	'value'     => $bag,
321
	        'sensitive' => $this->sensitive,
322
	        'key'       => $hash
323
        ];
324
    }
325
326
    /**
327
     * Writing captcha text
328
     */
329
    protected function text()
330
    {
331
        $marginTop = $this->image->height() / $this->length;
332
333
        $i = 0;
334
        foreach(str_split($this->text) as $char)
335
        {
336
            $marginLeft = $this->textLeftPadding +  ($i * ($this->image->width() - $this->textLeftPadding) / $this->length);
337
338
            $this->image->text($char, $marginLeft, $marginTop, function($font) {
339
                $font->file($this->font());
340
                $font->size($this->fontSize());
341
                $font->color($this->fontColor());
342
                $font->align('left');
343
                $font->valign('top');
344
                $font->angle($this->angle());
345
            });
346
347
            $i++;
348
        }
349
    }
350
351
    /**
352
     * Image fonts
353
     *
354
     * @return string
355
     */
356
    protected function font()
357
    {
358
        return $this->fonts[rand(0, count($this->fonts) - 1)];
359
    }
360
361
    /**
362
     * Random font size
363
     *
364
     * @return integer
365
     */
366
    protected function fontSize()
367
    {
368
        return rand($this->image->height() - 10, $this->image->height());
369
    }
370
371
    /**
372
     * Random font color
373
     *
374
     * @return array
375
     */
376
    protected function fontColor()
377
    {
378
        if ( ! empty($this->fontColors))
379
        {
380
            $color = $this->fontColors[rand(0, count($this->fontColors) - 1)];
381
        }
382
        else
383
        {
384
            $color = [rand(0, 255), rand(0, 255), rand(0, 255)];
385
        }
386
387
        return $color;
388
    }
389
390
    /**
391
     * Angle
392
     *
393
     * @return int
394
     */
395
    protected function angle()
396
    {
397
        return rand((-1 * $this->angle), $this->angle);
398
    }
399
400
    /**
401
     * Random image lines
402
     *
403
     * @return \Intervention\Image\Image
404
     */
405
    protected function lines()
406
    {
407
        for($i = 0; $i <= $this->lines; $i++)
408
        {
409
            $this->image->line(
410
                rand(0, $this->image->width()) + $i * rand(0, $this->image->height()),
411
                rand(0, $this->image->height()),
412
                rand(0, $this->image->width()),
413
                rand(0, $this->image->height()),
414
                function ($draw) {
415
                    $draw->color($this->fontColor());
416
                }
417
            );
418
        }
419
        return $this->image;
420
    }
421
422
	/**
423
	 * Captcha check
424
	 *
425
	 * @param $value
426
	 * @return bool
427
	 */
428
	public function check($value)
429
	{
430
		if ( ! $this->session->has('captcha'))
431
		{
432
			return false;
433
		}
434
435
		$key = $this->session->get('captcha.key');
436
		$sensitive = $this->session->get('captcha.sensitive');
437
438
		if ( ! $sensitive)
439
		{
440
			$value = $this->str->lower($value);
441
		}
442
443
		$this->session->remove('captcha');
444
445
		return $this->hasher->check($value, $key);
446
	}
447
448
	/**
449
	 * Captcha check
450
	 *
451
	 * @param $value
452
	 * @return bool
453
	 */
454
	public function check_api($value, $key)
455
	{
456
		return $this->hasher->check($value, $key);
457
	}
458
459
    /**
460
     * Generate captcha image source
461
     *
462
     * @param null $config
463
     * @return string
464
     */
465
    public function src($config = null)
466
    {
467
        return url('captcha' . ($config ? '/' . $config : '/default')) . '?' . $this->str->random(8);
468
    }
469
470
    /**
471
     * Generate captcha image html tag
472
     *
473
     * @param null $config
474
     * @param array $attrs HTML attributes supplied to the image tag where key is the attribute
475
     * and the value is the attribute value
476
     * @return string
477
     */
478
    public function img($config = null, $attrs = [])
479
    {
480
        $attrs_str = '';
481
        foreach($attrs as $attr => $value){
482
            if ($attr == 'src'){
483
                //Neglect src attribute
484
                continue;
485
            }
486
            $attrs_str .= $attr.'="'.$value.'" ';
487
        }
488
        return '<img src="' . $this->src($config) . '" '. trim($attrs_str).'>';
489
    }
490
491
}
492