Using 'base hook' in the theme hooks doesn't find theme suggestions (e.g. layout--onecol -> layout--onecol--node).

This has been a struggle for Display suite, see #2802429: Display layout twig not overridable..

A work around is to explicitly define 'template_preprocess_layout' in the preprocess functions key.

(needs a better issue summary)

Also, wondering whether this qualifies for 8.x-3.x directly since it's quite the annoying bug.

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

swentel created an issue. See original summary.

swentel’s picture

Status: Active » Needs review
FileSize
694 bytes
swentel’s picture

Title: remove 'base hook' key from layout theme hooks as it doesn't find definitions » remove 'base hook' key from layout theme hooks as it doesn't find template suggestions
swentel’s picture

Issue summary: View changes
tim.plunkett’s picture

As much as 'base hook' should 100% work, I'm also in favor of going with this.

The last submitted patch, 2: 2862683-2.patch, failed testing.

Status: Needs review » Needs work

The last submitted patch, 5: 2862683-layout-5.patch, failed testing.

swentel’s picture

Status: Needs work » Needs review
FileSize
4.91 KB

failing test - might be a bit weird, but my head is almost frozen ..

looking at the diff, I'm not even sure whether it even explains the problem nicely as the suggestion alter hook code is kind of cheating in a way

going to bed now.

tim.plunkett’s picture

The "fix" for the fail in #5 seems bad.

diff --git a/core/modules/layout_discovery/tests/src/Kernel/LayoutTest.php b/core/modules/layout_discovery/tests/src/Kernel/LayoutTest.php
index 9d4c446..7870b81 100644
--- a/core/modules/layout_discovery/tests/src/Kernel/LayoutTest.php
+++ b/core/modules/layout_discovery/tests/src/Kernel/LayoutTest.php
@@ -135,7 +135,7 @@ public function renderLayoutData() {
     ];
 
     $data['layout_onecol'][] = <<<'EOD'
-<div data-drupal-selector="edit-layout" class="layout--onecol">
+<div class="layout--onecol">
   <div class="layout-region layout-region--content">
     This is the content
   </div>

Status: Needs review » Needs work

The last submitted patch, 8: 2862683-8-fail.patch, failed testing.

swentel’s picture

So what I'm seeing is that 'data-drupal-selector="edit-layout"' is gone, the wrapper is still there with the layout--onecol class on .. not sure exactly where that selector is set atm or why it's needed.

swentel’s picture

Looked at other theme functions using 'base hook' in core and there are a few, like field, block, comment
I'm starting to wonder whether we simply can't get behind the fact that ds layouts aren't prefixed with 'layout--' (if I do that, switching happens ...)

swentel’s picture

So, after stepping through the discovery mechanism, I think I figured out why this isn't working, unless I'm missing something.

  // Find templates that implement possible "suggestion" variants of registered
  // theme hooks and add those as new registered theme hooks. See
  // drupal_find_theme_functions() for more information about suggestions and
  // the use of 'pattern' and 'base hook'.
  $patterns = array_keys($files);
  foreach ($cache as $hook => $info) {
    $pattern = isset($info['pattern']) ? $info['pattern'] : ($hook . '__');
    if (!isset($info['base hook']) && !empty($pattern)) {

Because layout hooks have 'base hook' key set explicitly, suggestions will not be registered.
Now, AFAICS, this isn't a problem of the layout module (as you already mentioned somewhere else), but a bug in the theme discovery code, so I think we can close this one.

Not sure about a proper fix though, but I've made an insane workaround for DS, see https://www.drupal.org/node/2802429#comment-12009414 - so I can live with that for now :)

tim.plunkett’s picture

Title: remove 'base hook' key from layout theme hooks as it doesn't find template suggestions » 'base hook' key prevents template suggestions from working
Component: layout.module » theme system

What about this?

effulgentsia’s picture

Status: Needs work » Needs review
FileSize
4.94 KB
780 bytes

The title of this issue isn't specific enough.

+++ b/core/modules/field_layout/tests/modules/field_layout_test/field_layout_test.module
@@ -0,0 +1,15 @@
+  if (isset($_GET['test_layout_theme_suggestion']) && $hook == 'layout__twocol') {

The only reason this test is failing is because we're checking $hook, but per the docs for hook_theme_suggestions_alter(), what we really need to check in this case is $variables['theme_hook_original']. When I make that change, this test passes. See attached patch.

I'm starting to wonder whether we simply can't get behind the fact that ds layouts aren't prefixed with 'layout--' (if I do that, switching happens ...)

I suspect there might still be a core bug if the specific layout and/or suggestion isn't prefixed with 'layout--'. But that's not what this issue title, summary, or test in patch is currently about. Do we want to repurpose this issue to be about that, or is there still some bug with layouts/suggestions that even are prefixed as such that needs to be addressed first?

Status: Needs review » Needs work

The last submitted patch, 15: 2862683-15-fail.patch, failed testing.

effulgentsia’s picture

Status: Needs work » Postponed (maintainer needs more info)

#15's retest passed, so setting to "maintainer needs more info" for figuring out how we want to proceed with this issue, per #15.

csedax90’s picture

I've tried #15 with configuration described here: https://www.drupal.org/node/2867794
but it doesn't work. Drupal returns:

Twig_Error_Loader: Template "themes/bootstrap/templates/bs-2col.html.twig" is not defined (Drupal\Core\Template\Loader\ThemeRegistryLoader: Unable to find template "themes/bootstrap/templates/bs-2col.html.twig" in the Drupal theme registry.) in "modules/ds/templates/ds-entity-view.html.twig" at line 10. in Twig_Loader_Chain->getCacheKey() (line 115 of vendor/twig/twig/lib/Twig/Loader/Chain.php).

csedax90’s picture

Status: Postponed (maintainer needs more info) » Needs work
fastangel’s picture

@sedax this isn't related with core this is a problem with boostrap theme https://www.drupal.org/node/2871551

fastangel’s picture

Status: Needs work » Postponed (maintainer needs more info)
markhalliwell’s picture

@fastangel, the Bootstrap base theme has nothing to do with this issue or @sedax's "issue".

edit: I was wrong

fastangel’s picture

Sorry @markcarver I forgot to tell. The error I comment is about the @sedax's issue :)

csedax90’s picture

Sorry, in DS issues tell me that the problem is core, here tell me it's bootstrap, i don't know what patches try XD

gambry’s picture

This is really a quite big issue. Websites working well with 8.2 are forced to update to 8.3 (to get security patches and bug fixes) and when they do if you use layout suggestions templates they won't work anymore.

DS got a workaround mentioned on #13, which so far only works if on your layout you specify the class '\Drupal\ds\Plugin\DsLayout'. The workaround makes its best to fix this issue for DS users (well done), but from my understanding specifying the DsLayout class creates an unneeded dependency?

Solution suggested on #2 - #5 fixes the problem, although from what I can see is not (yet) the right direction(?).
Also #15 passes. But isn't hat supposed to fail?

gambry’s picture

I answer my own comment:

Also #15 passes. But isn't hat supposed to fail?

According to this IS is supposed to fail, but it doesn't. As @effulgentsia explained in #15:

I'm starting to wonder whether we simply can't get behind the fact that ds layouts aren't prefixed with 'layout--' (if I do that, switching happens ...)

I suspect there might still be a core bug if the specific layout and/or suggestion isn't prefixed with 'layout--'. But that's not what this issue title, summary, or test in patch is currently about. Do we want to repurpose this issue to be about that, or is there still some bug with layouts/suggestions that even are prefixed as such that needs to be addressed first?

So I confirm there is an issue with layouts not being prefixed with layout--.
I succesfuly load my suggestions if I prefix both my layout definition with layout__ and it's (base) template with layout--, i.e.:

layout__onecol_hero:
  label: One column layout with hero (fixed)
  template: templates/layouts/layout--onecol-hero
  regions:
    hero:
      label: Hero
    main:
      label: Main
    footer:
      label: Footer

And of course all .twig templates prefixed with layout-- as well.

What's interesting is the layout defined on #15 test is with one underscore, but that doesn't work for me. I must use 2 underscores.

Worth mentioning I've only tested this against DS. I'll give a try against Panels as well and if we confirm the issue is with layout prefix we can change the IS (or open a new issue, as this one already looks messy).

tassos’s picture

@gambry did you manage to give it a try for panels?

gambry’s picture

Panels is slightly different, as - at least on my tests - you don't have suggestions and you have to create your own either with hook_theme_suggestions_alter() or hook_theme_suggestions_HOOK_alter() on mytheme.theme, where HOOK is the bundle name of your layout with layout_plugin and the base hook 'layout' with layout_discovery + core layout subsystem.

I managed to get my suggestions working just updating mytheme.theme from:

function mytheme_theme_suggestions_onecol_hero_alter(array &$suggestions, array $variables, $hook) {
  $suggestions[] = 'onecol_hero__front';
}

to

function mytheme_theme_suggestions_layout_alter(array &$suggestions, array $variables, $hook) {
  if($variables['theme_hook_original'] == 'onecol_hero') {
    $suggestions[] = 'layout__onecol_hero__front'';
  }
}

and renaming the file template suggestion from onecol-hero--front to layout--onecole-hero--front.

No other changes were needed.

gambry’s picture

So I confirm there is an issue with layouts not being prefixed with layout--.

Instead of that I would say there is an inconsistency on how layout templates and suggestions are loaded.

On 8.3 with layout discovery and this layout:

onecol_hero:
  label: One column layout with hero (fixed)
  template: templates/layouts/onecol-hero
  regions:
    hero:
      label: Hero
    main:
      label: Main
    footer:
      label: Footer
  • Base template templates/layouts/onecol-hero.html.twig loads correctly.
  • Suggesting onecol_hero__front does NOT load templates/layouts/onecol-hero--front.html.twig is not loaded.
  • Suggesting layout__onecol_hero__front DOES load templates/layouts/layout--onecol-hero--front.html.twig

Can anyone confirm this behaviour?

tim.plunkett’s picture

Title: 'base hook' key prevents template suggestions from working » 'base hook' key prevents template suggestions from working when the theme hook is not prefixed by $base_hook . '__'
FileSize
1.05 KB
2.66 KB

Here's what I'm seeing.

I want to preprocess a layout with the name foobar.

my_module_preprocess_layout__foobar() should work.

Currently it does not.

I believe this is because of the regex in Registry::postProcessExtension():
/^{$prefix}_preprocess_(((?:[^_]++|_(?!_))+)__.*)/
This very complex (and slightly malformed) regex would have the following matches:
0 => my_module_preprocess_layout__foobar
1 => layout__foobar
2 => layout

It then checks the existing theme hooks for 'layout__foobar', which doesn't exist.

If we switch the regex to /^{$prefix}_preprocess_(((?:[^_]++|_(?!_))+)__(.*))/, then we have the following matches:
0 => my_module_preprocess_layout__foobar
1 => layout__foobar
2 => layout
3 => foobar

Then if we check for 'foobar' and fallback to checking for 'layout__foobar'.
This allows the expected behavior to finally occur!

tim.plunkett’s picture

Status: Postponed (maintainer needs more info) » Needs review

The last submitted patch, 30: 2862683-layout-30-FAIL.patch, failed testing. View results

tim.plunkett’s picture

I'm not actually sure that I'm thinking of the same issue anymore. This was originally about template suggestions, not preprocess suggestions...
Might have to make a new issue.


Added docs so no one else has to guess what that regex does.
This patch adds the final $matches[3] by adding another set of parentheses.

tim.plunkett’s picture

Title: 'base hook' key prevents template suggestions from working when the theme hook is not prefixed by $base_hook . '__' » 'base hook' key prevents template suggestions from working
Status: Needs review » Postponed (maintainer needs more info)

I think my comments from #30 onward are really better served as a separate followup to #2559825: Preprocess functions from base hooks not triggered for theme hooks not using the __ pattern, restoring this issue.

tim.plunkett’s picture

Version: 8.4.x-dev » 8.5.x-dev

Drupal 8.4.0-alpha1 will be released the week of July 31, 2017, which means new developments and disruptive changes should now be targeted against the 8.5.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

joelpittet’s picture

Can this issue be closed, was it resolved in the follow-up issues? The issue summary is a bit lacking (as it mentions)

gambry’s picture

@joelpittet bug it's still there AFAIK, but I would rather open a new issue instead keeping this one open.

The starting point of the new issue should be #15 "I suspect there might still be a core bug if the specific layout and/or suggestion isn't prefixed with 'layout--'". There is already a bit of investigation from #25 to #29.

Will create the new issue, post the link here and the close this in favour of the other one.

gambry’s picture

Status: Postponed (maintainer needs more info) » Closed (duplicate)

Closing this in favour of https://www.drupal.org/node/2911996