Passed
Pull Request — master (#9)
by Alex
02:46
created

AbstractJoinTest::testInstanceOfAbstractJoin()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 1
eloc 1
c 1
b 0
f 0
nc 1
nop 0
dl 0
loc 3
rs 10
1
<?php
2
3
declare(strict_types=1);
4
5
namespace ArpTest\DoctrineQueryFilter\Filter;
6
7
use Arp\DoctrineQueryFilter\Enum\JoinConditionType;
8
use Arp\DoctrineQueryFilter\Filter\AbstractJoin;
9
use Arp\DoctrineQueryFilter\Filter\Exception\FilterException;
10
use Arp\DoctrineQueryFilter\Filter\Exception\InvalidArgumentException;
11
use Arp\DoctrineQueryFilter\Filter\FilterInterface;
12
use Arp\DoctrineQueryFilter\QueryBuilderInterface;
13
use Doctrine\ORM\Query\Expr\Base;
14
use Doctrine\ORM\Query\Expr\Composite;
15
use PHPUnit\Framework\MockObject\MockObject;
16
17
abstract class AbstractJoinTest extends AbstractFilterTest
18
{
19
    protected AbstractJoin $filter;
20
21
    protected string $filterClassName;
22
23
    public function setUp(): void
24
    {
25
        parent::setUp();
26
27
        /** @var AbstractJoin $filter */
28
        $filter = new $this->filterClassName($this->queryFilterManager, $this->typecaster, $this->paramNameGenerator);
29
        $this->filter = $filter;
30
    }
31
32
    public function testInstanceOfFilterInterface(): void
33
    {
34
        $this->assertInstanceOf(FilterInterface::class, $this->filter);
35
    }
36
37
    public function testInstanceOfAbstractJoin(): void
38
    {
39
        $this->assertInstanceOf(AbstractJoin::class, $this->filter);
40
    }
41
42
    /**
43
     * @throws FilterException
44
     */
45
    public function testFilterWillThrowInvalidArgumentExceptionIfTheRequiredFieldCriteriaIsNotProvided(): void
46
    {
47
        $this->expectException(InvalidArgumentException::class);
48
        $this->expectExceptionMessage(
49
            sprintf(
50
                'The required \'field\' criteria value is missing for filter \'%s\'',
51
                $this->filterClassName
52
            )
53
        );
54
55
        $this->filter->filter($this->queryBuilder, $this->metadata, []);
56
    }
57
58
    /**
59
     * @throws FilterException
60
     */
61
    public function testFilterWillThrowInvalidArgumentExceptionIfProvidedAnInvalidFieldName(): void
62
    {
63
        $entityName = 'Test';
64
        $fieldName = 'foo';
65
        $criteria = [
66
            'field' => $fieldName,
67
        ];
68
69
        $this->metadata->expects($this->once())
0 ignored issues
show
Bug introduced by
The method expects() does not exist on Arp\DoctrineQueryFilter\Metadata\MetadataInterface. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

69
        $this->metadata->/** @scrutinizer ignore-call */ 
70
                         expects($this->once())

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
70
            ->method('getName')
71
            ->willReturn($entityName);
72
73
        $this->metadata->expects($this->once())
74
            ->method('hasField')
75
            ->with($fieldName)
76
            ->willReturn(false);
77
78
        $this->metadata->expects($this->once())
79
            ->method('hasAssociation')
80
            ->with($fieldName)
81
            ->willReturn(false);
82
83
        $this->expectException(InvalidArgumentException::class);
84
        $this->expectExceptionMessage(
85
            sprintf(
86
                'Unable to apply query filter \'%s\': '
87
                . 'The entity class \'%s\' has no field or association named \'%s\'',
88
                $this->filterClassName,
89
                $entityName,
90
                $fieldName
91
            )
92
        );
93
94
        $this->filter->filter($this->queryBuilder, $this->metadata, $criteria);
95
    }
96
97
    /**
98
     * @param QueryBuilderInterface&MockObject $queryBuilder
99
     * @param string $fieldName
100
     * @param string $alias
101
     * @param null|string|Composite|Base $joinCondition
102
     * @param JoinConditionType|null $joinConditionType
103
     * @param string|null $indexBy
104
     */
105
    abstract protected function assertFilterJoin(
106
        QueryBuilderInterface $queryBuilder,
107
        string $fieldName,
108
        string $alias,
109
        null|string|Composite|Base $joinCondition = null,
110
        ?JoinConditionType $joinConditionType = null,
111
        ?string $indexBy = null
112
    ): void;
113
114
    /**
115
     * @throws InvalidArgumentException
116
     * @throws FilterException
117
     */
118
    public function testFilterWillApplyExpectedJoinWithoutConditions(): void
119
    {
120
        $fieldName = 'foo';
121
        $fieldAlias = 't';
122
123
        $joinAlias = 'a';
124
        $criteria = [
125
            'field' => $fieldAlias . '.' . $fieldName,
126
            'alias' => $joinAlias,
127
        ];
128
129
        $this->metadata->expects($this->once())
130
            ->method('hasField')
131
            ->with($fieldName)
132
            ->willReturn(true);
133
134
        $this->assertFilterJoin($this->queryBuilder, $fieldAlias . '.' . $fieldName, $joinAlias);
135
136
        $this->filter->filter($this->queryBuilder, $this->metadata, $criteria);
137
    }
138
}
139