Completed
Pull Request — master (#5580)
by Marco
10:58
created

testQueryEntityWithoutCache()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 8
Code Lines 4

Duplication

Lines 0
Ratio 0 %
Metric Value
dl 0
loc 8
rs 9.4286
cc 1
eloc 4
nc 1
nop 0
1
<?php
2
3
namespace Doctrine\Tests\ORM\Performance;
4
5
use Doctrine\DBAL\Logging\DebugStack;
6
use Doctrine\Tests\OrmFunctionalTestCase;
7
use Doctrine\Tests\Models\Cache\Country;
8
use Doctrine\Tests\Models\Cache\State;
9
use Doctrine\Tests\Models\Cache\City;
10
use Doctrine\ORM\EntityManagerInterface;
11
12
/**
13
 * @group DDC-2183
14
 * @group performance
15
 */
16
class SecondLevelCacheTest extends OrmFunctionalTestCase
17
{
18
    protected function setUp()
19
    {
20
        parent::useModelSet('cache');
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (useModelSet() instead of setUp()). Are you sure this is correct? If so, you might want to change this to $this->useModelSet().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
21
        parent::setUp();
22
    }
23
24
    /**
25
     * @return \Doctrine\ORM\EntityManagerInterface
26
     */
27
    public function createEntityManager()
28
    {
29
        $logger = new DebugStack();
30
        $em     = $this->_getEntityManager();
31
32
        $em->getConnection()->getConfiguration()->setSQLLogger($logger);
33
        $em->getConfiguration()->setSQLLogger($logger);
34
35
        return $em;
36
    }
37
38
    /**
39
     * @param \Doctrine\ORM\EntityManagerInterface $em
40
     * @return integer
41
     */
42
    public function countQuery(EntityManagerInterface $em)
43
    {
44
        return count($em->getConfiguration()->getSQLLogger()->queries);
0 ignored issues
show
Bug introduced by
Accessing queries on the interface Doctrine\DBAL\Logging\SQLLogger suggest that you code against a concrete implementation. How about adding an instanceof check?

If you access a property on an interface, you most likely code against a concrete implementation of the interface.

Available Fixes

  1. Adding an additional type check:

    interface SomeInterface { }
    class SomeClass implements SomeInterface {
        public $a;
    }
    
    function someFunction(SomeInterface $object) {
        if ($object instanceof SomeClass) {
            $a = $object->a;
        }
    }
    
  2. Changing the type hint:

    interface SomeInterface { }
    class SomeClass implements SomeInterface {
        public $a;
    }
    
    function someFunction(SomeClass $object) {
        $a = $object->a;
    }
    
Loading history...
45
    }
46
47
    public function testFindEntityWithoutCache()
48
    {
49
        $em = $this->createEntityManager();
50
51
        $this->findEntity($em, __FUNCTION__);
52
53
        $this->assertEquals(6002, $this->countQuery($em));
54
    }
55
56
    public function testFindEntityWithCache()
57
    {
58
        parent::enableSecondLevelCache(false);
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (enableSecondLevelCache() instead of testFindEntityWithCache()). Are you sure this is correct? If so, you might want to change this to $this->enableSecondLevelCache().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
59
60
        $em = $this->createEntityManager();
61
62
        $this->findEntity($em, __FUNCTION__);
63
64
        $this->assertEquals(502, $this->countQuery($em));
65
    }
66
67
    public function testFindAllEntityWithoutCache()
68
    {
69
        $em = $this->createEntityManager();
70
71
        $this->findAllEntity($em, __FUNCTION__);
72
73
        $this->assertEquals(153, $this->countQuery($em));
74
    }
75
76
    public function testFindAllEntityWithCache()
77
    {
78
        parent::enableSecondLevelCache(false);
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (enableSecondLevelCache() instead of testFindAllEntityWithCache()). Are you sure this is correct? If so, you might want to change this to $this->enableSecondLevelCache().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
79
80
        $em = $this->createEntityManager();
81
82
        $this->findAllEntity($em, __FUNCTION__);
83
84
        $this->assertEquals(53, $this->countQuery($em));
85
    }
86
87
    public function testFindEntityOneToManyWithoutCache()
88
    {
89
        $em = $this->createEntityManager();
90
91
        $this->findEntityOneToMany($em, __FUNCTION__);
92
93
        $this->assertEquals(502, $this->countQuery($em));
94
    }
95
96
    public function testFindEntityOneToManyWithCache()
97
    {
98
        parent::enableSecondLevelCache(false);
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (enableSecondLevelCache() instead of testFindEntityOneToManyWithCache()). Are you sure this is correct? If so, you might want to change this to $this->enableSecondLevelCache().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
99
100
        $em = $this->createEntityManager();
101
102
        $this->findEntityOneToMany($em, __FUNCTION__);
103
104
        $this->assertEquals(487, $this->countQuery($em));
105
    }
106
107
    public function testQueryEntityWithoutCache()
108
    {
109
        $em = $this->createEntityManager();
110
111
        $this->queryEntity($em, __FUNCTION__);
112
113
        $this->assertEquals(602, $this->countQuery($em));
114
    }
115
116
    public function testQueryEntityWithCache()
117
    {
118
        parent::enableSecondLevelCache(false);
0 ignored issues
show
Comprehensibility Bug introduced by
It seems like you call parent on a different method (enableSecondLevelCache() instead of testQueryEntityWithCache()). Are you sure this is correct? If so, you might want to change this to $this->enableSecondLevelCache().

This check looks for a call to a parent method whose name is different than the method from which it is called.

Consider the following code:

class Daddy
{
    protected function getFirstName()
    {
        return "Eidur";
    }

    protected function getSurName()
    {
        return "Gudjohnsen";
    }
}

class Son
{
    public function getFirstName()
    {
        return parent::getSurname();
    }
}

The getFirstName() method in the Son calls the wrong method in the parent class.

Loading history...
119
120
        $em = $this->createEntityManager();
121
122
        $this->queryEntity($em, __FUNCTION__);
123
124
        $this->assertEquals(503, $this->countQuery($em));
125
    }
126
127
    private function queryEntity(EntityManagerInterface $em, $label)
128
    {
129
        $times        = 100;
130
        $size         = 500;
131
        $startPersist = microtime(true);
132
133
        echo PHP_EOL . $label;
134
135
        for ($i = 0; $i < $size; $i++) {
136
            $em->persist(new Country("Country $i"));
137
        }
138
139
        $em->flush();
140
        $em->clear();
141
142
        printf("\n[%s] persist %s countries", number_format(microtime(true) - $startPersist, 6), $size);
143
144
        $dql        = 'SELECT c FROM Doctrine\Tests\Models\Cache\Country c WHERE c.name LIKE :name';
145
        $startFind  = microtime(true);
146
147
        for ($i = 0; $i < $times; $i++) {
148
            $em->createQuery($dql)
149
                ->setParameter('name', "%Country%")
150
                ->setCacheable(true)
151
                ->getResult();
152
        }
153
154
        printf("\n[%s] select %s countries (%s times)", number_format(microtime(true) - $startFind, 6), $size, $times);
155
        printf("\n%s\n", str_repeat('-', 50));
156
    }
157
158
    public function findEntityOneToMany(EntityManagerInterface $em, $label)
159
    {
160
        $times        = 50;
161
        $size         = 30;
162
        $states       = array();
163
        $cities       = array();
164
        $startPersist = microtime(true);
165
        $country      = new Country("Country");
166
167
        echo PHP_EOL . $label;
168
169
        $em->persist($country);
170
        $em->flush();
171
172
        for ($i = 0; $i < $size / 2; $i++) {
173
            $state = new State("State $i", $country);
174
175
            $em->persist($state);
176
177
            $states[] = $state;
178
        }
179
180
        $em->flush();
181
182
        foreach ($states as $key => $state) {
183
            for ($i = 0; $i < $size; $i++) {
184
                $city = new City("City $key - $i", $state);
185
186
                $em->persist($city);
187
188
                $state->addCity($city);
189
190
                $cities[] = $city;
191
            }
192
        }
193
194
        $em->flush();
195
        $em->clear();
196
197
        printf("\n[%s] persist %s states and %s cities", number_format( microtime(true) - $startPersist, 6), count($states), count($cities));
198
199
        $startFind  = microtime(true);
200
201
        for ($i = 0; $i < $times; $i++) {
202
203
            foreach ($states as $state) {
204
205
                $state = $em->find(State::CLASSNAME, $state->getId());
206
207
                foreach ($state->getCities() as $city) {
208
                    $city->getName();
209
                }
210
            }
211
        }
212
213
        printf("\n[%s] find %s states and %s cities (%s times)", number_format(microtime(true) - $startFind, 6), count($states), count($cities), $times);
214
        printf("\n%s\n", str_repeat('-', 50));
215
    }
216
217
    private function findEntity(EntityManagerInterface $em, $label)
218
    {
219
        $times        = 10;
220
        $size         = 500;
221
        $countries    = array();
222
        $startPersist = microtime(true);
223
224
        echo PHP_EOL . $label;
225
226
        for ($i = 0; $i < $size; $i++) {
227
            $country = new Country("Country $i");
228
229
            $em->persist($country);
230
231
            $countries[] = $country;
232
        }
233
234
        $em->flush();
235
        $em->clear();
236
237
        printf("\n[%s] persist %s countries", number_format(microtime(true) - $startPersist, 6), $size);
238
239
        $startFind  = microtime(true);
240
241
        for ($i = 0; $i <= $times; $i++) {
242
            foreach ($countries as $country) {
243
                $em->find(Country::CLASSNAME, $country->getId());
244
                $em->clear();
245
            }
246
        }
247
248
        printf("\n[%s] find %s countries (%s times)", number_format(microtime(true) - $startFind, 6), $size, $times);
249
        printf("\n%s\n", str_repeat('-', 50));
250
    }
251
252
    private function findAllEntity(EntityManagerInterface $em, $label)
253
    {
254
        $times        = 100;
255
        $size         = 50;
256
        $startPersist = microtime(true);
257
        $rep          = $em->getRepository(Country::CLASSNAME);
258
259
        echo PHP_EOL . $label;
260
261
        for ($i = 0; $i < $size; $i++) {
262
            $em->persist(new Country("Country $i"));
263
        }
264
265
        $em->flush();
266
        $em->clear();
267
268
        printf("\n[%s] persist %s countries", number_format(microtime(true) - $startPersist, 6), $size);
269
270
        $startFind  = microtime(true);
271
272
        for ($i = 0; $i <= $times; $i++) {
273
            $list = $rep->findAll();
274
            $em->clear();
275
276
            $this->assertCount($size, $list);
277
        }
278
279
        printf("\n[%s] find %s countries (%s times)", number_format(microtime(true) - $startFind, 6), $size, $times);
280
        printf("\n%s\n", str_repeat('-', 50));
281
    }
282
}