BaseEntity::getRawBase()   F
last analyzed

Complexity

Conditions 18
Paths 1536

Size

Total Lines 65
Code Lines 45

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 45
dl 0
loc 65
rs 0.7
c 0
b 0
f 0
cc 18
nc 1536
nop 1

How to fix   Long Method    Complexity   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
/**
3
 * Created by PhpStorm.
4
 * User: DrillCoder
5
 * Date: 12.09.17
6
 * Time: 11:55
7
 */
8
9
namespace DrillCoder\AmoCRM_Wrap;
10
11
use CURLFile;
12
use DateTime;
13
use DrillCoder\AmoCRM_Wrap\Helpers\Config;
14
use DrillCoder\AmoCRM_Wrap\Helpers\CustomField;
15
use DrillCoder\AmoCRM_Wrap\Helpers\Value;
16
use Exception;
17
use stdClass;
18
19
/**
20
 * Class Base
21
 * @package DrillCoder\AmoCRM_Wrap
22
 */
23
abstract class BaseEntity extends Base
24
{
25
    /**
26
     * @var string
27
     */
28
    protected $elementId;
29
30
    /**
31
     * @var int
32
     */
33
    protected $elementType;
34
35
    /**
36
     * @var string
37
     */
38
    protected $text;
39
40
    /**
41
     * @var string
42
     */
43
    private $id;
44
45
    /**
46
     * @var string
47
     */
48
    private $name;
49
50
    /**
51
     * @var Value[]
52
     */
53
    private $phones = array();
54
55
    /**
56
     * @var Value[]
57
     */
58
    private $emails = array();
59
60
    /**
61
     * @var string
62
     */
63
    protected $createdUserId;
64
65
    /**
66
     * @var DateTime
67
     */
68
    private $dateCreate;
69
70
    /**
71
     * @var DateTime
72
     */
73
    private $dateUpdate;
74
75
    /**
76
     * @var string
77
     */
78
    private $userIdUpdate;
79
80
    /**
81
     * @var string
82
     */
83
    private $responsibleUserId;
84
85
    /**
86
     * @var string
87
     */
88
    private $companyId;
89
90
    /**
91
     * @var int[]
92
     */
93
    private $leadsId = array();
94
95
    /**
96
     * @var int[]
97
     */
98
    private $contactsId = array();
99
100
    /**
101
     * @var string[]
102
     */
103
    private $tags = array();
104
105
    /**
106
     * @var CustomField[]
107
     */
108
    private $customFields = array();
109
110
    /**
111
     * @var int|string
112
     */
113
    protected $type;
114
115
    /**
116
     * @var array
117
     */
118
    private $unlink = array();
119
120
    /**
121
     * @var array
122
     */
123
    protected $config;
124
125
    /**
126
     * @param int|string|null $id
127
     *
128
     * @throws AmoWrapException
129
     */
130
    public function __construct($id = null)
131
    {
132
        if (!AmoCRM::isAuthorization()) {
133
            throw new AmoWrapException('Требуется авторизация');
134
        }
135
136
        $classNameArray = explode('\\', get_class($this));
137
        $className = mb_strtolower(array_pop($classNameArray));
138
        $this->config = Config::$$className;
139
140
        if ($id !== null) {
141
            $id = Base::onlyNumbers($id);
142
            $this->load($id);
0 ignored issues
show
Bug introduced by
$id of type string is incompatible with the type integer expected by parameter $id of DrillCoder\AmoCRM_Wrap\BaseEntity::load(). ( Ignorable by Annotation )

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

142
            $this->load(/** @scrutinizer ignore-type */ $id);
Loading history...
143
        }
144
    }
145
146
    /**
147
     * @param stdClass|array $data
148
     *
149
     * @throws AmoWrapException
150
     */
151
    public function loadInRaw($data)
152
    {
153
        try {
154
            $data = json_decode(json_encode($data));
155
            if (!empty($data->id)) {
156
                $this->id = Base::onlyNumbers($data->id);
157
                $this->name = isset($data->name) ? $data->name : null;
158
                $this->createdUserId = isset($data->created_by) ? Base::onlyNumbers($data->created_by) : null;
159
                $dateCreate = new DateTime();
160
                $dateCreate->setTimestamp($data->created_at);
161
                $this->dateCreate = $dateCreate;
162
                $dateUpdate = new DateTime();
163
                $dateUpdate->setTimestamp($data->updated_at);
164
                $this->dateUpdate = $dateUpdate;
165
                $this->responsibleUserId = isset($data->responsible_user_id) ?
166
                    Base::onlyNumbers($data->responsible_user_id) : null;
167
                $this->userIdUpdate = isset($data->updated_by) ? Base::onlyNumbers($data->updated_by) : null;
168
                $this->companyId = isset($data->company->id) ? Base::onlyNumbers($data->company->id) : null;
169
                $this->leadsId = isset($data->leads->id) ? $data->leads->id : array();
170
                $this->contactsId = isset($data->contacts->id) ? $data->contacts->id : array();
171
                $this->type = isset($data->note_type) ? (int)$data->note_type : null;
172
                $this->elementId = isset($data->element_id) ? Base::onlyNumbers($data->element_id) : null;
173
                $this->elementType = isset($data->element_type) ? (int)$data->element_type : null;
174
                $this->text = isset($data->text) ? $data->text : null;
175
176
                if (isset($data->tags) && is_array($data->tags)) {
177
                    foreach ($data->tags as $tag) {
178
                        $this->tags[$tag->id] = $tag->name;
179
                    }
180
                }
181
                if (isset($data->custom_fields) && is_array($data->custom_fields)) {
182
                    foreach ($data->custom_fields as $custom_field) {
183
                        $customField = CustomField::loadInRaw($custom_field);
184
                        if ($customField->getId() === AmoCRM::getPhoneFieldId()) {
185
                            $this->phones = $customField->getValues();
186
                        } elseif ($customField->getId() === AmoCRM::getEmailFieldId()) {
187
                            $this->emails = $customField->getValues();
188
                        } else {
189
                            $this->customFields[$customField->getId()] = $customField;
190
                        }
191
                    }
192
                }
193
            } else {
194
                throw new AmoWrapException('Не удалось загрузить сущность из сырых данных');
195
            }
196
        } catch (Exception $e) {
197
            throw new AmoWrapException("Ошибка в обёртке: {$e->getMessage()}", $e->getCode(), $e);
198
        }
199
    }
200
201
    /**
202
     * @return array
203
     */
204
    public function getRaw()
205
    {
206
        return $this->getRawBase($this->getExtraRaw());
207
    }
208
209
    /**
210
     * @return Company|Contact|Lead|Note|Task
211
     *
212
     * @throws AmoWrapException
213
     */
214
    public function save()
215
    {
216
        return $this->saveBase($this->getExtraRaw());
217
    }
218
219
    /**
220
     * @return BaseEntity|Company|Contact|Lead|Note|Task
221
     *
222
     * @throws AmoWrapException
223
     */
224
    public function delete()
225
    {
226
        $url = "ajax/{$this->config['delete']}/multiple/delete/";
227
        $post = array('ACTION' => 'DELETE', 'ID[]' => $this->id);
228
229
        $res = AmoCRM::cUrl($url, http_build_query($post), null, true);
0 ignored issues
show
Bug introduced by
http_build_query($post) of type string is incompatible with the type array expected by parameter $data of DrillCoder\AmoCRM_Wrap\Base::cUrl(). ( Ignorable by Annotation )

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

229
        $res = AmoCRM::cUrl($url, /** @scrutinizer ignore-type */ http_build_query($post), null, true);
Loading history...
230
        if ($res !== null && $res->status === 'success') {
231
            foreach ($this as $key => $item) {
232
                $this->$key = null;
233
            }
234
235
            return $this;
236
        }
237
238
        throw new AmoWrapException('Не удалось удалить сущность');
239
    }
240
241
    /**
242
     * @return string
243
     */
244
    public function getId()
245
    {
246
        return $this->id;
247
    }
248
249
    /**
250
     * @return string
251
     */
252
    public function getName()
253
    {
254
        return $this->name;
255
    }
256
257
    /**
258
     * @param string $name
259
     *
260
     * @return BaseEntity|Company|Contact|Lead
261
     */
262
    public function setName($name)
263
    {
264
        $this->name = $name;
265
        return $this;
266
    }
267
268
    /**
269
     * @return string
270
     */
271
    public function getResponsibleUserId()
272
    {
273
        return $this->responsibleUserId;
274
    }
275
276
    /**
277
     * @return string
278
     */
279
    public function getResponsibleUserName()
280
    {
281
        $usersIdAndName = AmoCRM::getUsers();
282
        return $usersIdAndName[$this->responsibleUserId];
283
    }
284
285
    /**
286
     * @param int|string $responsibleUserIdOrName
287
     *
288
     * @return BaseEntity|Company|Contact|Lead|Task
289
     *
290
     * @throws AmoWrapException
291
     */
292
    public function setResponsibleUser($responsibleUserIdOrName)
293
    {
294
        $this->responsibleUserId = AmoCRM::searchUserId($responsibleUserIdOrName);
295
296
        return $this;
297
    }
298
299
    /**
300
     * @return int
301
     */
302
    public function getCompanyId()
303
    {
304
        return $this->companyId;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $this->companyId returns the type string which is incompatible with the documented return type integer.
Loading history...
305
    }
306
307
    /**
308
     * @return Company
309
     *
310
     * @throws AmoWrapException
311
     */
312
    public function getCompany()
313
    {
314
        return new Company($this->companyId);
315
    }
316
317
    /**
318
     * @param Company $company
319
     *
320
     * @return BaseEntity|Contact|Lead
321
     */
322
    public function setCompany($company)
323
    {
324
        $id = $company instanceof Company ? $company->getId() : Base::onlyNumbers($company);
0 ignored issues
show
introduced by
$company is always a sub-type of DrillCoder\AmoCRM_Wrap\Company.
Loading history...
325
        $this->companyId = $id;
326
327
        return $this;
328
    }
329
330
    /**
331
     * @return string[]
332
     */
333
    public function getTags()
334
    {
335
        return $this->tags;
336
    }
337
338
    /**
339
     * @param string $tag
340
     *
341
     * @return BaseEntity|Company|Contact|Lead
342
     */
343
    public function addTag($tag)
344
    {
345
        $this->tags[] = $tag;
346
347
        return $this;
348
    }
349
350
    /**
351
     * @param string $tag
352
     *
353
     * @return BaseEntity|Company|Contact|Lead
354
     *
355
     * @throws AmoWrapException
356
     */
357
    public function delTag($tag)
358
    {
359
        $key = array_search($tag, $this->tags);
360
        if ($key !== false) {
361
            unset($this->tags[$key]);
362
363
            return $this;
364
        }
365
366
        throw new AmoWrapException('Тэг не найден');
367
    }
368
369
    /**
370
     * @param string $name
371
     * @param int    $type
372
     * @param array  $enums
373
     *
374
     * @return int
375
     *
376
     * @throws AmoWrapException
377
     */
378
    public function addCustomField($name, $type = CustomField::TYPE_TEXT, $enums = array())
379
    {
380
        if (!is_array($enums)) {
0 ignored issues
show
introduced by
The condition is_array($enums) is always true.
Loading history...
381
            $enums = array($enums);
382
        }
383
        $elementType = $this->config['elementType'];
384
        $data['request']['fields']['add'] = array(
0 ignored issues
show
Comprehensibility Best Practice introduced by
$data was never initialized. Although not strictly required by PHP, it is generally a good practice to add $data = array(); before regardless.
Loading history...
385
            array(
386
                'name' => $name,
387
                'type' => $type,
388
                'enums' => $enums,
389
                'element_type' => $elementType,
390
                'origin' => 'DrillCoder AmoCRM Wrap',
391
                'disabled' => false,
392
            )
393
        );
394
        $res = AmoCRM::cUrl('private/api/v2/json/fields/set', $data);
395
        if ($res !== null && isset($res->response->fields->add[0]->id)) {
396
            return $res->response->fields->add[0]->id;
397
        }
398
399
        throw new AmoWrapException('Не удалось добавить пользовательское поле');
400
    }
401
402
    /**
403
     * @param int|string $nameOrId
404
     *
405
     * @return BaseEntity|Company|Contact|Lead
406
     *
407
     * @throws AmoWrapException
408
     */
409
    public function delCustomField($nameOrId)
410
    {
411
        $id = $this->searchCustomFieldsId($nameOrId);
412
413
        $data['request']['fields']['delete'] = array(
0 ignored issues
show
Comprehensibility Best Practice introduced by
$data was never initialized. Although not strictly required by PHP, it is generally a good practice to add $data = array(); before regardless.
Loading history...
414
            array(
415
                'id' => $id,
416
                'origin' => 'DrillCoder AmoCRM Wrap'
417
            )
418
        );
419
        $res = AmoCRM::cUrl('private/api/v2/json/fields/set', $data);
420
        if ($res !== null && isset($res->response->fields->delete[0]->id) && $res->response->fields->delete[0]->id === $id) {
421
            return $this;
422
        }
423
424
        throw new AmoWrapException('Не удалось удалить пользовательское поле');
425
    }
426
427
    /**
428
     * @param string|int $nameOrId
429
     *
430
     * @return string
431
     *
432
     * @throws AmoWrapException
433
     */
434
    public function getCustomFieldValueInStr($nameOrId)
435
    {
436
        return $this->getCustomField($nameOrId)->getValuesInStr();
437
    }
438
439
    /**
440
     * @param string|int $nameOrId
441
     *
442
     * @return string[]
443
     *
444
     * @throws AmoWrapException
445
     */
446
    public function getCustomFieldValueInArray($nameOrId)
447
    {
448
        return $this->getCustomField($nameOrId)->getValuesInArray();
449
    }
450
451
    /**
452
     * @param string|int   $nameOrId
453
     * @param string|array $values
454
     * @param int|null     $subtype
455
     *
456
     * @return BaseEntity|Company|Contact|Lead
457
     *
458
     * @throws AmoWrapException
459
     */
460
    public function setCustomFieldValue($nameOrId, $values, $subtype = null)
461
    {
462
        $customField = $this->getCustomField($nameOrId);
463
        if (!is_array($values)) {
464
            $values = array($values);
465
        }
466
467
        if ($subtype !== null) {
468
            $valueObj = $customField->getValues();
469
        } else {
470
            $valueObj = array();
471
        }
472
473
        foreach ($values as $value) {
474
            $value = trim($value);
475
            $customFieldsEnums = $this->getEnums($customField->getId());
476
            $enum = null;
477
            foreach ($customFieldsEnums as $enumId => $enumName) {
478
                if (mb_stripos($enumName, $value) !== false) {
479
                    $enum = $enumId;
480
                }
481
            }
482
            $valueObj[] = new Value($value, $enum, $subtype);
483
        }
484
        $customField->setValues($valueObj);
485
486
        return $this;
487
    }
488
489
    /**
490
     * @return string
491
     */
492
    public function getElementId()
493
    {
494
        return $this->elementId;
495
    }
496
497
    /**
498
     * @param string $elementId
499
     *
500
     * @return BaseEntity|Note|Task
501
     */
502
    public function setElementId($elementId)
503
    {
504
        $this->elementId = Base::onlyNumbers($elementId);
505
506
        return $this;
507
    }
508
509
    /**
510
     * @return int
511
     */
512
    public function getElementType()
513
    {
514
        return $this->elementType;
515
    }
516
517
    /**
518
     * @param int $elementType
519
     *
520
     * @return BaseEntity|Note|Task
521
     */
522
    public function setElementType($elementType)
523
    {
524
        $this->elementType = (int)$elementType;
525
526
        return $this;
527
    }
528
529
    /**
530
     * @return string
531
     */
532
    public function getText()
533
    {
534
        return $this->text;
535
    }
536
537
    /**
538
     * @param string $text
539
     *
540
     * @return BaseEntity|Note|Task
541
     */
542
    public function setText($text)
543
    {
544
        $this->text = $text;
545
546
        return $this;
547
    }
548
549
    /**
550
     * @return int|string
551
     */
552
    public function getType()
553
    {
554
        return $this->type;
555
    }
556
557
    /**
558
     * @param int|string $type
559
     *
560
     * @return BaseEntity|Note|Task
561
     */
562
    public function setType($type)
563
    {
564
        $this->type = $type;
565
566
        return $this;
567
    }
568
569
    /**
570
     * @return DateTime
571
     */
572
    public function getDateCreate()
573
    {
574
        return $this->dateCreate;
575
    }
576
577
    /**
578
     * @return DateTime
579
     */
580
    public function getDateUpdate()
581
    {
582
        return $this->dateUpdate;
583
    }
584
585
    /**
586
     * @return string
587
     */
588
    public function getUserIdUpdate()
589
    {
590
        return $this->userIdUpdate;
591
    }
592
593
    /**
594
     * @return string
595
     */
596
    public function getUserNameUpdate()
597
    {
598
        $users = AmoCRM::getUsers();
599
600
        return $users[$this->userIdUpdate];
601
    }
602
603
    /**
604
     * @return string
605
     */
606
    public function getCreatedUserId()
607
    {
608
        return $this->createdUserId;
609
    }
610
611
    /**
612
     * @return string
613
     */
614
    public function getCreatedUserName()
615
    {
616
        $users = AmoCRM::getUsers();
617
618
        return $users[$this->createdUserId];
619
    }
620
621
    /**
622
     * @return int[]
623
     */
624
    public function getLeadsId()
625
    {
626
        return $this->leadsId;
627
    }
628
629
    /**
630
     * @return Lead[]
631
     *
632
     * @throws AmoWrapException
633
     */
634
    public function getLeads()
635
    {
636
        $leads = array();
637
        foreach ($this->leadsId as $leadId) {
638
            $lead = new Lead($leadId);
639
            $leads[] = $lead;
640
        }
641
        return $leads;
642
    }
643
644
    /**
645
     * @param Lead|string|int $lead
646
     *
647
     * @return BaseEntity|Company|Contact
648
     */
649
    public function addLead($lead)
650
    {
651
        $id = $lead instanceof Lead ? $lead->getId() : Base::onlyNumbers($lead);
652
        $this->leadsId[] = $id;
653
654
        return $this;
655
    }
656
657
    /**
658
     * @param Lead|string|int $lead
659
     *
660
     * @return BaseEntity|Company|Contact
661
     *
662
     * @throws AmoWrapException
663
     */
664
    public function delLead($lead)
665
    {
666
        $id = $lead instanceof Lead ? $lead->getId() : Base::onlyNumbers($lead);
667
        $delKeys = array_keys($this->leadsId, $id);
668
        if (count($delKeys) > 0) {
669
            foreach ($delKeys as $delKey) {
670
                unset($this->leadsId[$delKey]);
671
            }
672
            $this->unlink['leads_id'][] = $id;
673
674
            return $this;
675
        }
676
677
        throw new AmoWrapException('Не найден id сделки');
678
    }
679
680
    /**
681
     * @return int[]
682
     */
683
    public function getContactsId()
684
    {
685
        return $this->contactsId;
686
    }
687
688
    /**
689
     * @return Contact[]
690
     *
691
     * @throws AmoWrapException
692
     */
693
    public function getContacts()
694
    {
695
        $contacts = array();
696
        foreach ($this->contactsId as $contactId) {
697
            $contact = new Contact($contactId);
698
            $contacts[] = $contact;
699
        }
700
        return $contacts;
701
    }
702
703
    /**
704
     * @param Contact|string|int $contact
705
     *
706
     * @return BaseEntity|Company|Lead
707
     */
708
    public function addContact($contact)
709
    {
710
        $id = $contact instanceof Contact ? $contact->getId() : Base::onlyNumbers($contact);
711
        $this->contactsId[] = $id;
712
713
        return $this;
714
    }
715
716
    /**
717
     * @param Contact|string|int $contact
718
     *
719
     * @return BaseEntity|Company|Lead
720
     *
721
     * @throws AmoWrapException
722
     */
723
    public function delContact($contact)
724
    {
725
        $id = $contact instanceof Contact ? $contact->getId() : Base::onlyNumbers($contact);
726
        $delKeys = array_keys($this->contactsId, $id);
727
        if (!empty($delKeys)) {
728
            foreach ($delKeys as $delKey) {
729
                unset($this->contactsId[$delKey]);
730
            }
731
            $this->unlink['contacts_id'][] = $id;
732
            return $this;
733
        }
734
        throw new AmoWrapException('Не найден id контакта');
735
    }
736
737
    /**
738
     * @return string[]
739
     */
740
    public function getPhones()
741
    {
742
        $phones = array();
743
        foreach ($this->phones as $value) {
744
            $phones[] = $value->getValue();
745
        }
746
        return $phones;
747
    }
748
749
    /**
750
     * @param string $phone
751
     * @param string $enum
752
     *
753
     * @return BaseEntity|Company|Contact
754
     *
755
     * @throws AmoWrapException
756
     */
757
    public function addPhone($phone, $enum = CustomField::PHONE_OTHER)
758
    {
759
        $enum = mb_strtoupper($enum);
760
        if (count($this->phones) > 0) {
761
            foreach ($this->phones as $value) {
762
                if (Base::onlyNumbers($value->getValue()) === Base::onlyNumbers($phone)) {
763
                    return $this;
764
                }
765
            }
766
        }
767
768
        $idPhoneEnums = AmoCRM::getPhoneEnums();
769
        if (isset($idPhoneEnums[$enum])) {
770
            $this->phones[] = new Value($phone, $idPhoneEnums[$enum]);
771
772
            return $this;
773
        }
774
775
        throw new AmoWrapException('Не удалось добавить телефон');
776
    }
777
778
    /**
779
     * @param string $phone
780
     *
781
     * @return BaseEntity|Company|Contact
782
     *
783
     * @throws AmoWrapException
784
     */
785
    public function delPhone($phone)
786
    {
787
        if (count($this->phones) > 0) {
788
            foreach ($this->phones as $key => $value) {
789
                if (AmoCRM::onlyNumbers($value->getValue()) === AmoCRM::onlyNumbers($phone)) {
790
                    unset($this->phones[$key]);
791
792
                    return $this;
793
                }
794
            }
795
        }
796
797
        throw new AmoWrapException('Не удалось удалить телефон');
798
    }
799
800
    /**
801
     * @return string[]
802
     */
803
    public function getEmails()
804
    {
805
        $emails = array();
806
        foreach ($this->emails as $value) {
807
            $emails[] = $value->getValue();
808
        }
809
        return $emails;
810
    }
811
812
    /**
813
     * @param string $email
814
     * @param string $enum
815
     *
816
     * @return BaseEntity|Company|Contact
817
     *
818
     * @throws AmoWrapException
819
     */
820
    public function addEmail($email, $enum = CustomField::EMAIL_OTHER)
821
    {
822
        $email = mb_strtolower($email);
823
        $enum = mb_strtoupper($enum);
824
        if (!empty($this->emails)) {
825
            foreach ($this->emails as $value) {
826
                if (mb_strtolower($value->getValue()) === $email) {
827
                    return $this;
828
                }
829
            }
830
        }
831
832
        $emailEnums = AmoCRM::getEmailEnums();
833
        if (isset($emailEnums[$enum])) {
834
            $this->emails[] = new Value($email, $emailEnums[$enum]);
835
836
            return $this;
837
        }
838
839
        throw new AmoWrapException('Не удалось добавить почту');
840
    }
841
842
    /**
843
     * @param string $email
844
     *
845
     * @return BaseEntity|Company|Contact
846
     *
847
     * @throws AmoWrapException
848
     */
849
    public function delEmail($email)
850
    {
851
        $email = mb_strtolower($email);
852
        if (!empty($this->emails)) {
853
            foreach ($this->emails as $key => $value) {
854
                if (mb_strtolower($value->getValue()) === $email) {
855
                    unset($this->emails[$key]);
856
857
                    return $this;
858
                }
859
            }
860
        }
861
862
        throw new AmoWrapException('Не удалось удалить почту');
863
    }
864
865
    /**
866
     * @param string $text
867
     *
868
     * @return BaseEntity|Company|Contact|Lead
869
     *
870
     * @throws AmoWrapException
871
     */
872
    public function addNote($text)
873
    {
874
        if ($this->id === null) {
875
            $this->save();
876
        }
877
878
        $note = new Note();
879
        $note->setText($text)
880
            ->setType(4)
881
            ->setElementId($this->id)
882
            ->setElementType($this->config['elementType'])
883
            ->save();
884
885
        return $this;
886
    }
887
888
    /**
889
     * @param string $text
890
     * @param string $serviceName
891
     *
892
     * @return BaseEntity|Company|Contact|Lead
893
     *
894
     * @throws AmoWrapException
895
     */
896
    public function addNoteSystem($text, $serviceName)
897
    {
898
        if ($this->id === null) {
899
            $this->save();
900
        }
901
902
        $note = new Note();
903
        $note->setText($text)
904
            ->setType(25)
905
            ->setService($serviceName)
906
            ->setElementId($this->id)
907
            ->setElementType($this->config['elementType'])
908
            ->save();
909
910
        return $this;
911
    }
912
913
    /**
914
     * @param string $text
915
     * @param string $phone
916
     *
917
     * @return BaseEntity|Company|Contact|Lead
918
     *
919
     * @throws AmoWrapException
920
     */
921
    public function addNoteSmsOut($text, $phone)
922
    {
923
        if ($this->id === null) {
924
            $this->save();
925
        }
926
927
        $note = new Note();
928
        $note->setText($text)
929
            ->setType(103)
930
            ->setPhone($phone)
931
            ->setElementId($this->id)
932
            ->setElementType($this->config['elementType'])
933
            ->save();
934
935
        return $this;
936
    }
937
938
    /**
939
     * @param string $text
940
     * @param string $phone
941
     *
942
     * @return BaseEntity|Company|Contact|Lead
943
     *
944
     * @throws AmoWrapException
945
     */
946
    public function addNoteSmsIn($text, $phone)
947
    {
948
        if ($this->id === null) {
949
            $this->save();
950
        }
951
952
        $note = new Note();
953
        $note->setText($text)
954
            ->setType(102)
955
            ->setPhone($phone)
956
            ->setCreatedUser($this->getResponsibleUserId())
957
            ->setElementId($this->id)
958
            ->setElementType($this->config['elementType'])
959
            ->save();
960
961
        return $this;
962
    }
963
964
    /**
965
     * @param string          $text
966
     * @param int|string|null $responsibleUserIdOrName
967
     * @param DateTime|null   $completeTill
968
     * @param int|string      $type
969
     *
970
     * @return BaseEntity|Company|Contact|Lead
971
     *
972
     * @throws AmoWrapException
973
     */
974
    public function addTask($text, $responsibleUserIdOrName = null, DateTime $completeTill = null, $type = 3)
975
    {
976
        if (empty($this->amoId)) {
977
            $this->save();
978
        }
979
        $tapeId = AmoCRM::searchTaskType($type);
980
981
        if ($responsibleUserIdOrName === null) {
982
            $responsibleUserIdOrName = $this->responsibleUserId;
983
        }
984
985
        $task = new Task();
986
        if ($completeTill !== null) {
987
            $task->setCompleteTill($completeTill);
988
        }
989
990
        $task->setText($text)
991
            ->setType($tapeId)
992
            ->setResponsibleUser($responsibleUserIdOrName)
993
            ->setElementId($this->id)
994
            ->setElementType($this->config['elementType'])
995
            ->save();
996
997
        return $this;
998
    }
999
1000
    /**
1001
     * @param string $pathToFile
1002
     *
1003
     * @return BaseEntity|Company|Contact|Lead
1004
     *
1005
     * @throws AmoWrapException
1006
     */
1007
    public function addFile($pathToFile)
1008
    {
1009
        if ($this->id === null) {
1010
            $this->save();
1011
        }
1012
1013
        if (is_file($pathToFile) && file_exists($pathToFile)) {
1014
            $elementType = $this->config['elementType'];
1015
            if (class_exists('CURLFile')) {
1016
                $CURLFile = new CURLFile(realpath($pathToFile));
1017
                $post = array(
1018
                    'UserFile' => $CURLFile
1019
                );
1020
            } else {
1021
                $post = array(
1022
                    'UserFile' => '@' . $pathToFile
1023
                );
1024
            }
1025
            $url = "/private/notes/upload.php?ACTION=ADD_NOTE&ELEMENT_ID={$this->id}&ELEMENT_TYPE={$elementType}&fileapi" .
1026
	               str_replace('.', '', microtime(true));
1027
            $res = AmoCRM::cUrl($url, $post, null, true);
1028
            if ($res !== null && isset($res->status) && $res->status === 'fail') {
1029
                throw new AmoWrapException('Не удалось добавить файл');
1030
            }
1031
            $post = array(
1032
                'ACTION' => 'ADD_NOTE',
1033
                'DATE_CREATE' => time(),
1034
                'ATTACH' => $res->note->params->link,
1035
                'BODY' => $res->note->params->text,
1036
                'ELEMENT_ID' => $this->id,
1037
                'ELEMENT_TYPE' => $elementType,
1038
            );
1039
            $res = AmoCRM::cUrl('private/notes/edit2.php', $post, null, true);
1040
            if ($res !== null && isset($res->status) && $res->status !== 'ok') {
1041
                throw new AmoWrapException('Не удалось добавить файл');
1042
            }
1043
        }
1044
1045
        return $this;
1046
    }
1047
1048
    /**
1049
     * @return array
1050
     */
1051
    abstract protected function getExtraRaw();
1052
1053
    /**
1054
     * @param int $id
1055
     *
1056
     * @throws AmoWrapException
1057
     */
1058
    protected function load($id)
1059
    {
1060
        $typeUrl = $this->config['url'];
1061
        $link = "api/v2/$typeUrl?id=$id";
1062
1063
        if ($this->config['info'] === 'note') {
1064
            $type = Config::$types[$this->elementType];
1065
            $link .= "&type=$type";
1066
        }
1067
1068
        $res = AmoCRM::cUrl($link);
1069
        if ($res !== null && count($res->_embedded->items) > 0) {
1070
            $this->loadInRaw(current($res->_embedded->items));
1071
        } else {
1072
            throw new AmoWrapException('Не удалось загрузить сущность');
1073
        }
1074
    }
1075
1076
    /**
1077
     * @param string|int $nameOrId
1078
     *
1079
     * @return CustomField
1080
     *
1081
     * @throws AmoWrapException
1082
     */
1083
    private function getCustomField($nameOrId)
1084
    {
1085
        $id = $this->searchCustomFieldsId($nameOrId);
1086
        if (!isset($this->customFields[$id])) {
1087
            $this->customFields[$id] = new CustomField($id);
1088
        }
1089
1090
        return $this->customFields[$id];
1091
    }
1092
1093
1094
    /**
1095
     * @param string|int $nameOrId
1096
     *
1097
     * @return int
1098
     *
1099
     * @throws AmoWrapException
1100
     */
1101
    public function searchCustomFieldsId($nameOrId)
1102
    {
1103
        $customFields = AmoCRM::getCustomFields($this->config['info']);
1104
1105
        if (isset($customFields[$nameOrId])) {
1106
            return $nameOrId;
0 ignored issues
show
Bug Best Practice introduced by
The expression return $nameOrId also could return the type string which is incompatible with the documented return type integer.
Loading history...
1107
        }
1108
1109
        foreach ($customFields as $customFieldId => $customFieldName) {
1110
            if (mb_stripos($customFieldName, $nameOrId) !== false) {
1111
                return $customFieldId;
1112
            }
1113
        }
1114
1115
        throw new AmoWrapException('Не удалось найти пользовательское поле');
1116
    }
1117
1118
    /**
1119
     * @param array $data
1120
     *
1121
     * @return BaseEntity|Company|Contact|Lead|Note|Task
1122
     *
1123
     * @throws AmoWrapException
1124
     */
1125
    private function saveBase($data = array())
1126
    {
1127
        if ($this->id === null) {
1128
            $method = 'add';
1129
        } else {
1130
            $method = 'update';
1131
        }
1132
        $requestData[$method] = array($this->getRawBase($data));
0 ignored issues
show
Comprehensibility Best Practice introduced by
$requestData was never initialized. Although not strictly required by PHP, it is generally a good practice to add $requestData = array(); before regardless.
Loading history...
1133
        $res = AmoCRM::cUrl("api/v2/{$this->config['url']}", $requestData);
1134
        if ($res !== null && isset($res->_embedded->items[0]->id)) {
1135
            $classFullName = get_class($this);
1136
            /** @var BaseEntity $entity */
1137
            $entity = new $classFullName;
1138
            if ($this->config['info'] === 'note') {
1139
                $entity->setElementType($this->elementType);
1140
            }
1141
            $entity->load($res->_embedded->items[0]->id);
1142
1143
            return $entity;
1144
        }
1145
1146
        throw new AmoWrapException('Не удалось сохранить сущность');
1147
    }
1148
1149
    /**
1150
     * @param array $data
1151
     *
1152
     * @return array
1153
     */
1154
    private function getRawBase($data = array())
1155
    {
1156
        if ($this->name !== null) {
1157
            $data['name'] = $this->name;
1158
        }
1159
        if ($this->responsibleUserId !== null) {
1160
            $data['responsible_user_id'] = $this->responsibleUserId;
1161
        }
1162
        if ($this->companyId !== null) {
1163
            $data['company_id'] = $this->companyId;
1164
        }
1165
        if (count($this->leadsId) > 0) {
1166
            $data['leads_id'] = $this->leadsId;
1167
        }
1168
        if (count($this->contactsId) > 0) {
1169
            $data['contacts_id'] = $this->contactsId;
1170
        }
1171
        $data['tags'] = implode(',', $this->tags);
1172
        if (count($this->unlink) > 0) {
1173
            $data['unlink'] = $this->unlink;
1174
        }
1175
        if ($this->id === null) {
1176
            $data['created_by'] = isset($data['created_by']) ? $data['created_by'] : 0;
1177
        } else {
1178
            $data['id'] = $this->id;
1179
            $data['updated_at'] = date('U');
1180
            $data['updated_by'] = 0;
1181
        }
1182
        $customFields = $this->customFields;
1183
        if (count($this->phones) > 0) {
1184
            $idPhoneEnums = AmoCRM::getPhoneEnums();
1185
            foreach ($this->phones as $phone) {
1186
                if ($phone->getEnum() === 0) {
1187
                    $phone->setEnum($idPhoneEnums['OTHER']);
1188
                }
1189
            }
1190
            $customFields[] = new CustomField(AmoCRM::getPhoneFieldId(), $this->phones);
1191
        }
1192
        if (count($this->emails) > 0) {
1193
            $idEmailEnums = AmoCRM::getEmailEnums();
1194
            foreach ($this->emails as $email) {
1195
                if ($email->getEnum() === 0) {
1196
                    $email->setEnum($idEmailEnums['OTHER']);
1197
                }
1198
            }
1199
            $customFields[] = new CustomField(AmoCRM::getEmailFieldId(), $this->emails);
1200
        }
1201
        if (count($customFields) > 0) {
1202
            foreach ($customFields as $customFieldObj) {
1203
                $values = array();
1204
                foreach ($customFieldObj->getValues() as $valueObj) {
1205
                    $value = array(
1206
                        'enum' => $valueObj->getEnum(),
1207
                        'value' => $valueObj->getValue(),
1208
                        'subtype' => $valueObj->getSubtype(),
1209
                    );
1210
                    $values[] = $value;
1211
                }
1212
                $data['custom_fields'][] = array(
1213
                    'id' => $customFieldObj->getId(),
1214
                    'values' => $values
1215
                );
1216
            }
1217
        }
1218
        return $data;
1219
    }
1220
1221
    /**
1222
     * @param string $id
1223
     *
1224
     * @return array
1225
     */
1226
    private function getEnums($id)
1227
    {
1228
        $enums = AmoCRM::getCustomFieldsEnums($this->config['info']);
1229
1230
        return isset($enums[$id]) ? $enums[$id] : array();
1231
    }
1232
}