46

myfield is a plain text field. {{ content.field_myfield }} renders the field with HTML markup and the field label.

How do I render the raw value of the field? {{ content.field_myfield.value }} doesn't work.

9 Answers 9

80

{{ entity.field_name.value }} to get the true raw value, includes tags and encoding.

  • Example: {{ node.body.value }}
  • result: <p>Batman &amp; Robin</p>

{{ content.field_name.0 }} to get the raw value minus tags and encoding.

  • Example: {{ content.body.0 }}
  • result: Batman & Robin

raw

This filter should be avoided whenever possible, particularly if you're outputting data that could be user-entered. See this page for more information on auto-escape in Drupal 8.

source: Filters - Modifying Variables In Twig Templates

The raw filter marks the value as being "safe", which means that in an environment with automatic escaping enabled this variable will not be escaped if raw is the last filter applied to it

source: Twig's official docs


For example, you can use:

{{ node.body.value|striptags }}
{{ paragraph.field_text.value|striptags }}

The problem with using twig's |striptags is double encoding of html entities, not markup, so & becomes &amp; and then &amp;amp; – Berdir

11
  • 8
    the content examples are not correct. See drupal.stackexchange.com/questions/198694/…. What you can use is content.field_text.0, then you only get the inner part of the first field item, without the field templates. That's especially useful for lists, references and so on, where you want the formatted output, not the raw value
    – Berdir
    Commented Feb 13, 2017 at 7:21
  • 2
    Better, but still not quite correct. content.field_myfield|striptags doesn't work, you can't pass a render array to that. You would need to render it first and then pass it through that. striptags and so on also have problems with & and other characters that can get encoded twice, so you oftne need a |striptags|raw actually.
    – Berdir
    Commented Feb 13, 2017 at 12:35
  • 2
    Just |raw leaves the html tags and prints them. The problem with |striptags is then double encoding of html entities, not markup, so & becomes &amp; and then &amp;amp;
    – Berdir
    Commented Feb 13, 2017 at 13:40
  • 2
    This is not double escaping, you can see that < and > are displayed correctly. The ampersand is probably already single escaped before you output it. But the question is about a plain text field, not a formatted text field processed by text filters. (To answer this not asked question, the raw value (if someone really wants that) would still be in .value and it would be correctly single escaped by Twig, for security reasons, because you never should output a formatted text field unfiltered)
    – 4uk4
    Commented Dec 27, 2017 at 9:32
  • 2
    Yes, this is what I meant (auto-escaping = single escaping). So your examples for outputting entity field values are perfect, only without the striptag filter, because this would produce the ugly double escaped output. (BTW the &amp; output in your example is wrong, this doesn't happen in autoescaping unless the field content is already escaped one time).
    – 4uk4
    Commented Dec 27, 2017 at 10:21
14

Here is the code:

{{ content.field_title|render|striptags|trim|lower }}

it works fine.

4
  • 1
    Thanks Thristy Six, this worked like a charm. {% set parp_state = participating_state_1|render|striptags|trim|lower %} {% if parp_state == "60" %}
    – Matt
    Commented Aug 3, 2021 at 10:11
  • 2
    This is the best solution I've found; I think it should be the accepted answer Commented Sep 10, 2021 at 18:24
  • 1
    I tried all of the solutions and this was the only one that worked for appending a field value to a class name and then adding that class attribute to a div.
    – rtd1123
    Commented Apr 7, 2022 at 1:52
  • caveat: |striptags is double encoding so & becomes &amp ,at least for me
    – john Smith
    Commented Aug 8, 2022 at 5:29
8

You can use Twig Field Value module in this case. After install this module You will get access to partial data from field render arrays. For ex.

{{ content.field_name|field_value }}
content.field_image|field_target_entity.uri.value

etc. More info on projects page

2
  • great answer, IMO this should be in core Commented May 23, 2023 at 15:20
  • Be careful with this one. One day you wonder why the value not refreshes or is printed although user should not have access. Then remove |field_value and simply use field templates removing the wrappers. |field_value tends to circumvent default caching and permission.
    – leymannx
    Commented Nov 1, 2023 at 13:59
6

None of the suggestions so far worked for my text field. My text field is not multivalue, just a simple text field. Here is what did work for me:

content.field_myfieldname['#items'].getString()
4
{{ content.body | raw }} 

get the raw field value in a twig template

2

Another way is preprocess the plain text through a text_filter. With this method you keep leveraging Drupal's text filters like basic_html. So this way is more secure than rendering the plain text as html in twig.

In this example the field-name is 'field_myfield'. The text-formatter is 'basic_html'. But you could also use 'full_html' or any other available formatter. And it is a paragraph of type 'hero' is preprocessed.

In THEME.theme

/**
 * Implements TEMPLATE_preprocess_HOOK().
 */
function THEME_preprocess_paragraph__hero(&$variables) {
  $entity = $variables['paragraph'];

  $variables['content']['field_myfield'] = check_markup(
    $entity->get('field_myfield')->getValue()[0]['value'],
    'basic_html',
    $entity->language()->getId()
  );
}

And in Twig nothing has changed.

{{ content.field_myfield }}
1

In case this helps anyone, I wanted to only have the start year of a datetime range field displayed, instead of both parts of the range, within a field Twig template.

So I ended up overriding the usual field template with this:

{% if label_hidden %}
  {% if multiple %}
    <div{{ attributes.addClass(classes, 'field--items') }}>
      {% for key, item in items %}
        <h3{{ item.attributes.addClass('field--item') }}>{{ element['#items'][key].value|date('Y') }}</h3>
      {% endfor %}
    </div>
  {% else %}
    {% for key, item in items %}
      <h3{{ attributes.addClass(classes, 'field--item') }}>{{ element['#items'][key].value|date('Y') }}</h3>
    {% endfor %}
  {% endif %}
{% else %}
  <div{{ attributes.addClass(classes) }}>
    <div{{ title_attributes.addClass(title_classes) }}>{{ label }}</div>
    {% if multiple %}
      <div class="field--items">
    {% endif %}
    {% for key, item in items %}
      <h3{{ item.attributes.addClass('field--item') }}>{{ element['#items'][key].value|date('Y') }}</h3>
    {% endfor %}
    {% if multiple %}
      </div>
    {% endif %}
  </div>
{% endif %}
0
{{ entity.field_name.value }}

will give you either an empty array (if the field is not filled in) or a string (if it is). Therefore, you cannot assume this is a string.

For example, if you pipe it to a function which expects a string, like:

{{ entity.field_name.value|split(',') }}

This might work only if the field has data, but will throw a warning (in PHP 7) or an error (in PHP 8), such as explode() expects parameter 2 to be string.

Always test your template with empty fields and non-empty fields before using it. Always check your error log , and never assume entity.field_name.value will be a string.

Also, note that this technique will show you the first value in a multi-value field.

See also https://www.drupal.org/project/drupal/issues/3215952#comment-14498809

0

I have found this useful article from Sarah Carney, in which she explains how to get the values from different field types: body, text, list, link, image, file, boolean, number, email, phone, date, and taxonomy/entity reference.

This is an example that she explains to get the name tags in a ul (Example 2)

{% if content.field_name[0] %}
  <ul>
    {% for key, item in content.field_name if key|first != '#' %}
      <li>{{ item['#title'] }}</li>
    {% endfor %}
  </ul>
{% endif %}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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