Creating a new inheritance doesn't get added to existing children

Created on 21 June 2024, 10 days ago

There is a fault in field_inheritance, when you add new fields/inheritances, it doesn't get updated on the old eventinstances until they get saved from the form. Saving the entity programmatically doesnt do it alone.

This is because the logic that links eventinstances and eventseries together is set by field_inheritance directly in the form_alter and form_submit.

This is an example of how i semi-manually fixed my existing children (eventinstances) to respect a new field. I've run this in an update hook:

/**
 * Linking new field inheritances with existing eventinstances.
 *
 * There is a fault in field_inheritance, when you add new fields/inheritances,
 * it doesn't get updated on the old eventinstances until they get saved from
 * the form.
 * This is because the logic that links eventinstances and eventseries together
 * is set by field_inheritance directly in the form_alter and form_submit.
 * This helper function allows you to pass along a name of a field inherited
 * field that has been set up at /admin/structure/field_inheritance, and
 * the helper will find all eventinstances and make sure the new field is
 * linked together with the relevant eventseries.
 */
function _example_module_update_field_inheritance($field_inheritance_name): string {
  $ids =
    \Drupal::entityQuery('eventinstance')
      ->accessCheck(FALSE)
      ->execute();

  if (empty($ids) || is_int($ids)) {
    return 'No entities to update.';
  }

  $entities =
    \Drupal::entityTypeManager()->getStorage('eventinstance')->loadMultiple($ids);

  $count = 0;

  foreach ($entities as $entity) {
    try {
      if (!($entity instanceof EventInstance)) {
        continue;
      }

      $event_series = $entity->getEventSeries();

      if (!($event_series instanceof EventSeries)) {
        continue;
      }

      // This matches the key that is defined in field_inheritance.
      $state_key = $entity->getEntityTypeId() . ':' . $entity->uuid();
      $field_inheritance = \Drupal::keyValue('field_inheritance')->get($state_key);

      // In theory, an eventinstance could be set up to inherit from another
      // entity than the eventseries - but in practice, this is really unlikely,
      // and something we're willing to disregard.
      $field_inheritance[$field_inheritance_name] = [
        'entity' => $event_series->id(),
      ];

      \Drupal::keyValue('field_inheritance')->set($state_key, $field_inheritance);

      $entity->save();
      $count++;
    }
    catch (\Exception $e) {
      \Drupal::logger('example_module')->error('Could not update field_inheritance on eventinstance @id - Error: @message', [
        '@message' => $e->getMessage(),
        '@id' => $entity->id(),
      ]);
    }
  }

  return t(
    "Updated @count eventinstances, linking field  '@field' to inherit from eventseries.",
    ['@field' => $field_inheritance_name, '@count' => $count]
  )->render();
}

πŸ› Bug report
Status

Active

Version

2.0

Component

Code

Created by

πŸ‡©πŸ‡°Denmark ras-ben Copenhagen

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Comments & Activities

Production build 0.69.0 2024