AddMultiElements::addElements()   B
last analyzed

Complexity

Conditions 6
Paths 20

Size

Total Lines 31

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 31
rs 8.8017
c 0
b 0
f 0
cc 6
nc 20
nop 5
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\Struct\Pnr;
24
25
use Amadeus\Client\RequestOptions\Pnr\Element;
26
use Amadeus\Client\RequestOptions\Pnr\Element\ReceivedFrom;
27
use Amadeus\Client\RequestOptions\Pnr\Itinerary;
28
use Amadeus\Client\RequestOptions\Pnr\Segment;
29
use Amadeus\Client\RequestOptions\Pnr\Traveller;
30
use Amadeus\Client\RequestOptions\Pnr\TravellerGroup;
31
use Amadeus\Client\RequestOptions\PnrAddMultiElementsBase;
32
use Amadeus\Client\RequestOptions\PnrAddMultiElementsOptions;
33
use Amadeus\Client\RequestOptions\PnrCreatePnrOptions;
34
use Amadeus\Client\Struct\BaseWsMessage;
35
use Amadeus\Client\Struct\InvalidArgumentException;
36
use Amadeus\Client\Struct\Pnr\AddMultiElements\AirAuxItinerary;
37
use Amadeus\Client\Struct\Pnr\AddMultiElements\DataElementsIndiv;
38
use Amadeus\Client\Struct\Pnr\AddMultiElements\DataElementsMaster;
39
use Amadeus\Client\Struct\Pnr\AddMultiElements\ElementManagementItinerary;
40
use Amadeus\Client\Struct\Pnr\AddMultiElements\ItineraryInfo;
41
use Amadeus\Client\Struct\Pnr\AddMultiElements\OriginDestination;
42
use Amadeus\Client\Struct\Pnr\AddMultiElements\OriginDestinationDetails;
43
use Amadeus\Client\Struct\Pnr\AddMultiElements\Reference;
44
use Amadeus\Client\Struct\Pnr\AddMultiElements\ReferenceForDataElement;
45
use Amadeus\Client\Struct\Pnr\AddMultiElements\ReferenceForSegment;
46
use Amadeus\Client\Struct\Pnr\AddMultiElements\TravellerInfo;
47
48
/**
49
 * Structure class for representing the PNR_AddMultiElements request message
50
 *
51
 * @package Amadeus\Client\Struct\Pnr
52
 * @author Dieter Devlieghere <[email protected]>
53
 */
54
class AddMultiElements extends BaseWsMessage
55
{
56
    /**
57
     * @var AddMultiElements\ReservationInfo
58
     */
59
    public $reservationInfo;
60
    /**
61
     * @var AddMultiElements\PnrActions
62
     */
63
    public $pnrActions;
64
    /**
65
     * @var AddMultiElements\TravellerInfo[]
66
     */
67
    public $travellerInfo = [];
68
    /**
69
     * @var AddMultiElements\OriginDestinationDetails[]
70
     */
71
    public $originDestinationDetails = [];
72
    /**
73
     * @var AddMultiElements\DataElementsMaster
74
     */
75
    public $dataElementsMaster;
76
77
    /**
78
     * Create PNR_AddMultiElements object
79
     *
80
     * @param PnrAddMultiElementsBase|null $params
81
     * @throws \ReflectionException
82
     */
83
    public function __construct(PnrAddMultiElementsBase $params = null)
84
    {
85
        if (!is_null($params)) {
86
            if ($params instanceof PnrCreatePnrOptions) {
87
                $this->loadCreatePnr($params);
88
            } elseif ($params instanceof PnrAddMultiElementsOptions) {
89
                $this->loadBare($params);
90
            }
91
        }
92
    }
93
94
    /**
95
     * PNR_AddMultiElements call which only adds requested data to the message
96
     *
97
     * For doing specific actions like ignoring or saving PNR.
98
     *
99
     * @param PnrAddMultiElementsOptions $params
100
     * @throws \ReflectionException
101
     */
102
    protected function loadBare(PnrAddMultiElementsOptions $params)
103
    {
104
        $tattooCounter = 0;
105
106
        if (!is_null($params->actionCode)) {
107
            $this->pnrActions = new AddMultiElements\PnrActions(
108
                $params->actionCode
0 ignored issues
show
Bug introduced by
It seems like $params->actionCode can also be of type array<integer,integer>; however, Amadeus\Client\Struct\Pn...rActions::__construct() does only seem to accept integer, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
109
            );
110
        }
111
112
        if (!is_null($params->recordLocator)) {
113
            $this->reservationInfo = new AddMultiElements\ReservationInfo($params->recordLocator);
114
        }
115
116
        if ($params->travellerGroup !== null) {
117
            $this->addTravellerGroup($params->travellerGroup);
118
        } else {
119
            $this->addTravellers($params->travellers);
120
        }
121
122
        $this->addItineraries($params->itineraries, $params->tripSegments, $tattooCounter);
0 ignored issues
show
Deprecated Code introduced by
The property Amadeus\Client\RequestOp...sOptions::$tripSegments has been deprecated with message: use $this->itinerary instead

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
123
124
        if (!empty($params->elements)) {
125
            $this->addElements(
126
                $params->elements,
127
                $tattooCounter,
128
                $params->autoAddReceivedFrom,
129
                $params->defaultReceivedFrom,
0 ignored issues
show
Deprecated Code introduced by
The property Amadeus\Client\RequestOp...e::$defaultReceivedFrom has been deprecated with message: This is a workaround until we can decide on what happens with RF elements for the next major version.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
130
                $params->receivedFrom
131
            );
132
        } else {
133
            $this->addReceivedFrom(
134
                $params->receivedFrom,
135
                $params->autoAddReceivedFrom,
136
                $params->defaultReceivedFrom,
0 ignored issues
show
Deprecated Code introduced by
The property Amadeus\Client\RequestOp...e::$defaultReceivedFrom has been deprecated with message: This is a workaround until we can decide on what happens with RF elements for the next major version.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
137
                $tattooCounter
138
            );
139
        }
140
    }
141
142
    /**
143
     * Make PNR_AddMultiElements structure from a PnrCreatePnrOptions input.
144
     *
145
     * @throws InvalidArgumentException When invalid input is provided
146
     * @param PnrCreatePnrOptions $params
147
     * @throws \ReflectionException
148
     */
149
    protected function loadCreatePnr(PnrCreatePnrOptions $params)
150
    {
151
        $this->pnrActions = new AddMultiElements\PnrActions(
152
            $params->actionCode
0 ignored issues
show
Bug introduced by
It seems like $params->actionCode can also be of type array<integer,integer>; however, Amadeus\Client\Struct\Pn...rActions::__construct() does only seem to accept integer, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
153
        );
154
155
        $tattooCounter = 0;
156
157
        if ($params->travellerGroup !== null) {
158
            $this->addTravellerGroup($params->travellerGroup);
159
        } else {
160
            $this->addTravellers($params->travellers);
161
        }
162
163
        $this->addItineraries($params->itineraries, $params->tripSegments, $tattooCounter);
0 ignored issues
show
Deprecated Code introduced by
The property Amadeus\Client\RequestOp...rOptions::$tripSegments has been deprecated with message: use $this->itinerary instead

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
164
165
        $this->addElements(
166
            $params->elements,
167
            $tattooCounter,
168
            $params->autoAddReceivedFrom,
169
            $params->defaultReceivedFrom,
0 ignored issues
show
Deprecated Code introduced by
The property Amadeus\Client\RequestOp...e::$defaultReceivedFrom has been deprecated with message: This is a workaround until we can decide on what happens with RF elements for the next major version.

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
170
            $params->receivedFrom
171
        );
172
    }
173
174
    /**
175
     * Load Segment itinerary
176
     *
177
     * @param Itinerary[] $itineraries
178
     * @param Segment[] $legacySegments
179
     * @param int $tattooCounter (BYREF)
180
     * @throws \ReflectionException
181
     */
182
    protected function addItineraries($itineraries, $legacySegments, &$tattooCounter)
183
    {
184
        if (!empty($legacySegments)) {
185
            $this->addSegments($legacySegments, $tattooCounter);
186
        }
187
188
        foreach ($itineraries as $itinerary) {
189
            $this->addSegments(
190
                $itinerary->segments,
191
                $tattooCounter,
192
                $itinerary->origin,
193
                $itinerary->destination
194
            );
195
        }
196
    }
197
198
    /**
199
     * @param Segment[] $segments
200
     * @param int $tattooCounter
201
     * @param string|null $origin
202
     * @param string|null $destination
203
     * @throws \ReflectionException
204
     */
205
    protected function addSegments($segments, &$tattooCounter, $origin = null, $destination = null)
206
    {
207
        $tmpOrigDest = new OriginDestinationDetails();
208
209
        foreach ($segments as $segment) {
210
            $tmpOrigDest->itineraryInfo[] = $this->createSegment($segment, $tattooCounter);
211
        }
212
213
        if (!is_null($origin) && !is_null($destination)) {
214
            $tmpOrigDest->originDestination = new OriginDestination($origin, $destination);
215
        }
216
217
        $this->originDestinationDetails[] = $tmpOrigDest;
218
    }
219
220
    /**
221
     * @param Segment $segment
222
     * @param int $tattooCounter (BYREF)
223
     * @return ItineraryInfo
224
     * @throws \ReflectionException
225
     */
226
    protected function createSegment($segment, &$tattooCounter)
227
    {
228
        $createdSegment = null;
0 ignored issues
show
Unused Code introduced by
$createdSegment 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...
229
230
        $tattooCounter++;
231
232
        $reflect = new \ReflectionClass($segment);
233
        $segmentType = $reflect->getShortName();
234
235
        switch ($segmentType) {
236 View Code Duplication
            case 'Miscellaneous':
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...
237
                /** @var Segment\Miscellaneous $segment */
238
                $createdSegment = new ItineraryInfo($tattooCounter, ElementManagementItinerary::SEGMENT_MISCELLANEOUS);
239
                $createdSegment->airAuxItinerary = new AirAuxItinerary($segmentType, $segment);
240
                break;
241
            case 'Air':
242
                /** @var Segment\Air $segment */
243
                $createdSegment = new ItineraryInfo($tattooCounter, ElementManagementItinerary::SEGMENT_AIR);
244
                $createdSegment->airAuxItinerary = new AirAuxItinerary($segmentType, $segment);
245
                break;
246 View Code Duplication
            case 'ArrivalUnknown':
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...
247
                /** @var Segment\ArrivalUnknown $segment */
248
                $createdSegment = new ItineraryInfo($tattooCounter, ElementManagementItinerary::SEGMENT_AIR);
249
                $createdSegment->airAuxItinerary = new AirAuxItinerary($segmentType, $segment);
250
                break;
251
            case 'Ghost':
252
                throw new \RuntimeException('NOT YET IMPLEMENTED');
253
                break;
0 ignored issues
show
Unused Code introduced by
break; does not seem to be reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
254
            default:
255
                throw new InvalidArgumentException('Segment type '.$segmentType.' is not supported');
256
                break;
0 ignored issues
show
Unused Code introduced by
break; does not seem to be reachable.

This check looks for unreachable code. It uses sophisticated control flow analysis techniques to find statements which will never be executed.

Unreachable code is most often the result of return, die or exit statements that have been added for debug purposes.

function fx() {
    try {
        doSomething();
        return true;
    }
    catch (\Exception $e) {
        return false;
    }

    return false;
}

In the above example, the last return false will never be executed, because a return statement has already been met in every possible execution path.

Loading history...
257
        }
258
259
        if (count($segment->references) > 0) {
260
            $createdSegment->referenceForSegment = new ReferenceForSegment();
261
            foreach ($segment->references as $singleRef) {
262
                $createdSegment->referenceForSegment->reference[] = new Reference($singleRef->type, $singleRef->id);
263
            }
264
        }
265
266
        return $createdSegment;
267
    }
268
269
270
    /**
271
     * @param Traveller[] $travellers
272
     */
273
    protected function addTravellers($travellers)
274
    {
275
        foreach ($travellers as $traveller) {
276
            $this->travellerInfo[] = $this->createTraveller($traveller);
277
        }
278
    }
279
280
    /**
281
     * @param Traveller $traveller
282
     * @return TravellerInfo
283
     */
284
    protected function createTraveller($traveller)
285
    {
286
        return new TravellerInfo($traveller);
287
    }
288
289
    /**
290
     * @param TravellerGroup $group
291
     */
292
    protected function addTravellerGroup($group)
293
    {
294
        $this->travellerInfo[] = new TravellerInfo(null, $group);
295
296
        $this->addTravellers($group->travellers);
297
    }
298
299
    /**
300
     * @param Element[] $elements
301
     * @param int $tattooCounter (BYREF)
302
     * @param bool $autoAddRf
303
     * @param string|null $defaultRf
304
     * @param string|null $explicitRf
305
     * @throws \ReflectionException
306
     */
307
    protected function addElements($elements, &$tattooCounter, $autoAddRf, $defaultRf, $explicitRf = null)
308
    {
309
        if ($this->dataElementsMaster === null) {
310
            $this->dataElementsMaster = new DataElementsMaster();
311
        }
312
313
        //Only add a default RF element if there is no explicitly provided RF element!
314
        $hasReceivedFromElement = false;
315
316
        foreach ($elements as $element) {
317
            if ($element instanceof Element) {
318
                $this->dataElementsMaster->dataElementsIndiv[] = $this->createElement(
319
                    $element,
320
                    $tattooCounter
321
                );
322
            }
323
324
            if ($element instanceof ReceivedFrom) {
325
                $hasReceivedFromElement = true;
326
            }
327
        }
328
329
        if (!$hasReceivedFromElement) {
330
            $this->addReceivedFrom(
331
                $explicitRf,
332
                $autoAddRf,
333
                $defaultRf,
334
                $tattooCounter
335
            );
336
        }
337
    }
338
339
    /**
340
     * @param Element $element
341
     * @param int $tattooCounter (BYREF)
342
     * @throws InvalidArgumentException
343
     * @return DataElementsIndiv
344
     * @throws \ReflectionException
345
     */
346
    protected function createElement($element, &$tattooCounter)
347
    {
348
        $createdElement = null;
0 ignored issues
show
Unused Code introduced by
$createdElement 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...
349
350
        $tattooCounter++;
351
352
        $createdElement = new DataElementsIndiv($element, $tattooCounter);
353
354
        if (!empty($element->references)) {
355
            $createdElement->referenceForDataElement = new ReferenceForDataElement($element->references);
356
        }
357
358
        return $createdElement;
359
    }
360
361
    /**
362
     * Add Received From field - if needed.
363
     *
364
     * @param string|null $explicitRf Explicitly provided RF string on request.
365
     * @param bool $doAutoAdd Wether to automatically add an RF field.
366
     * @param string|null $defaultRf The default RF string set in the client.
367
     * @param int $tattooCounter (BYREF)
368
     * @throws \ReflectionException
369
     */
370
    protected function addReceivedFrom($explicitRf, $doAutoAdd, $defaultRf, &$tattooCounter)
371
    {
372
        if ($this->dataElementsMaster === null) {
373
            $this->dataElementsMaster = new DataElementsMaster();
374
        }
375
376
        if (!empty($explicitRf) || ($doAutoAdd && !empty($defaultRf))) {
377
            //Set a received from if explicitly provided or if auto received from is enabled
378
379
            $tattooCounter++;
380
381
            $rfToAdd = (!empty($explicitRf)) ? $explicitRf : $defaultRf;
382
383
            $this->dataElementsMaster->dataElementsIndiv[] = $this->createElement(
384
                new ReceivedFrom(['receivedFrom' => $rfToAdd]),
385
                $tattooCounter
386
            );
387
        }
388
    }
389
}
390