This module only performs one part of the operations needed to update a field schema.

I had to run manually the steps described in:

https://www.drupal.org/docs/8/api/update-api/updating-database-schema-an...

To get rid of the Status page error.

Comments

rodrigoaguilera created an issue. See original summary.

babis.p’s picture

Hello,
I have exactly the same problem. Could you tell me exactly what were the extra steps that you had to do manually?
Thanks in advance

rodrigoaguilera’s picture

In the link I posted at the end there is a function db_change_varchar_field()

If you call it with the right parameters the schema will be updated.

Do not forget to clear cache after.

guncha25’s picture

This worked for me, when having data in table, so drush entup -y was out of question:

/**
 * Implements hook_update_N().
 */
function my_module_update_8001(&$sandbox) {
  db_change_varchar_field('node', 'title', 8000);
}


/**
 * Change length of a varchar entity field with data, safe with entity-updates.
 *
 * This updates the storage schema, the databasse schema, and the last
 * installed schema.
 *
 * The entity schema must also be changed in code in the entities
 * baseFieldDefinitions() or in an alter.
 *
 * @param string $entity_type_id
 *   The entity type.
 * @param string $field_name
 *   The field name to change.
 * @param int $field_length
 *   The new length of the field, must be larger than the previous value.
 */
function db_change_varchar_field($entity_type_id, $field_name, $field_length) {
  // Ignore entity manager caches.
  /** @var \Drupal\Core\Entity\EntityManager $entity_manager */
  $entity_manager = \Drupal::service('entity.manager');
  $entity_manager->useCaches(FALSE);

  /** @var \Drupal\Core\Entity\EntityLastInstalledSchemaRepositoryInterface $schema_repository */
  $schema_repository = \Drupal::service('entity.last_installed_schema.repository');
  /** @var \Drupal\Core\Entity\EntityFieldManager $entity_field_manager */
  $entity_field_manager = \Drupal::service('entity_field.manager');
  $base_field_definitions = $entity_field_manager->getBaseFieldDefinitions($entity_type_id);
  $schema_repository->setLastInstalledFieldStorageDefinition($base_field_definitions[$field_name]);
  $field_storage_definitions = $schema_repository->getLastInstalledFieldStorageDefinitions($entity_type_id);
  $field_storage_definitions[$field_name]['schema'] = $field_storage_definitions[$field_name]->getSchema();
  $field_storage_definitions[$field_name]['schema']['columns']['value']['length'] = $field_length;
  $schema_repository->setLastInstalledFieldStorageDefinitions($entity_type_id, $field_storage_definitions);
  $is_revisionable = $field_storage_definitions[$field_name]->isRevisionable();

  // Update the storage schema.
  $key_value = \Drupal::keyValue('entity.storage_schema.sql');
  $key_name = $entity_type_id . '.field_schema_data.' . $field_name;
  $storage_schema = $key_value->get($key_name);
  $storage_schema[$entity_type_id . '_field_data']['fields'][$field_name]['length'] = $field_length;
  if ($is_revisionable) {
    $storage_schema[$entity_type_id . '_field_revision']['fields'][$field_name]['length'] = $field_length;
  }
  $key_value->set($key_name, $storage_schema);

  // Change node title length (data table).
  $schema = Drupal\Core\Database\Database::getConnection()->schema();
  $schema->changeField($entity_type_id . '_field_data', $field_name, $field_name, [
    'type' => 'varchar',
    'length' => $field_length,
    'binary' => FALSE,
    'not null' => TRUE,
  ]);

  // Change node title length (revisions table).
  $schema = Drupal\Core\Database\Database::getConnection()->schema();
  $schema->changeField($entity_type_id . '_field_revision', $field_name, $field_name, [
    'type' => 'varchar',
    'length' => $field_length,
    'binary' => FALSE,
    'not null' => TRUE,
  ]);
}
leolandotan’s picture

I'm getting an error when using the code provided:

$ drush updb --entity-updates -y
 ------------------ ----------- --------------- -------------------------------------------------------
  Module             Update ID   Type            Description
 ------------------ ----------- --------------- -------------------------------------------------------
  mysite             8009        hook_update_n   8009 -
  node entity type               entity-update   The node.field_description field needs to be updated.
 ------------------ ----------- --------------- -------------------------------------------------------

 Do you wish to run the specified pending updates? (yes/no) [yes]:
 >

 [notice] Update started: mysite_update_8009
 [error]  Argument 1 passed to Drupal\Core\Entity\EntityLastInstalledSchemaRepository::setLastInstalledFieldStorageDefinition() must implement interface Drupal\Core\Field\FieldStorageDefinitionInterface, null given, called in /app/html/modules/custom/mysite/mysite.module on line 2047
 [error]  Update failed: mysite_update_8009
 [error]  Drupal\Core\Entity\Exception\FieldStorageDefinitionUpdateForbiddenException: The SQL storage cannot change the schema for an existing field (field_description in node entity) with data. in Drupal\Core\Entity\Sql\SqlContentEntityStorageSchema->updateDedicatedTableSchema() (line 1493 of /app/html/core/lib/Drupal/Core/Entity/Sql/SqlContentEntityStorageSchema.php).
 [error]  Update aborted by: mysite_update_8009, update_entity_definitions
 [error]  Finished performing updates.
hchonov’s picture

I've found this issue while searching for the documentation referenced in the issue summary and wanted just to notify you, that I've updated the function for updating the schema, as it didn't consider the serialized schema property of the field storage definition.

iuana’s picture

I had the same issue, the code from #4 worked for me. Thank you!

  • cbccharlie committed 070f871 on 8.x-1.x
    Issue #2950092: Module modifies sql schema without modifiying the stored...
cbccharlie’s picture

Status: Active » Fixed
cbccharlie’s picture

Status: Fixed » Closed (fixed)