0

I need to put an image field url into the header meta tag (open graph image). The obvious ways to put things in the header are in html.html.twig, hook_preprocess_html, and hook_page_attachments. But in any of these, how do I access the content to be rendered in order to see what the image url is?

And this is complicated by the fact that the rendered entity is a commerce product, while the desired image field is on the product_variation entity, with drupal commerce rendering the desired variation using a query string and an EntityViewBulder::alterBuild.

This means I can't use e.g. $product = \Drupal::routeMatch()->getParameter('commerce_product') because we wouldn't know what variation is being shown.

Once the variation is to be had, it would be fine to get the delta 0 image from the image field on the variation.

1 Answer 1

0

The essence of the problem is how to move a value from the field template preprocess to the html theme preprocess. I did this by using a one-off static variable function, provided by a helper module:

/*
 * Generates a static variable in the scope of the page request
 * to set instantiate like
 *  $var = &p2p_helpers_ogimage_function(); $var = 'my value';
 *    to read the var,
 *   instantiate without.
 */
function &p2p_helpers_ogimage_function() {
  $var = &drupal_static(__FUNCTION__);
 if (!isset($var)) {
    // generate contents of static variable
    $var = NULL;
  }
  return $var;
}

Then I can do the rest in the THEME.theme file.

In the field template preprocess hook I can do this:

/**
 * Prepares variables for blazy.html.twig templates.
 */
function p2p_bootstrap_preprocess_blazy(&$variables) {
  $url = p2p_helpers_ogimage_function();
  if (!$url) {
    $url = &p2p_helpers_ogimage_function();
    $url = $variables['url'];
  }
  ...

This will fill check if the variable is already set, so it only sets it once for the first image in the field.

Then in hook_preprocess_html:

$url = p2p_helpers_ogimage_function();
if ($url) {
  $ogimage = [
    '#tag' => 'meta',
    '#attributes' => [
      'property' => 'og:image:secure_url',
      'content' => $url,
    ],
  ];

  $variables['page']['#attached']['html_head'][] = [$ogimage, 'og:image'];
}

Does anyone see any better way to do this?

2
  • You can try to attach the meta tag to the build array of the field. This should bubble up to the page in the rendering process.
    – 4uk4
    Commented Feb 20, 2017 at 17:08
  • Yes, the last snippet should basically work anywhere where you can define render arrays. You could for example write a field formatter for this. We often use our sharemessage project for this, which can do this out of the box based on tokens: drupal.org/project/sharemessage
    – Berdir
    Commented Feb 20, 2017 at 19:39

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.