Score:1

Can't save value of custom datetime field

in flag

I'm reaching out because I just can't find out why my custom datetime field isn't saving its value after I submit.

Context:

I've created a field containing two datetime fields. I will use it to add or remove events from an event list, depending on whether they have passed or not (for example if a festival is scheduled from the 12 to the 14 of December, the event will be removed after the 14th).

Events in my case are generated from a custom entity, I can manage its fields from my back office. My goal is to get the the dates from my custom datetime field on twig to filter which events are showed.

I know I can just add two Date fields but I find it lacks the elegance I seek.

My code:

So I have created a custom field that itself contains two datetime fields. I followed many tutorials to find a version that works for me and here is the code for my Field Type, Widget and Formatter

  • Field Type: ScheduleItem.php
class ScheduleItem extends FieldItemBase {

  /**
   * {@inheritdoc}
   */
  public function isEmpty() {
    $isEmpty =
      empty($this->get('start')->getValue()) &&
      empty($this->get('finish')->getValue());

    return $isEmpty;
  }

  /**
   * {@inheritdoc}
   */
  public static function propertyDefinitions(FieldStorageDefinitionInterface $field_definition) {
    $properties = [];
    $properties['start'] = DataDefinition::create('datetime_iso8601')
      ->setLabel(t('Date de publication'));
    $properties['finish'] = DataDefinition::create('datetime_iso8601')
      ->setLabel(t('Date de suppression'));
    return $properties;
  }

  /**
   * {@inheritdoc}
   */
  public static function schema(FieldStorageDefinitionInterface $field_definition) {

    $columns = [
      'start' => [
        'type' => 'varchar',
        'mysql_type' => 'datetime',
        'not null' => FALSE,
        'default' => NULL,
      ],
      'finish' => [
        'type' => 'varchar',
        'mysql_type' => 'datetime',
        'not null' => FALSE,
        'default' => NULL,
        ],
    ];

    return [
      'value' => $columns,
      // @DCG Add indexes here if necessary.
    ];

  }

Not much to say here. I don't know if there is a conflict in the types that I use, as mysql_type, type and DataDefinition::create have different values...

  • Field Widget: ScheduleWidget
class ScheduleWidget extends DateTimeWidgetBase {

  /**
   * {@inheritdoc}
   */
  public function formElement(
    FieldItemListInterface $items,
                           $delta,
    Array $element,
    Array &$form,
    FormStateInterface $formState
  ) {

    $element += array(
      '#delta' => $delta,
    );

    $element['start'] = [
      '#type' => 'datetime',
      '#title' => $this->t('Date de publication'),

      // Set here the current value for this field, or a default value (or
      // null) if there is no a value
      '#default_value' => isset($items[$delta]->start) ?
        $items[$delta]->start : null,
      '#empty_value' => '',
    ];

    $element['finish'] = [
      '#type' => 'datetime',
      '#title' =>  $this->t('Date de suppression'),
      '#default_value' => isset($items[$delta]->finish) ?
        $items[$delta]->finish : null,
      '#empty_value' => '',
    ];

    return $element;
  }

}

Contrary to most custom field widgets I extend DateTimeWidgetBase and not WidgetBase, the point here is to use the pre-made massageFormValues function from the class. It is supposed to convert my values to a database-ready format if I understood correctly, but so far it hasn't helped me.

  • Field Formatter: ScheduleDefaultFormatter.php
class ScheduleDefaultFormatter extends FormatterBase {

  /**
   * {@inheritdoc}
   */
  public function viewElements(FieldItemListInterface $items, $langcode)
  {

    $elements = [];
    foreach ($items as $delta => $item) {
      $elements[$delta] = [
        '#start' => $item->start,
        '#finish' => $item->finish
      ];
    }

    return $elements;
  }

}

Thats pretty much it for my code, I thought it was good, well it looked as such to me but...

THE ISSUE

When I added my new custom field to my event entity in the "Manage Fields" section, created a new event and added dates to it, I got...

This value should be of the correct primitive type.

What I tried

I dumped $values just before massageFormValues returned it and this is what it looks like:

dump of my custom field value

My question to you, why isn't it working ?

I tried being as clear as possible, however my experience on Drupal is still limited, don't hesitate if you need more information about my code, as long as it helps solving the issue!

mangohost

Post an answer

Most people don’t grasp that asking a lot of questions unlocks learning and improves interpersonal bonding. In Alison’s studies, for example, though people could accurately recall how many questions had been asked in their conversations, they didn’t intuit the link between questions and liking. Across four studies, in which participants were engaged in conversations themselves or read transcripts of others’ conversations, people tended not to realize that question asking would influence—or had influenced—the level of amity between the conversationalists.