Problem/Motivation

Steps to reproduce:

Create a new theme. In the .info.yml file include this line but don't declare any libraries underneath it or append [].

libraries:

When installing your theme or clearing caches you should see the following:

Warning: Invalid argument supplied for foreach() in Drupal\Core\Extension\ThemeHandler->addTheme() (line 203 of core/lib/Drupal/Core/Extension/ThemeHandler.php).

Proposed resolution

Either ignore that libraries is not an array at this point, or throw a meaningful exception. Either would improve the experience.

Since the following keys in theme .info.yml are allowed to be empty without throwing errors we have landed on ignoring the key without a value:

ckeditor_stylesheets
quickedit_stylesheets
libraries-extend
libraries-override

Remaining tasks

Patch
Tests
Review

User interface changes

n/a

API changes

n/a

Data model changes

n/a

CommentFileSizeAuthor
#45 empty-libraries-in-theme-2594937-45.patch2.3 KBAnonymous (not verified)
#41 empty-libraries-in-theme-2594937-40.patch1.75 KBchgasparoto
#41 empty-libraries-in-theme-2594937-38-diff.patch792 byteschgasparoto
#38 empty-libraries-in-theme-2594937-38.patch2.32 KBPeacog
#36 empty-libraries-in-theme-2594937-36.patch2.4 KBPeacog
#34 interdiff-2594937-28-34.txt1.4 KBPeacog
#34 empty-libraries-in-theme-2594937-34.patch2.39 KBPeacog
#30 interdiff-2594937-19-30.patch957 bytesSagar Ramgade
#28 empty_libraries_in-2594937-28.patch1.69 KBiStryker
#25 interdiff-2594937-19-25.patch956 bytesSagar Ramgade
#21 emptyLibrary.png18.67 KBjoyceg
#19 empty_libraries_in-2594937-19.patch1.69 KBalvar0hurtad0
#17 2594937-17.patch2.36 KBaerozeppelin
#17 interdiff-2594937-6-17.txt1.63 KBaerozeppelin
#6 empty_libraries_in-2594937-6.patch746 bytescilefen
#2 empty_libraries_in-2594937-2.patch976 bytescilefen
Support from Acquia helps fund testing for Drupal Acquia logo

Comments

Cottser created an issue. See original summary.

cilefen’s picture

Status: Active » Needs review
FileSize
976 bytes
star-szr’s picture

Status: Needs review » Needs work

Thanks for the patch @cilefen!

It seems like the following keys don't give any kind of error when they are left empty:

ckeditor_stylesheets
quickedit_stylesheets
libraries-extend
libraries-override

So maybe we should just do the same for a more consistent and friendly experience rather than throwing an exception. This came up in real world usage commenting out a lone library in the .info.yml file for testing purposes.

Where we should throw a friendlier exception IMO is for keys like 'regions:', where when present you are actually overriding something. (That should be a separate issue.)

cilefen’s picture

+++ b/core/lib/Drupal/Core/Extension/ThemeHandler.php
@@ -313,6 +314,11 @@ public function rebuildThemeData() {
+      if (!is_array($theme->info['libraries'])) {
+        $name = $theme->info['name'];
+        throw new ConfigException(sprintf('The libraries configuration for theme %s is not an array.', $name));
+      }

So, maybe quietly make it an array if it isn't one then.

star-szr’s picture

Or what libraries-override and libraries-extend do is just wrap in an !empty check:

    // Add libraries overrides declared by this theme.
    if (!empty($theme->info['libraries-override'])) {
      foreach ($theme->info['libraries-override'] as $library => $override) {
        $values['libraries_override'][$theme->getPath()][$library] = $override;
      }
    }
cilefen’s picture

Status: Needs work » Needs review
FileSize
746 bytes
Wim Leers’s picture

Component: asset library system » theme system
star-szr’s picture

Status: Needs review » Needs work

Good call, thanks @Wim Leers!

I guess this needs work for tests at this point.

anchal29’s picture

What exactly that test should do? If i'm going right then it should make sure that $info['libraries'] and themes->library are empty? or something else need to be done?

claudiu.cristea’s picture

Issue tags: +#SprintLUX2016, +SprintWeekend2016
raulbordallo@gmail.com’s picture

Assigned: Unassigned » raulbordallo@gmail.com

I working on it.

raulbordallo@gmail.com’s picture

Status: Needs work » Reviewed & tested by the community

This patch #6 work for me.

raulbordallo@gmail.com’s picture

Assigned: raulbordallo@gmail.com » Unassigned
betarobot’s picture

#6 worked fine for me too.

claudiu.cristea’s picture

Issue tags: -#SprintLUX2016
alexpott’s picture

Status: Reviewed & tested by the community » Needs work

Still needs tests.

aerozeppelin’s picture

Status: Needs work » Needs review
FileSize
1.63 KB
2.36 KB

Tests for #6.

gvso’s picture

Status: Needs review » Needs work
+++ b/core/modules/system/tests/themes/test_theme_libraries_empty/test_theme_libraries_empty.info.yml
@@ -0,0 +1,12 @@
\ No newline at end of file

\No newline at end of file patch warning

+++ b/core/tests/Drupal/Tests/Core/Extension/ThemeHandlerTest.php
@@ -138,6 +138,20 @@ public function testRebuildThemeData() {
+    catch (\Exception $e) {
+      $this->fail('Warning: Invalid argument supplied for foreach() thrown.');
+    }

Shouldn't we add a better description of the exception?

alvar0hurtad0’s picture

This patch try to solve #18

gvso’s picture

#19 looks good to me.

joyceg’s picture

FileSize
18.67 KB

#19 works fine. It was applied successfuly.

joyceg’s picture

Status: Needs review » Reviewed & tested by the community
cilefen’s picture

Version: 8.0.x-dev » 8.1.x-dev
Status: Reviewed & tested by the community » Needs review

@joyceg: Cool, but we need a little more in a review. Did you test with a bad theme file and observe the proper error? Did you execute the test on its own to prove it works? We don't know.

On a side note, please do not post images of console output. It is enough to say that the patch applies. We all know what that means.

The final release of 8.0.x is out so this is moved to 8.1.x.

star-szr’s picture

Status: Needs review » Needs work

This is looking really good, happy to see this still active :)

  1. +++ b/core/tests/Drupal/Tests/Core/Extension/ThemeHandlerTest.php
    @@ -138,6 +138,20 @@ public function testRebuildThemeData() {
    +   * Tests Empty libraries in theme.info.yml file
    

    I think this would more accurately be "Tests empty libraries in theme .info.yml files."

    Making it into a complete sentence ending in a period, normalized capitalization and changing the theme.info.yml.

  2. +++ b/core/tests/Drupal/Tests/Core/Extension/ThemeHandlerTest.php
    @@ -138,6 +138,20 @@ public function testRebuildThemeData() {
    +      $this->assertTrue(TRUE, 'No Warnings encountered.');
    

    This could be lowercase W - "No warnings" otherwise the capitalization is a bit odd.

Sagar Ramgade’s picture

Here it goes, patch attached addresses #24.

martin107’s picture

Status: Needs work » Needs review

Fixes everything from #24, triggering testbot.

Status: Needs review » Needs work

The last submitted patch, 25: interdiff-2594937-19-25.patch, failed testing.

iStryker’s picture

@Sagar Ramgade you forgot a period.

Reroll patch for testing

star-szr’s picture

An interdiff would be great here, at a glance looks OK but I always encourage interdiffs.

Sagar Ramgade’s picture

@Cottsert, interdiff attached which includes suggestion by @iStryker.

Status: Needs review » Needs work

The last submitted patch, 30: interdiff-2594937-19-30.patch, failed testing.

almaudoh’s picture

Status: Needs work » Needs review

Back to NR. Fail was due to an interdiff posted as a patch.

Wim Leers’s picture

Status: Needs review » Needs work

The test method name does not reflect what it is testing.

The test asserts true is true, instead of using the pass() method.

The assertion messages in the test don't make sense: they call exceptions "warnings" and don't mention what this is about: the libraries key.

The actual change looks fine :)

Peacog’s picture

Here's a patch that addresses @Wim Leers suggestions, and adds back the test .info.yml file that fell out of the patch a few rolls back.

The test asserts true is true, instead of using the pass() method.

ThemeHandler test cases are based on PHPUnit, which doesn't have a pass() method, so I've kept the assertTrue().

The assertion messages in the test don't make sense: they call exceptions "warnings"

"Warnings" is correct. The bug manifests as PHP warnings in the DB log.

Status: Needs review » Needs work

The last submitted patch, 34: empty-libraries-in-theme-2594937-34.patch, failed testing.

Peacog’s picture

Status: Needs work » Needs review
FileSize
2.4 KB

There was a problem with adding the test .info.yml file. Trying again...

Status: Needs review » Needs work

The last submitted patch, 36: empty-libraries-in-theme-2594937-36.patch, failed testing.

Peacog’s picture

Status: Needs work » Needs review
FileSize
2.32 KB

And again...

Peacog’s picture

sebas5384’s picture

Hey! we are reviewing this issue at a code sprint from DrupalCamp Campinas 2016 Brazil.
http://campinas2016.drupalcamp.com.br

chgasparoto’s picture

We reviewed the patch and worked. @sebas5384 @feraline @racarvalho1987

After run the coder we found a variable that was not being used and we removed it.

It's ready to be commited.

Thank you!

chgasparoto’s picture

Status: Needs review » Reviewed & tested by the community

The last submitted patch, 41: empty-libraries-in-theme-2594937-38-diff.patch, failed testing.

Status: Reviewed & tested by the community » Needs work

The last submitted patch, 41: empty-libraries-in-theme-2594937-40.patch, failed testing.

Anonymous’s picture

Sorry we have upload the wrong patch file.

sebas5384’s picture

Status: Needs work » Needs review
erickbj’s picture

Status: Needs review » Reviewed & tested by the community

Reviewed patch at #45 and it works, marking as RTBC.

Wim Leers’s picture

The proposed resolution in the IS says:

Either ignore that libraries is not an array at this point, or throw a meaningful exception. Either would improve the experience.

So this patch went with the second option.

Is that really desirable though? It means it's okay for a key without values to exist in a theme's *.info.yml file.

I think this change needs to be carefully considered. One could argue for either option. I think this compiles with https://en.wikipedia.org/wiki/Robustness_principle, so I'm personally fine with it (even though it makes me twitch as a developer who favors strictness).

Status: Reviewed & tested by the community » Needs work

The last submitted patch, 45: empty-libraries-in-theme-2594937-45.patch, failed testing.

Wim Leers’s picture

Status: Needs work » Reviewed & tested by the community

Random fails in Drupal\field\Tests\Update\FieldUpdateTest. Re-testing and restoring previous status.

Status: Reviewed & tested by the community » Needs work

The last submitted patch, 45: empty-libraries-in-theme-2594937-45.patch, failed testing.

cilefen’s picture

Status: Needs work » Reviewed & tested by the community

Same as #50

Status: Reviewed & tested by the community » Needs work

The last submitted patch, 45: empty-libraries-in-theme-2594937-45.patch, failed testing.

Peacog’s picture

Status: Needs work » Reviewed & tested by the community

The same random failures are happening elsewhere too, so the errors seem to be unrelated to this patch specifically. See #2749955: Random fails in UpdatePathTestBase tests

star-szr’s picture

Issue summary: View changes

@Wim Leers thanks for the thoughtful input! I think the strictness ship has sailed since most of the other keys allow for a key without values as I pointed out in #3 (added that info to the issue summary). Not sure those have coverage but they worked at least at the time of that writing.

+1 to RTBC from me.

Wim Leers’s picture

#55: that is then fully consistent behavior. So, no more concerns then! :)

cilefen’s picture

almaudoh’s picture

This is already RTBC, so maybe this is a late comment, but considering that this seems to share the same characteristics with #2730807: WSOD on admin/modules if description is set but is NULL in module.info.yml and #2558645: Malformed module.info.yml prevents install with a confusing error, we should look for a more robust and generic solution. Like using sane defaults for when any of the required entries are missing from a .info.yml file, or better yet, displaying a more helpful message for the admin to react to, rather than the WSOD.

xjm’s picture

Version: 8.1.x-dev » 8.2.x-dev

So from a release management perspective, making this key interpret empty as empty, as it were, is mostly non-disruptive, and consistent with the behavior of some other keys. We also have @Cottser's signoff for the theme system.

However, in general, I too would prefer to fail meaningfully rather than silently. I also agree with @almaudoh's feedback above. The disadvantage of removing the exception here to silently accept an empty value is that we cannot then make it throw an explicit error again in a minor release. So, for example, if we went for a holistic solution for this and #2730807: WSOD on admin/modules if description is set but is NULL in module.info.yml and the like, we would just provide a BC fallback for the keys that do already allow empty values, but this issue would move us away from failing in a way that communicates something.

On the other hand, from a DX perspective, it is actually pretty convenient to just allow an empty template that you fill in, especially for such basic functionality as defining a new project and especially for the theme developer audience. From @Cottser:

This came up in real world usage commenting out a lone library in the .info.yml file for testing purposes.

To me, that is a compelling reason to allow empty non-required keys in .info.yml files in general. The only risk is that you don't realize you left it blank, but that seems a reasonable risk to me because if it's blank, and you go to the source and it seems blank, then that explains why it's blank. :)

That would also point to initializing the optional keys to array or emptystring or whatever at a higher level, rather than going through every place one of these keys is defined and adding a babysitting if (!empty())) check, but that is something that would work as a followup.

I've argued with myself back and forth a lot about whether to just commit this patch, which is probably a sign that we should indeed get that framework manager review. :) I do think we should at least move it to 8.2.x only. I'll reach out to the framework managers.

Thanks everyone!

xjm’s picture

(Saving credit.)

xjm’s picture

Adding @racarvalho1987 per #41.

alexpott’s picture

I think this change is fine - the most important thing is that it behaves predictably - and I don't think this changes that. If you have an empty libraries key in your theme you don't expect it to break or load any libraries. If you have a broken library declared in the libraries key this doesn't affect that either so I'm +1 from a framework manager perspective.

alexpott’s picture

Status: Reviewed & tested by the community » Fixed

Committed 2fb3a05 and pushed to 8.2.x. Thanks!

  • alexpott committed 2fb3a05 on 8.2.x
    Issue #2594937 by Peacog, cilefen, Sagar Ramgade, chgasparoto,...
alexpott’s picture

I think we should open a follow to address this in a little bit more of generic way... So both modules and themes have a default array to merge to the information in .info.yml - see _system_rebuild_module_data() and \Drupal\Core\Extension\ThemeHandler::rebuildThemeData(). I think it is worth considering that if the yaml value is NULL we should use the default. That would fix both #2730807: WSOD on admin/modules if description is set but is NULL in module.info.yml and #2594937: Empty 'libraries:' in theme .info.yml file produces confusing PHP warning

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.