Completed
Push — master ( 2bb369...448aae )
by Dieter
05:42
created

Base::analyzeGenericOfferResponse()   B

Complexity

Conditions 5
Paths 4

Size

Total Lines 32
Code Lines 18

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 32
rs 8.439
c 0
b 0
f 0
cc 5
eloc 18
nc 4
nop 1
1
<?php
2
/**
3
 * amadeus-ws-client
4
 *
5
 * Copyright 2015 Amadeus Benelux NV
6
 *
7
 * Licensed under the Apache License, Version 2.0 (the "License");
8
 * you may not use this file except in compliance with the License.
9
 * You may obtain a copy of the License at
10
 *
11
 * http://www.apache.org/licenses/LICENSE-2.0
12
 *
13
 * Unless required by applicable law or agreed to in writing, software
14
 * distributed under the License is distributed on an "AS IS" BASIS,
15
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
 * See the License for the specific language governing permissions and
17
 * limitations under the License.
18
 *
19
 * @package Amadeus
20
 * @license https://opensource.org/licenses/Apache-2.0 Apache 2.0
21
 */
22
23
namespace Amadeus\Client\ResponseHandler;
24
25
use Amadeus\Client\Exception;
26
use Amadeus\Client\ResponseHandler\Air\RetrieveSeatMap;
27
use Amadeus\Client\Result;
28
use Amadeus\Client\Session\Handler\SendResult;
29
30
/**
31
 * Default Response Handler
32
 *
33
 * @package Amadeus\Client\ResponseHandler
34
 * @author Dieter Devlieghere <[email protected]>
35
 */
36
class Base implements ResponseHandlerInterface
37
{
38
    /**
39
     * Default namespace prefix we'll be using for xpath queries
40
     *
41
     * Why not "m"? It's as good as any other letter.
42
     */
43
    const XMLNS_PREFIX = "m";
44
45
    /**
46
     * Analyze the response from the server and throw an exception when an error has been detected.
47
     *
48
     * @param SendResult $sendResult The Send Result from the Session Handler
49
     * @param string $messageName The message that was called
50
     *
51
     * @throws Exception
52
     * @throws \RuntimeException
53
     * @return Result
54
     */
55
    public function analyzeResponse($sendResult, $messageName)
56
    {
57
        $methodName = 'analyze' . str_replace('_', '', ucfirst($messageName)) . 'Response';
58
59
        if (!empty($sendResult->exception)) {
60
            return $this->makeResultForException($sendResult);
61
        } elseif (method_exists($this, $methodName)) {
62
            return $this->$methodName(
63
                $sendResult
64
            );
65
        } else {
66
            return new Result($sendResult, Result::STATUS_UNKNOWN);
67
        }
68
    }
69
70
    /**
71
     * Analysing a Security_Authenticate
72
     *
73
     * @param SendResult $response Security_Authenticate result
74
     * @return Result
75
     */
76
    protected function analyzeSecurityAuthenticateResponse($response)
77
    {
78
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
79
    }
80
81
    /**
82
     * Analysing a Security_Authenticate
83
     *
84
     * @param SendResult $response Security_Authenticate result
85
     * @return Result
86
     */
87
    protected function analyzeSecuritySignOutResponse($response)
88
    {
89
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
90
    }
91
92
    /**
93
     * Unknown response for Command_Cryptic because you need to analyse the cryptic response yourself
94
     *
95
     * @param SendResult $response
96
     * @return Result
97
     */
98
    protected function analyzeCommandCrypticResponse($response)
99
    {
100
        $ccResult = new Result($response, Result::STATUS_UNKNOWN);
101
        $ccResult->messages[] = new Result\NotOk(
102
            0,
103
            "Response handling not supported for cryptic entries"
104
        );
105
106
        return $ccResult;
107
    }
108
109 View Code Duplication
    protected function analyzeAirMultiAvailabilityResponse($response)
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...
110
    {
111
        $analyzeResponse = new Result($response);
112
113
        $message = null;
114
115
        $domXpath = $this->makeDomXpath($response->responseXml);
116
117
        $codeNode = $domXpath->query("//m:errorOrWarningSection/m:errorOrWarningInfo//m:code")->item(0);
118
        if ($codeNode instanceof \DOMNode) {
119
            $analyzeResponse->status = Result::STATUS_ERROR;
120
121
            $categoryNode = $domXpath->query("//m:errorOrWarningSection/m:errorOrWarningInfo//m:type")->item(0);
122
            if ($categoryNode instanceof \DOMNode) {
123
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNode->nodeValue);
124
            }
125
126
            $messageNodes = $domXpath->query('//m:errorOrWarningSection/m:textInformation/m:freeText');
127
            if ($messageNodes->length > 0) {
128
                $message = $this->makeMessageFromMessagesNodeList($messageNodes);
129
            }
130
            $analyzeResponse->messages [] = new Result\NotOk($codeNode->nodeValue, $message);
131
        }
132
133
        return $analyzeResponse;
134
    }
135
136
    protected function analyzeAirSellFromRecommendationResponse($response)
137
    {
138
        $analyzeResponse = new Result($response);
139
140
        $errMsgMap = [
141
            "288" => "UNABLE TO SATISFY, NEED CONFIRMED FLIGHT STATUS",
142
            "390" => "UNABLE TO REFORMAT"
143
        ];
144
145
        $domXpath = $this->makeDomXpath($response->responseXml);
146
147
        $codeNode = $domXpath->query("//m:errorSegment/m:errorDetails/m:errorCode")->item(0);
148
        if ($codeNode instanceof \DOMNode) {
149
            $analyzeResponse->status = Result::STATUS_ERROR;
150
151
            $categoryNode = $domXpath->query("//m:errorSegment/m:errorDetails/m:errorCategory")->item(0);
152
            if ($categoryNode instanceof \DOMNode) {
153
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNode->nodeValue);
154
            }
155
156
            $message = (array_key_exists($codeNode->nodeValue, $errMsgMap)) ? $errMsgMap[$codeNode->nodeValue] : 'UNKNOWN ERROR';
0 ignored issues
show
Coding Style introduced by
This line exceeds maximum limit of 120 characters; contains 129 characters

Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.

Loading history...
157
158
            $analyzeResponse->messages [] = new Result\NotOk($codeNode->nodeValue, $message);
159
        }
160
161
        return $analyzeResponse;
162
    }
163
164
    /**
165
     * @param SendResult $response
166
     * @return Result
167
     */
168
    protected function analyzeAirFlightInfoResponse($response)
169
    {
170
        $analyzeResponse = new Result($response);
171
172
        $code = null;
173
        $message = null;
174
175
        $domXpath = $this->makeDomXpath($response->responseXml);
176
177
        $categoryNodes = $domXpath->query('//m:responseError/m:errorInfo/m:errorDetails/m:errorCategory');
178
        if ($categoryNodes->length > 0) {
179
            $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNodes->item(0)->nodeValue);
180
        }
181
182
        $codeNodes = $domXpath->query('//m:responseError/m:errorInfo/m:errorDetails/m:errorCode');
183
        if ($codeNodes->length > 0) {
184
            $code = $codeNodes->item(0)->nodeValue;
185
        }
186
187
        $messageNodes = $domXpath->query('//m:responseError/m:interactiveFreeText/m:freeText');
188
        if ($messageNodes->length > 0) {
189
            $message = $this->makeMessageFromMessagesNodeList($messageNodes);
190
        }
191
192
        if (!is_null($message) && !is_null($code)) {
193
            $analyzeResponse->messages[] = new Result\NotOk($code, $message);
194
        }
195
196
        return $analyzeResponse;
197
    }
198
199
    /**
200
     * @param SendResult $response
201
     * @return Result
202
     */
203
    protected function analyzeAirRetrieveSeatMapResponse($response)
204
    {
205
        $analyzeResponse = new Result($response);
206
207
        $code = null;
0 ignored issues
show
Unused Code introduced by
$code is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
208
        $message = null;
0 ignored issues
show
Unused Code introduced by
$message is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
209
210
        $domXpath = $this->makeDomXpath($response->responseXml);
211
212
        $errorCodeNode = $domXpath->query('//m:errorInformation/m:errorDetails/m:code');
213 View Code Duplication
        if ($errorCodeNode->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
214
            $analyzeResponse->status = Result::STATUS_ERROR;
215
216
            $errCode = $errorCodeNode->item(0)->nodeValue;
217
            $level = null;
218
            $errDesc = null;
0 ignored issues
show
Unused Code introduced by
$errDesc is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
219
220
            $errorLevelNode = $domXpath->query('//m:errorInformation/m:errorDetails/m:processingLevel');
221
            if ($errorLevelNode->length > 0) {
222
                $level = RetrieveSeatMap::decodeProcessingLevel($errorLevelNode->item(0)->nodeValue);
223
            }
224
225
            $errorDescNode = $domXpath->query('//m:errorInformation/m:errorDetails/m:description');
226
            if ($errorDescNode->length > 0) {
227
                $errDesc = $errorDescNode->item(0)->nodeValue;
228
            } else {
229
                $errDesc = RetrieveSeatMap::findMessage($errCode);
230
            }
231
232
            $analyzeResponse->messages[] = new Result\NotOk(
233
                $errCode,
234
                $errDesc,
235
                $level
236
            );
237
        }
238
239
        $codeNode = $domXpath->query('//m:warningInformation/m:warningDetails/m:number');
240 View Code Duplication
        if ($codeNode->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
241
            $analyzeResponse->status = Result::STATUS_WARN;
242
243
            $warnCode = $codeNode->item(0)->nodeValue;
244
            $level = null;
245
            $warnDesc = null;
0 ignored issues
show
Unused Code introduced by
$warnDesc is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
246
247
            $levelNode = $domXpath->query('//m:warningInformation/m:warningDetails/m:processingLevel');
248
            if ($levelNode->length > 0) {
249
                $level = RetrieveSeatMap::decodeProcessingLevel($levelNode->item(0)->nodeValue);
250
            }
251
252
            $descNode = $domXpath->query('//m:warningInformation/m:warningDetails/m:description');
253
            if ($descNode->length > 0) {
254
                $warnDesc = $descNode->item(0)->nodeValue;
255
            } else {
256
                $warnDesc = RetrieveSeatMap::findMessage($warnCode);
257
            }
258
259
            $analyzeResponse->messages[] = new Result\NotOk(
260
                $warnCode,
261
                $warnDesc,
262
                $level
263
            );
264
        }
265
266
        return $analyzeResponse;
267
    }
268
269
    /**
270
     * Analysing a PNR_Retrieve response
271
     *
272
     * @param SendResult $response PNR_Retrieve result
273
     * @return Result
274
     */
275
    protected function analyzePnrRetrieveResponse($response)
276
    {
277
        return $this->analyzePnrReply($response);
278
    }
279
280
    /**
281
     * @param SendResult $response PNR_AddMultiElements result
282
     * @return Result
283
     */
284
    protected function analyzePnrAddMultiElementsResponse($response)
285
    {
286
        return $this->analyzePnrReply($response);
287
    }
288
289
    /**
290
     * @param SendResult $response PNR_Cancel result
291
     * @return Result
292
     */
293
    protected function analyzePnrCancelResponse($response)
294
    {
295
        return $this->analyzePnrReply($response);
296
    }
297
298
    /**
299
     * Analysing a PNR_Reply
300
     *
301
     * @param SendResult $response PNR_Retrieve result
302
     * @return Result
303
     */
304
    protected function analyzePnrReply($response)
305
    {
306
        $analyzeResponse = new Result($response);
307
308
        $domXpath = $this->makeDomXpath($response->responseXml);
309
310
        //General Errors:
311
        $queryAllErrorCodes = "//m:generalErrorInfo//m:errorOrWarningCodeDetails/m:errorDetails/m:errorCode";
312
        $queryAllErrorMsg = "//m:generalErrorInfo/m:errorWarningDescription/m:freeText";
313
314
        $errorCodeNodeList = $domXpath->query($queryAllErrorCodes);
315
316 View Code Duplication
        if ($errorCodeNodeList->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
317
            $analyzeResponse->status = Result::STATUS_ERROR;
318
319
            $code = $errorCodeNodeList->item(0)->nodeValue;
320
            $errorTextNodeList = $domXpath->query($queryAllErrorMsg);
321
            $message = $this->makeMessageFromMessagesNodeList($errorTextNodeList);
322
323
            $analyzeResponse->messages[] = new Result\NotOk($code, trim($message), 'general');
324
        }
325
326
        //Segment errors:
327
        $querySegmentErrorCodes = "//m:originDestinationDetails//m:errorInfo/m:errorOrWarningCodeDetails/m:errorDetails/m:errorCode";
0 ignored issues
show
Coding Style introduced by
This line exceeds maximum limit of 120 characters; contains 133 characters

Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.

Loading history...
328
        $querySegmentErrorMsg = "//m:originDestinationDetails//m:errorInfo/m:errorWarningDescription/m:freeText";
329
330
        $errorCodeNodeList = $domXpath->query($querySegmentErrorCodes);
331
332 View Code Duplication
        if ($errorCodeNodeList->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
333
            $analyzeResponse->status = Result::STATUS_ERROR;
334
335
            $code = $errorCodeNodeList->item(0)->nodeValue;
336
            $errorTextNodeList = $domXpath->query($querySegmentErrorMsg);
337
            $message = $this->makeMessageFromMessagesNodeList($errorTextNodeList);
338
339
            $analyzeResponse->messages[] = new Result\NotOk($code, trim($message), 'segment');
340
        }
341
342
        //Element errors:
343
        $queryElementErrorCodes = "//m:dataElementsIndiv/m:elementErrorInformation/m:errorOrWarningCodeDetails/m:errorDetails/m:errorCode";
0 ignored issues
show
Coding Style introduced by
This line exceeds maximum limit of 120 characters; contains 139 characters

Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.

Loading history...
344
        $queryElementErrorMsg = "//m:dataElementsIndiv//m:elementErrorInformation/m:errorWarningDescription/m:freeText";
345
346
        $errorCodeNodeList = $domXpath->query($queryElementErrorCodes);
347
348 View Code Duplication
        if ($errorCodeNodeList->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
349
            $analyzeResponse->status = Result::STATUS_ERROR;
350
351
            $code = $errorCodeNodeList->item(0)->nodeValue;
352
353
            $errorTextNodeList = $domXpath->query($queryElementErrorMsg);
354
            $message = $this->makeMessageFromMessagesNodeList($errorTextNodeList);
355
356
            $analyzeResponse->messages[] = new Result\NotOk($code, trim($message), 'element');
357
        }
358
359
        return $analyzeResponse;
360
    }
361
362
    /**
363
     * @param SendResult $response Pnr_RetrieveAndDisplay response
364
     * @return Result
365
     * @throws Exception
366
     */
367
    protected function analyzePnrRetrieveAndDisplayResponse($response)
368
    {
369
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
370
    }
371
372
    /**
373
     * Analysing a PNR_DisplayHistoryReply
374
     *
375
     * @param SendResult $response PNR_DisplayHistoryReply result
376
     * @return Result
377
     * @throws Exception
378
     */
379
    protected function analyzePnrDisplayHistoryResponse($response)
380
    {
381
        $analyzeResponse = new Result($response);
382
383
        $domXpath = $this->makeDomXpath($response->responseXml);
384
385
        $queryAllErrorCodes = "//m:generalErrorGroup//m:errorNumber/m:errorDetails/m:errorCode";
386
        $queryAllErrorMsg = "//m:generalErrorGroup/m:genrealErrorText/m:freeText";
387
388
        $errorCodeNodeList = $domXpath->query($queryAllErrorCodes);
389
390 View Code Duplication
        if ($errorCodeNodeList->length > 0) {
0 ignored issues
show
Duplication introduced by
This code seems to be duplicated across 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...
391
            $analyzeResponse->status = Result::STATUS_ERROR;
392
393
            $code = $errorCodeNodeList->item(0)->nodeValue;
394
            $errorTextNodeList = $domXpath->query($queryAllErrorMsg);
395
            $message = $this->makeMessageFromMessagesNodeList($errorTextNodeList);
396
397
            $analyzeResponse->messages[] = new Result\NotOk($code, trim($message));
398
        }
399
400
        return $analyzeResponse;
401
    }
402
403
    /**
404
     * @param SendResult $response Queue_RemoveItem response
405
     * @return Result
406
     * @throws Exception
407
     */
408
    protected function analyzeQueueRemoveItemResponse($response)
409
    {
410
        return $this->analyzeGenericQueueResponse($response);
411
    }
412
413
    /**
414
     * @param SendResult $response Queue_MoveItem response
415
     * @return Result
416
     * @throws Exception
417
     */
418
    protected function analyzeQueueMoveItemResponse($response)
419
    {
420
        return $this->analyzeGenericQueueResponse($response);
421
    }
422
423
    /**
424
     * @param SendResult $response Queue_PlacePNR response
425
     * @return Result
426
     * @throws Exception
427
     */
428
    protected function analyzeQueuePlacePNRResponse($response)
429
    {
430
        return $this->analyzeGenericQueueResponse($response);
431
    }
432
433
    /**
434
     * @param SendResult $response Queue_List result
435
     * @return Result
436
     * @throws Exception
437
     */
438
    protected function analyzeQueueListResponse($response)
439
    {
440
        return $this->analyzeGenericQueueResponse($response);
441
    }
442
443
    /**
444
     * Analyze a generic Queue response
445
     *
446
     * @param SendResult $response Queue_*Reply result
447
     * @return Result
448
     * @throws Exception
449
     */
450
    protected function analyzeGenericQueueResponse($response)
451
    {
452
        $analysisResponse = new Result($response);
453
454
        $domDoc = $this->loadDomDocument($response->responseXml);
455
456
        $errorCodeNode = $domDoc->getElementsByTagName("errorCode")->item(0);
457
458
        if (!is_null($errorCodeNode)) {
459
            $analysisResponse->status = Result::STATUS_WARN;
460
461
            $errorCode = $errorCodeNode->nodeValue;
462
            $errorMessage = $this->getErrorTextFromQueueErrorCode($errorCode);
463
464
            $analysisResponse->messages[] = new Result\NotOk($errorCode, $errorMessage);
465
        }
466
467
        return $analysisResponse;
468
    }
469
470
471
    /**
472
     *
473
     * <Fare_PricePNRWithBookingClassReply xmlns="http://xml.amadeus.com/TPCBRR_13_2_1A">
474
     * <applicationError>
475
     * <errorOrWarningCodeDetails>
476
     * <errorDetails>
477
     * <errorCode>00477</errorCode>
478
     * <errorCategory>EC</errorCategory>
479
     * <errorCodeOwner>1A</errorCodeOwner>
480
     * </errorDetails>
481
     * </errorOrWarningCodeDetails>
482
     * <errorWarningDescription>
483
     * <freeText>INVALID FORMAT</freeText>
484
     * </errorWarningDescription>
485
     * </applicationError>
486
     * </Fare_PricePNRWithBookingClassReply>
487
     *
488
     * @param SendResult $response Fare_PricePNRWithBookingClass result
489
     * @return Result
490
     * @throws Exception
491
     */
492 View Code Duplication
    protected function analyzeFarePricePNRWithBookingClassResponse($response)
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...
493
    {
494
        $analyzeResponse = new Result($response);
495
496
        $domXpath = $this->makeDomXpath($response->responseXml);
497
498
        $queryErrorCode = "//m:applicationError//m:errorOrWarningCodeDetails/m:errorDetails/m:errorCode";
499
        $queryErrorCategory = "//m:applicationError//m:errorOrWarningCodeDetails/m:errorDetails/m:errorCategory";
500
        $queryErrorMsg = "//m:applicationError/m:errorWarningDescription/m:freeText";
501
502
        $errorCodeNodeList = $domXpath->query($queryErrorCode);
503
504
        if ($errorCodeNodeList->length > 0) {
505
            $analyzeResponse->status = Result::STATUS_ERROR;
506
507
            $errorCatNode = $domXpath->query($queryErrorCategory)->item(0);
508
            if ($errorCatNode instanceof \DOMNode) {
509
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($errorCatNode->nodeValue);
510
            }
511
512
            $analyzeResponse->messages[] = new Result\NotOk(
513
                $errorCodeNodeList->item(0)->nodeValue,
514
                $this->makeMessageFromMessagesNodeList(
515
                    $domXpath->query($queryErrorMsg)
516
                )
517
            );
518
        }
519
520
        return $analyzeResponse;
521
    }
522
523
    /**
524
     * @param SendResult $response
525
     * @return Result
526
     */
527
    protected function analyzeFareMasterPricerTravelBoardSearchResponse($response)
528
    {
529
        $analyzeResponse = new Result($response);
530
531
        $domXpath = $this->makeDomXpath($response->responseXml);
532
533
        $queryErrCode = "//m:applicationError//m:applicationErrorDetail/m:error";
534
        $queryErrMsg = "//m:errorMessageText/m:description";
535
536
        $codeNode = $domXpath->query($queryErrCode)->item(0);
537
538
        if ($codeNode instanceof \DOMNode) {
539
            $analyzeResponse->status = Result::STATUS_ERROR;
540
541
            $errMsg = '';
542
            $errMsgNode = $domXpath->query($queryErrMsg)->item(0);
543
            if ($errMsgNode instanceof \DOMNode) {
544
                $errMsg = $errMsgNode->nodeValue;
545
            }
546
547
            $analyzeResponse->messages[] = new Result\NotOk(
548
                $codeNode->nodeValue,
549
                $errMsg
550
            );
551
        }
552
553
        return $analyzeResponse;
554
    }
555
556
    /**
557
     * @param SendResult $response
558
     * @return Result
559
     */
560
    protected function analyzeFareConvertCurrencyResponse($response)
561
    {
562
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
563
    }
564
565
    /**
566
     * @param SendResult $response
567
     * @return Result
568
     */
569
    protected function analyzeFareCheckRulesResponse($response)
570
    {
571
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
572
    }
573
574
    /**
575
     * @param SendResult $response
576
     * @return Result
577
     */
578
    protected function analyzeFareInformativePricingWithoutPNRResponse($response)
579
    {
580
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
581
    }
582
583
584
    /**
585
     * @param SendResult $response
586
     * @return Result
587
     */
588
    protected function analyzeDocIssuanceIssueTicketResponse($response)
589
    {
590
        return $this->analyzeSimpleResponseErrorCodeAndMessageStatusCode($response);
591
    }
592
593
    /**
594
     * @param SendResult $response Ticket_DeleteTST result
595
     * @return Result
596
     */
597
    protected function analyzeTicketDeleteTSTResponse($response)
598
    {
599
        return $this->analyzeTicketCreateTSTFromPricingResponse($response);
600
    }
601
602
    /**
603
     * @param SendResult $response Ticket_CreateTSTFromPricing result
604
     * @return Result
605
     */
606 View Code Duplication
    protected function analyzeTicketCreateTSTFromPricingResponse($response)
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...
607
    {
608
        $analyzeResponse = new Result($response);
609
610
        $domDoc = $this->loadDomDocument($response->responseXml);
611
612
        $errorCodeNode = $domDoc->getElementsByTagName("applicationErrorCode")->item(0);
613
614
        if (!is_null($errorCodeNode)) {
615
            $analyzeResponse->status = Result::STATUS_ERROR;
616
617
            $errorCatNode = $domDoc->getElementsByTagName("codeListQualifier")->item(0);
618
            if ($errorCatNode instanceof \DOMNode) {
619
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($errorCatNode->nodeValue);
620
            }
621
622
            $errorCode = $errorCodeNode->nodeValue;
623
            $errorTextNodeList = $domDoc->getElementsByTagName("errorFreeText");
624
625
            $analyzeResponse->messages[] = new Result\NotOk(
626
                $errorCode,
627
                $this->makeMessageFromMessagesNodeList($errorTextNodeList)
628
            );
629
        }
630
631
        return $analyzeResponse;
632
    }
633
634
    /**
635
     * @param SendResult $response
636
     * @return Result
637
     */
638
    protected function analyzeOfferConfirmCarOfferResponse($response)
639
    {
640
        return $this->analyzeGenericOfferResponse($response);
641
    }
642
643
    /**
644
     * @param SendResult $response
645
     * @return Result
646
     */
647
    protected function analyzeOfferConfirmHotelOfferResponse($response)
648
    {
649
        $analyzeResponse = new Result($response);
650
651
        $domXpath = $this->makeDomXpath($response->responseXml);
652
653
        $codeNode = $domXpath->query("//m:errorDetails/m:errorCode")->item(0);
654
        if ($codeNode instanceof \DOMNode) {
655
            $analyzeResponse->status = Result::STATUS_ERROR;
656
657
            $categoryNode = $domXpath->query("//m:errorDetails/m:errorCategory")->item(0);
658
            if ($categoryNode instanceof \DOMNode) {
659
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNode->nodeValue);
660
            }
661
662
            $msgNode = $domXpath->query('//m:errorDescription/m:freeText')->item(0);
663
664
            $analyzeResponse->messages[] = new Result\NotOk(
665
                $codeNode->nodeValue,
666
                trim($msgNode->nodeValue)
667
            );
668
        }
669
670
        return $analyzeResponse;
671
    }
672
673
    /**
674
     * @param SendResult $response
675
     * @return Result
676
     */
677
    protected function analyzeOfferConfirmAirOfferResponse($response)
678
    {
679
        return $this->analyzeGenericOfferResponse($response);
680
    }
681
682
    /**
683
     * @param SendResult $response
684
     * @return Result
685
     */
686
    protected function analyzeOfferVerifyOfferResponse($response)
687
    {
688
        return $this->analyzeGenericOfferResponse($response);
689
    }
690
691
    /**
692
     * @param SendResult $response
693
     * @return Result
694
     */
695
    protected function analyzeGenericOfferResponse($response)
696
    {
697
        $analyzeResponse = new Result($response);
698
699
        $domXpath = $this->makeDomXpath($response->responseXml);
700
701
        $msgNode = $domXpath->query('//m:errorsDescription/m:errorWarningDescription/m:freeText')->item(0);
702
703
        if ($msgNode instanceof \DOMNode) {
704
            if (trim($msgNode->nodeValue) === "OFFER CONFIRMED SUCCESSFULLY" || trim($msgNode->nodeValue) === "OFFER VERIFIED SUCCESSFULLY") {
0 ignored issues
show
Coding Style introduced by
This line exceeds maximum limit of 120 characters; contains 142 characters

Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.

Loading history...
705
                $analyzeResponse->messages[] = new Result\NotOk(
706
                    0,
707
                    trim($msgNode->nodeValue)
708
                );
709
                return $analyzeResponse;
710
            }
711
712
            $categoryNode = $domXpath->query('//m:errorDetails/m:errorCategory')->item(0);
713
            if ($categoryNode instanceof \DOMNode) {
714
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNode->nodeValue);
715
            }
716
717
            $codeNode = $domXpath->query('//m:errorDetails/m:errorCode')->item(0);
718
719
            $analyzeResponse->messages[] = new Result\NotOk(
720
                $codeNode->nodeValue,
721
                trim($msgNode->nodeValue)
722
            );
723
        }
724
725
        return $analyzeResponse;
726
    }
727
728
    protected function analyzeMiniRuleGetFromPricingRecResponse($response)
729
    {
730
        $analyzeResponse = new Result($response);
731
732
        $domXpath = $this->makeDomXpath($response->responseXml);
733
734
        $statusNode = $domXpath->query('//m:responseDetails/m:statusCode')->item(0);
735
        if ($statusNode instanceof \DOMNode) {
736
            $code = $statusNode->nodeValue;
737
738
            if ($code !== 'O') {
739
                $categoryNode = $domXpath->query('//m:errorOrWarningCodeDetails/m:errorDetails/m:errorCategory')->item(0);
0 ignored issues
show
Coding Style introduced by
This line exceeds maximum limit of 120 characters; contains 122 characters

Overly long lines are hard to read on any screen. Most code styles therefor impose a maximum limit on the number of characters in a line.

Loading history...
740
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($categoryNode->nodeValue);
741
742
                $codeNode = $domXpath->query('//m:errorOrWarningCodeDetails/m:errorDetails/m:errorCode')->item(0);
743
                $msgNode = $domXpath->query('//m:errorWarningDescription/m:freeText')->item(0);
744
745
                if ($codeNode instanceof \DOMNode && $msgNode instanceof \DOMNode) {
746
                    $analyzeResponse->messages[] = new Result\NotOk(
747
                        $codeNode->nodeValue,
748
                        $msgNode->nodeValue
749
                    );
750
                }
751
            }
752
        }
753
754
        return $analyzeResponse;
755
    }
756
757
    /**
758
     * @param SendResult $response
759
     * @return Result
760
     */
761
    protected function analyzeInfoEncodeDecodeCityResponse($response)
762
    {
763
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
764
    }
765
766
    /**
767
     * @param SendResult $response
768
     * @return Result
769
     */
770
    protected function analyzePriceXplorerExtremeSearchResponse($response)
771
    {
772
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
773
    }
774
775
    /**
776
     * @param SendResult $response
777
     * @return Result
778
     */
779
    protected function analyzeSalesReportsDisplayQueryReportResponse($response)
780
    {
781
        return $this->analyzeSimpleResponseErrorCodeAndMessage($response);
782
    }
783
784
    /**
785
     * @param SendResult $response WebService message Send Result
786
     * @return Result
787
     * @throws Exception
788
     */
789 View Code Duplication
    protected function analyzeSimpleResponseErrorCodeAndMessage($response)
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...
790
    {
791
        $analyzeResponse = new Result($response);
792
793
        $domDoc = $this->loadDomDocument($response->responseXml);
794
795
        $errorCodeNode = $domDoc->getElementsByTagName("errorCode")->item(0);
796
797
        if (!is_null($errorCodeNode)) {
798
            $errorCatNode = $domDoc->getElementsByTagName("errorCategory")->item(0);
799
            if ($errorCatNode instanceof \DOMNode) {
800
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($errorCatNode->nodeValue);
801
            } else {
802
                $analyzeResponse->status = Result::STATUS_ERROR;
803
            }
804
805
            $errorCode = $errorCodeNode->nodeValue;
806
            $errorTextNodeList = $domDoc->getElementsByTagName("freeText");
807
808
            $analyzeResponse->messages[] = new Result\NotOk(
809
                $errorCode,
810
                $this->makeMessageFromMessagesNodeList($errorTextNodeList)
811
            );
812
        }
813
814
        return $analyzeResponse;
815
    }
816
817
    /**
818
     * @param SendResult $response WebService message Send Result
819
     * @return Result
820
     * @throws Exception
821
     */
822 View Code Duplication
    protected function analyzeSimpleResponseErrorCodeAndMessageStatusCode($response)
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...
823
    {
824
        $analyzeResponse = new Result($response);
825
826
        $domDoc = $this->loadDomDocument($response->responseXml);
827
828
        $errorCodeNode = $domDoc->getElementsByTagName("errorCode")->item(0);
829
830
        if (!is_null($errorCodeNode)) {
831
            $analyzeResponse->status = Result::STATUS_ERROR;
832
833
            $errorCatNode = $domDoc->getElementsByTagName("statusCode")->item(0);
834
            if ($errorCatNode instanceof \DOMNode) {
835
                $analyzeResponse->status = $this->makeStatusFromErrorQualifier($errorCatNode->nodeValue);
836
            }
837
838
            $errorCode = $errorCodeNode->nodeValue;
839
            $errorTextNodeList = $domDoc->getElementsByTagName("freeText");
840
841
            $analyzeResponse->messages[] = new Result\NotOk(
842
                $errorCode,
843
                $this->makeMessageFromMessagesNodeList($errorTextNodeList)
844
            );
845
        }
846
847
        return $analyzeResponse;
848
    }
849
850
    /**
851
     * Returns the errortext from a Queue_*Reply errorcode
852
     *
853
     * This function is necessary because the core only responds
854
     * with errorcode but does not send an errortext.
855
     *
856
     * The errorcodes for all Queue_*Reply messages are the same.
857
     *
858
     * @link https://webservices.amadeus.com/extranet/viewArea.do?id=10
859
     * @param string $errorCode
860
     * @return string the errortext for this errorcode.
861
     */
862
    protected function getErrorTextFromQueueErrorCode($errorCode)
863
    {
864
        $recognizedErrors = [
865
            '723' => "Invalid category",
866
            '911' => "Unable to process - system error",
867
            '913' => "Item/data not found or data not existing in processing host",
868
            '79D' => "Queue identifier has not been assigned for specified office identification",
869
            '91C' => "invalid record locator",
870
            '91F' => "Invalid queue number",
871
            '921' => "target not specified",
872
            '922' => "Targetted queue has wrong queue type",
873
            '926' => "Queue category empty",
874
            '928' => "Queue category not assigned",
875
            '92A' => "Queue category full",
876
        ];
877
878
        $errorMessage = (array_key_exists($errorCode, $recognizedErrors)) ? $recognizedErrors[$errorCode] : '';
879
880
        if ($errorMessage === '') {
881
            $errorMessage = "QUEUE ERROR '" . $errorCode . "' (Error message unavailable)";
882
        }
883
884
        return $errorMessage;
885
    }
886
887
    /**
888
     * @param string $response
889
     * @return \DOMDocument
890
     * @throws Exception when there's a problem loading the message
891
     */
892
    protected function loadDomDocument($response)
893
    {
894
        $domDoc = new \DOMDocument('1.0', 'UTF-8');
895
896
        $loadResult = $domDoc->loadXML($response);
897
        if ($loadResult === false) {
898
            throw new Exception('Could not load response message into DOMDocument');
899
        }
900
901
        return $domDoc;
902
    }
903
904
    /**
905
     * @param string $qualifier
906
     * @return string Result::STATUS_*
907
     */
908
    protected function makeStatusFromErrorQualifier($qualifier)
909
    {
910
        $status = null;
0 ignored issues
show
Unused Code introduced by
$status is not used, you could remove the assignment.

This check looks for variable assignements that are either overwritten by other assignments or where the variable is not used subsequently.

$myVar = 'Value';
$higher = false;

if (rand(1, 6) > 3) {
    $higher = true;
} else {
    $higher = false;
}

Both the $myVar assignment in line 1 and the $higher assignment in line 2 are dead. The first because $myVar is never used and the second because $higher is always overwritten for every possible time line.

Loading history...
911
912
        switch ($qualifier) {
913
            case 'INF':
914
                $status = Result::STATUS_INFO;
915
                break;
916
            case 'WEC':
917
            case 'WZZ': //Mutually defined warning
918
            case 'W':
919
                $status = Result::STATUS_WARN;
920
                break;
921
            case 'EC':
922
            case 'X':
923
            case '001': //Air_MultiAvailability
924
                $status = Result::STATUS_ERROR;
925
                break;
926
            case 'O':
927
                $status = Result::STATUS_OK;
928
                break;
929
            case 'ZZZ': //Mutually defined
930
            default:
931
                $status = Result::STATUS_UNKNOWN;
932
                break;
933
        }
934
935
        return $status;
936
    }
937
938
939
    /**
940
     * Make a Xpath-queryable object for an XML string
941
     *
942
     * registers TNS namespace with prefix self::XMLNS_PREFIX
943
     *
944
     * @param string $response
945
     * @return \DOMXPath
946
     * @throws Exception when there's a problem loading the message
947
     */
948
    protected function makeDomXpath($response)
949
    {
950
        $domDoc = $this->loadDomDocument($response);
951
        $domXpath = new \DOMXPath($domDoc);
952
953
        $domXpath->registerNamespace(
954
            self::XMLNS_PREFIX,
955
            $domDoc->documentElement->lookupNamespaceUri(null)
956
        );
957
958
        return $domXpath;
959
    }
960
961
    /**
962
     * Convert a DomNodeList of nodes containing a (potentially partial) error message into a string.
963
     *
964
     * @param \DOMNodeList $errorTextNodeList
965
     * @return string|null
966
     */
967
    protected function makeMessageFromMessagesNodeList($errorTextNodeList)
968
    {
969
        return implode(
970
            ' - ',
971
            array_map(
972
                function ($item) {
973
                    return trim($item->nodeValue);
974
                },
975
                iterator_to_array($errorTextNodeList)
976
            )
977
        );
978
    }
979
980
    /**
981
     * @param SendResult $sendResult
982
     * @return Result
983
     */
984
    protected function makeResultForException($sendResult)
985
    {
986
        $result = new Result($sendResult, Result::STATUS_FATAL);
987
988
        $result->messages[] = $this->makeMessageFromException($sendResult->exception);
989
990
        return $result;
991
    }
992
993
    /**
994
     * @param \Exception $exception
995
     * @return Result\NotOk
996
     * @throws Exception
997
     */
998
    protected function makeMessageFromException(\Exception $exception)
999
    {
1000
        $message = new Result\NotOk();
1001
1002
        if ($exception instanceof \SoapFault) {
1003
            $info = explode('|', $exception->getMessage());
1004
            $message->code = $info[0];
1005
            if (count($info) === 3) {
1006
                $message->level = $info[1];
1007
                $message->text = $info[2];
1008
            }
1009
        }
1010
1011
        return $message;
1012
    }
1013
}
1014