Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 113
0.00% covered (danger)
0.00%
0 / 6
CRAP
0.00% covered (danger)
0.00%
0 / 1
ContactForm
0.00% covered (danger)
0.00%
0 / 113
0.00% covered (danger)
0.00%
0 / 6
420
0.00% covered (danger)
0.00%
0 / 1
 __construct
0.00% covered (danger)
0.00%
0 / 3
0.00% covered (danger)
0.00%
0 / 1
2
 create
0.00% covered (danger)
0.00%
0 / 7
0.00% covered (danger)
0.00%
0 / 1
2
 form
0.00% covered (danger)
0.00%
0 / 35
0.00% covered (danger)
0.00%
0 / 1
30
 save
0.00% covered (danger)
0.00%
0 / 30
0.00% covered (danger)
0.00%
0 / 1
30
 doPrimaryRelationship
0.00% covered (danger)
0.00%
0 / 21
0.00% covered (danger)
0.00%
0 / 1
20
 doPrimaryField
0.00% covered (danger)
0.00%
0 / 17
0.00% covered (danger)
0.00%
0 / 1
20
1<?php
2
3namespace Drupal\crm\Form;
4
5use Drupal\Component\Datetime\TimeInterface;
6use Drupal\Core\Datetime\DateFormatterInterface;
7use Drupal\Core\Entity\ContentEntityForm;
8use Drupal\Core\Entity\EntityRepositoryInterface;
9use Drupal\Core\Entity\EntityTypeBundleInfoInterface;
10use Drupal\Core\Form\FormStateInterface;
11use Drupal\Core\Session\AccountInterface;
12use Symfony\Component\DependencyInjection\ContainerInterface;
13
14/**
15 * Form controller for the contact entity edit forms.
16 */
17class ContactForm extends ContentEntityForm {
18
19  /**
20   * The date formatter service.
21   *
22   * @var \Drupal\Core\Datetime\DateFormatterInterface
23   */
24  protected $dateFormatter;
25
26  /**
27   * The current user.
28   *
29   * @var \Drupal\Core\Session\AccountInterface
30   */
31  protected $currentUser;
32
33  /**
34   * Constructs a ContactForm object.
35   *
36   * @param \Drupal\Core\Entity\EntityRepositoryInterface $entity_repository
37   *   The entity repository.
38   * @param \Drupal\Component\Datetime\TimeInterface $time
39   *   The time service.
40   * @param \Drupal\Core\Datetime\DateFormatterInterface $date_formatter
41   *   The date formatter service.
42   * @param \Drupal\Core\Session\AccountInterface $current_user
43   *   The current user.
44   * @param \Drupal\Core\Entity\EntityTypeBundleInfoInterface|null $entity_type_bundle_info
45   *   The entity type bundle service.
46   */
47  public function __construct(
48    EntityRepositoryInterface $entity_repository,
49    TimeInterface $time,
50    DateFormatterInterface $date_formatter,
51    AccountInterface $current_user,
52    ?EntityTypeBundleInfoInterface $entity_type_bundle_info = NULL,
53  ) {
54
55    parent::__construct($entity_repository, $entity_type_bundle_info, $time);
56    $this->dateFormatter = $date_formatter;
57    $this->currentUser = $current_user;
58  }
59
60  /**
61   * {@inheritdoc}
62   */
63  final public static function create(ContainerInterface $container) {
64    return new self(
65      $container->get('entity.repository'),
66      $container->get('datetime.time'),
67      $container->get('date.formatter'),
68      $container->get('current_user'),
69      $container->get('entity_type.bundle.info'),
70    );
71  }
72
73  /**
74   * {@inheritdoc}
75   */
76  public function form(array $form, FormStateInterface $form_state) {
77    /** @var \Drupal\crm\CrmContactInterface $contact */
78    $contact = $this->entity;
79
80    $form = parent::form($form, $form_state);
81
82    $this->doPrimaryField($form);
83
84    $form['advanced']['#attributes']['class'][] = 'entity-meta';
85
86    $form['meta'] = [
87      '#type' => 'details',
88      '#group' => 'advanced',
89      '#weight' => -10,
90      '#title' => $this->t('Status'),
91      '#attributes' => ['class' => ['entity-meta__header']],
92      '#tree' => TRUE,
93      '#access' => $this->currentUser->hasPermission('administer crm'),
94    ];
95    $form['meta']['published'] = [
96      '#type' => 'item',
97      '#markup' => $contact->isPublished() ? $this->t('Active') : $this->t('Inactive'),
98      '#access' => !$contact->isNew(),
99      '#wrapper_attributes' => ['class' => ['entity-meta__title']],
100    ];
101    $form['meta']['changed'] = [
102      '#type' => 'item',
103      '#title' => $this->t('Last saved'),
104      '#markup' => !$contact->isNew() ? $this->dateFormatter->format($contact->getChangedTime(), 'short') : $this->t('Not saved yet'),
105      '#wrapper_attributes' => ['class' => ['entity-meta__last-saved']],
106    ];
107
108    $form['meta']['status'] = &$form['status'];
109    unset($form['status']);
110
111    if (isset($form['uid'])) {
112      unset($form['uid']);
113    }
114
115    if (isset($form['created'])) {
116      $form['created']['#weight'] = 200;
117      $form['meta']['created'] = &$form['created'];
118      unset($form['created']);
119    }
120
121    // Add a custom submit handler to the entity form.
122    $form['revision']['#default_value'] = TRUE;
123
124    return $form;
125  }
126
127  /**
128   * {@inheritdoc}
129   */
130  public function save(array $form, FormStateInterface $form_state) {
131
132    $contact = $this->getEntity();
133    // Set new Revision.
134    $contact->setNewRevision(TRUE);
135
136    $result = parent::save($form, $form_state);
137    $this->doPrimaryRelationship();
138
139    $message_arguments = ['%label' => $contact->toLink()->toString()];
140    $logger_arguments = [
141      '%label' => $contact->label(),
142      'link' => $contact->toLink($this->t('View'))->toString(),
143    ];
144
145    switch ($result) {
146      case SAVED_NEW:
147        $this->messenger()->addStatus($this->t('New contact %label has been created.', $message_arguments));
148        $this->logger('crm_contact')->notice('Created new contact %label', $logger_arguments);
149        break;
150
151      case SAVED_UPDATED:
152        $this->messenger()->addStatus($this->t('The contact %label has been updated.', $message_arguments));
153        $this->logger('crm_contact')->notice('Updated contact %label.', $logger_arguments);
154        break;
155    }
156
157    $form_state->setRedirect('entity.crm_contact.canonical', [
158      'crm_contact' => $contact->id(),
159    ]);
160
161    if ($contact->id()) {
162      $form_state->setValue('id', $contact->id());
163      $form_state->set('id', $contact->id());
164      if ($contact->access('view')) {
165        $form_state->setRedirect(
166          'entity.crm_contact.canonical',
167          ['crm_contact' => $contact->id()]
168        );
169      }
170      else {
171        $form_state->setRedirect('<front>');
172      }
173
174    }
175
176    return $result;
177  }
178
179  /**
180   * Ensures there is a relationship for the primary contact.
181   */
182  private function doPrimaryRelationship() {
183    $contact = $this->getEntity();
184    $primary = $contact->get('primary')->entity;
185    $relationship_type_id = $contact->get('bundle')->entity->get('primary');
186    if (!$primary || !$relationship_type_id) {
187      return;
188    }
189
190    $relationship_type = $this->entityTypeManager->getStorage('crm_relationship_type')->load($relationship_type_id);
191    $bundle = $contact->get('bundle')->target_id;
192
193    $is_a = $relationship_type->get('contact_type_a') == $bundle;
194
195    $storage = $this->entityTypeManager->getStorage('crm_relationship');
196    $query = $storage->getQuery();
197    $query->condition('bundle', $relationship_type_id);
198
199    $query->condition('contacts', $contact->id());
200    $query->condition('contacts', $primary->id());
201
202    $has_relationship = $query->accessCheck(FALSE)->count()->execute();
203    if (!$has_relationship) {
204      $storage->create([
205        'bundle' => $relationship_type_id,
206        'contact_a' => $contact->id(),
207        'contact_b' => $primary->id(),
208        'start' => $this->time->getRequestTime(),
209      ])->save();
210    }
211
212  }
213
214  /**
215   * Bundle specific changes to the primary field.
216   *
217   * @param array $form
218   *   The form array.
219   */
220  private function doPrimaryField(&$form) {
221    if (!isset($form['primary'])) {
222      return;
223    }
224    $entity = $this->getEntity();
225    $relationship_type_id = $entity->get('bundle')->entity->get('primary');
226    if (!$relationship_type_id) {
227      return;
228    }
229    $relationship_type = $this->entityTypeManager->getStorage('crm_relationship_type')->load($relationship_type_id);
230    $bundle = $entity->get('bundle')->target_id;
231    $is_a = $relationship_type->get('contact_type_a') == $bundle;
232    $target_id = &$form['primary']['widget'][0]['target_id'];
233    if ($is_a) {
234      $target_bundles = [$relationship_type->get('contact_type_b')];
235      $target_id['#title'] = $relationship_type->get('label_b');
236    }
237    else {
238      $target_bundles = [$relationship_type->get('contact_type_a')];
239      $target_id['#title'] = $relationship_type->label();
240    }
241
242    $target_id['#selection_settings']['target_bundles'] = $target_bundles;
243
244    $target_id['#description'] = $relationship_type->get('description');
245  }
246
247}