Completed
Push — master ( 47d2ac...3fd795 )
by Marijn
22s
created

ClientTest::getClientProxyMock()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 12
Code Lines 9

Duplication

Lines 0
Ratio 0 %

Importance

Changes 4
Bugs 0 Features 1
Metric Value
c 4
b 0
f 1
dl 0
loc 12
rs 9.4285
cc 1
eloc 9
nc 1
nop 0
1
<?php
2
namespace Test\Werkspot\BingAdsApiBundle\Api;
3
4
use BingAds\Bulk\ReportTimePeriod;
5
use BingAds\Proxy\ClientProxy;
6
use Mockery;
7
use Mockery\MockInterface;
8
use PHPUnit_Framework_TestCase;
9
use SoapFault;
10
use stdClass;
11
use Werkspot\BingAdsApiBundle\Api\Client;
12
use Werkspot\BingAdsApiBundle\Api\Exceptions;
13
use Werkspot\BingAdsApiBundle\Api\Helper;
14
use Werkspot\BingAdsApiBundle\Guzzle\OauthTokenService;
15
use Werkspot\BingAdsApiBundle\Model\AccessToken;
16
use Werkspot\BingAdsApiBundle\Model\ApiDetails;
17
18
class ClientTest extends PHPUnit_Framework_TestCase
19
{
20
    const ACCESS_TOKEN = '2ec09aeccaf634d982eec793037e37fe';
21
    const REFRESH_TOKEN = '0c59f7e609b0cc467067e39d523116ce';
22
23
    public function testSetApiDetails()
24
    {
25
        $expected = new Client(
26
            new OauthTokenService(new \GuzzleHttp\Client()),
27
            new ApiDetails('1', '2', '3', '4', '5'),
28
            new ClientProxy('example.com'),
29
            new Helper\File(),
30
            new Helper\Csv(),
31
            $this->getTimeHelperMock()
32
        );
33
34
        $api = new Client(
35
            new OauthTokenService(new \GuzzleHttp\Client()),
36
            new ApiDetails(null, null, null, null, null),
37
            new ClientProxy('example.com'),
38
            new Helper\File(),
39
            new Helper\Csv(),
40
            $this->getTimeHelperMock()
41
        );
42
        $api->setApiDetails(new ApiDetails('1', '2', '3', '4', '5'));
43
        $this->assertEquals($expected, $api);
44
    }
45
46
    /**
47
     * @dataProvider getTestSoapExceptionData
48
     *
49
     * @param int $code
50
     * @param string $exceptionClassName
51
     */
52
    public function testSoapExceptions($code, $exceptionClassName)
53
    {
54
        $this->expectException($exceptionClassName);
55
        $this->runClientSoapException($code);
56
    }
57
58
    /**
59
     * @dataProvider getTestSoapExceptionData
60
     *
61
     * @param int $code
62
     * @param string $exceptionClassName
63
     */
64
    public function testSoapOperationErrorExceptions($code, $exceptionClassName)
65
    {
66
        $this->expectException($exceptionClassName);
67
        $this->runClientSoapException($code, 'OperationError');
68
    }
69
70
    /**
71
     * @dataProvider getTestSoapExceptionData
72
     *
73
     * @param int $code
74
     * @param string $exceptionClassName
75
     */
76
    public function testSoapBatchErrorExceptions($code, $exceptionClassName)
77
    {
78
        $this->expectException($exceptionClassName);
79
        $this->runClientSoapException($code, 'BatchErrors');
80
    }
81
82
    public function getTestSoapExceptionData()
83
    {
84
        return [
85
            0 => [
86
                'errorCode' => 0,
87
                'exceptionClassName' => Exceptions\SoapInternalErrorException::class
88
            ],
89
            105 => [
90
                'errorCode' => 105,
91
                'exceptionClassName' => Exceptions\SoapInvalidCredentialsException::class,
92
            ],
93
            106 => [
94
                'errorCode' => 106,
95
                'exceptionClassName' => Exceptions\SoapUserIsNotAuthorizedException::class,
96
            ],
97
            2004 => [
98
                'errorCode' => 2004,
99
                'exceptionClassName' => Exceptions\SoapNoCompleteDataAvailableException::class,
100
            ],
101
            2100 => [
102
                'errorCode' => 2100,
103
                'exceptionClassName' => Exceptions\SoapReportingServiceInvalidReportIdException::class,
104
            ],
105
            9999 => [
106
                'errorCode' => 9999,
107
                'exceptionClassName' => Exceptions\SoapUnknownErrorException::class,
108
            ],
109
        ];
110
    }
111
112
    /**
113
     * @param int $code
114
     * @param null|string $type
115
     *
116
     * @return MockInterface
0 ignored issues
show
Documentation introduced by
Should the return type not be MockInterface|null?

This check compares the return type specified in the @return annotation of a function or method doc comment with the types returned by the function and raises an issue if they mismatch.

Loading history...
117
     */
118
    private function runClientSoapException($code, $type = null)
119
    {
120
        $clientProxyMock = $this->getClientProxyMock();
121
        $clientProxyMock
122
            ->shouldReceive('GetService')
123
            ->andThrow($this->generateSoapFault($code, $type));
124
125
        $apiClient = $this->getApiClient(
126
            $this->getOauthTokenServiceMock(),
127
            new ApiDetails('refreshToken', 'clientId', 'clientSecret', 'redirectUri', 'devToken'),
128
            $clientProxyMock,
129
            new Helper\File(),
130
            new Helper\Csv(),
131
            $this->getTimeHelperMock()
132
        );
133
        $apiClient->get([], 'GeoLocationPerformanceReport', ReportTimePeriod::LastWeek);
134
    }
135
136
    /**
137
     * @return Mockery\MockInterface
138
     */
139 View Code Duplication
    private function getOauthTokenServiceMock()
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
140
    {
141
        $oauthTokenServiceMock = Mockery::mock(OauthTokenService::class);
142
        $oauthTokenServiceMock
143
            ->shouldReceive('refreshToken')
144
            ->with('clientId', 'clientSecret', 'redirectUri', AccessToken::class)
145
            ->once()
146
            ->andReturn(new AccessToken(self::ACCESS_TOKEN, self::REFRESH_TOKEN));
147
148
        return $oauthTokenServiceMock;
149
    }
150
151
    private function getTimeHelperMock()
152
    {
153
        $timeHelperMock = Mockery::mock(Helper\Time::class);
154
        $timeHelperMock->shouldReceive('sleep')->andReturnNull();
155
156
        return $timeHelperMock;
157
    }
158
159
    /**
160
     * @param OauthTokenService $oauthTokenService
161
     * @param ClientProxy $clientProxy
162
     * @param Helper\File $fileHelper
163
     * @param Helper\Csv $csvHelper
164
     * @param Helper\Time $timeHelper
165
     *
166
     * @return Client
167
     */
168 View Code Duplication
    private function getApiClient(OauthTokenService $oauthTokenService, ApiDetails $apiDetails, ClientProxy $clientProxy, Helper\File $fileHelper, Helper\Csv $csvHelper, Helper\Time $timeHelper)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

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

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

Loading history...
169
    {
170
        $apiClient = new Client($oauthTokenService, $apiDetails, $clientProxy, $fileHelper, $csvHelper, $timeHelper);
171
        $apiClient->setConfig(['cache_dir' => '/tmp']);
172
173
        return $apiClient;
174
    }
175
176
    /**
177
     * @param int $code
178
     * @param null|string $type
179
     *
180
     * @return \SoapFault
181
     */
182
    private function generateSoapFault($code, $type = null)
183
    {
184
        $message = "an error message {$code}";
0 ignored issues
show
Coding Style Best Practice introduced by
As per coding-style, please use concatenation or sprintf for the variable $code instead of interpolation.

It is generally a best practice as it is often more readable to use concatenation instead of interpolation for variables inside strings.

// Instead of
$x = "foo $bar $baz";

// Better use either
$x = "foo " . $bar . " " . $baz;
$x = sprintf("foo %s %s", $bar, $baz);
Loading history...
185
        $error = new stdClass();
186
        $error->Code = $code;
187
        $error->Message = $message;
188
        $exception = new SoapFault('Server', '');
189
        $exception->detail = new stdClass();
1 ignored issue
show
Bug introduced by
The property detail does not seem to exist in SoapFault.

An attempt at access to an undefined property has been detected. This may either be a typographical error or the property has been renamed but there are still references to its old name.

If you really want to allow access to undefined properties, you can define magic methods to allow access. See the php core documentation on Overloading.

Loading history...
190
        if ($type === 'BatchErrors') {
191
            $exception->detail->ApiFaultDetail = new stdClass();
192
            $exception->detail->ApiFaultDetail->BatchErrors = new stdClass();
193
            $exception->detail->ApiFaultDetail->BatchErrors->BatchError = [$error];
194
        } elseif ($type === 'OperationError') {
195
            $exception->detail->ApiFaultDetail = new stdClass();
196
            $exception->detail->ApiFaultDetail->OperationErrors = new stdClass();
197
            $exception->detail->ApiFaultDetail->OperationErrors->OperationError = [$error];
198
        } else {
199
            $exception->detail->AdApiFaultDetail = new stdClass();
200
            $exception->detail->AdApiFaultDetail->Errors = new stdClass();
201
            $exception->detail->AdApiFaultDetail->Errors->AdApiError = [$error];
202
        }
203
204
        return $exception;
205
    }
206
207
    private function getClientProxyMock()
208
    {
209
        $clientProxyMock = Mockery::mock(ClientProxy::class);
210
        $clientProxyMock
211
            ->shouldReceive('ConstructWithCredentials')
212
            ->andReturnSelf()
213
            ->once()
214
            ->shouldReceive('GetNamespace')
215
            ->andReturn('Namespace');
216
217
        return $clientProxyMock;
218
    }
219
}
220