In a custom module (sel), I have this code:

function sel_cron()
  $accountSwitcher = Drupal::service('account_switcher');
  $account = \Drupal\user\Entity\User::load(1);

  $query = \Drupal::entityQuery('service_category');
  $dLastExtractionDate = strftime("%Y-%m-%d", strtotime("- 1 week", strtotime(\Drupal::state()->get('sel.NextEmailForNewServices'))));
  $view = views_embed_view('sel_services', 'embed_2', $dLastExtractionDate);
  $view = \Drupal::service('renderer')->render($view);   <--------------------- problem here


The expected result of the view is a table but when the result is empty (because of the value of the contextual filter), an unfiltered text ("Nothing to display today. Too bad!") should be displayed instead.
But in this case, I get this error logged:

LogicException: Render context is empty, because render() was called outside of a renderRoot() or renderPlain() call. Use renderPlain()/renderRoot() or #lazy_builder/#pre_render instead. in Drupal\Core\Render\Renderer->doRender() (line 243 of /Users/efalzon/Sites/JdP8/web/core/lib/Drupal/Core/Render/Renderer.php).

How to fix that?

  • 1
    That's a cron job though - where are you expecting it to render?
    – Clive
    Apr 28, 2020 at 12:11
  • The result of the view becomes the body of an email sent with \Drupal::service('plugin.manager.mail')->mail(some params);
    – gbmapo
    Apr 28, 2020 at 12:17
  • 4
    Oh ok, in that case you want to use renderPlain, not render. See drupal.stackexchange.com/questions/292171/…
    – Clive
    Apr 28, 2020 at 12:22

1 Answer 1

$view = \Drupal::service('renderer')->renderPlain($view);

instead of

$view = \Drupal::service('renderer')->render($view);

was the solution!
Thanks to @Clive

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.