I am using 25 words for the teaser view for a particular content type, however the token for the meta description [node:summary] seems to use 25 characters for the trim value. Do you know how I can work around this, is there a token for the smart trimmed value of the body in the Metatag module?

Thanks for the help!

Comments

interdruper’s picture

Issue tags: -description metatag +description metatag token node summary

The problem is that the Smart Trim module uses the same element ('trim_length') for storing the length in chars and the length in words. This element is used by the core's Node module for building the value of the [node:summary] token. And the Node module assumes that this length is about characters.

I run into this problem using the [node:summary] token (as usual) for the description metatag in the Metatag module, and finding that the metatag length was very short (even shorter if the body starts with HTML tags).

Here is the code that fix the problem for me, in fact it is just a workaround. If the approach is interesting for someone else, I can provide it in form of patch to the Smart Trim module.

/**
 * Implements hook_tokens_alter().
 *
 * See issue https://www.drupal.org/node/2139587
 */
define('NODE_SUMMARY_TOKEN_TRIM_LENGTH', '200');

function smart_trim_tokens_alter(array &$replacements, array $context) {

  // Only proceed if this is working on a node.
  if ($context['type'] == 'node' && !empty($context['data']['node'])) {
    // Loop through each of the tokens.
    foreach ($context['tokens'] as $name => $original) {
      // Only deal with the 'node:summary' token, that's the one being fixed.
      if ($name == 'summary') {
        // A shortcut to the node being processed.
        $node = $context['data']['node'];

        // Work out the langcode being used.
        if (isset($context['options']['language'])) {
          $langcode = $context['options']['language']->language;
        }
        else {
          $langcode = NULL;
        }

        // Decide whether the string needs to be sanitized.
        $sanitize = !empty($context['options']['sanitize']);

        if ($items = field_get_items('node', $node, 'body', $langcode)) {
          $instance = field_info_instance('node', 'body', $node->type);
          $field_langcode = field_language('node', $node, 'body', $langcode);

          // If the summary is not empty, use it.
          if (!empty($items[0]['summary'])) {
            $output = $sanitize ? _text_sanitize($instance, $field_langcode, $items[0], 'summary') : $items[0]['summary'];
          }

          // Attempt to provide a suitable version of the 'body' field.
          else {
            $output = $sanitize ? _text_sanitize($instance, $field_langcode, $items[0], 'value') : $items[0]['value'];
            // A summary was requested.
            if ($name == 'summary') {
              if (isset($instance['display']['teaser']['settings']['trim_length'])) {
                $trim_length = $instance['display']['teaser']['settings']['trim_length'];

                // Here is the fix: check if 'trim_length' is less than
                // the recommended 150-200 chars for description metatag
                // and adjust it accordingly.
                if (intval($trim_length) < intval(NODE_SUMMARY_TOKEN_TRIM_LENGTH)) {
                  $trim_length = NODE_SUMMARY_TOKEN_TRIM_LENGTH;
                }
              }
              else {
                // Use default value ( variable_get('teaser_length', 600); )
                $trim_length = NULL;
              }
              // Generate an optionally trimmed summary of the body field.
              $output = text_summary($output, $instance['settings']['text_processing'] ? $items[0]['format'] : NULL, $trim_length);
            }
          }
          // Override the original value.
          $replacements[$original] = $output;
        }
      }
    }
  }
}

duncan.moo’s picture

Issue tags: -description metatag token node summary
Related issues: +#2782455: Smart Trim Tokens for text with summary fields

I have taken a slightly different approach, which I would appreciate others' input on. I have submitted a patch which adds a dynamic smart trim token (https://www.drupal.org/node/2782455).

The patch does not trim on word-count though, which was part of your OP, but it does respect word boundaries.

voleger’s picture

Status: Active » Postponed

Thanks for the code snippet @interdruper !

Module introduce trim_type words which not supported during token generation, so that is reasonable that module must provide token alteration to respect field teaser settings.
I will postpone this issue in favor of #2782455: Smart Trim Tokens for text with summary fields.