Problem/Motivation

When a Views field renders an empty value as NULL, it triggers a fatal error on PHP 8.3+ due to strict typing.

Drupal\Component\Utility\Html::escape() expects a string, but NULL is passed via FormattableMarkup when Views field output is empty. This can result in a WSOD

TypeError: Drupal\Component\Utility\Html::escape(): Argument #1 ($text) must be of type string, null given, called in /var/www/html/docroot/core/lib/Drupal/Component/Render/FormattableMarkup.php on line 238 in Drupal\Component\Utility\Html.php on line 433

Steps to reproduce

1. Upgrade a Drupal site (8 → 9 → 10 → 11).
2. Create a View with a field that may be empty (NULL).
3. Render the View on PHP 8.3+ or higher.
4. Observe that rendering fails with the TypeError above.

Proposed resolution

Normalize NULL field values before rendering in FieldPluginBase::renderText():

$value = $this->last_render === NULL ? '' : (string) $this->last_render;

This ensures that all Views fields are safely cast to strings, preventing invalid input from reaching Html::escape() and avoiding WSODs.

Issue fork drupal-3564838

Command icon Show commands

Start within a Git clone of the project using the version control instructions.

Or, if you do not have SSH keys set up on git.drupalcode.org:

Comments

hanmant.sapkal created an issue. See original summary.

hanmant.sapkal’s picture

Title: In placeholderEscape Cast values to string » Cast values to string in placeholderEscape

elfakhar made their first commit to this issue’s fork.

elfakhar’s picture

Status: Active » Needs review
smustgrave’s picture

Version: 11.3.x-dev » 11.x-dev
Status: Needs review » Needs work
Issue tags: +Needs tests

Have not reviewed as the MR is 1000+ changes

Am tagging for tests though if this is causing a bug

Thanks

elfakhar’s picture

xjm’s picture

Title: Cast values to string in placeholderEscape » Handle blank user input or null data input in Views without UI errors and/or broken view configuration
Priority: Normal » Major
Related issues: +#3501659: Pager option 'Items per page' with empty value gives WSOD, +#3361177: An empty views pager offset field can cause a PHP type error to be triggered

I think this needs to be fixed in Views instead. FormattableMarkup should absolutely not just cast any placeholder it receives to strings; that will hide all kinds of bugs and data integrity problems instead of properly reporting them to the developer.

xjm’s picture

Component: markup » views.module
xjm’s picture

Status: Needs work » Active

Setting active as there isn't really a workable MR.

xjm changed the visibility of the branch fix-3564838-adapt-placeholderescape to hidden.

smustgrave’s picture

Copying my comments over

what if we don't case a string and instead just add ($value ?? '') that fixes it too

elfakhar’s picture

Status: Active » Needs review
smustgrave’s picture

Status: Needs review » Needs work
Issue tags: +Needs issue summary update

Now that the fix has changed we need to update the issue summary to reflect.

Also definitely think we need test coverage, especially since the related issue resulted in WSOD.

elfakhar’s picture

Title: Handle blank user input or null data input in Views without UI errors and/or broken view configuration » Views: Fatal error when rendering NULL field values due to strict string typing in PHP 8.3+
Issue summary: View changes
Status: Needs work » Needs review

Hello I’ve updated the issue summary to reflect the current fix. I also added a Kernel test that reproduces the fatal error with the original code and passes with this fix, covering the regression.

smustgrave’s picture

Status: Needs review » Needs work

Not seen a kernel test like that before, very interesting! But we already have FieldPluginBaseTest think we can just extend some of those tests to cover. May work to add a new data provider to that test for different scenarios

But I did test the fix from here combined with #3501659: Pager option 'Items per page' with empty value gives WSOD and still get a WSOD.

smustgrave’s picture

Am pinging people to try and get clear guidance on what actually needs to change so no one goes around in circles.

catch’s picture

I think we should be initialising $this->last_render to '' much earlier in the method, there are various code paths where it doesn't get initialized. Overall there doesn't seem to be any valid use case for it being NULL, so maybe it should always be initialized to a string?

I'm also struggling to see why this has to be a property, we could open an issue to look at refactoring this overall.

Version: 11.x-dev » main

Drupal core is now using the main branch as the primary development branch. New developments and disruptive changes should now be targeted to the main branch.

Read more in the announcement.

davidiio’s picture

We had this issue and the WSOD was fixed thanks to this issue here https://www.drupal.org/project/drupal/issues/3554974
I was then able to edit the view and when setting items per page to NULL I just had a "oops something went wrong" but was able to save the view anyway.
Should https://www.drupal.org/project/drupal/issues/3554974 be added in related issues?