Completed
Push — master ( be5479...2f6e9d )
by Philip
02:21
created

TransactionManager   A

Complexity

Total Complexity 12

Size/Duplication

Total Lines 99
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 4

Test Coverage

Coverage 60.98%

Importance

Changes 0
Metric Value
wmc 12
lcom 1
cbo 4
dl 0
loc 99
ccs 25
cts 41
cp 0.6098
rs 10
c 0
b 0
f 0

7 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 5 1
A beginTransaction() 0 4 1
A commitTransaction() 0 21 3
A rollbackTransaction() 0 11 2
A isInTransaction() 0 6 1
A transactional() 0 21 3
A setLogger() 0 4 1
1
<?php
2
3
namespace Dontdrinkandroot\Repository;
4
5
use Doctrine\ORM\EntityManagerInterface;
6
use Psr\Log\LoggerInterface;
7
use Psr\Log\NullLogger;
8
9
/**
10
 * @author Philip Washington Sorst <[email protected]>
11
 */
12
class TransactionManager
13
{
14
    /**
15
     * @var LoggerInterface
16
     */
17
    private $logger;
18
19
    /**
20
     * @var EntityManagerInterface
21
     */
22
    private $entityManager;
23
24 28
    public function __construct(EntityManagerInterface $entityManager)
25
    {
26 28
        $this->entityManager = $entityManager;
27 28
        $this->logger = new NullLogger();
28 28
    }
29
30 18
    public function beginTransaction()
31
    {
32 18
        $this->entityManager->beginTransaction();
33 18
    }
34
35 18
    public function commitTransaction(): bool
36
    {
37 18
        $nestingLevel = $this->entityManager->getConnection()->getTransactionNestingLevel();
38 18
        $flush = false;
39
40
        /* No active transaction */
41 18
        if (!$this->isInTransaction()) {
42
            $this->logger->warning('No active Transaction for commit');
43
44
            return $flush;
45
        }
46
47
        /* Topmost transaction, flush */
48 18
        if (1 === $nestingLevel) {
49 18
            $flush = true;
50 18
            $this->entityManager->flush();
51
        }
52 18
        $this->entityManager->commit();
53
54 18
        return $flush;
55
    }
56
57
    public function rollbackTransaction()
58
    {
59
        /* No active transaction */
60
        if (!$this->isInTransaction()) {
61
            $this->logger->warning('No active Transaction for commit');
62
63
            return;
64
        }
65
66
        $this->entityManager->rollback();
67
    }
68
69 18
    public function isInTransaction()
70
    {
71 18
        $hasTransaction = 0 !== $this->entityManager->getConnection()->getTransactionNestingLevel();
72
73 18
        return ($hasTransaction);
74
    }
75
76
    /**
77
     * @param callable $func
78
     *
79
     * @return mixed
80
     */
81 18
    public function transactional($func)
82
    {
83 18
        if (!is_callable($func)) {
84
            throw new \InvalidArgumentException('Expected argument of type "callable", got "' . gettype($func) . '"');
85
        }
86
87 18
        $this->beginTransaction();
88
89
        try {
90 18
            $return = call_user_func($func, $this);
91
92 18
            $this->commitTransaction();
93
94 18
            return $return;
95
        } catch (\Exception $e) {
96
            $this->entityManager->close();
97
            $this->rollbackTransaction();
98
99
            throw $e;
100
        }
101
    }
102
103
    /**
104
     * @param LoggerInterface $logger
105
     */
106
    public function setLogger(LoggerInterface $logger)
107
    {
108
        $this->logger = $logger;
109
    }
110
}
111