1

I have a multi-value text-field, projects. Its length is 4, and I would like to increase it to 255, but there are values saved in the database for that field.

How can I increase its length?

  • 2
    backup, export field's db table, delete field, clear the cache, create same field with 255, import, clear the cache. – No Sssweat Sep 10 '17 at 7:41
3

I got an answer from my friend as well. I would like to share his code here:

/**
 * Update field.
 */
function MODULE_update_8301() {
  $db = \Drupal::database();
  $field_name = 'field_MY_TEXT_FIELD';
  $table_prefixes = [
    'node',
    'node_revision'
  ];
  foreach ($table_prefixes as $table_prefix) {
    $db->schema()->changeField(
      "{$table_prefix}__{$field_name}",
      "{$field_name}_value",
      "{$field_name}_value",
      [
        'type' => 'varchar',
        'length' => 255,
        'default' => '',
      ]
    );
  }

  $config = \Drupal::configFactory()->getEditable('field.storage.node.' . $field_name);
  $settings = $config->get('settings');
  $settings['max_length'] = 255;
  $config->set('settings', $settings);
  $config->save();
}
  • 1
    I strongly against this solution. You shouldn't manipulate the fields by yourself. Do this via Drupal API. – ssibal Sep 11 '17 at 8:40
0

The schema of a field is not changeable until it has data inside. There can be many scenarios like you have multiple languages, or revisions are important etc, but the following steps can be an abstract approach of the situation:

  1. Keep in memory (variable) or save all the field values, which host field you are about to manipulate
  2. Delete your old field and import the new one (you can do it based on the YML file itself)
  3. Backup all the information with help of the EntityTypeManager.

This is indeed an advanced part of Drupal, but once you master it, updates like this will work like charm.

0

I tried the answer of asrob, but it doesnt work with entity update (drush entup).

There is a better solution using Drupal API. The code is from here: https://coderwall.com/p/uyidlq/updating-the-storage-definition-of-entities-that-already-have-content-in-drupal-8

/**
 * Increase FIELD size to 50.
 */
function MODULE_update_8XXX() {
  $database = \Drupal::database();
  // Retrieve existing field data.
  $entity_type = 'ENTITY_TYPE';
  $field = 'FIELD_NAME';
  $tables = [
    "{$entity_type}__$field",
    "{$entity_type}_revision__$field",
  ];
  $existing_data = [];
  foreach ($tables as $table) {
    // Get the old data.
    $existing_data[$table] = $database->select($table)
      ->fields($table)
      ->execute()
      ->fetchAll(PDO::FETCH_ASSOC);

    // Wipe it.
    $database->truncate($table)->execute();
  }

  $field_storage_configs = \Drupal::entityTypeManager()
    ->getStorage('field_storage_config')
    ->loadByProperties([
      'field_name' => $field,
    ]);
  foreach ($field_storage_configs as $field_storage) {
    $new_field_storage = $field_storage->toArray();
    $new_field_storage['settings']['max_length'] = 50;

    $new_field_storage = FieldStorageConfig::create($new_field_storage);
    $new_field_storage->original = $new_field_storage;
    $new_field_storage->enforceIsNew(FALSE);

    $new_field_storage->save();
  }

  // Restore the data.
  foreach ($tables as $table) {
    $insert_query = $database
      ->insert($table)
      ->fields(array_keys(end($existing_data[$table])));
    foreach ($existing_data[$table] as $row) {
      $insert_query->values(array_values($row));
    }
    $insert_query->execute();
  }
}
0

This is what I do. I would only use it to increase the length of a string. I have not tested, but assume that shortening a string will truncate data.

First, backup the database.

Then, edit the structure of the following tables (change yourfield to match the name of your field):

field_data_field_yourfield
field_revision_field_yourfield

Change the length of the field_data_field_yourfield_value field (VARCHAR) in both tables to the value you want. This allows the fields to hold more characters. But doesn't tell Drupal about the change in length.

Next, locate this table:

field_config

Find your field in the list and edit the data value. Look for a section like this:

s:10:"max_length";s:3:"100";

The length of the field in this example is 100. Change it to match the change you made earlier. If the number of characters changes (e.g. you increase it from 100 to 1000), change the s:3 value to reflect the new character count.

Flush all caches.

Edit the field on an entity type to which it is attached to verify that its length has changed.

Edit an entity with this field and verify that you are able to enter a value that is the new length.

That's all ....

0

Up-to-date method for Drupal 8 (for field name "field_myfield"):

  1. Backup database
  2. Edit structure for table node__field_myfield, set new length for column field_myfield_value.
  3. Edit structure for table node_revision__field_myfield, set new length for column field_myfield_value.
  4. Use Admin Toolbar Extra Tools module, top menu: go to Development > Config editor
  5. Filter by "field.storage.node.field_myfield"
  6. Edit the max_length: line under settings: to match new column length.
  7. Flush all caches.
  8. Enable the entity_update module.
  9. drush @miniloco upe --show
  10. Give up....

Will keep trying and will come and edit this if/when I find a solution.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.