/**
  * {@inheritdoc}
  */
 public function form(array $form, FormStateInterface $form_state)
 {
     $form = parent::form($form, $form_state);
     $field_label = $form_state->get('field_config')->label();
     $form['#title'] = $field_label;
     $form['#prefix'] = '<p>' . $this->t('These settings apply to the %field field everywhere it is used. These settings impact the way that data is stored in the database and cannot be changed once data has been created.', array('%field' => $field_label)) . '</p>';
     // See if data already exists for this field.
     // If so, prevent changes to the field settings.
     if ($this->entity->hasData()) {
         $form['#prefix'] = '<div class="messages messages--error">' . $this->t('There is data for this field in the database. The field settings can no longer be changed.') . '</div>' . $form['#prefix'];
     }
     // Add settings provided by the field module. The field module is
     // responsible for not returning settings that cannot be changed if
     // the field already has data.
     $form['settings'] = array('#weight' => -10, '#tree' => TRUE);
     // Create an arbitrary entity object, so that we can have an instantiated
     // FieldItem.
     $ids = (object) array('entity_type' => $form_state->get('entity_type_id'), 'bundle' => $form_state->get('bundle'), 'entity_id' => NULL);
     $entity = _field_create_entity_from_ids($ids);
     $items = $entity->get($this->entity->getName());
     $item = $items->first() ?: $items->appendItem();
     $form['settings'] += $item->storageSettingsForm($form, $form_state, $this->entity->hasData());
     // Build the configurable field values.
     $cardinality = $this->entity->getCardinality();
     $form['cardinality_container'] = array('#parents' => array(), '#type' => 'fieldset', '#title' => $this->t('Allowed number of values'), '#attributes' => array('class' => array('container-inline', 'fieldgroup', 'form-composite')));
     $form['cardinality_container']['cardinality'] = array('#type' => 'select', '#title' => $this->t('Allowed number of values'), '#title_display' => 'invisible', '#options' => array('number' => $this->t('Limited'), FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED => $this->t('Unlimited')), '#default_value' => $cardinality == FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED ? FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED : 'number');
     $form['cardinality_container']['cardinality_number'] = array('#type' => 'number', '#default_value' => $cardinality != FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED ? $cardinality : 1, '#min' => 1, '#title' => $this->t('Limit'), '#title_display' => 'invisible', '#size' => 2, '#states' => array('visible' => array(':input[name="cardinality"]' => array('value' => 'number')), 'disabled' => array(':input[name="cardinality"]' => array('value' => FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED))));
     return $form;
 }
Exemplo n.º 2
0
/**
 * Forbid a field storage update from occurring.
 *
 * Any module may forbid any update for any reason. For example, the
 * field's storage module might forbid an update if it would change
 * the storage schema while data for the field exists. A field type
 * module might forbid an update if it would change existing data's
 * semantics, or if there are external dependencies on field settings
 * that cannot be updated.
 *
 * To forbid the update from occurring, throw a
 * \Drupal\Core\Entity\Exception\FieldStorageDefinitionUpdateForbiddenException.
 *
 * @param \Drupal\field\FieldStorageConfigInterface $field_storage
 *   The field storage as it will be post-update.
 * @param \Drupal\field\FieldStorageConfigInterface $prior_field_storage
 *   The field storage as it is pre-update.
 *
 * @see entity_crud
 */
function hook_field_storage_config_update_forbid(\Drupal\field\FieldStorageConfigInterface $field_storage, \Drupal\field\FieldStorageConfigInterface $prior_field_storage)
{
    if ($field_storage->module == 'options' && $field_storage->hasData()) {
        // Forbid any update that removes allowed values with actual data.
        $allowed_values = $field_storage->getSetting('allowed_values');
        $prior_allowed_values = $prior_field_storage->getSetting('allowed_values');
        $lost_keys = array_keys(array_diff_key($prior_allowed_values, $allowed_values));
        if (_options_values_in_use($field_storage->getTargetEntityTypeId(), $field_storage->getName(), $lost_keys)) {
            throw new \Drupal\Core\Entity\Exception\FieldStorageDefinitionUpdateForbiddenException(t('A list field (@field_name) with existing data cannot have its keys changed.', array('@field_name' => $field_storage->getName())));
        }
    }
}
 /**
  * @covers ::getType
  */
 public function testGetType()
 {
     // Ensure that FieldConfig::getType() is not delegated to
     // FieldStorage.
     $this->entityManager->expects($this->never())->method('getFieldStorageDefinitions');
     $this->fieldStorage->expects($this->never())->method('getType');
     $field = new FieldConfig(array('field_name' => $this->fieldStorage->getName(), 'entity_type' => 'test_entity_type', 'bundle' => 'test_bundle', 'field_type' => 'test_field'), $this->entityTypeId);
     $this->assertEquals('test_field', $field->getType());
 }
 /**
  * @covers ::toArray()
  */
 public function testToArray()
 {
     $values = array('field_name' => $this->fieldStorage->getName(), 'entity_type' => 'test_entity_type', 'bundle' => 'test_bundle');
     $instance = new FieldInstanceConfig($values, $this->entityTypeId);
     $expected = array('id' => 'test_entity_type.test_bundle.field_test', 'uuid' => NULL, 'status' => TRUE, 'langcode' => LanguageInterface::LANGCODE_NOT_SPECIFIED, 'field_name' => 'field_test', 'entity_type' => 'test_entity_type', 'bundle' => 'test_bundle', 'label' => '', 'description' => '', 'required' => FALSE, 'default_value' => array(), 'default_value_function' => '', 'settings' => array(), 'dependencies' => array(), 'field_type' => 'test_field');
     $this->entityManager->expects($this->any())->method('getDefinition')->with($this->entityTypeId)->will($this->returnValue($this->entityType));
     $this->entityType->expects($this->once())->method('getKey')->with('id')->will($this->returnValue('id'));
     $this->typedConfigManager->expects($this->once())->method('getDefinition')->will($this->returnValue(array('mapping' => array_fill_keys(array_keys($expected), ''))));
     $export = $instance->toArray();
     $this->assertEquals($expected, $export);
 }
 /**
  * {@inheritdoc}
  */
 public function validateForm(array &$form, FormStateInterface $form_state)
 {
     parent::validateForm($form, $form_state);
     $field_storage_definitions = \Drupal::service('entity_field.manager')->getFieldStorageDefinitions($this->entity->getTargetEntityTypeId());
     // Validate field cardinality.
     if ($form_state->getValue('cardinality') === 'number' && !$form_state->getValue('cardinality_number')) {
         $form_state->setErrorByName('cardinality_number', $this->t('Number of values is required.'));
     } elseif (!$this->entity->isNew() && isset($field_storage_definitions[$this->entity->getName()]) && $form_state->getValue('cardinality') != FieldStorageDefinitionInterface::CARDINALITY_UNLIMITED) {
         // Get a count of entities that have a value in a delta higher than the
         // one selected. Deltas start with 0, so the selected value does not
         // need to be incremented.
         $entities_with_higher_delta = \Drupal::entityQuery($this->entity->getTargetEntityTypeId())->condition($this->entity->getName() . '.%delta', $form_state->getValue('cardinality'))->count()->execute();
         if ($entities_with_higher_delta) {
             $form_state->setErrorByName('cardinality_number', $this->formatPlural($entities_with_higher_delta, 'There is @count entity with @delta or more values in this field.', 'There are @count entities with @delta or more values in this field.', ['@delta' => $form_state->getValue('cardinality') + 1]));
         }
     }
 }
Exemplo n.º 6
0
/**
 * Alter the Views data on a per field basis.
 *
 * The field module's implementation of hook_views_data_alter() invokes this for
 * each field storage, in the module that defines the field type. It is not
 * invoked in other modules.
 *
 * Unlike hook_field_views_data_alter(), this operates on the whole of the views
 * data. This allows a field type to add data that concerns its fields in
 * other tables, which would not yet be defined at the point when
 * hook_field_views_data() and hook_field_views_data_alter() are invoked. For
 * example, entityreference adds reverse relationships on the tables for the
 * entities which are referenced by entityreference fields.
 *
 * (Note: this is weirdly named so as not to conflict with
 * hook_field_views_data_alter().)
 *
 * @param array $data
 *   The views data.
 * @param \Drupal\field\FieldStorageConfigInterface $field
 *   The field storage config entity.
 *
 * @see hook_field_views_data()
 * @see hook_field_views_data_alter()
 * @see field_views_data_alter()
 */
function hook_field_views_data_views_data_alter(array &$data, \Drupal\field\FieldStorageConfigInterface $field)
{
    $field_name = $field->getName();
    $data_key = 'field_data_' . $field_name;
    $entity_type_id = $field->entity_type;
    $entity_type = \Drupal::entityManager()->getDefinition($entity_type_id);
    $pseudo_field_name = 'reverse_' . $field_name . '_' . $entity_type_id;
    list($label) = field_views_field_label($entity_type_id, $field_name);
    // Views data for this field is in $data[$data_key].
    $data[$data_key][$pseudo_field_name]['relationship'] = array('title' => t('@entity using @field', array('@entity' => $entity_type->getLabel(), '@field' => $label)), 'help' => t('Relate each @entity with a @field set to the term.', array('@entity' => $entity_type->getLabel(), '@field' => $label)), 'id' => 'entity_reverse', 'field_name' => $field_name, 'entity_type' => $entity_type_id, 'field table' => ContentEntityDatabaseStorage::_fieldTableName($field), 'field field' => $field_name . '_target_id', 'base' => $entity_type->getBaseTable(), 'base field' => $entity_type->getKey('id'), 'label' => t('!field_name', array('!field_name' => $field_name)), 'join_extra' => array(0 => array('field' => 'deleted', 'value' => 0, 'numeric' => TRUE)));
}
 /**
  * {@inheritdoc}
  */
 public function fieldGetPermissionType(FieldStorageConfigInterface $field)
 {
     $config = \Drupal::service('config.factory')->getEditable('field_permissions.field.settings');
     $field_settings_perm = $config->get('permission_type_' . $field->getName());
     return $field_settings_perm ? $field_settings_perm : FIELD_PERMISSIONS_PUBLIC;
 }