Exported config entries have an improper EOL signature on split lines

Created on 10 August 2020, over 4 years ago
Updated 23 August 2023, over 1 year ago

Problem/Motivation

Given the following config YML:

ckeditor_custom_config: "pasteFromWordPromptCleanup = true\r\npasteFromWordRemoveFontStyles = true\r\nforceSimpleAmpersand = true\r\nbodyClass = text-long u-max-w-measure-lg u-leading-normal u-o-3 u-m-3\r\nremovePlugins = magicline\r\ndisableNativeSpellChecker = false"

This module will transform that (on the file system) to:

ckeditor_custom_config: |
        pasteFromWordPromptCleanup = true
        pasteFromWordRemoveFontStyles = true
        forceSimpleAmpersand = true
        bodyClass = text-long u-max-w-measure-lg u-leading-normal u-o-3 u-m-3
        removePlugins = magicline
        disableNativeSpellChecker = false

But when the config is imported by \Drupal\Component\Serialization\Yaml::decode in \Drupal\Core\Config\FileStorage::decode the resulting string that is stored in the database will be:

pasteFromWordPromptCleanup = true\npasteFromWordRemoveFontStyles = true\nforceSimpleAmpersand = true\nbodyClass = text-long u-max-w-measure-lg u-leading-normal u-o-3 u-m-3\nremovePlugins = magicline\ndisableNativeSpellChecker = false\n

(Note the trailing \n)

The trailing newline is a problem for modules that use the newline character to iterate over a set of data, for example this example from the CKEditor custom config module:

// Build array from string.
$config_array = preg_split('/\R/', $custom_config);

// Loop through config lines and append to editorSettings.
foreach ($config_array as $value) {
  $exploded_value = explode(" = ", $value);
  // … more code, omitted for brevity.
}

---

The problematic trailing newline is added because of how YAML works:

Block Chomping Indicator: The chomping indicator controls what should happen with newlines at the end of the string. The default, clip, puts a single newline at the end of the string. To remove all newlines, strip them by putting a minus sign (-) after the style indicator. Both clip and strip ignore how many newlines are actually at the end of the block; to keep them all put a plus sign (+) after the style indicator.

We want to remove the trailing newlines, so we need to use the strip indicator, so now our YAML should look like this:

ckeditor_custom_config: |-
        pasteFromWordPromptCleanup = true
        pasteFromWordRemoveFontStyles = true
        forceSimpleAmpersand = true
        bodyClass = text-long u-max-w-measure-lg u-leading-normal u-o-3 u-m-3
        removePlugins = magicline
        disableNativeSpellChecker = false

Steps to reproduce

  1. Import multiline config
  2. Inspect the config as it is stored in the database, for example with Drush: drush cget editor.editor.full_html

Proposed resolution

I couldn't find a way to tell \Symfony\Component\Yaml\Dumper to use the strip indicator, but I've got a patch (will upload in a later comment) that rewrites the YAML strings with str_replace:

$yaml = str_replace(": |\n", ": |-\n", $yaml);

I'm not sure this is the best way to do it, but it works for me. Does anyone else have any ideas?

🐛 Bug report
Status

Fixed

Version

1.0

Component

Code

Created by

🇬🇧United Kingdom Phil Wolstenholme

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

Comments & Activities

Not all content is available!

It's likely this issue predates Contrib.social: some issue and comment data are missing.

Production build 0.71.5 2024