DestroyEqualResourceCommand::getFileHash()   A
last analyzed

Complexity

Conditions 2
Paths 2

Size

Total Lines 12
Code Lines 7

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 2.0116

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 12
ccs 6
cts 7
cp 0.8571
rs 9.4285
cc 2
eloc 7
nc 2
nop 1
crap 2.0116
1
<?php
2
namespace Staticus\Resources\Commands;
3
4
use League\Flysystem\FilesystemInterface;
5
use Staticus\Resources\Exceptions\CommandErrorException;
6
use Staticus\Resources\ResourceDOInterface;
7
8
class DestroyEqualResourceCommand implements ResourceCommandInterface
9
{
10
    const HASH_ALGORITHM = 'md5';
11
    /**
12
     * @var ResourceDOInterface
13
     */
14
    protected $originResourceDO;
15
    /**
16
     * @var ResourceDOInterface
17
     */
18
    protected $suspectResourceDO;
19
    /**
20
     * @var FilesystemInterface
21
     */
22
    protected $filesystem;
23
24
    /**
25
     * @param ResourceDOInterface $originResourceDO This is a model resource for comparing
26
     * @param ResourceDOInterface $suspectResourceDO This resource will be deleted, if it's equal to $originResourceDO
27
     * @param FilesystemInterface $filesystem
28
     */
29 7
    public function __construct(
30
        ResourceDOInterface $originResourceDO
31
        , ResourceDOInterface $suspectResourceDO
32
        , FilesystemInterface $filesystem
33
    )
34
    {
35 7
        $this->originResourceDO = $originResourceDO;
36 7
        $this->suspectResourceDO = $suspectResourceDO;
37 7
        $this->filesystem = $filesystem;
38 7
    }
39
40
    /**
41
     * @return ResourceDOInterface SuspectResource if it have been deleted or OriginResource if the Suspect is not equal
42
     */
43 7
    public function __invoke()
44
    {
45 7
        $originName = $this->originResourceDO->getName();
46 7
        $suspectName = $this->suspectResourceDO->getName();
47 7
        $originType = $this->originResourceDO->getType();
48 7
        $suspectType = $this->suspectResourceDO->getType();
49 7
        $originFilePath = $this->originResourceDO->getFilePath();
50 7
        $suspectFilePath = $this->suspectResourceDO->getFilePath();
51
52 7
        if (!$originName || !$originType) {
53 1
            throw new CommandErrorException('Cannot destroy equal resource: the origin resource is empty');
54
        }
55 6
        if (!$suspectName || !$suspectType) {
56 1
            throw new CommandErrorException('Cannot destroy equal resource: the suspect resource is empty');
57
        }
58 5
        if ($originFilePath === $suspectFilePath) {
59 1
            throw new CommandErrorException('Cannot destroy equal resource: Origin and Suspect have same paths');
60
        }
61
62
        // Unfortunately, this condition can not always work fine.
63
        // Because some Middlewares can compress, resize etc. the resource that saved before
64
        // and the second uploaded copy will never be equal
65
        if ($originType === $suspectType
66 4
            && $this->filesystem->has($originFilePath) === $this->filesystem->has($suspectFilePath)
67 4
            && $this->filesystem->getSize($originFilePath) === $this->filesystem->getSize($suspectFilePath)
68 4
            && $this->getFileHash($originFilePath) === $this->getFileHash($suspectFilePath)
69 4
        ) {
70 2
            $command = new DestroyResourceCommand($this->suspectResourceDO, $this->filesystem);
71
72 2
            return $command(true);
73
        }
74
75 2
        return $this->originResourceDO;
76
    }
77
78 2
    public function getFileHash($path)
79
    {
80 2
        $stream = $this->filesystem->readStream($path);
81 2
        if ($stream !== false) {
82 2
            $context = hash_init(self::HASH_ALGORITHM);
83 2
            hash_update_stream($context, $stream);
84
85 2
            return hash_final($context);
86
        }
87
88
        return false;
89
    }
90
}