CsrfHeaderCheckMiddleware   A
last analyzed

Complexity

Total Complexity 4

Size/Duplication

Total Lines 57
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 2

Importance

Changes 0
Metric Value
wmc 4
lcom 1
cbo 2
dl 0
loc 57
rs 10
c 0
b 0
f 0

2 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 6 1
A process() 0 16 3
1
<?php
2
declare(strict_types=1);
3
4
namespace TheCodingMachine\Middlewares;
5
6
use Psr\Http\Message\ResponseInterface;
7
use Psr\Http\Message\ServerRequestInterface;
8
use Psr\Http\Server\MiddlewareInterface;
9
use Psr\Http\Server\RequestHandlerInterface;
10
use TheCodingMachine\Middlewares\OriginFetchers\SourceOriginInterface;
11
use TheCodingMachine\Middlewares\OriginFetchers\TargetOriginInterface;
12
use TheCodingMachine\Middlewares\SafeRequests\IsSafeHttpRequestInterface;
13
14
/**
15
 * This class will check that all POST/PUT/DELETE... requests and verify that the "Origin" of the request is your own website.
16
 */
17
final class CsrfHeaderCheckMiddleware implements MiddlewareInterface
18
{
19
    /**
20
     * @var IsSafeHttpRequestInterface
21
     */
22
    private $isSafeHttpRequest;
23
    /**
24
     * @var TargetOriginInterface
25
     */
26
    private $targetOrigins;
27
28
    /**
29
     * @var SourceOriginInterface
30
     */
31
    private $sourceOrigin;
32
33
    const STRICT_COMPARE = true;
34
35
    /**
36
     * CsrfHeaderCheckMiddleware constructor.
37
     * @param IsSafeHttpRequestInterface $isSafeHttpRequest
38
     * @param TargetOriginInterface $targetOrigins
39
     * @param SourceOriginInterface $sourceOrigin
40
     */
41
    public function __construct(IsSafeHttpRequestInterface $isSafeHttpRequest, TargetOriginInterface $targetOrigins, SourceOriginInterface $sourceOrigin)
42
    {
43
        $this->isSafeHttpRequest = $isSafeHttpRequest;
44
        $this->targetOrigins = $targetOrigins;
45
        $this->sourceOrigin = $sourceOrigin;
46
    }
47
48
    /**
49
     * Process an incoming server request and return a response, optionally delegating
50
     * to the next middleware component to create the response.
51
     *
52
     * @param ServerRequestInterface $request
53
     * @param RequestHandlerInterface $delegate
54
     * @return ResponseInterface
55
     * @throws CsrfHeaderCheckMiddlewareException
56
     */
57
    public function process(ServerRequestInterface $request, RequestHandlerInterface $delegate): ResponseInterface
58
    {
59
        $isSafeHttpRequest = $this->isSafeHttpRequest;
60
        if (!$isSafeHttpRequest($request)) {
61
            $sourceOrigin = $this->sourceOrigin;
62
            $targetOrigins = $this->targetOrigins;
63
64
            $source = $sourceOrigin($request);
65
            $targets = $targetOrigins($request);
66
67
            if (!in_array($source, $targets, self::STRICT_COMPARE)) {
68
                throw new CsrfHeaderCheckMiddlewareException('Potential CSRF attack stopped. Source origin and target origin do not match.');
69
            }
70
        }
71
        return $delegate->handle($request);
72
    }
73
}
74