LocalChangesTracker   A
last analyzed

Complexity

Total Complexity 6

Size/Duplication

Total Lines 124
Duplicated Lines 33.87 %

Coupling/Cohesion

Components 1
Dependencies 5

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 6
c 1
b 0
f 0
lcom 1
cbo 5
dl 42
loc 124
rs 10

5 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 5 1
B createTrackingTables() 0 25 1
A createInsertTrigger() 22 22 1
A createDeleteTrigger() 20 20 1
B createUpdateTrigger() 0 31 2

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
3
4
namespace Wabel\Zoho\CRM\Copy;
5
use Doctrine\DBAL\Connection;
6
use Doctrine\DBAL\Schema\Table;
7
use Psr\Log\LoggerInterface;
8
9
/**
10
 * This class is in charge of tracking local files.
11
 * To do so, it can add a set of triggers that observe and track changes in tables.
12
 */
13
class LocalChangesTracker
14
{
15
    /**
16
     * @var Connection
17
     */
18
    private $connection;
19
20
    /**
21
     * @var LoggerInterface
22
     */
23
    private $logger;
24
25
    /**
26
     * @param Connection $connection
27
     */
28
    public function __construct(Connection $connection, LoggerInterface $logger)
29
    {
30
        $this->connection = $connection;
31
        $this->logger = $logger;
32
    }
33
34
35
    public function createTrackingTables()
36
    {
37
        $schema = new \Doctrine\DBAL\Schema\Schema();
38
39
        $localUpdate = $schema->createTable("local_update");
40
        $localUpdate->addColumn("table_name", 'string', ['length' => 100]);
41
        $localUpdate->addColumn("id", 'string', ['length' => 100]);
42
        $localUpdate->addColumn("field_name", 'string', ['length' => 100]);
43
        $localUpdate->setPrimaryKey(array("table_name", "id", "field_name"));
44
45
        $localInsert = $schema->createTable("local_insert");
46
        $localInsert->addColumn("table_name", 'string', ['length' => 100]);
47
        $localInsert->addColumn("id", 'string', ['length' => 100]);
48
        $localInsert->setPrimaryKey(array("table_name", "id"));
49
50
        $localDelete = $schema->createTable("local_delete");
51
        $localDelete->addColumn("table_name", 'string', ['length' => 100]);
52
        $localDelete->addColumn("id", 'string', ['length' => 100]);
53
        $localDelete->setPrimaryKey(array("table_name", "id"));
54
55
        $dbalTableDiffService = new DbalTableDiffService($this->connection, $this->logger);
56
        $dbalTableDiffService->createOrUpdateTable($localUpdate);
57
        $dbalTableDiffService->createOrUpdateTable($localInsert);
58
        $dbalTableDiffService->createOrUpdateTable($localDelete);
59
    }
60
61 View Code Duplication
    public function createInsertTrigger(Table $table)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
62
    {
63
        $triggerName = sprintf("TRG_%s_ONINSERT", $table->getName());
64
65
        $sql = sprintf('
66
            DROP TRIGGER IF EXISTS %s;
67
            
68
            CREATE TRIGGER %s AFTER INSERT ON `%s` 
69
            FOR EACH ROW
70
            BEGIN
71
              IF (NEW.lastActivityTime IS NULL) THEN
72
                INSERT INTO local_insert VALUES (%s, NEW.id);
73
                DELETE FROM local_delete WHERE table_name = %s AND id = NEW.id;
74
                DELETE FROM local_update WHERE table_name = %s AND id = NEW.id;
75
              END IF;
76
            END;
77
            
78
            ', $triggerName, $triggerName, $table->getName(), $this->connection->quote($table->getName()), $this->connection->quote($table->getName()), $this->connection->quote($table->getName()));
79
80
81
        $this->connection->exec($sql);
82
    }
83
84 View Code Duplication
    public function createDeleteTrigger(Table $table)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
85
    {
86
        $triggerName = sprintf("TRG_%s_ONDELETE", $table->getName());
87
88
        $sql = sprintf('
89
            DROP TRIGGER IF EXISTS %s;
90
            
91
            CREATE TRIGGER %s BEFORE DELETE ON `%s` 
92
            FOR EACH ROW
93
            BEGIN
94
              INSERT INTO local_delete VALUES (%s, OLD.id);
95
              DELETE FROM local_insert WHERE table_name = %s AND id = OLD.id;
96
              DELETE FROM local_update WHERE table_name = %s AND id = OLD.id;
97
            END;
98
            
99
            ', $triggerName, $triggerName, $table->getName(), $this->connection->quote($table->getName()), $this->connection->quote($table->getName()), $this->connection->quote($table->getName()));
100
101
102
        $this->connection->exec($sql);
103
    }
104
105
    public function createUpdateTrigger(Table $table)
106
    {
107
        $triggerName = sprintf("TRG_%s_ONUPDATE", $table->getName());
108
109
        $innerCode = '';
110
111
        foreach ($table->getColumns() as $column) {
112
            $columnName = $this->connection->quoteIdentifier($column->getName());
113
            $innerCode .= sprintf('
114
                IF (NEW.%s != OLD.%s) THEN
115
                  REPLACE INTO local_update VALUES (%s, NEW.id, %s);
116
                END IF;
117
            ', $columnName, $columnName, $this->connection->quote($table->getName()), $this->connection->quote($column->getName()));
118
        }
119
120
        $sql = sprintf('
121
            DROP TRIGGER IF EXISTS %s;
122
            
123
            CREATE TRIGGER %s AFTER UPDATE ON `%s` 
124
            FOR EACH ROW
125
            BEGIN
126
              IF (NEW.lastActivityTime = OLD.lastActivityTime) THEN
127
            %s
128
              END IF;
129
            END;
130
            
131
            ', $triggerName, $triggerName, $table->getName(), $innerCode);
132
133
134
        $this->connection->exec($sql);
135
    }
136
}
137