Issues (2)

src/Offer.php (1 issue)

Labels
Severity
1
<?php
2
3
namespace TPG\Pcflib;
4
5
use TPG\Pcflib\Categories\Category;
6
use TPG\Pcflib\Contracts\Arrayable;
7
use TPG\Pcflib\Traits\Collectable;
8
use TPG\Pcflib\Traits\HasAttributes;
9
10
/**
11
 * Class Offer
12
 * @package TPG\Pcflib
13
 */
14
class Offer implements Arrayable
15
{
16
    use HasAttributes, Collectable;
17
18
    const CONTRACT_PERIOD_MONTHS = 'Months';
19
    const CONTRACT_PERIOD_WEEKS = 'Weeks';
20
    const CONTRACT_PERIOD_DAYS = 'Days';
21
22
    const AVAILABILITY_IN_STOCK = 'In Stock';
23
    const AVAILABILITY_OUT_OF_STOCK = 'Out of Stock';
24
25
    const ORDERED_FROM_SUPPLIER = -1;
26
27
    const UNIT_MEASURE_ML = 'ml';
28
    const UNIT_MEASURE_L = 'l';
29
    const UNIT_MEASURE_KL = 'kl';
30
    const UNIT_MEASURE_MM = 'mm';
31
    const UNIT_MEASURE_CM = 'cm';
32
    const UNIT_MEASURE_M = 'm';
33
34
    /**
35
     * The text fields that need to be wrapped in CDATA when exporting to XML.
36
     *
37
     * @var array
38
     */
39
    protected $textFields = [
40
        'Category',
41
        'ProductName',
42
        'Manufacturer',
43
        'ShopSKU',
44
        'ModelNumber',
45
        'Description',
46
        'ProductURL',
47
        'ImageURL',
48
        'Notes',
49
        'StockAvailability',
50
        'GroupID',
51
    ];
52
53
    /**
54
     * Second Hand product
55
     *
56
     * @var bool
57
     */
58
    protected $secondHand = false;
59
60
    /**
61
     * Set the category signature
62
     *
63
     * @param array $categories
64
     */
65
    protected function setCategorySignature(array $categories)
66
    {
67
        $this->attributes['Category'] = implode(' > ', $categories);
68
    }
69
70
    /**
71
     * Offer constructor.
72
     *
73
     * @param array $categorySignature
74
     * @param Category|null $categoryAttributes
75
     */
76
    public function __construct(array $categorySignature = null, Category $categoryAttributes = null)
77
    {
78
        $this->requiredAttributes = [
79
            'Category',
80
            'Price',
81
            'ProductName',
82
            'Manufacturer',
83
            'ShopSKU',
84
        ];
85
86
        $this->attributes['Category'] = null;
87
88
        if ($categorySignature) {
89
90
            $this->setCategorySignature($categorySignature);
91
        }
92
93
        $this->attributes['Attributes'] = $categoryAttributes ? $categoryAttributes->toArray() : null;
94
    }
95
96
    /**
97
     * Fill with attributes
98
     *
99
     * @param array $attributes
100
     * @return $this
101
     */
102
    public function fill(array $attributes)
103
    {
104
        $this->attributes = array_map(function ($attributes) {
105
            return strip_tags($attributes);
106
        }, $attributes);
107
        return $this;
108
    }
109
110
    /**
111
     * Set category details
112
     *
113
     * @param array $signature
114
     * @param Category $attributes
115
     * @return $this
116
     */
117
    public function category(array $signature, Category $attributes = null): Offer
118
    {
119
        $this->setCategorySignature($signature);
120
121
        $this->attributes['Attributes'] = $attributes ? $attributes->toArray() : (
122
            $this->attributes['Attributes'] ?? null
123
        );
124
125
        return $this;
126
    }
127
128
    /**
129
     * Set product name
130
     *
131
     * @param string $name
132
     * @return Offer
133
     */
134
    public function name(string $name): Offer
135
    {
136
        $this->attributes['ProductName'] = strip_tags($name);
137
138
        return $this;
139
    }
140
141
    /**
142
     * Set manufacturer
143
     *
144
     * @param string $manufacturer
145
     * @return Offer
146
     */
147
    public function manufacturer(string $manufacturer): Offer
148
    {
149
        $this->attributes['Manufacturer'] = strip_tags($manufacturer);
150
151
        return $this;
152
    }
153
154
    /**
155
     * Set shop SKU
156
     *
157
     * @param string $sku
158
     * @return Offer
159
     */
160
    public function sku(string $sku): Offer
161
    {
162
        $this->attributes['ShopSKU'] = strip_tags($sku);
163
        return $this;
164
    }
165
166
    /**
167
     * Set description
168
     *
169
     * @param string $description
170
     * @return Offer
171
     */
172
    public function description(string $description): Offer
173
    {
174
        $this->attributes['Description'] = strip_tags($description);
175
176
        return $this;
177
    }
178
179
    /**
180
     * Set EAN
181
     *
182
     * @param string $ean
183
     * @return Offer
184
     */
185
    public function ean(string $ean): Offer
186
    {
187
        $this->attributes['EAN'] = strip_tags($ean);
188
        return $this;
189
    }
190
191
    /**
192
     * Set UPC
193
     *
194
     * @param string $upc
195
     * @return Offer
196
     */
197
    public function upc(string $upc): Offer
198
    {
199
        $this->attributes['UPC'] = strip_tags($upc);
200
        return $this;
201
    }
202
203
    /**
204
     * Set the product pricing
205
     *
206
     * @param float $price
207
     * @param float|null $salePrice
208
     * @param float|null $deliveryCost
209
     * @return Offer
210
     */
211
    public function price(float $price, float $salePrice = null, float $deliveryCost = null): Offer
212
    {
213
        $this->attributes['Price'] = $price;
214
215
        if ($salePrice) {
216
            $this->salesPrice($salePrice);
217
        }
218
219
        if ($deliveryCost) {
220
            $this->deliveryCost($deliveryCost);
221
        }
222
223
        return $this;
224
    }
225
226
    /**
227
     * Set the sales price
228
     *
229
     * @param float $salePrice
230
     * @return Offer
231
     */
232
    public function salesPrice(float $salePrice): Offer
233
    {
234
        $this->attributes['SalePrice'] = $salePrice;
235
        return $this;
236
    }
237
238
    /**
239
     * Set the delivery cost
240
     *
241
     * @param float $deliveryCost
242
     * @return Offer
243
     */
244
    public function deliveryCost(float $deliveryCost): Offer
245
    {
246
        $this->attributes['DeliveryCost'] = $deliveryCost;
247
        return $this;
248
    }
249
250
    /**
251
     * @param float $cash
252
     * @param int $periodLength
253
     * @param string $periodType
254
     * @return Offer
255
     */
256
    public function contractPricing(float $cash, int $periodLength, string $periodType = self::CONTRACT_PERIOD_MONTHS): Offer
257
    {
258
        $this->attributes['ContractPricing'] = [
259
            'CashComponent' => $cash,
260
            'PeriodLength' => $periodLength,
261
            'PeriodType' => strip_tags($periodType)
262
        ];
263
        return $this;
264
    }
265
266
    /**
267
     * Set model number
268
     *
269
     * @param string $modelNumber
270
     * @return Offer
271
     */
272
    public function modelNumber(string $modelNumber): Offer
273
    {
274
        $this->attributes['ModelNumber'] = strip_tags($modelNumber);
275
        return $this;
276
    }
277
278
    /**
279
     * Set stock availabilities
280
     *
281
     * @param string|null $stockAvailability
282
     * @param int|null $stockLevel
283
     * @return Offer
284
     */
285
    public function availability(string $stockAvailability = null, int $stockLevel = null)
286
    {
287
        $this->attributes['StockAvailability'] = $stockAvailability;
288
        $this->attributes['StockLevel'] = $stockLevel;
289
        return $this;
290
    }
291
292
    /**
293
     * Set the product URL
294
     *
295
     * @param string $url
296
     * @return Offer
297
     */
298
    public function productUrl(string $url): Offer
299
    {
300
        $this->attributes['ProductURL'] = strip_tags($url);
301
        return $this;
302
    }
303
304
    /**
305
     * Set the product image URL
306
     *
307
     * @param string $url
308
     * @return Offer
309
     */
310
    public function imageUrl(string $url): Offer
311
    {
312
        $this->attributes['ImageURL'] = strip_tags($url);
313
        return $this;
314
    }
315
316
    /**
317
     * Set a product as second hand
318
     *
319
     * @param bool $secondHand
320
     * @return Offer
321
     */
322
    public function secondHand($secondHand = true): Offer
323
    {
324
        $this->secondHand = $secondHand;
325
        return $this;
326
    }
327
328
    /**
329
     * Set the product notes
330
     *
331
     * @param string $notes
332
     * @return Offer
333
     */
334
    public function notes(string $notes): Offer
335
    {
336
        $this->attributes['Notes'] = strip_tags($notes) . ($this->secondHand ? ' SecondHand' : null);
337
        return $this;
338
    }
339
340
    /**
341
     * Set this offer on the marketplace
342
     *
343
     * @param bool $marketplace
344
     * @return Offer
345
     */
346
    public function marketplace($marketplace = true): Offer
347
    {
348
        $this->attributes['Marketplace'] = $marketplace ? '1' : null;
349
        return $this;
350
    }
351
352
    /**
353
     * @param bool $bundle
354
     * @return Offer
355
     */
356
    public function bundle($bundle = true): Offer
357
    {
358
        $this->attributes['Bundle'] = $bundle ? '1' : null;
359
        return $this;
360
    }
361
362
    /**
363
     * @param $groupId
364
     * @return Offer
365
     */
366
    public function groupId($groupId): Offer
367
    {
368
        $this->attributes['GroupID'] = $groupId;
369
        return $this;
370
    }
371
372
    /**
373
     * Set the number of units and their size
374
     *
375
     * @param int $count
376
     * @param int $unit
377
     * @param string $measure
378
     * @return $this
379
     */
380
    public function units(int $count, int $unit, string $measure)
381
    {
382
        $this->attributes['NoOfUnits'] = $count;
383
384
        $this->attributes['UnitMeasure'] = [
385
            'Unit' => $unit,
386
            'Measure' => strip_tags($measure)
387
        ];
388
        return $this;
389
    }
390
391
    /**
392
     * Delete this Offer from the parent collection
393
     */
394
    public function delete()
395
    {
396
        if ($this->parent && array_key_exists('ShopSKU', $this->attributes)) {
397
398
            $this->parent->delete($this->attributes['ShopSKU']);
399
        }
400
    }
401
402
    /**
403
     * Output an array
404
     *
405
     * @return array
406
     */
407
    public function toArray(): array
408
    {
409
        return array_filter($this->attributes, function ($attribute) {
410
            return $attribute ? true : false;
411
        });
412
    }
413
414
    /**
415
     * Add attributes to the XML node
416
     *
417
     * @param \DOMNode $node
418
     * @param array|null $attributes
419
     * @return void
420
     */
421
    protected function addAttributesToXmlElement(\DOMNode $node, array $attributes = null)
422
    {
423
        foreach ($attributes as $key => $value) {
424
425
            if ($value) {
426
427
                $offerNode = new \DOMElement($key);
0 ignored issues
show
The call to DOMElement::__construct() has too few arguments starting with value. ( Ignorable by Annotation )

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

427
                $offerNode = /** @scrutinizer ignore-call */ new \DOMElement($key);

This check compares calls to functions or methods with their respective definitions. If the call has less 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. Please note the @ignore annotation hint above.

Loading history...
428
429
                $node->appendChild($offerNode);
430
431
                if (is_array($value)) {
432
                    $this->addAttributesToXmlElement($offerNode, $value);
433
                } else {
434
435
                    if (in_array($key, $this->textFields)) {
436
437
                        $value = $node->ownerDocument->createCDATASection($value);
438
                        $offerNode->appendChild($value);
439
                    } else {
440
441
                        $offerNode->textContent = $value;
442
                    }
443
444
                    $node->appendChild($offerNode);
445
                }
446
            }
447
        }
448
    }
449
450
    /**
451
     * @param \DOMNode $node
452
     * @return void
453
     * @throws Exceptions\MissingRequiredAttribute
454
     */
455
    public function toXmlNode(\DOMNode $node) {
456
        $this->verifyAttributes();
457
        $this->addAttributesToXmlElement($node, $this->attributes);
458
    }
459
}
460