Completed
Push — 3.x ( b75183...b1c847 )
by Oskar
04:45
created

tests/Admin/AdminTest.php (10 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
declare(strict_types=1);
4
5
/*
6
 * This file is part of the Sonata Project package.
7
 *
8
 * (c) Thomas Rabaix <[email protected]>
9
 *
10
 * For the full copyright and license information, please view the LICENSE
11
 * file that was distributed with this source code.
12
 */
13
14
namespace Sonata\AdminBundle\Tests\Admin;
15
16
use Doctrine\Common\Collections\Collection;
17
use Knp\Menu\FactoryInterface;
18
use Knp\Menu\ItemInterface;
19
use PHPUnit\Framework\TestCase;
20
use Sonata\AdminBundle\Admin\AbstractAdmin;
21
use Sonata\AdminBundle\Admin\AbstractAdminExtension;
22
use Sonata\AdminBundle\Admin\AdminExtensionInterface;
23
use Sonata\AdminBundle\Admin\AdminInterface;
24
use Sonata\AdminBundle\Admin\BreadcrumbsBuilder;
25
use Sonata\AdminBundle\Admin\BreadcrumbsBuilderInterface;
26
use Sonata\AdminBundle\Admin\FieldDescriptionInterface;
27
use Sonata\AdminBundle\Admin\Pool;
28
use Sonata\AdminBundle\Builder\DatagridBuilderInterface;
29
use Sonata\AdminBundle\Builder\FormContractorInterface;
30
use Sonata\AdminBundle\Builder\ListBuilderInterface;
31
use Sonata\AdminBundle\Builder\RouteBuilderInterface;
32
use Sonata\AdminBundle\Builder\ShowBuilderInterface;
33
use Sonata\AdminBundle\Datagrid\DatagridInterface;
34
use Sonata\AdminBundle\Datagrid\PagerInterface;
35
use Sonata\AdminBundle\Model\AuditManagerInterface;
36
use Sonata\AdminBundle\Model\ModelManagerInterface;
37
use Sonata\AdminBundle\Route\DefaultRouteGenerator;
38
use Sonata\AdminBundle\Route\PathInfoBuilder;
39
use Sonata\AdminBundle\Route\RouteGeneratorInterface;
40
use Sonata\AdminBundle\Route\RoutesCache;
41
use Sonata\AdminBundle\Security\Handler\AclSecurityHandlerInterface;
42
use Sonata\AdminBundle\Security\Handler\SecurityHandlerInterface;
43
use Sonata\AdminBundle\Templating\MutableTemplateRegistryInterface;
44
use Sonata\AdminBundle\Tests\Fixtures\Admin\CommentAdmin;
45
use Sonata\AdminBundle\Tests\Fixtures\Admin\CommentVoteAdmin;
46
use Sonata\AdminBundle\Tests\Fixtures\Admin\CommentWithCustomRouteAdmin;
47
use Sonata\AdminBundle\Tests\Fixtures\Admin\FieldDescription;
48
use Sonata\AdminBundle\Tests\Fixtures\Admin\FilteredAdmin;
49
use Sonata\AdminBundle\Tests\Fixtures\Admin\ModelAdmin;
50
use Sonata\AdminBundle\Tests\Fixtures\Admin\PostAdmin;
51
use Sonata\AdminBundle\Tests\Fixtures\Admin\PostWithCustomRouteAdmin;
52
use Sonata\AdminBundle\Tests\Fixtures\Admin\TagAdmin;
53
use Sonata\AdminBundle\Tests\Fixtures\Bundle\Entity\BlogPost;
54
use Sonata\AdminBundle\Tests\Fixtures\Bundle\Entity\Comment;
55
use Sonata\AdminBundle\Tests\Fixtures\Bundle\Entity\Post;
56
use Sonata\AdminBundle\Tests\Fixtures\Bundle\Entity\Tag;
57
use Sonata\AdminBundle\Tests\Fixtures\Entity\FooToString;
58
use Sonata\AdminBundle\Tests\Fixtures\Entity\FooToStringNull;
59
use Sonata\AdminBundle\Translator\LabelTranslatorStrategyInterface;
60
use Sonata\Doctrine\Adapter\AdapterInterface;
61
use Symfony\Component\DependencyInjection\Container;
62
use Symfony\Component\DependencyInjection\ContainerInterface;
63
use Symfony\Component\Form\FormBuilder;
64
use Symfony\Component\Form\FormBuilderInterface;
65
use Symfony\Component\Form\FormEvent;
66
use Symfony\Component\Form\FormEvents;
67
use Symfony\Component\HttpFoundation\ParameterBag;
68
use Symfony\Component\HttpFoundation\Request;
69
use Symfony\Component\PropertyAccess\PropertyAccess;
70
use Symfony\Component\Routing\RouterInterface;
71
use Symfony\Component\Security\Core\Exception\AccessDeniedException;
72
use Symfony\Component\Translation\TranslatorInterface;
73
use Symfony\Component\Validator\Mapping\MemberMetadata;
74
use Symfony\Component\Validator\Validator\ValidatorInterface;
75
76
class AdminTest extends TestCase
77
{
78
    protected $cacheTempFolder;
79
80
    public function setUp(): void
81
    {
82
        $this->cacheTempFolder = sys_get_temp_dir().'/sonata_test_route';
83
84
        exec('rm -rf '.$this->cacheTempFolder);
85
    }
86
87
    /**
88
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::__construct
89
     */
90
    public function testConstructor(): void
91
    {
92
        $class = 'Application\Sonata\NewsBundle\Entity\Post';
93
        $baseControllerName = 'SonataNewsBundle:PostAdmin';
94
95
        $admin = new PostAdmin('sonata.post.admin.post', $class, $baseControllerName);
96
        $this->assertInstanceOf(AbstractAdmin::class, $admin);
97
        $this->assertSame($class, $admin->getClass());
98
        $this->assertSame($baseControllerName, $admin->getBaseControllerName());
99
    }
100
101
    public function testGetClass(): void
102
    {
103
        $class = Post::class;
104
        $baseControllerName = 'SonataNewsBundle:PostAdmin';
105
106
        $admin = new PostAdmin('sonata.post.admin.post', $class, $baseControllerName);
107
108
        $admin->setModelManager($this->getMockForAbstractClass(ModelManagerInterface::class));
109
110
        $admin->setSubject(new BlogPost());
111
        $this->assertSame(BlogPost::class, $admin->getClass());
112
113
        $admin->setSubClasses(['foo']);
114
        $this->assertSame(BlogPost::class, $admin->getClass());
115
116
        $admin->setSubject(null);
117
        $admin->setSubClasses([]);
118
        $this->assertSame($class, $admin->getClass());
119
120
        $admin->setSubClasses(['foo' => 'bar']);
121
        $admin->setRequest(new Request(['subclass' => 'foo']));
122
        $this->assertSame('bar', $admin->getClass());
123
    }
124
125
    public function testGetClassException(): void
126
    {
127
        $this->expectException(\RuntimeException::class);
128
        $this->expectExceptionMessage('Feature not implemented: an embedded admin cannot have subclass');
129
130
        $class = 'Application\Sonata\NewsBundle\Entity\Post';
131
        $baseControllerName = 'SonataNewsBundle:PostAdmin';
132
133
        $admin = new PostAdmin('sonata.post.admin.post', $class, $baseControllerName);
134
        $admin->setParentFieldDescription(new FieldDescription());
135
        $admin->setSubClasses(['foo' => 'bar']);
136
        $admin->setRequest(new Request(['subclass' => 'foo']));
137
        $admin->getClass();
138
    }
139
140
    public function testCheckAccessThrowsExceptionOnMadeUpAction(): void
141
    {
142
        $admin = new PostAdmin(
143
            'sonata.post.admin.post',
144
            'Application\Sonata\NewsBundle\Entity\Post',
145
            'SonataNewsBundle:PostAdmin'
146
        );
147
        $this->expectException(
148
            \InvalidArgumentException::class
149
        );
150
        $this->expectExceptionMessage(
151
            'Action "made-up" could not be found'
152
        );
153
        $admin->checkAccess('made-up');
154
    }
155
156
    public function testCheckAccessThrowsAccessDeniedException(): void
157
    {
158
        $admin = new PostAdmin(
159
            'sonata.post.admin.post',
160
            'Application\Sonata\NewsBundle\Entity\Post',
161
            'SonataNewsBundle:PostAdmin'
162
        );
163
        $securityHandler = $this->prophesize(SecurityHandlerInterface::class);
164
        $securityHandler->isGranted($admin, 'CUSTOM_ROLE', $admin)->willReturn(true);
165
        $securityHandler->isGranted($admin, 'EXTRA_CUSTOM_ROLE', $admin)->willReturn(false);
166
        $customExtension = $this->prophesize(AbstractAdminExtension::class);
167
        $customExtension->getAccessMapping($admin)->willReturn(
168
            ['custom_action' => ['CUSTOM_ROLE', 'EXTRA_CUSTOM_ROLE']]
169
        );
170
        $admin->addExtension($customExtension->reveal());
171
        $admin->setSecurityHandler($securityHandler->reveal());
172
        $this->expectException(
173
            AccessDeniedException::class
174
        );
175
        $this->expectExceptionMessage(
176
            'Access Denied to the action custom_action and role EXTRA_CUSTOM_ROLE'
177
        );
178
        $admin->checkAccess('custom_action');
179
    }
180
181
    public function testHasAccessOnMadeUpAction(): void
182
    {
183
        $admin = new PostAdmin(
184
            'sonata.post.admin.post',
185
            'Application\Sonata\NewsBundle\Entity\Post',
186
            'SonataNewsBundle:PostAdmin'
187
        );
188
189
        $this->assertFalse($admin->hasAccess('made-up'));
190
    }
191
192
    public function testHasAccess(): void
193
    {
194
        $admin = new PostAdmin(
195
            'sonata.post.admin.post',
196
            'Application\Sonata\NewsBundle\Entity\Post',
197
            'SonataNewsBundle:PostAdmin'
198
        );
199
        $securityHandler = $this->prophesize(SecurityHandlerInterface::class);
200
        $securityHandler->isGranted($admin, 'CUSTOM_ROLE', $admin)->willReturn(true);
201
        $securityHandler->isGranted($admin, 'EXTRA_CUSTOM_ROLE', $admin)->willReturn(false);
202
        $customExtension = $this->prophesize(AbstractAdminExtension::class);
203
        $customExtension->getAccessMapping($admin)->willReturn(
204
            ['custom_action' => ['CUSTOM_ROLE', 'EXTRA_CUSTOM_ROLE']]
205
        );
206
        $admin->addExtension($customExtension->reveal());
207
        $admin->setSecurityHandler($securityHandler->reveal());
208
209
        $this->assertFalse($admin->hasAccess('custom_action'));
210
    }
211
212
    public function testHasAccessAllowsAccess(): void
213
    {
214
        $admin = new PostAdmin(
215
            'sonata.post.admin.post',
216
            'Application\Sonata\NewsBundle\Entity\Post',
217
            'SonataNewsBundle:PostAdmin'
218
        );
219
        $securityHandler = $this->prophesize(SecurityHandlerInterface::class);
220
        $securityHandler->isGranted($admin, 'CUSTOM_ROLE', $admin)->willReturn(true);
221
        $securityHandler->isGranted($admin, 'EXTRA_CUSTOM_ROLE', $admin)->willReturn(true);
222
        $customExtension = $this->prophesize(AbstractAdminExtension::class);
223
        $customExtension->getAccessMapping($admin)->willReturn(
224
            ['custom_action' => ['CUSTOM_ROLE', 'EXTRA_CUSTOM_ROLE']]
225
        );
226
        $admin->addExtension($customExtension->reveal());
227
        $admin->setSecurityHandler($securityHandler->reveal());
228
229
        $this->assertTrue($admin->hasAccess('custom_action'));
230
    }
231
232
    public function testHasAccessAllowsAccessEditAction(): void
233
    {
234
        $admin = new PostAdmin(
235
            'sonata.post.admin.post',
236
            'Application\Sonata\NewsBundle\Entity\Post',
237
            'SonataNewsBundle:PostAdmin'
238
        );
239
        $securityHandler = $this->prophesize(SecurityHandlerInterface::class);
240
        $securityHandler->isGranted($admin, 'EDIT_ROLE', $admin)->willReturn(true);
241
        $customExtension = $this->prophesize(AbstractAdminExtension::class);
242
        $customExtension->getAccessMapping($admin)->willReturn(
243
            ['edit_action' => ['EDIT_ROLE']]
244
        );
245
        $admin->addExtension($customExtension->reveal());
246
        $admin->setSecurityHandler($securityHandler->reveal());
247
248
        $this->assertTrue($admin->hasAccess('edit_action'));
249
    }
250
251
    /**
252
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::hasChild
253
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::addChild
254
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getChild
255
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::isChild
256
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::hasChildren
257
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getChildren
258
     */
259
    public function testChildren(): void
260
    {
261
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
262
        $this->assertFalse($postAdmin->hasChildren());
263
        $this->assertFalse($postAdmin->hasChild('comment'));
264
265
        $commentAdmin = new CommentAdmin('sonata.post.admin.comment', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
266
        $postAdmin->addChild($commentAdmin, 'post');
267
268
        $this->assertTrue($postAdmin->hasChildren());
269
        $this->assertTrue($postAdmin->hasChild('sonata.post.admin.comment'));
270
271
        $this->assertSame('sonata.post.admin.comment', $postAdmin->getChild('sonata.post.admin.comment')->getCode());
272
        $this->assertSame('sonata.post.admin.post|sonata.post.admin.comment', $postAdmin->getChild('sonata.post.admin.comment')->getBaseCodeRoute());
273
        $this->assertSame($postAdmin, $postAdmin->getChild('sonata.post.admin.comment')->getParent());
274
        $this->assertSame('post', $commentAdmin->getParentAssociationMapping());
275
276
        $this->assertFalse($postAdmin->isChild());
277
        $this->assertTrue($commentAdmin->isChild());
278
279
        $this->assertSame(['sonata.post.admin.comment' => $commentAdmin], $postAdmin->getChildren());
280
    }
281
282
    /**
283
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::configure
284
     */
285
    public function testConfigure(): void
286
    {
287
        $admin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
288
        $this->assertNotNull($admin->getUniqid());
289
290
        $admin->initialize();
291
        $this->assertNotNull($admin->getUniqid());
292
        $this->assertSame('Post', $admin->getClassnameLabel());
293
294
        $admin = new CommentAdmin('sonata.post.admin.comment', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
295
        $admin->setClassnameLabel('postcomment');
296
297
        $admin->initialize();
298
        $this->assertSame('postcomment', $admin->getClassnameLabel());
299
    }
300
301
    public function testConfigureWithValidParentAssociationMapping(): void
302
    {
303
        $admin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
304
        $admin->setParentAssociationMapping('Category');
305
306
        $admin->initialize();
307
        $this->assertSame('Category', $admin->getParentAssociationMapping());
308
    }
309
310
    public function provideGetBaseRoutePattern()
311
    {
312
        return [
313
            [
314
                'Application\Sonata\NewsBundle\Entity\Post',
315
                '/sonata/news/post',
316
            ],
317
            [
318
                'Application\Sonata\NewsBundle\Document\Post',
319
                '/sonata/news/post',
320
            ],
321
            [
322
                'MyApplication\MyBundle\Entity\Post',
323
                '/myapplication/my/post',
324
            ],
325
            [
326
                'MyApplication\MyBundle\Entity\Post\Category',
327
                '/myapplication/my/post-category',
328
            ],
329
            [
330
                'MyApplication\MyBundle\Entity\Product\Category',
331
                '/myapplication/my/product-category',
332
            ],
333
            [
334
                'MyApplication\MyBundle\Entity\Other\Product\Category',
335
                '/myapplication/my/other-product-category',
336
            ],
337
            [
338
                'Symfony\Cmf\Bundle\FooBundle\Document\Menu',
339
                '/cmf/foo/menu',
340
            ],
341
            [
342
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\Phpcr\Menu',
343
                '/cmf/foo/menu',
344
            ],
345
            [
346
                'Symfony\Bundle\BarBarBundle\Doctrine\Phpcr\Menu',
347
                '/symfony/barbar/menu',
348
            ],
349
            [
350
                'Symfony\Bundle\BarBarBundle\Doctrine\Phpcr\Menu\Item',
351
                '/symfony/barbar/menu-item',
352
            ],
353
            [
354
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\Orm\Menu',
355
                '/cmf/foo/menu',
356
            ],
357
            [
358
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\MongoDB\Menu',
359
                '/cmf/foo/menu',
360
            ],
361
            [
362
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\CouchDB\Menu',
363
                '/cmf/foo/menu',
364
            ],
365
            [
366
                'AppBundle\Entity\User',
367
                '/app/user',
368
            ],
369
            [
370
                'App\Entity\User',
371
                '/app/user',
372
            ],
373
        ];
374
    }
375
376
    /**
377
     * @dataProvider provideGetBaseRoutePattern
378
     */
379
    public function testGetBaseRoutePattern($objFqn, $expected): void
380
    {
381
        $admin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
382
        $this->assertSame($expected, $admin->getBaseRoutePattern());
383
    }
384
385
    /**
386
     * @dataProvider provideGetBaseRoutePattern
387
     */
388
    public function testGetBaseRoutePatternWithChildAdmin($objFqn, $expected): void
389
    {
390
        $postAdmin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
391
        $commentAdmin = new CommentAdmin('sonata.post.admin.comment', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
392
        $commentAdmin->setParent($postAdmin);
393
394
        $this->assertSame($expected.'/{id}/comment', $commentAdmin->getBaseRoutePattern());
395
    }
396
397
    /**
398
     * @dataProvider provideGetBaseRoutePattern
399
     */
400
    public function testGetBaseRoutePatternWithTwoNestedChildAdmin($objFqn, $expected): void
401
    {
402
        $postAdmin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
403
        $commentAdmin = new CommentAdmin(
404
            'sonata.post.admin.comment',
405
            'Application\Sonata\NewsBundle\Entity\Comment',
406
            'SonataNewsBundle:CommentAdmin'
407
        );
408
        $commentVoteAdmin = new CommentVoteAdmin(
409
            'sonata.post.admin.comment_vote',
410
            'Application\Sonata\NewsBundle\Entity\CommentVote',
411
            'SonataNewsBundle:CommentVoteAdmin'
412
        );
413
        $commentAdmin->setParent($postAdmin);
414
        $commentVoteAdmin->setParent($commentAdmin);
415
416
        $this->assertSame($expected.'/{id}/comment/{childId}/commentvote', $commentVoteAdmin->getBaseRoutePattern());
417
    }
418
419
    public function testGetBaseRoutePatternWithSpecifedPattern(): void
420
    {
421
        $postAdmin = new PostWithCustomRouteAdmin('sonata.post.admin.post_with_custom_route', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostWithCustomRouteAdmin');
422
423
        $this->assertSame('/post-custom', $postAdmin->getBaseRoutePattern());
424
    }
425
426
    public function testGetBaseRoutePatternWithChildAdminAndWithSpecifedPattern(): void
427
    {
428
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
429
        $commentAdmin = new CommentWithCustomRouteAdmin('sonata.post.admin.comment_with_custom_route', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentWithCustomRouteAdmin');
430
        $commentAdmin->setParent($postAdmin);
431
432
        $this->assertSame('/sonata/news/post/{id}/comment-custom', $commentAdmin->getBaseRoutePattern());
433
    }
434
435
    public function testGetBaseRoutePatternWithUnreconizedClassname(): void
436
    {
437
        $this->expectException(\RuntimeException::class);
438
439
        $admin = new PostAdmin('sonata.post.admin.post', 'News\Thing\Post', 'SonataNewsBundle:PostAdmin');
440
        $admin->getBaseRoutePattern();
441
    }
442
443
    public function provideGetBaseRouteName()
444
    {
445
        return [
446
            [
447
                'Application\Sonata\NewsBundle\Entity\Post',
448
                'admin_sonata_news_post',
449
            ],
450
            [
451
                'Application\Sonata\NewsBundle\Document\Post',
452
                'admin_sonata_news_post',
453
            ],
454
            [
455
                'MyApplication\MyBundle\Entity\Post',
456
                'admin_myapplication_my_post',
457
            ],
458
            [
459
                'MyApplication\MyBundle\Entity\Post\Category',
460
                'admin_myapplication_my_post_category',
461
            ],
462
            [
463
                'MyApplication\MyBundle\Entity\Product\Category',
464
                'admin_myapplication_my_product_category',
465
            ],
466
            [
467
                'MyApplication\MyBundle\Entity\Other\Product\Category',
468
                'admin_myapplication_my_other_product_category',
469
            ],
470
            [
471
                'Symfony\Cmf\Bundle\FooBundle\Document\Menu',
472
                'admin_cmf_foo_menu',
473
            ],
474
            [
475
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\Phpcr\Menu',
476
                'admin_cmf_foo_menu',
477
            ],
478
            [
479
                'Symfony\Bundle\BarBarBundle\Doctrine\Phpcr\Menu',
480
                'admin_symfony_barbar_menu',
481
            ],
482
            [
483
                'Symfony\Bundle\BarBarBundle\Doctrine\Phpcr\Menu\Item',
484
                'admin_symfony_barbar_menu_item',
485
            ],
486
            [
487
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\Orm\Menu',
488
                'admin_cmf_foo_menu',
489
            ],
490
            [
491
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\MongoDB\Menu',
492
                'admin_cmf_foo_menu',
493
            ],
494
            [
495
                'Symfony\Cmf\Bundle\FooBundle\Doctrine\CouchDB\Menu',
496
                'admin_cmf_foo_menu',
497
            ],
498
            [
499
                'AppBundle\Entity\User',
500
                'admin_app_user',
501
            ],
502
            [
503
                'App\Entity\User',
504
                'admin_app_user',
505
            ],
506
        ];
507
    }
508
509
    /**
510
     * @dataProvider provideGetBaseRouteName
511
     */
512
    public function testGetBaseRouteName($objFqn, $expected): void
513
    {
514
        $admin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
515
516
        $this->assertSame($expected, $admin->getBaseRouteName());
517
    }
518
519
    /**
520
     * @group legacy
521
     * @expectedDeprecation Calling "addChild" without second argument is deprecated since 3.35 and will not be allowed in 4.0.
522
     * @dataProvider provideGetBaseRouteName
523
     */
524
    public function testGetBaseRouteNameWithChildAdmin($objFqn, $expected): void
525
    {
526
        $routeGenerator = new DefaultRouteGenerator(
527
            $this->createMock(RouterInterface::class),
0 ignored issues
show
$this->createMock(\Symfo...RouterInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Symfony\Component\Routing\RouterInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
528
            new RoutesCache($this->cacheTempFolder, true)
529
        );
530
531
        $container = new Container();
532
        $pool = new Pool($container, 'Sonata Admin', '/path/to/pic.png');
533
534
        $pathInfo = new PathInfoBuilder($this->createMock(AuditManagerInterface::class));
0 ignored issues
show
$this->createMock(\Sonat...anagerInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Sonata\AdminBundl...\AuditManagerInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
535
        $postAdmin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
536
        $container->set('sonata.post.admin.post', $postAdmin);
537
        $postAdmin->setConfigurationPool($pool);
538
        $postAdmin->setRouteBuilder($pathInfo);
539
        $postAdmin->setRouteGenerator($routeGenerator);
540
        $postAdmin->initialize();
541
542
        $commentAdmin = new CommentAdmin(
543
            'sonata.post.admin.comment',
544
            'Application\Sonata\NewsBundle\Entity\Comment',
545
            'SonataNewsBundle:CommentAdmin'
546
        );
547
        $container->set('sonata.post.admin.comment', $commentAdmin);
548
        $commentAdmin->setConfigurationPool($pool);
549
        $commentAdmin->setRouteBuilder($pathInfo);
550
        $commentAdmin->setRouteGenerator($routeGenerator);
551
        $commentAdmin->initialize();
552
553
        $postAdmin->addChild($commentAdmin, 'post');
554
555
        $commentVoteAdmin = new CommentVoteAdmin(
556
            'sonata.post.admin.comment_vote',
557
            'Application\Sonata\NewsBundle\Entity\CommentVote',
558
            'SonataNewsBundle:CommentVoteAdmin'
559
        );
560
561
        $container->set('sonata.post.admin.comment_vote', $commentVoteAdmin);
562
        $commentVoteAdmin->setConfigurationPool($pool);
563
        $commentVoteAdmin->setRouteBuilder($pathInfo);
564
        $commentVoteAdmin->setRouteGenerator($routeGenerator);
565
        $commentVoteAdmin->initialize();
566
567
        $commentAdmin->addChild($commentVoteAdmin);
568
        $pool->setAdminServiceIds([
569
            'sonata.post.admin.post',
570
            'sonata.post.admin.comment',
571
            'sonata.post.admin.comment_vote',
572
        ]);
573
574
        $this->assertSame($expected.'_comment', $commentAdmin->getBaseRouteName());
575
576
        $this->assertTrue($postAdmin->hasRoute('show'));
577
        $this->assertTrue($postAdmin->hasRoute('sonata.post.admin.post.show'));
578
        $this->assertTrue($postAdmin->hasRoute('sonata.post.admin.post|sonata.post.admin.comment.show'));
579
        $this->assertTrue($postAdmin->hasRoute('sonata.post.admin.post|sonata.post.admin.comment|sonata.post.admin.comment_vote.show'));
580
        $this->assertTrue($postAdmin->hasRoute('sonata.post.admin.comment.list'));
581
        $this->assertTrue($postAdmin->hasRoute('sonata.post.admin.comment|sonata.post.admin.comment_vote.list'));
582
        $this->assertFalse($postAdmin->hasRoute('sonata.post.admin.post|sonata.post.admin.comment.edit'));
583
        $this->assertFalse($commentAdmin->hasRoute('edit'));
584
        $this->assertSame('post', $commentAdmin->getParentAssociationMapping());
585
586
        /*
587
         * Test the route name from request
588
         */
589
        $postListRequest = new Request(
590
            [],
591
            [],
592
            [
593
                '_route' => $postAdmin->getBaseRouteName().'_list',
594
            ]
595
        );
596
597
        $postAdmin->setRequest($postListRequest);
598
        $commentAdmin->setRequest($postListRequest);
599
600
        $this->assertTrue($postAdmin->isCurrentRoute('list'));
601
        $this->assertFalse($postAdmin->isCurrentRoute('create'));
602
        $this->assertFalse($commentAdmin->isCurrentRoute('list'));
603
        $this->assertFalse($commentVoteAdmin->isCurrentRoute('list'));
604
        $this->assertTrue($commentAdmin->isCurrentRoute('list', 'sonata.post.admin.post'));
605
        $this->assertFalse($commentAdmin->isCurrentRoute('edit', 'sonata.post.admin.post'));
606
        $this->assertTrue($commentVoteAdmin->isCurrentRoute('list', 'sonata.post.admin.post'));
607
        $this->assertFalse($commentVoteAdmin->isCurrentRoute('edit', 'sonata.post.admin.post'));
608
    }
609
610
    public function testGetBaseRouteNameWithUnreconizedClassname(): void
611
    {
612
        $this->expectException(\RuntimeException::class);
613
614
        $admin = new PostAdmin('sonata.post.admin.post', 'News\Thing\Post', 'SonataNewsBundle:PostAdmin');
615
        $admin->getBaseRouteName();
616
    }
617
618
    public function testGetBaseRouteNameWithSpecifiedName(): void
619
    {
620
        $postAdmin = new PostWithCustomRouteAdmin('sonata.post.admin.post_with_custom_route', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
621
622
        $this->assertSame('post_custom', $postAdmin->getBaseRouteName());
623
    }
624
625
    public function testGetBaseRouteNameWithChildAdminAndWithSpecifiedName(): void
626
    {
627
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
628
        $commentAdmin = new CommentWithCustomRouteAdmin('sonata.post.admin.comment_with_custom_route', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentWithCustomRouteAdmin');
629
        $commentAdmin->setParent($postAdmin);
630
631
        $this->assertSame('admin_sonata_news_post_comment_custom', $commentAdmin->getBaseRouteName());
632
    }
633
634
    public function testGetBaseRouteNameWithTwoNestedChildAdminAndWithSpecifiedName(): void
635
    {
636
        $postAdmin = new PostAdmin(
637
            'sonata.post.admin.post',
638
            'Application\Sonata\NewsBundle\Entity\Post',
639
            'SonataNewsBundle:PostAdmin'
640
        );
641
        $commentAdmin = new CommentWithCustomRouteAdmin(
642
            'sonata.post.admin.comment_with_custom_route',
643
            'Application\Sonata\NewsBundle\Entity\Comment',
644
            'SonataNewsBundle:CommentWithCustomRouteAdmin'
645
        );
646
        $commentVoteAdmin = new CommentVoteAdmin(
647
            'sonata.post.admin.comment_vote',
648
            'Application\Sonata\NewsBundle\Entity\CommentVote',
649
            'SonataNewsBundle:CommentVoteAdmin'
650
        );
651
        $commentAdmin->setParent($postAdmin);
652
        $commentVoteAdmin->setParent($commentAdmin);
653
654
        $this->assertSame('admin_sonata_news_post_comment_custom_commentvote', $commentVoteAdmin->getBaseRouteName());
655
    }
656
657
    /**
658
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::setUniqid
659
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getUniqid
660
     */
661
    public function testSetUniqid(): void
662
    {
663
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
664
665
        $uniqid = uniqid();
666
        $admin->setUniqid($uniqid);
667
668
        $this->assertSame($uniqid, $admin->getUniqid());
669
    }
670
671
    public function testUniqidConsistency(): void
672
    {
673
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
674
            'sonata.abstract.admin',
675
            'AbstractBundle\Entity\Foo',
676
            'SonataAbstractBundle:FooAdmin',
677
        ]);
678
        $admin->initialize();
679
680
        $uniqid = $admin->getUniqid();
681
        $admin->setUniqid(null);
682
683
        $this->assertSame($uniqid, $admin->getUniqid());
684
685
        $parentAdmin = $this->getMockForAbstractClass(AbstractAdmin::class, [
686
            'sonata.abstract.parent.admin',
687
            'AbstractBundle\Entity\Bar',
688
            'SonataAbstractBundle:BarAdmin',
689
        ]);
690
        $parentAdmin->initialize();
691
692
        $admin->setParent($parentAdmin);
693
        $admin->setUniqid(null);
694
695
        $this->assertNotSame($uniqid, $admin->getUniqid());
696
    }
697
698
    public function testToString(): void
699
    {
700
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
701
702
        $s = new \stdClass();
703
704
        $this->assertNotEmpty($admin->toString($s));
705
706
        $s = new FooToString();
707
        $this->assertSame('salut', $admin->toString($s));
708
709
        // To string method is implemented, but returns null
710
        $s = new FooToStringNull();
711
        $this->assertNotEmpty($admin->toString($s));
712
713
        $this->assertSame('', $admin->toString(false));
714
    }
715
716
    public function testIsAclEnabled(): void
717
    {
718
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
719
720
        $this->assertFalse($postAdmin->isAclEnabled());
721
722
        $commentAdmin = new CommentAdmin('sonata.post.admin.comment', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
723
        $commentAdmin->setSecurityHandler($this->createMock(AclSecurityHandlerInterface::class));
0 ignored issues
show
$this->createMock(\Sonat...andlerInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Sonata\AdminBundl...curityHandlerInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
724
        $this->assertTrue($commentAdmin->isAclEnabled());
725
    }
726
727
    /**
728
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getSubClasses
729
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getSubClass
730
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::setSubClasses
731
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::hasSubClass
732
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::hasActiveSubClass
733
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getActiveSubClass
734
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getActiveSubclassCode
735
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getClass
736
     */
737
    public function testSubClass(): void
738
    {
739
        $admin = new PostAdmin(
740
            'sonata.post.admin.post',
741
            Post::class,
742
            'SonataNewsBundle:PostAdmin'
743
        );
744
        $this->assertFalse($admin->hasSubClass('test'));
745
        $this->assertFalse($admin->hasActiveSubClass());
746
        $this->assertCount(0, $admin->getSubClasses());
747
        $this->assertNull($admin->getActiveSubClass());
748
        $this->assertNull($admin->getActiveSubclassCode());
749
        $this->assertSame(Post::class, $admin->getClass());
750
751
        // Just for the record, if there is no inheritance set, the getSubject is not used
752
        // the getSubject can also lead to some issue
753
        $admin->setSubject(new BlogPost());
754
        $this->assertSame(BlogPost::class, $admin->getClass());
755
756
        $admin->setSubClasses([
757
            'extended1' => 'NewsBundle\Entity\PostExtended1',
758
            'extended2' => 'NewsBundle\Entity\PostExtended2',
759
        ]);
760
        $this->assertFalse($admin->hasSubClass('test'));
761
        $this->assertTrue($admin->hasSubClass('extended1'));
762
        $this->assertFalse($admin->hasActiveSubClass());
763
        $this->assertCount(2, $admin->getSubClasses());
764
        $this->assertNull($admin->getActiveSubClass());
765
        $this->assertNull($admin->getActiveSubclassCode());
766
        $this->assertSame(
767
            BlogPost::class,
768
            $admin->getClass(),
769
            'When there is no subclass in the query the class parameter should be returned'
770
        );
771
772
        $request = new Request(['subclass' => 'extended1']);
773
        $admin->setRequest($request);
774
        $this->assertFalse($admin->hasSubClass('test'));
775
        $this->assertTrue($admin->hasSubClass('extended1'));
776
        $this->assertTrue($admin->hasActiveSubClass());
777
        $this->assertCount(2, $admin->getSubClasses());
778
        $this->assertSame(
779
            'NewsBundle\Entity\PostExtended1',
780
            $admin->getActiveSubClass(),
781
            'It should return the curently active sub class.'
782
        );
783
        $this->assertSame('extended1', $admin->getActiveSubclassCode());
784
        $this->assertSame(
785
            'NewsBundle\Entity\PostExtended1',
786
            $admin->getClass(),
787
            'getClass() should return the name of the sub class when passed through a request query parameter.'
788
        );
789
790
        $request->query->set('subclass', 'inject');
791
        $this->assertNull($admin->getActiveSubclassCode());
792
    }
793
794
    public function testNonExistantSubclass(): void
795
    {
796
        $this->expectException(\RuntimeException::class);
797
798
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
799
        $admin->setModelManager($this->getMockForAbstractClass(ModelManagerInterface::class));
800
801
        $admin->setRequest(new Request(['subclass' => 'inject']));
802
803
        $admin->setSubClasses(['extended1' => 'NewsBundle\Entity\PostExtended1', 'extended2' => 'NewsBundle\Entity\PostExtended2']);
804
805
        $this->assertTrue($admin->hasActiveSubClass());
806
807
        $admin->getActiveSubClass();
808
    }
809
810
    /**
811
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::hasActiveSubClass
812
     */
813
    public function testOnlyOneSubclassNeededToBeActive(): void
814
    {
815
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
816
        $admin->setSubClasses(['extended1' => 'NewsBundle\Entity\PostExtended1']);
817
        $request = new Request(['subclass' => 'extended1']);
818
        $admin->setRequest($request);
819
        $this->assertTrue($admin->hasActiveSubClass());
820
    }
821
822
    /**
823
     * @group legacy
824
     * @expectedDeprecation Method "Sonata\AdminBundle\Admin\AbstractAdmin::addSubClass" is deprecated since 3.30 and will be removed in 4.0.
825
     */
826
    public function testAddSubClassIsDeprecated(): void
827
    {
828
        $admin = new PostAdmin(
829
            'sonata.post.admin.post',
830
            Post::class,
831
            'SonataNewsBundle:PostAdmin'
832
        );
833
        $admin->addSubClass('whatever');
834
    }
835
836
    public function testGetPerPageOptions(): void
837
    {
838
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
839
840
        $perPageOptions = $admin->getPerPageOptions();
841
842
        foreach ($perPageOptions as $perPage) {
843
            $this->assertSame(0, $perPage % 4);
844
        }
845
846
        $admin->setPerPageOptions([500, 1000]);
847
        $this->assertSame([500, 1000], $admin->getPerPageOptions());
848
    }
849
850
    public function testGetLabelTranslatorStrategy(): void
851
    {
852
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
853
854
        $this->assertNull($admin->getLabelTranslatorStrategy());
855
856
        $labelTranslatorStrategy = $this->createMock(LabelTranslatorStrategyInterface::class);
857
        $admin->setLabelTranslatorStrategy($labelTranslatorStrategy);
858
        $this->assertSame($labelTranslatorStrategy, $admin->getLabelTranslatorStrategy());
859
    }
860
861
    public function testGetRouteBuilder(): void
862
    {
863
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
864
865
        $this->assertNull($admin->getRouteBuilder());
866
867
        $routeBuilder = $this->createMock(RouteBuilderInterface::class);
868
        $admin->setRouteBuilder($routeBuilder);
869
        $this->assertSame($routeBuilder, $admin->getRouteBuilder());
870
    }
871
872
    public function testGetMenuFactory(): void
873
    {
874
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
875
876
        $this->assertNull($admin->getMenuFactory());
877
878
        $menuFactory = $this->createMock(FactoryInterface::class);
879
        $admin->setMenuFactory($menuFactory);
880
        $this->assertSame($menuFactory, $admin->getMenuFactory());
881
    }
882
883
    public function testGetExtensions(): void
884
    {
885
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
886
887
        $this->assertSame([], $admin->getExtensions());
888
889
        $adminExtension1 = $this->createMock(AdminExtensionInterface::class);
890
        $adminExtension2 = $this->createMock(AdminExtensionInterface::class);
891
892
        $admin->addExtension($adminExtension1);
893
        $admin->addExtension($adminExtension2);
894
        $this->assertSame([$adminExtension1, $adminExtension2], $admin->getExtensions());
895
    }
896
897
    public function testGetFilterTheme(): void
898
    {
899
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
900
901
        $this->assertSame([], $admin->getFilterTheme());
902
903
        $admin->setFilterTheme(['FooTheme']);
904
        $this->assertSame(['FooTheme'], $admin->getFilterTheme());
905
    }
906
907
    public function testGetFormTheme(): void
908
    {
909
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
910
911
        $this->assertSame([], $admin->getFormTheme());
912
913
        $admin->setFormTheme(['FooTheme']);
914
915
        $this->assertSame(['FooTheme'], $admin->getFormTheme());
916
    }
917
918
    public function testGetValidator(): void
919
    {
920
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
921
922
        $this->assertNull($admin->getValidator());
923
924
        $validator = $this->getMockForAbstractClass(ValidatorInterface::class);
925
926
        $admin->setValidator($validator);
927
        $this->assertSame($validator, $admin->getValidator());
928
    }
929
930
    public function testGetSecurityHandler(): void
931
    {
932
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
933
934
        $this->assertNull($admin->getSecurityHandler());
935
936
        $securityHandler = $this->createMock(SecurityHandlerInterface::class);
937
        $admin->setSecurityHandler($securityHandler);
938
        $this->assertSame($securityHandler, $admin->getSecurityHandler());
939
    }
940
941
    public function testGetSecurityInformation(): void
942
    {
943
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
944
945
        $this->assertSame([], $admin->getSecurityInformation());
946
947
        $securityInformation = [
948
            'GUEST' => ['VIEW', 'LIST'],
949
            'STAFF' => ['EDIT', 'LIST', 'CREATE'],
950
        ];
951
952
        $admin->setSecurityInformation($securityInformation);
953
        $this->assertSame($securityInformation, $admin->getSecurityInformation());
954
    }
955
956
    public function testGetManagerType(): void
957
    {
958
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
959
960
        $this->assertNull($admin->getManagerType());
961
962
        $admin->setManagerType('foo_orm');
963
        $this->assertSame('foo_orm', $admin->getManagerType());
964
    }
965
966
    public function testGetModelManager(): void
967
    {
968
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
969
970
        $this->assertNull($admin->getModelManager());
971
972
        $modelManager = $this->createMock(ModelManagerInterface::class);
973
974
        $admin->setModelManager($modelManager);
975
        $this->assertSame($modelManager, $admin->getModelManager());
976
    }
977
978
    /**
979
     * NEXT_MAJOR: remove this method.
980
     *
981
     * @group legacy
982
     */
983
    public function testGetBaseCodeRoute(): void
984
    {
985
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
986
987
        $this->assertSame('', $admin->getBaseCodeRoute());
988
989
        $admin->setBaseCodeRoute('foo');
990
        $this->assertSame('foo', $admin->getBaseCodeRoute());
991
    }
992
993
    // NEXT_MAJOR: uncomment this method.
994
    // public function testGetBaseCodeRoute()
995
    // {
996
    //     $postAdmin = new PostAdmin(
997
    //         'sonata.post.admin.post',
998
    //         'NewsBundle\Entity\Post',
999
    //         'SonataNewsBundle:PostAdmin'
1000
    //     );
1001
    //     $commentAdmin = new CommentAdmin(
1002
    //         'sonata.post.admin.comment',
1003
    //         'Application\Sonata\NewsBundle\Entity\Comment',
1004
    //         'SonataNewsBundle:CommentAdmin'
1005
    //     );
1006
    //
1007
    //     $this->assertSame($postAdmin->getCode(), $postAdmin->getBaseCodeRoute());
1008
    //
1009
    //     $postAdmin->addChild($commentAdmin);
1010
    //
1011
    //     $this->assertSame(
1012
    //         'sonata.post.admin.post|sonata.post.admin.comment',
1013
    //         $commentAdmin->getBaseCodeRoute()
1014
    //     );
1015
    // }
1016
1017
    public function testGetRouteGenerator(): void
1018
    {
1019
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1020
1021
        $this->assertNull($admin->getRouteGenerator());
1022
1023
        $routeGenerator = $this->createMock(RouteGeneratorInterface::class);
1024
1025
        $admin->setRouteGenerator($routeGenerator);
1026
        $this->assertSame($routeGenerator, $admin->getRouteGenerator());
1027
    }
1028
1029
    public function testGetConfigurationPool(): void
1030
    {
1031
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1032
1033
        $this->assertNull($admin->getConfigurationPool());
1034
1035
        $pool = $this->getMockBuilder(Pool::class)
1036
            ->disableOriginalConstructor()
1037
            ->getMock();
1038
1039
        $admin->setConfigurationPool($pool);
1040
        $this->assertSame($pool, $admin->getConfigurationPool());
1041
    }
1042
1043
    public function testGetShowBuilder(): void
1044
    {
1045
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1046
1047
        $this->assertNull($admin->getShowBuilder());
1048
1049
        $showBuilder = $this->createMock(ShowBuilderInterface::class);
1050
1051
        $admin->setShowBuilder($showBuilder);
1052
        $this->assertSame($showBuilder, $admin->getShowBuilder());
1053
    }
1054
1055
    public function testGetListBuilder(): void
1056
    {
1057
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1058
1059
        $this->assertNull($admin->getListBuilder());
1060
1061
        $listBuilder = $this->createMock(ListBuilderInterface::class);
1062
1063
        $admin->setListBuilder($listBuilder);
1064
        $this->assertSame($listBuilder, $admin->getListBuilder());
1065
    }
1066
1067
    public function testGetDatagridBuilder(): void
1068
    {
1069
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1070
1071
        $this->assertNull($admin->getDatagridBuilder());
1072
1073
        $datagridBuilder = $this->createMock(DatagridBuilderInterface::class);
1074
1075
        $admin->setDatagridBuilder($datagridBuilder);
1076
        $this->assertSame($datagridBuilder, $admin->getDatagridBuilder());
1077
    }
1078
1079
    public function testGetFormContractor(): void
1080
    {
1081
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1082
1083
        $this->assertNull($admin->getFormContractor());
1084
1085
        $formContractor = $this->createMock(FormContractorInterface::class);
1086
1087
        $admin->setFormContractor($formContractor);
1088
        $this->assertSame($formContractor, $admin->getFormContractor());
1089
    }
1090
1091
    public function testGetRequest(): void
1092
    {
1093
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1094
1095
        $this->assertFalse($admin->hasRequest());
1096
1097
        $request = new Request();
1098
1099
        $admin->setRequest($request);
1100
        $this->assertSame($request, $admin->getRequest());
1101
        $this->assertTrue($admin->hasRequest());
1102
    }
1103
1104
    public function testGetRequestWithException(): void
1105
    {
1106
        $this->expectException(\RuntimeException::class);
1107
        $this->expectExceptionMessage('The Request object has not been set');
1108
1109
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1110
        $admin->getRequest();
1111
    }
1112
1113
    public function testGetTranslationDomain(): void
1114
    {
1115
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1116
1117
        $this->assertSame('messages', $admin->getTranslationDomain());
1118
1119
        $admin->setTranslationDomain('foo');
1120
        $this->assertSame('foo', $admin->getTranslationDomain());
1121
    }
1122
1123
    /**
1124
     * @group legacy
1125
     */
1126
    public function testGetTranslator(): void
1127
    {
1128
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1129
1130
        $this->assertNull($admin->getTranslator());
1131
1132
        $translator = $this->createMock(TranslatorInterface::class);
1133
1134
        $admin->setTranslator($translator);
1135
        $this->assertSame($translator, $admin->getTranslator());
1136
    }
1137
1138
    public function testGetShowGroups(): void
1139
    {
1140
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1141
1142
        $this->assertFalse($admin->getShowGroups());
1143
1144
        $groups = ['foo', 'bar', 'baz'];
1145
1146
        $admin->setShowGroups($groups);
1147
        $this->assertSame($groups, $admin->getShowGroups());
1148
    }
1149
1150
    public function testGetFormGroups(): void
1151
    {
1152
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1153
1154
        $this->assertFalse($admin->getFormGroups());
1155
1156
        $groups = ['foo', 'bar', 'baz'];
1157
1158
        $admin->setFormGroups($groups);
1159
        $this->assertSame($groups, $admin->getFormGroups());
1160
    }
1161
1162
    public function testGetMaxPageLinks(): void
1163
    {
1164
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1165
1166
        $this->assertSame(25, $admin->getMaxPageLinks());
1167
1168
        $admin->setMaxPageLinks(14);
1169
        $this->assertSame(14, $admin->getMaxPageLinks());
1170
    }
1171
1172
    public function testGetMaxPerPage(): void
1173
    {
1174
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1175
1176
        $this->assertSame(32, $admin->getMaxPerPage());
1177
1178
        $admin->setMaxPerPage(94);
1179
        $this->assertSame(94, $admin->getMaxPerPage());
1180
    }
1181
1182
    public function testGetLabel(): void
1183
    {
1184
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1185
1186
        $this->assertNull($admin->getLabel());
1187
1188
        $admin->setLabel('FooLabel');
1189
        $this->assertSame('FooLabel', $admin->getLabel());
1190
    }
1191
1192
    public function testGetBaseController(): void
1193
    {
1194
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1195
1196
        $this->assertSame('SonataNewsBundle:PostAdmin', $admin->getBaseControllerName());
1197
1198
        $admin->setBaseControllerName('SonataNewsBundle:FooAdmin');
1199
        $this->assertSame('SonataNewsBundle:FooAdmin', $admin->getBaseControllerName());
1200
    }
1201
1202
    public function testGetTemplates(): void
1203
    {
1204
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1205
1206
        $templates = [
1207
            'list' => '@FooAdmin/CRUD/list.html.twig',
1208
            'show' => '@FooAdmin/CRUD/show.html.twig',
1209
            'edit' => '@FooAdmin/CRUD/edit.html.twig',
1210
        ];
1211
1212
        $templateRegistry = $this->prophesize(MutableTemplateRegistryInterface::class);
1213
        $templateRegistry->getTemplates()->shouldBeCalled()->willReturn($templates);
1214
1215
        $admin->setTemplateRegistry($templateRegistry->reveal());
1216
1217
        $this->assertSame($templates, $admin->getTemplates());
1218
    }
1219
1220
    public function testGetTemplate1(): void
1221
    {
1222
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1223
1224
        $templateRegistry = $this->prophesize(MutableTemplateRegistryInterface::class);
1225
        $templateRegistry->getTemplate('edit')->shouldBeCalled()->willReturn('@FooAdmin/CRUD/edit.html.twig');
1226
        $templateRegistry->getTemplate('show')->shouldBeCalled()->willReturn('@FooAdmin/CRUD/show.html.twig');
1227
1228
        $admin->setTemplateRegistry($templateRegistry->reveal());
1229
1230
        $this->assertSame('@FooAdmin/CRUD/edit.html.twig', $admin->getTemplate('edit'));
1231
        $this->assertSame('@FooAdmin/CRUD/show.html.twig', $admin->getTemplate('show'));
1232
    }
1233
1234
    public function testGetIdParameter(): void
1235
    {
1236
        $postAdmin = new PostAdmin(
1237
            'sonata.post.admin.post',
1238
            'NewsBundle\Entity\Post',
1239
            'SonataNewsBundle:PostAdmin'
1240
        );
1241
1242
        $this->assertSame('id', $postAdmin->getIdParameter());
1243
        $this->assertFalse($postAdmin->isChild());
1244
1245
        $commentAdmin = new CommentAdmin(
1246
            'sonata.post.admin.comment',
1247
            'Application\Sonata\NewsBundle\Entity\Comment',
1248
            'SonataNewsBundle:CommentAdmin'
1249
        );
1250
        $commentAdmin->setParent($postAdmin);
1251
1252
        $this->assertTrue($commentAdmin->isChild());
1253
        $this->assertSame('childId', $commentAdmin->getIdParameter());
1254
1255
        $commentVoteAdmin = new CommentVoteAdmin(
1256
            'sonata.post.admin.comment_vote',
1257
            'Application\Sonata\NewsBundle\Entity\CommentVote',
1258
            'SonataNewsBundle:CommentVoteAdmin'
1259
        );
1260
        $commentVoteAdmin->setParent($commentAdmin);
1261
1262
        $this->assertTrue($commentVoteAdmin->isChild());
1263
        $this->assertSame('childChildId', $commentVoteAdmin->getIdParameter());
1264
    }
1265
1266
    public function testGetExportFormats(): void
1267
    {
1268
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1269
1270
        $this->assertSame(['json', 'xml', 'csv', 'xls'], $admin->getExportFormats());
1271
    }
1272
1273
    public function testGetUrlsafeIdentifier(): void
1274
    {
1275
        $admin = new PostAdmin('sonata.post.admin.post', 'Acme\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1276
1277
        $entity = new \stdClass();
1278
1279
        $modelManager = $this->createMock(ModelManagerInterface::class);
1280
        $modelManager->expects($this->once())
1281
            ->method('getUrlsafeIdentifier')
1282
            ->with($this->equalTo($entity))
1283
            ->will($this->returnValue('foo'));
1284
        $admin->setModelManager($modelManager);
1285
1286
        $this->assertSame('foo', $admin->getUrlsafeIdentifier($entity));
1287
    }
1288
1289
    public function testDeterminedPerPageValue(): void
1290
    {
1291
        $admin = new PostAdmin('sonata.post.admin.post', 'Acme\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1292
1293
        $this->assertFalse($admin->determinedPerPageValue('foo'));
1294
        $this->assertFalse($admin->determinedPerPageValue(123));
1295
        $this->assertTrue($admin->determinedPerPageValue(16));
1296
1297
        $admin->setPerPageOptions([101, 102, 103]);
1298
        $this->assertFalse($admin->determinedPerPageValue(16));
1299
        $this->assertTrue($admin->determinedPerPageValue(101));
1300
    }
1301
1302
    public function testIsGranted(): void
1303
    {
1304
        $admin = new PostAdmin('sonata.post.admin.post', 'Acme\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1305
1306
        $entity = new \stdClass();
1307
1308
        $securityHandler = $this->createMock(AclSecurityHandlerInterface::class);
1309
        $securityHandler->expects($this->any())
1310
            ->method('isGranted')
1311
            ->will($this->returnCallback(function (AdminInterface $adminIn, $attributes, $object = null) use ($admin, $entity) {
1312
                if ($admin === $adminIn && 'FOO' === $attributes) {
1313
                    if (($object === $admin) || ($object === $entity)) {
1314
                        return true;
1315
                    }
1316
                }
1317
1318
                return false;
1319
            }));
1320
1321
        $admin->setSecurityHandler($securityHandler);
1322
1323
        $this->assertTrue($admin->isGranted('FOO'));
1324
        $this->assertTrue($admin->isGranted('FOO', $entity));
1325
        $this->assertFalse($admin->isGranted('BAR'));
1326
        $this->assertFalse($admin->isGranted('BAR', $entity));
1327
    }
1328
1329
    public function testSupportsPreviewMode(): void
1330
    {
1331
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1332
1333
        $this->assertFalse($admin->supportsPreviewMode());
1334
    }
1335
1336
    public function testGetPermissionsShow(): void
1337
    {
1338
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1339
1340
        $this->assertSame(['LIST'], $admin->getPermissionsShow(AbstractAdmin::CONTEXT_DASHBOARD));
1341
        $this->assertSame(['LIST'], $admin->getPermissionsShow(AbstractAdmin::CONTEXT_MENU));
1342
        $this->assertSame(['LIST'], $admin->getPermissionsShow('foo'));
1343
    }
1344
1345
    public function testShowIn(): void
1346
    {
1347
        $admin = new PostAdmin('sonata.post.admin.post', 'Acme\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1348
1349
        $securityHandler = $this->createMock(AclSecurityHandlerInterface::class);
1350
        $securityHandler->expects($this->any())
1351
            ->method('isGranted')
1352
            ->will($this->returnCallback(function (AdminInterface $adminIn, $attributes, $object = null) use ($admin) {
1353
                if ($admin === $adminIn && $attributes === ['LIST']) {
1354
                    return true;
1355
                }
1356
1357
                return false;
1358
            }));
1359
1360
        $admin->setSecurityHandler($securityHandler);
1361
1362
        $this->assertTrue($admin->showIn(AbstractAdmin::CONTEXT_DASHBOARD));
1363
        $this->assertTrue($admin->showIn(AbstractAdmin::CONTEXT_MENU));
1364
        $this->assertTrue($admin->showIn('foo'));
1365
    }
1366
1367
    public function testGetObjectIdentifier(): void
1368
    {
1369
        $admin = new PostAdmin('sonata.post.admin.post', 'Acme\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1370
1371
        $this->assertSame('sonata.post.admin.post', $admin->getObjectIdentifier());
1372
    }
1373
1374
    /**
1375
     * @group legacy
1376
     */
1377
    public function testTrans(): void
1378
    {
1379
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1380
        $admin->setTranslationDomain('fooMessageDomain');
1381
1382
        $translator = $this->createMock(TranslatorInterface::class);
1383
        $admin->setTranslator($translator);
1384
1385
        $translator->expects($this->once())
1386
            ->method('trans')
1387
            ->with($this->equalTo('foo'), $this->equalTo([]), $this->equalTo('fooMessageDomain'))
1388
            ->will($this->returnValue('fooTranslated'));
1389
1390
        $this->assertSame('fooTranslated', $admin->trans('foo'));
1391
    }
1392
1393
    /**
1394
     * @group legacy
1395
     */
1396
    public function testTransWithMessageDomain(): void
1397
    {
1398
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1399
1400
        $translator = $this->createMock(TranslatorInterface::class);
1401
        $admin->setTranslator($translator);
1402
1403
        $translator->expects($this->once())
1404
            ->method('trans')
1405
            ->with($this->equalTo('foo'), $this->equalTo(['name' => 'Andrej']), $this->equalTo('fooMessageDomain'))
1406
            ->will($this->returnValue('fooTranslated'));
1407
1408
        $this->assertSame('fooTranslated', $admin->trans('foo', ['name' => 'Andrej'], 'fooMessageDomain'));
1409
    }
1410
1411
    /**
1412
     * @group legacy
1413
     */
1414
    public function testTransChoice(): void
1415
    {
1416
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1417
        $admin->setTranslationDomain('fooMessageDomain');
1418
1419
        $translator = $this->createMock(TranslatorInterface::class);
1420
        $admin->setTranslator($translator);
1421
1422
        $translator->expects($this->once())
1423
            ->method('transChoice')
1424
            ->with($this->equalTo('foo'), $this->equalTo(2), $this->equalTo([]), $this->equalTo('fooMessageDomain'))
1425
            ->will($this->returnValue('fooTranslated'));
1426
1427
        $this->assertSame('fooTranslated', $admin->transChoice('foo', 2));
1428
    }
1429
1430
    /**
1431
     * @group legacy
1432
     */
1433
    public function testTransChoiceWithMessageDomain(): void
1434
    {
1435
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1436
1437
        $translator = $this->createMock(TranslatorInterface::class);
1438
        $admin->setTranslator($translator);
1439
1440
        $translator->expects($this->once())
1441
            ->method('transChoice')
1442
            ->with($this->equalTo('foo'), $this->equalTo(2), $this->equalTo(['name' => 'Andrej']), $this->equalTo('fooMessageDomain'))
1443
            ->will($this->returnValue('fooTranslated'));
1444
1445
        $this->assertSame('fooTranslated', $admin->transChoice('foo', 2, ['name' => 'Andrej'], 'fooMessageDomain'));
1446
    }
1447
1448
    public function testSetFilterPersister(): void
1449
    {
1450
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1451
1452
        $filterPersister = $this->createMock('Sonata\AdminBundle\Filter\Persister\FilterPersisterInterface');
1453
1454
        $this->assertAttributeSame(null, 'filterPersister', $admin);
1455
        $admin->setFilterPersister($filterPersister);
1456
        $this->assertAttributeSame($filterPersister, 'filterPersister', $admin);
1457
        $this->assertAttributeSame(true, 'persistFilters', $admin);
1458
    }
1459
1460
    public function testGetRootCode(): void
1461
    {
1462
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1463
1464
        $this->assertSame('sonata.post.admin.post', $admin->getRootCode());
1465
1466
        $parentAdmin = new PostAdmin('sonata.post.admin.post.parent', 'NewsBundle\Entity\PostParent', 'SonataNewsBundle:PostParentAdmin');
1467
        $parentFieldDescription = $this->createMock(FieldDescriptionInterface::class);
1468
        $parentFieldDescription->expects($this->once())
1469
            ->method('getAdmin')
1470
            ->will($this->returnValue($parentAdmin));
1471
1472
        $this->assertNull($admin->getParentFieldDescription());
1473
        $admin->setParentFieldDescription($parentFieldDescription);
1474
        $this->assertSame($parentFieldDescription, $admin->getParentFieldDescription());
1475
        $this->assertSame('sonata.post.admin.post.parent', $admin->getRootCode());
1476
    }
1477
1478
    public function testGetRoot(): void
1479
    {
1480
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1481
1482
        $this->assertSame($admin, $admin->getRoot());
1483
1484
        $parentAdmin = new PostAdmin('sonata.post.admin.post.parent', 'NewsBundle\Entity\PostParent', 'SonataNewsBundle:PostParentAdmin');
1485
        $parentFieldDescription = $this->createMock(FieldDescriptionInterface::class);
1486
        $parentFieldDescription->expects($this->once())
1487
            ->method('getAdmin')
1488
            ->will($this->returnValue($parentAdmin));
1489
1490
        $this->assertNull($admin->getParentFieldDescription());
1491
        $admin->setParentFieldDescription($parentFieldDescription);
1492
        $this->assertSame($parentFieldDescription, $admin->getParentFieldDescription());
1493
        $this->assertSame($parentAdmin, $admin->getRoot());
1494
    }
1495
1496
    public function testGetExportFields(): void
1497
    {
1498
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1499
1500
        $modelManager = $this->createMock(ModelManagerInterface::class);
1501
        $modelManager->expects($this->once())
1502
            ->method('getExportFields')
1503
            ->with($this->equalTo('NewsBundle\Entity\Post'))
1504
            ->will($this->returnValue(['foo', 'bar']));
1505
1506
        $admin->setModelManager($modelManager);
1507
        $this->assertSame(['foo', 'bar'], $admin->getExportFields());
1508
    }
1509
1510
    public function testGetPersistentParametersWithNoExtension(): void
1511
    {
1512
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1513
1514
        $this->assertEmpty($admin->getPersistentParameters());
1515
    }
1516
1517
    public function testGetPersistentParametersWithInvalidExtension(): void
1518
    {
1519
        $this->expectException(\RuntimeException::class);
1520
1521
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1522
1523
        $extension = $this->createMock(AdminExtensionInterface::class);
1524
        $extension->expects($this->once())->method('getPersistentParameters')->will($this->returnValue(null));
1525
1526
        $admin->addExtension($extension);
1527
1528
        $admin->getPersistentParameters();
1529
    }
1530
1531
    public function testGetPersistentParametersWithValidExtension(): void
1532
    {
1533
        $expected = [
1534
            'context' => 'foobar',
1535
        ];
1536
1537
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1538
1539
        $extension = $this->createMock(AdminExtensionInterface::class);
1540
        $extension->expects($this->once())->method('getPersistentParameters')->will($this->returnValue($expected));
1541
1542
        $admin->addExtension($extension);
1543
1544
        $this->assertSame($expected, $admin->getPersistentParameters());
1545
    }
1546
1547
    public function testGetFormWithNonCollectionParentValue(): void
1548
    {
1549
        $post = new Post();
1550
        $tagAdmin = $this->createTagAdmin($post);
1551
        $tag = $tagAdmin->getSubject();
1552
1553
        $tag->setPosts(null);
1554
        $tagAdmin->getForm();
1555
        $this->assertSame($post, $tag->getPosts());
1556
    }
1557
1558
    public function testGetFormWithCollectionParentValue(): void
1559
    {
1560
        $post = new Post();
1561
        $tagAdmin = $this->createTagAdmin($post);
1562
        $tag = $tagAdmin->getSubject();
1563
1564
        // Case of a doctrine collection
1565
        $this->assertInstanceOf(Collection::class, $tag->getPosts());
1566
        $this->assertCount(0, $tag->getPosts());
1567
1568
        $tag->addPost(new Post());
1569
1570
        $this->assertCount(1, $tag->getPosts());
1571
1572
        $tagAdmin->getForm();
1573
1574
        $this->assertInstanceOf(Collection::class, $tag->getPosts());
1575
        $this->assertCount(2, $tag->getPosts());
1576
        $this->assertContains($post, $tag->getPosts());
1577
1578
        // Case of an array
1579
        $tag->setPosts([]);
1580
        $this->assertCount(0, $tag->getPosts());
1581
1582
        $tag->addPost(new Post());
1583
1584
        $this->assertCount(1, $tag->getPosts());
1585
1586
        $tagAdmin->getForm();
1587
1588
        $this->assertInternalType('array', $tag->getPosts());
1589
        $this->assertCount(2, $tag->getPosts());
1590
        $this->assertContains($post, $tag->getPosts());
1591
    }
1592
1593
    public function testFormAddPostSubmitEventForPreValidation(): void
1594
    {
1595
        $modelAdmin = new ModelAdmin('sonata.post.admin.model', 'Application\Sonata\FooBundle\Entity\Model', 'SonataFooBundle:ModelAdmin');
1596
        $object = new \stdClass();
1597
1598
        $labelTranslatorStrategy = $this->createMock(LabelTranslatorStrategyInterface::class);
1599
        $modelAdmin->setLabelTranslatorStrategy($labelTranslatorStrategy);
1600
1601
        $validator = $this->createMock(ValidatorInterface::class);
1602
        $validator->expects($this->any())
1603
                ->method('getMetadataFor')
1604
                ->will($this->returnValue($this->createMock(MemberMetadata::class)));
1605
        $modelAdmin->setValidator($validator);
1606
1607
        $modelManager = $this->createMock(ModelManagerInterface::class);
1608
        $modelManager->expects($this->any())
1609
            ->method('getNewFieldDescriptionInstance')
1610
            ->will($this->returnValue(new FieldDescription()));
1611
        $modelAdmin->setModelManager($modelManager);
1612
1613
        // a Admin class to test that preValidate is called
1614
        $testAdminPreValidate = $this->createMock(AbstractAdmin::class, ['preValidate']);
1615
        $testAdminPreValidate->expects($this->once())
1616
                ->method('preValidate')
1617
                ->with($this->identicalTo($object));
1618
1619
        $event = $this->createMock(FormEvent::class);
1620
        $event->expects($this->any())
1621
                ->method('getData')
1622
                ->will($this->returnValue($object));
1623
1624
        $formBuild = $this->createMock(FormBuilder::class, ['addEventListener']);
1625
        $formBuild->expects($this->once())
1626
                ->method('addEventListener')
1627
                ->with($this->identicalTo(FormEvents::POST_SUBMIT),
1628
                        $this->callback(function ($callback) use ($testAdminPreValidate, $event) {
1629
                            if (\is_callable($callback)) {
1630
                                $closure = $callback->bindTo($testAdminPreValidate);
1631
                                $closure($event);
1632
1633
                                return true;
1634
                            }
1635
1636
                            return false;
1637
                        }),
1638
                        $this->greaterThan(0)
1639
                    );
1640
1641
        $formContractor = $this->createMock(FormContractorInterface::class, ['getDefaultOptions', 'getFormBuilder']);
1642
        $formContractor->expects($this->any())
1643
                ->method('getDefaultOptions')
1644
                ->will($this->returnValue([]));
1645
        $formContractor->expects($this->any())
1646
                ->method('getFormBuilder')
1647
                ->will($this->returnValue($formBuild));
1648
1649
        $modelAdmin->setFormContractor($formContractor);
1650
        $modelAdmin->defineFormBuilder($formBuild);
1651
        $modelAdmin->getForm();
1652
    }
1653
1654
    public function testRemoveFieldFromFormGroup(): void
1655
    {
1656
        $formGroups = [
1657
            'foobar' => [
1658
                'fields' => [
1659
                    'foo' => 'foo',
1660
                    'bar' => 'bar',
1661
                ],
1662
            ],
1663
        ];
1664
1665
        $admin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1666
        $admin->setFormGroups($formGroups);
1667
1668
        $admin->removeFieldFromFormGroup('foo');
1669
        $this->assertSame($admin->getFormGroups(), [
1670
            'foobar' => [
1671
                'fields' => [
1672
                    'bar' => 'bar',
1673
                ],
1674
            ],
1675
        ]);
1676
1677
        $admin->removeFieldFromFormGroup('bar');
1678
        $this->assertSame($admin->getFormGroups(), []);
1679
    }
1680
1681
    public function testGetFilterParameters(): void
1682
    {
1683
        $authorId = uniqid();
1684
1685
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'Application\Sonata\NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1686
1687
        $commentAdmin = new CommentAdmin('sonata.post.admin.comment', 'Application\Sonata\NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
1688
        $commentAdmin->setParentAssociationMapping('post.author');
1689
        $commentAdmin->setParent($postAdmin);
1690
1691
        $request = $this->createMock(Request::class, ['get']);
0 ignored issues
show
The call to AdminTest::createMock() has too many arguments starting with array('get').

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
1692
        $query = $this->createMock(ParameterBag::class, ['get']);
0 ignored issues
show
The call to AdminTest::createMock() has too many arguments starting with array('get').

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
1693
        $query->expects($this->any())
1694
            ->method('get')
1695
            ->will($this->returnValue([]));
1696
        $request->query = $query;
1697
        $request->expects($this->any())
1698
            ->method('get')
1699
            ->will($this->returnValue($authorId));
1700
1701
        $commentAdmin->setRequest($request);
1702
1703
        $modelManager = $this->createMock(ModelManagerInterface::class);
1704
        $modelManager->expects($this->any())
1705
            ->method('getDefaultSortValues')
1706
            ->will($this->returnValue([]));
1707
1708
        $commentAdmin->setModelManager($modelManager);
1709
1710
        $parameters = $commentAdmin->getFilterParameters();
1711
1712
        $this->assertTrue(isset($parameters['post__author']));
1713
        $this->assertSame(['value' => $authorId], $parameters['post__author']);
1714
    }
1715
1716
    public function testGetFilterFieldDescription(): void
1717
    {
1718
        $modelAdmin = new ModelAdmin('sonata.post.admin.model', 'Application\Sonata\FooBundle\Entity\Model', 'SonataFooBundle:ModelAdmin');
1719
1720
        $fooFieldDescription = new FieldDescription();
1721
        $barFieldDescription = new FieldDescription();
1722
        $bazFieldDescription = new FieldDescription();
1723
1724
        $modelManager = $this->createMock(ModelManagerInterface::class);
1725
        $modelManager->expects($this->exactly(3))
1726
            ->method('getNewFieldDescriptionInstance')
1727
            ->will($this->returnCallback(function ($adminClass, $name, $filterOptions) use ($fooFieldDescription, $barFieldDescription, $bazFieldDescription) {
1728
                switch ($name) {
1729
                    case 'foo':
1730
                        $fieldDescription = $fooFieldDescription;
1731
1732
                        break;
1733
1734
                    case 'bar':
1735
                        $fieldDescription = $barFieldDescription;
1736
1737
                        break;
1738
1739
                    case 'baz':
1740
                        $fieldDescription = $bazFieldDescription;
1741
1742
                        break;
1743
1744
                    default:
1745
                        throw new \RuntimeException(sprintf('Unknown filter name "%s"', $name));
1746
                        break;
1747
                }
1748
1749
                $fieldDescription->setName($name);
1750
1751
                return $fieldDescription;
1752
            }));
1753
1754
        $modelAdmin->setModelManager($modelManager);
1755
1756
        $pager = $this->createMock(PagerInterface::class);
1757
1758
        $datagrid = $this->createMock(DatagridInterface::class);
1759
        $datagrid->expects($this->once())
1760
            ->method('getPager')
1761
            ->will($this->returnValue($pager));
1762
1763
        $datagridBuilder = $this->createMock(DatagridBuilderInterface::class);
1764
        $datagridBuilder->expects($this->once())
1765
            ->method('getBaseDatagrid')
1766
            ->with($this->identicalTo($modelAdmin), [])
1767
            ->will($this->returnValue($datagrid));
1768
1769
        $datagridBuilder->expects($this->exactly(3))
1770
            ->method('addFilter')
1771
            ->will($this->returnCallback(function ($datagrid, $type, $fieldDescription, AdminInterface $admin): void {
1772
                $admin->addFilterFieldDescription($fieldDescription->getName(), $fieldDescription);
1773
                $fieldDescription->mergeOption('field_options', ['required' => false]);
1774
            }));
1775
1776
        $modelAdmin->setDatagridBuilder($datagridBuilder);
1777
1778
        $this->assertSame(['foo' => $fooFieldDescription, 'bar' => $barFieldDescription, 'baz' => $bazFieldDescription], $modelAdmin->getFilterFieldDescriptions());
1779
        $this->assertFalse($modelAdmin->hasFilterFieldDescription('fooBar'));
1780
        $this->assertTrue($modelAdmin->hasFilterFieldDescription('foo'));
1781
        $this->assertTrue($modelAdmin->hasFilterFieldDescription('bar'));
1782
        $this->assertTrue($modelAdmin->hasFilterFieldDescription('baz'));
1783
        $this->assertSame($fooFieldDescription, $modelAdmin->getFilterFieldDescription('foo'));
1784
        $this->assertSame($barFieldDescription, $modelAdmin->getFilterFieldDescription('bar'));
1785
        $this->assertSame($bazFieldDescription, $modelAdmin->getFilterFieldDescription('baz'));
1786
    }
1787
1788
    public function testGetSubjectNoRequest(): void
1789
    {
1790
        $modelManager = $this->createMock(ModelManagerInterface::class);
1791
        $modelManager
1792
            ->expects($this->never())
1793
            ->method('find');
1794
1795
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1796
        $admin->setModelManager($modelManager);
1797
1798
        $this->assertNull($admin->getSubject());
1799
    }
1800
1801
    public function testGetSideMenu(): void
1802
    {
1803
        $item = $this->createMock(ItemInterface::class);
1804
        $item
1805
            ->expects($this->once())
1806
            ->method('setChildrenAttribute')
1807
            ->with('class', 'nav navbar-nav');
1808
        $item
1809
            ->expects($this->once())
1810
            ->method('setExtra')
1811
            ->with('translation_domain', 'foo_bar_baz');
1812
1813
        $menuFactory = $this->createMock(FactoryInterface::class);
1814
        $menuFactory
1815
            ->expects($this->once())
1816
            ->method('createItem')
1817
            ->will($this->returnValue($item));
1818
1819
        $modelAdmin = new ModelAdmin('sonata.post.admin.model', 'Application\Sonata\FooBundle\Entity\Model', 'SonataFooBundle:ModelAdmin');
1820
        $modelAdmin->setMenuFactory($menuFactory);
1821
        $modelAdmin->setTranslationDomain('foo_bar_baz');
1822
1823
        $modelAdmin->getSideMenu('foo');
1824
    }
1825
1826
    /**
1827
     * @return array
1828
     */
1829
    public function provideGetSubject()
1830
    {
1831
        return [
1832
            [23],
1833
            ['azerty'],
1834
            ['4f69bbb5f14a13347f000092'],
1835
            ['0779ca8d-e2be-11e4-ac58-0242ac11000b'],
1836
            ['123'.AdapterInterface::ID_SEPARATOR.'my_type'], // composite keys are supported
1837
        ];
1838
    }
1839
1840
    /**
1841
     * @dataProvider provideGetSubject
1842
     */
1843
    public function testGetSubjectFailed($id): void
1844
    {
1845
        $modelManager = $this->createMock(ModelManagerInterface::class);
1846
        $modelManager
1847
            ->expects($this->once())
1848
            ->method('find')
1849
            ->with('NewsBundle\Entity\Post', $id)
1850
            ->will($this->returnValue(null)); // entity not found
1851
1852
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1853
        $admin->setModelManager($modelManager);
1854
1855
        $admin->setRequest(new Request(['id' => $id]));
1856
        $this->assertNull($admin->getSubject());
1857
    }
1858
1859
    /**
1860
     * @dataProvider provideGetSubject
1861
     */
1862
    public function testGetSubject($id): void
1863
    {
1864
        $entity = new Post();
1865
1866
        $modelManager = $this->createMock(ModelManagerInterface::class);
1867
        $modelManager
1868
            ->expects($this->once())
1869
            ->method('find')
1870
            ->with('NewsBundle\Entity\Post', $id)
1871
            ->will($this->returnValue($entity));
1872
1873
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1874
        $admin->setModelManager($modelManager);
1875
1876
        $admin->setRequest(new Request(['id' => $id]));
1877
        $this->assertSame($entity, $admin->getSubject());
1878
        $this->assertSame($entity, $admin->getSubject()); // model manager must be used only once
1879
    }
1880
1881
    public function testGetSubjectWithParentDescription(): void
1882
    {
1883
        $adminId = 1;
1884
1885
        $comment = new Comment();
1886
1887
        $modelManager = $this->createMock(ModelManagerInterface::class);
1888
        $modelManager
1889
            ->expects($this->any())
1890
            ->method('find')
1891
            ->with('NewsBundle\Entity\Comment', $adminId)
1892
            ->will($this->returnValue($comment));
1893
1894
        $request = new Request(['id' => $adminId]);
1895
1896
        $postAdmin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1897
        $postAdmin->setRequest($request);
1898
1899
        $commentAdmin = new CommentAdmin('sonata.post.admin.comment', 'NewsBundle\Entity\Comment', 'SonataNewsBundle:CommentAdmin');
1900
        $commentAdmin->setRequest($request);
1901
        $commentAdmin->setModelManager($modelManager);
1902
1903
        $this->assertSame($comment, $commentAdmin->getSubject());
1904
1905
        $commentAdmin->setSubject(null);
1906
        $commentAdmin->setParentFieldDescription(new FieldDescription());
1907
1908
        $this->assertNull($commentAdmin->getSubject());
1909
    }
1910
1911
    /**
1912
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::configureActionButtons
1913
     */
1914
    public function testGetActionButtonsList(): void
1915
    {
1916
        $expected = [
1917
            'create' => [
1918
                'template' => 'Foo.html.twig',
1919
            ],
1920
        ];
1921
1922
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1923
1924
        $templateRegistry = $this->prophesize(MutableTemplateRegistryInterface::class);
1925
        $templateRegistry->getTemplate('button_create')->willReturn('Foo.html.twig');
1926
1927
        $admin->setTemplateRegistry($templateRegistry->reveal());
1928
1929
        $securityHandler = $this->createMock(SecurityHandlerInterface::class);
1930
        $securityHandler
1931
            ->expects($this->once())
1932
            ->method('isGranted')
1933
            ->with($admin, 'CREATE', $admin)
1934
            ->will($this->returnValue(true));
1935
        $admin->setSecurityHandler($securityHandler);
1936
1937
        $routeGenerator = $this->createMock(RouteGeneratorInterface::class);
1938
        $routeGenerator
1939
            ->expects($this->once())
1940
            ->method('hasAdminRoute')
1941
            ->with($admin, 'create')
1942
            ->will($this->returnValue(true));
1943
        $admin->setRouteGenerator($routeGenerator);
1944
1945
        $this->assertSame($expected, $admin->getActionButtons('list', null));
1946
    }
1947
1948
    /**
1949
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::configureActionButtons
1950
     */
1951
    public function testGetActionButtonsListCreateDisabled(): void
1952
    {
1953
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
1954
1955
        $securityHandler = $this->createMock(SecurityHandlerInterface::class);
1956
        $securityHandler
1957
            ->expects($this->once())
1958
            ->method('isGranted')
1959
            ->with($admin, 'CREATE', $admin)
1960
            ->will($this->returnValue(false));
1961
        $admin->setSecurityHandler($securityHandler);
1962
1963
        $this->assertSame([], $admin->getActionButtons('list', null));
1964
    }
1965
1966
    /**
1967
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::configureBatchActions
1968
     */
1969
    public function testGetBatchActions(): void
1970
    {
1971
        $expected = [
1972
            'delete' => [
1973
                'label' => 'action_delete',
1974
                'translation_domain' => 'SonataAdminBundle',
1975
                'ask_confirmation' => true, // by default always true
1976
            ],
1977
            'foo' => [
1978
                'label' => 'action_foo',
1979
                'translation_domain' => 'SonataAdminBundle',
1980
            ],
1981
            'bar' => [
1982
                'label' => 'batch.label_bar',
1983
                'translation_domain' => 'SonataAdminBundle',
1984
            ],
1985
            'baz' => [
1986
                'label' => 'action_baz',
1987
                'translation_domain' => 'AcmeAdminBundle',
1988
            ],
1989
        ];
1990
1991
        $pathInfo = new PathInfoBuilder($this->createMock(AuditManagerInterface::class));
0 ignored issues
show
$this->createMock(\Sonat...anagerInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Sonata\AdminBundl...\AuditManagerInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
1992
1993
        $labelTranslatorStrategy = $this->createMock(LabelTranslatorStrategyInterface::class);
1994
        $labelTranslatorStrategy->expects($this->any())
1995
            ->method('getLabel')
1996
            ->will($this->returnCallback(function ($label, $context = '', $type = '') {
1997
                return $context.'.'.$type.'_'.$label;
1998
            }));
1999
2000
        $admin = new PostAdmin('sonata.post.admin.model', 'Application\Sonata\FooBundle\Entity\Model', 'SonataFooBundle:ModelAdmin');
2001
        $admin->setRouteBuilder($pathInfo);
2002
        $admin->setTranslationDomain('SonataAdminBundle');
2003
        $admin->setLabelTranslatorStrategy($labelTranslatorStrategy);
2004
2005
        $routeGenerator = $this->createMock(RouteGeneratorInterface::class);
2006
        $routeGenerator
2007
            ->expects($this->once())
2008
            ->method('hasAdminRoute')
2009
            ->with($admin, 'delete')
2010
            ->will($this->returnValue(true));
2011
        $admin->setRouteGenerator($routeGenerator);
2012
2013
        $securityHandler = $this->createMock(SecurityHandlerInterface::class);
2014
        $securityHandler->expects($this->any())
2015
            ->method('isGranted')
2016
            ->will($this->returnCallback(function (AdminInterface $adminIn, $attributes, $object = null) use ($admin) {
2017
                if ($admin === $adminIn && 'DELETE' === $attributes) {
2018
                    return true;
2019
                }
2020
2021
                return false;
2022
            }));
2023
        $admin->setSecurityHandler($securityHandler);
2024
2025
        $this->assertSame($expected, $admin->getBatchActions());
2026
    }
2027
2028
    /**
2029
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::showMosaicButton
2030
     */
2031
    public function testShowMosaicButton(): void
2032
    {
2033
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
2034
        $listModes = $admin->getListModes();
2035
2036
        $admin->showMosaicButton(true);
2037
2038
        $this->assertSame($listModes, $admin->getListModes());
2039
    }
2040
2041
    /**
2042
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::showMosaicButton
2043
     */
2044
    public function testShowMosaicButtonHideMosaic(): void
2045
    {
2046
        $admin = new PostAdmin('sonata.post.admin.post', 'NewsBundle\Entity\Post', 'SonataNewsBundle:PostAdmin');
2047
        $listModes = $admin->getListModes();
2048
        $expected['list'] = $listModes['list'];
2049
2050
        $admin->showMosaicButton(false);
2051
2052
        $this->assertSame($expected, $admin->getListModes());
2053
    }
2054
2055
    /**
2056
     * @covers \Sonata\AdminBundle\Admin\AbstractAdmin::getDashboardActions
2057
     * @dataProvider provideGetBaseRouteName
2058
     */
2059
    public function testDefaultDashboardActionsArePresent($objFqn, $expected): void
2060
    {
2061
        $pathInfo = new PathInfoBuilder($this->createMock(AuditManagerInterface::class));
0 ignored issues
show
$this->createMock(\Sonat...anagerInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Sonata\AdminBundl...\AuditManagerInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
2062
2063
        $routeGenerator = new DefaultRouteGenerator(
2064
            $this->createMock(RouterInterface::class),
0 ignored issues
show
$this->createMock(\Symfo...RouterInterface::class) is of type object<PHPUnit\Framework\MockObject\MockObject>, but the function expects a object<Symfony\Component\Routing\RouterInterface>.

It seems like the type of the argument is not accepted by the function/method which you are calling.

In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug.

We suggest to add an explicit type cast like in the following example:

function acceptsInteger($int) { }

$x = '123'; // string "123"

// Instead of
acceptsInteger($x);

// we recommend to use
acceptsInteger((integer) $x);
Loading history...
2065
            new RoutesCache($this->cacheTempFolder, true)
2066
        );
2067
2068
        $admin = new PostAdmin('sonata.post.admin.post', $objFqn, 'SonataNewsBundle:PostAdmin');
2069
        $admin->setRouteBuilder($pathInfo);
2070
        $admin->setRouteGenerator($routeGenerator);
2071
        $admin->initialize();
2072
2073
        $templateRegistry = $this->prophesize(MutableTemplateRegistryInterface::class);
2074
        $templateRegistry->getTemplate('action_create')->willReturn('Foo.html.twig');
2075
2076
        $admin->setTemplateRegistry($templateRegistry->reveal());
2077
2078
        $securityHandler = $this->createMock(SecurityHandlerInterface::class);
2079
        $securityHandler->expects($this->any())
2080
            ->method('isGranted')
2081
            ->will($this->returnCallback(function (AdminInterface $adminIn, $attributes, $object = null) use ($admin) {
2082
                if ($admin === $adminIn && ('CREATE' === $attributes || 'LIST' === $attributes)) {
2083
                    return true;
2084
                }
2085
2086
                return false;
2087
            }));
2088
2089
        $admin->setSecurityHandler($securityHandler);
2090
2091
        $this->assertArrayHasKey('list', $admin->getDashboardActions());
2092
        $this->assertArrayHasKey('create', $admin->getDashboardActions());
2093
    }
2094
2095
    public function testDefaultFilters(): void
2096
    {
2097
        $admin = new FilteredAdmin('sonata.post.admin.model', 'Application\Sonata\FooBundle\Entity\Model', 'SonataFooBundle:ModelAdmin');
2098
2099
        $subjectId = uniqid();
2100
2101
        $request = $this->createMock(Request::class, ['get']);
0 ignored issues
show
The call to AdminTest::createMock() has too many arguments starting with array('get').

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
2102
        $query = $this->createMock(ParameterBag::class, ['set', 'get']);
0 ignored issues
show
The call to AdminTest::createMock() has too many arguments starting with array('set', 'get').

This check compares calls to functions or methods with their respective definitions. If the call has more arguments than are defined, it raises an issue.

If a function is defined several times with a different number of parameters, the check may pick up the wrong definition and report false positives. One codebase where this has been known to happen is Wordpress.

In this case you can add the @ignore PhpDoc annotation to the duplicate definition and it will be ignored.

Loading history...
2103
        $query->expects($this->any())
2104
            ->method('get')
2105
            ->with($this->equalTo('filter'))
2106
            ->will($this->returnValue([
2107
                'a' => [
2108
                    'value' => 'b',
2109
                ],
2110
                'foo' => [
2111
                    'type' => '1',
2112
                    'value' => 'bar',
2113
                ],
2114
                'baz' => [
2115
                    'type' => '5',
2116
                    'value' => 'test',
2117
                ],
2118
            ]));
2119
        $request->query = $query;
2120
2121
        $request->expects($this->any())
2122
            ->method('get')
2123
            ->will($this->returnValue($subjectId));
2124
2125
        $admin->setRequest($request);
2126
2127
        $modelManager = $this->createMock(ModelManagerInterface::class);
2128
        $modelManager->expects($this->any())
2129
            ->method('getDefaultSortValues')
2130
            ->will($this->returnValue([]));
2131
2132
        $admin->setModelManager($modelManager);
2133
2134
        $this->assertSame([
2135
            '_page' => 1,
2136
            '_per_page' => 32,
2137
            'foo' => [
2138
                'type' => '1',
2139
                'value' => 'bar',
2140
            ],
2141
            'baz' => [
2142
                'type' => '5',
2143
                'value' => 'test',
2144
            ],
2145
            'a' => [
2146
                'value' => 'b',
2147
            ],
2148
        ], $admin->getFilterParameters());
2149
2150
        $this->assertTrue($admin->isDefaultFilter('foo'));
2151
        $this->assertFalse($admin->isDefaultFilter('bar'));
2152
        $this->assertFalse($admin->isDefaultFilter('a'));
2153
    }
2154
2155
    /**
2156
     * @group legacy
2157
     */
2158
    public function testDefaultBreadcrumbsBuilder(): void
2159
    {
2160
        $container = $this->createMock(ContainerInterface::class);
2161
        $container->expects($this->once())
2162
            ->method('getParameter')
2163
            ->with('sonata.admin.configuration.breadcrumbs')
2164
            ->will($this->returnValue([]));
2165
2166
        $pool = $this->getMockBuilder(Pool::class)
2167
            ->disableOriginalConstructor()
2168
            ->getMock();
2169
        $pool->expects($this->once())
2170
            ->method('getContainer')
2171
            ->will($this->returnValue($container));
2172
2173
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
2174
            'admin.my_code', 'My\Class', 'MyBundle:ClassAdmin',
2175
        ], '', true, true, true, ['getConfigurationPool']);
2176
        $admin->expects($this->once())
2177
            ->method('getConfigurationPool')
2178
            ->will($this->returnValue($pool));
2179
2180
        $this->assertInstanceOf(BreadcrumbsBuilder::class, $admin->getBreadcrumbsBuilder());
2181
    }
2182
2183
    /**
2184
     * @group legacy
2185
     */
2186
    public function testBreadcrumbsBuilderSetter(): void
2187
    {
2188
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
2189
            'admin.my_code', 'My\Class', 'MyBundle:ClassAdmin',
2190
        ]);
2191
        $this->assertSame($admin, $admin->setBreadcrumbsBuilder($builder = $this->createMock(
2192
            BreadcrumbsBuilderInterface::class
2193
        )));
2194
        $this->assertSame($builder, $admin->getBreadcrumbsBuilder());
2195
    }
2196
2197
    /**
2198
     * @group legacy
2199
     */
2200
    public function testGetBreadcrumbs(): void
2201
    {
2202
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
2203
            'admin.my_code', 'My\Class', 'MyBundle:ClassAdmin',
2204
        ]);
2205
        $builder = $this->prophesize(BreadcrumbsBuilderInterface::class);
2206
        $action = 'myaction';
2207
        $builder->getBreadcrumbs($admin, $action)->shouldBeCalled();
2208
        $admin->setBreadcrumbsBuilder($builder->reveal())->getBreadcrumbs($action);
2209
    }
2210
2211
    /**
2212
     * @group legacy
2213
     */
2214
    public function testBuildBreadcrumbs(): void
2215
    {
2216
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
2217
            'admin.my_code', 'My\Class', 'MyBundle:ClassAdmin',
2218
        ]);
2219
        $builder = $this->prophesize(BreadcrumbsBuilderInterface::class);
2220
        $action = 'myaction';
2221
        $menu = $this->createMock(ItemInterface::class);
2222
        $builder->buildBreadcrumbs($admin, $action, $menu)
2223
            ->shouldBeCalledTimes(1)
2224
            ->willReturn($menu);
2225
        $admin->setBreadcrumbsBuilder($builder->reveal());
2226
2227
        /* check the called is proxied only once */
2228
        $this->assertSame($menu, $admin->buildBreadcrumbs($action, $menu));
2229
        $this->assertSame($menu, $admin->buildBreadcrumbs($action, $menu));
2230
    }
2231
2232
    /**
2233
     * NEXT_MAJOR: remove this method.
2234
     *
2235
     * @group legacy
2236
     */
2237
    public function testCreateQueryLegacyCallWorks(): void
2238
    {
2239
        $admin = $this->getMockForAbstractClass(AbstractAdmin::class, [
2240
            'admin.my_code', 'My\Class', 'MyBundle:ClassAdmin',
2241
        ]);
2242
        $modelManager = $this->createMock(ModelManagerInterface::class);
2243
        $modelManager->expects($this->once())
2244
            ->method('createQuery')
2245
            ->with('My\Class')
2246
            ->willReturn('a query');
2247
2248
        $admin->setModelManager($modelManager);
2249
        $this->assertSame('a query', $admin->createQuery('list'));
2250
    }
2251
2252
    public function testGetDataSourceIterator(): void
2253
    {
2254
        $datagrid = $this->createMock(DatagridInterface::class);
2255
        $datagrid->method('buildPager');
2256
2257
        $modelManager = $this->createMock(ModelManagerInterface::class);
2258
        $modelManager->method('getExportFields')->will($this->returnValue([
2259
            'field',
2260
            'foo',
2261
            'bar',
2262
        ]));
2263
        $modelManager->expects($this->once())->method('getDataSourceIterator')
2264
            ->with($this->equalTo($datagrid), $this->equalTo([
2265
                'Feld' => 'field',
2266
                1 => 'foo',
2267
                2 => 'bar',
2268
            ]));
2269
2270
        $admin = $this->getMockBuilder(AbstractAdmin::class)
2271
            ->disableOriginalConstructor()
2272
            ->setMethods(['getDatagrid', 'getTranslationLabel', 'trans'])
2273
            ->getMockForAbstractClass();
2274
        $admin->method('getDatagrid')->will($this->returnValue($datagrid));
2275
        $admin->setModelManager($modelManager);
2276
2277
        $admin->expects($this->any())
2278
            ->method('getTranslationLabel')
2279
            ->will($this->returnCallback(function ($label, $context = '', $type = '') {
2280
                return $context.'.'.$type.'_'.$label;
2281
            }));
2282
        $admin->expects($this->any())
2283
            ->method('trans')
2284
            ->will($this->returnCallback(function ($label) {
2285
                if ('export.label_field' === $label) {
2286
                    return 'Feld';
2287
                }
2288
2289
                return $label;
2290
            }));
2291
2292
        $admin->getDataSourceIterator();
2293
    }
2294
2295
    public function testCircularChildAdmin(): void
2296
    {
2297
        $this->expectException(
2298
            \RuntimeException::class,
2299
            'Circular reference detected! The child admin `sonata.post.admin.post` is already in the parent tree of the `sonata.post.admin.comment` admin.'
2300
        );
2301
2302
        $postAdmin = new PostAdmin(
2303
            'sonata.post.admin.post',
2304
            'Application\Sonata\NewsBundle\Entity\Post',
2305
            'SonataNewsBundle:PostAdmin'
2306
        );
2307
        $commentAdmin = new CommentAdmin(
2308
            'sonata.post.admin.comment',
2309
            'Application\Sonata\NewsBundle\Entity\Comment',
2310
            'SonataNewsBundle:CommentAdmin'
2311
        );
2312
        $postAdmin->addChild($commentAdmin, 'post');
2313
        $commentAdmin->addChild($postAdmin, 'comment');
2314
    }
2315
2316
    public function testCircularChildAdminTripleLevel(): void
2317
    {
2318
        $this->expectException(
2319
            \RuntimeException::class,
2320
            'Circular reference detected! The child admin `sonata.post.admin.post` is already in the parent tree of the `sonata.post.admin.comment_vote` admin.'
2321
        );
2322
2323
        $postAdmin = new PostAdmin(
2324
            'sonata.post.admin.post',
2325
            'Application\Sonata\NewsBundle\Entity\Post',
2326
            'SonataNewsBundle:PostAdmin'
2327
        );
2328
        $commentAdmin = new CommentAdmin(
2329
            'sonata.post.admin.comment',
2330
            'Application\Sonata\NewsBundle\Entity\Comment',
2331
            'SonataNewsBundle:CommentAdmin'
2332
        );
2333
        $commentVoteAdmin = new CommentVoteAdmin(
2334
            'sonata.post.admin.comment_vote',
2335
            'Application\Sonata\NewsBundle\Entity\CommentVote',
2336
            'SonataNewsBundle:CommentVoteAdmin'
2337
        );
2338
        $postAdmin->addChild($commentAdmin, 'post');
2339
        $commentAdmin->addChild($commentVoteAdmin, 'comment');
2340
        $commentVoteAdmin->addChild($postAdmin, 'post');
2341
    }
2342
2343
    public function testCircularChildAdminWithItself(): void
2344
    {
2345
        $this->expectException(
2346
            \RuntimeException::class,
2347
            'Circular reference detected! The child admin `sonata.post.admin.post` is already in the parent tree of the `sonata.post.admin.post` admin.'
2348
        );
2349
2350
        $postAdmin = new PostAdmin(
2351
            'sonata.post.admin.post',
2352
            'Application\Sonata\NewsBundle\Entity\Post',
2353
            'SonataNewsBundle:PostAdmin'
2354
        );
2355
        $postAdmin->addChild($postAdmin);
2356
    }
2357
2358
    public function testGetRootAncestor(): void
2359
    {
2360
        $postAdmin = new PostAdmin(
2361
            'sonata.post.admin.post',
2362
            'Application\Sonata\NewsBundle\Entity\Post',
2363
            'SonataNewsBundle:PostAdmin'
2364
        );
2365
        $commentAdmin = new CommentAdmin(
2366
            'sonata.post.admin.comment',
2367
            'Application\Sonata\NewsBundle\Entity\Comment',
2368
            'SonataNewsBundle:CommentAdmin'
2369
        );
2370
        $commentVoteAdmin = new CommentVoteAdmin(
2371
            'sonata.post.admin.comment_vote',
2372
            'Application\Sonata\NewsBundle\Entity\CommentVote',
2373
            'SonataNewsBundle:CommentVoteAdmin'
2374
        );
2375
2376
        $this->assertSame($postAdmin, $postAdmin->getRootAncestor());
2377
        $this->assertSame($commentAdmin, $commentAdmin->getRootAncestor());
2378
        $this->assertSame($commentVoteAdmin, $commentVoteAdmin->getRootAncestor());
2379
2380
        $postAdmin->addChild($commentAdmin, 'post');
2381
2382
        $this->assertSame($postAdmin, $postAdmin->getRootAncestor());
2383
        $this->assertSame($postAdmin, $commentAdmin->getRootAncestor());
2384
        $this->assertSame($commentVoteAdmin, $commentVoteAdmin->getRootAncestor());
2385
2386
        $commentAdmin->addChild($commentVoteAdmin, 'comment');
2387
2388
        $this->assertSame($postAdmin, $postAdmin->getRootAncestor());
2389
        $this->assertSame($postAdmin, $commentAdmin->getRootAncestor());
2390
        $this->assertSame($postAdmin, $commentVoteAdmin->getRootAncestor());
2391
    }
2392
2393
    public function testGetChildDepth(): void
2394
    {
2395
        $postAdmin = new PostAdmin(
2396
            'sonata.post.admin.post',
2397
            'Application\Sonata\NewsBundle\Entity\Post',
2398
            'SonataNewsBundle:PostAdmin'
2399
        );
2400
        $commentAdmin = new CommentAdmin(
2401
            'sonata.post.admin.comment',
2402
            'Application\Sonata\NewsBundle\Entity\Comment',
2403
            'SonataNewsBundle:CommentAdmin'
2404
        );
2405
        $commentVoteAdmin = new CommentVoteAdmin(
2406
            'sonata.post.admin.comment_vote',
2407
            'Application\Sonata\NewsBundle\Entity\CommentVote',
2408
            'SonataNewsBundle:CommentVoteAdmin'
2409
        );
2410
2411
        $this->assertSame(0, $postAdmin->getChildDepth());
2412
        $this->assertSame(0, $commentAdmin->getChildDepth());
2413
        $this->assertSame(0, $commentVoteAdmin->getChildDepth());
2414
2415
        $postAdmin->addChild($commentAdmin, 'post');
2416
2417
        $this->assertSame(0, $postAdmin->getChildDepth());
2418
        $this->assertSame(1, $commentAdmin->getChildDepth());
2419
        $this->assertSame(0, $commentVoteAdmin->getChildDepth());
2420
2421
        $commentAdmin->addChild($commentVoteAdmin, 'comment');
2422
2423
        $this->assertSame(0, $postAdmin->getChildDepth());
2424
        $this->assertSame(1, $commentAdmin->getChildDepth());
2425
        $this->assertSame(2, $commentVoteAdmin->getChildDepth());
2426
    }
2427
2428
    public function testGetCurrentLeafChildAdmin(): void
2429
    {
2430
        $postAdmin = new PostAdmin(
2431
            'sonata.post.admin.post',
2432
            'Application\Sonata\NewsBundle\Entity\Post',
2433
            'SonataNewsBundle:PostAdmin'
2434
        );
2435
        $commentAdmin = new CommentAdmin(
2436
            'sonata.post.admin.comment',
2437
            'Application\Sonata\NewsBundle\Entity\Comment',
2438
            'SonataNewsBundle:CommentAdmin'
2439
        );
2440
        $commentVoteAdmin = new CommentVoteAdmin(
2441
            'sonata.post.admin.comment_vote',
2442
            'Application\Sonata\NewsBundle\Entity\CommentVote',
2443
            'SonataNewsBundle:CommentVoteAdmin'
2444
        );
2445
2446
        $postAdmin->addChild($commentAdmin, 'post');
2447
        $commentAdmin->addChild($commentVoteAdmin, 'comment');
2448
2449
        $this->assertNull($postAdmin->getCurrentLeafChildAdmin());
2450
        $this->assertNull($commentAdmin->getCurrentLeafChildAdmin());
2451
        $this->assertNull($commentVoteAdmin->getCurrentLeafChildAdmin());
2452
2453
        $commentAdmin->setCurrentChild(true);
2454
2455
        $this->assertSame($commentAdmin, $postAdmin->getCurrentLeafChildAdmin());
2456
        $this->assertNull($commentAdmin->getCurrentLeafChildAdmin());
2457
        $this->assertNull($commentVoteAdmin->getCurrentLeafChildAdmin());
2458
2459
        $commentVoteAdmin->setCurrentChild(true);
2460
2461
        $this->assertSame($commentVoteAdmin, $postAdmin->getCurrentLeafChildAdmin());
2462
        $this->assertSame($commentVoteAdmin, $commentAdmin->getCurrentLeafChildAdmin());
2463
        $this->assertNull($commentVoteAdmin->getCurrentLeafChildAdmin());
2464
    }
2465
2466
    private function createTagAdmin(Post $post): TagAdmin
2467
    {
2468
        $postAdmin = $this->getMockBuilder(PostAdmin::class)
2469
            ->disableOriginalConstructor()
2470
            ->getMock();
2471
2472
        $postAdmin->expects($this->any())->method('getObject')->will($this->returnValue($post));
2473
2474
        $formBuilder = $this->createMock(FormBuilderInterface::class);
2475
        $formBuilder->expects($this->any())->method('getForm')->will($this->returnValue(null));
2476
2477
        $tagAdmin = $this->getMockBuilder(TagAdmin::class)
2478
            ->setConstructorArgs([
2479
                'admin.tag',
2480
                Tag::class,
2481
                'MyBundle:MyController',
2482
            ])
2483
            ->setMethods(['getFormBuilder'])
2484
            ->getMock();
2485
2486
        $tagAdmin->expects($this->any())->method('getFormBuilder')->will($this->returnValue($formBuilder));
2487
        $tagAdmin->setParent($postAdmin);
2488
2489
        $tag = new Tag();
2490
        $tagAdmin->setSubject($tag);
2491
2492
        $request = $this->createMock(Request::class);
2493
        $tagAdmin->setRequest($request);
2494
2495
        $configurationPool = $this->getMockBuilder(Pool::class)
2496
            ->disableOriginalConstructor()
2497
            ->getMock();
2498
2499
        $configurationPool->expects($this->any())->method('getPropertyAccessor')->will($this->returnValue(PropertyAccess::createPropertyAccessor()));
2500
2501
        $tagAdmin->setConfigurationPool($configurationPool);
2502
2503
        return $tagAdmin;
2504
    }
2505
}
2506