Page MenuHomePhabricator

Thumbnails are broken (False decimal point in srcset when locale is not English)
Open, MediumPublic

Description

Since update to MediaWiki 1.30 there is a problem with decimal point in the values of a srcset for images.

expected: srcset="URL1 1.5x, URL2 2x" [.]
but you get: srcset="URL1 1,5x, URL2 2x" [,]

The image display fails. For now I disabled the Responsiv Images. But I don't know where else this problem occurs.

Locale is set to:
$wgShellLocale = "de_DE.utf8";

mediawiki 1.29 and now 1.30rc

Related Objects

Event Timeline

That looks like something is applying european style number formatting (. swapped for ,)

	static function srcSet( array $urls ) {
		$candidates = [];
		foreach ( $urls as $density => $url ) {
			// Cast density to float to strip 'x', then back to string to serve
			// as array index.
			$density = (string)(float)$density;
			$candidates[$density] = $url;
		}

		// Remove duplicates that are the same as a smaller value
		ksort( $candidates, SORT_NUMERIC );
		$candidates = array_unique( $candidates );

		// Append density info to the url
		foreach ( $candidates as $density => $url ) {
			$candidates[$density] = $url . ' ' . $density . 'x';
		}

		return implode( ", ", $candidates );
	}

Does casting to a float if local is de cause this problem?

Seb35 subscribed.

We could either use number_format, but then we end up with 1.0x instead of 1x, or I guess we can do character replacement...
Neither is particularly ideal really...

I wonder if it would be safe to simply set setlocale(LC_NUMERIC, "C") somewhere on the code. Who knows where else it may be happening.

I just opened an other but related issue T184458 with floats being truncated to their integer part in SQL when locale is not English. Setting setlocale(LC_NUMERIC, "C") would solve both issues, but it will probably have side-effects elsewhere.

This is probably a common issue in PHP world, perhaps other projects have fixed it in a nice manner.

PS: this is not related to PHP 7.2, it can be reproduced with older PHP versions.

Seb35 renamed this task from False decimal point in srcset #php7.2 to False decimal point in srcset when locale is not English.Jan 8 2018, 5:07 PM

From a comment in https://www.mediawiki.org/wiki/Topic:U7h4x03lzgbzd2qd#flow-post-uhgx58vkowl5xsoh:

Setting setlocale(LC_NUMERIC, "C"); alone doesn't solve the problem (or not always?, I dunno). The user had to comment out/unset $wgShellLocale for this to work. Maybe MediaWiki does another setlocale with $wgShellLocale during setup, overriding any previous setlocale in LocalSettings.php.

Our wiki (Marjorie-Wiki) is using (nearly) the same templates as de.wikipedia.org.
It is a German wiki, so we were using
$wgShellLocale = "de_DE.utf8";
$wgLanguageCode = "de";
We were using Mediawiki 1.28.3 (with PHP 7.0). $wgResponsiveImages was "true" (and working). The Template:Coordinate was working like expected (i.e. like at de.wikipedia.org).

After updating from 1.28.3 to 1.30.0 our thumbnails were broken.
Furthermore Template:Coordinate expanded to

<span class="geo microformat"><span class="body"></span><span class="latitude">48,46471</span><span class="longitude">8,6613</span><span class="elevation"></span></span><span id="coordinates" class="coordinates plainlinks-print"><span title="Koordinatensystem WGS84">…

(note the commas instead of colons)

First quick solution was $wgResponsiveImages=false, which brought the thumbnails back.

Setting
setlocale(LC_NUMERIC, "C");
together with
$wgShellLocale = "de_DE.utf8";
did not make responsive images or Coordinates working again.

However setting
$wgShellLocale = "C.UTF-8";
as described in
https://www.mediawiki.org/wiki/MediaWiki_1.30#Configuration_changes
and
https://www.mediawiki.org/wiki/Manual:$wgShellLocale
together with
$wgResponsiveImages=true
and without the
setlocale(LC_NUMERIC, "C");
made responsive images and Template:Coordinate work again.
(right now responsive images are intentionally deactivated for testing purposes)

As this task has many duplicates I'm boldly adding Platform Engineering and ask for feedback (though wondering if this could also be Language related)?

Maybe MediaWiki does another setlocale with $wgShellLocale during setup, overriding any previous setlocale in LocalSettings.php.

At Setup.php line 141, the setting of LC_ALL overrides the LC_NUMERIC. I wonder whether there would be any drawback to MediaWiki doing setlocale( LC_NUMERIC, 'C' ) just after that line unconditionally.

mobrovac subscribed.

Maybe MediaWiki does another setlocale with $wgShellLocale during setup, overriding any previous setlocale in LocalSettings.php.

At Setup.php line 141, the setting of LC_ALL overrides the LC_NUMERIC. I wonder whether there would be any drawback to MediaWiki doing setlocale( LC_NUMERIC, 'C' ) just after that line unconditionally.

Wouldn't that mess with the way decimal points are displayed then?

It would mess with the way decimal points are displayed when PHP code casts a float to a string, as in the cases being complained about by this bug. It shouldn't affect code that is using Language::formatNum(), which is what anything in MediaWiki actually displaying decimal points for humans to read should be using.

More specifically, it shouldn't affect anything on Wikimedia wikis because those all already use C.UTF-8, and as far as I know C versus C.UTF-8 doesn't make a difference for LC_NUMERIC.

Chealer renamed this task from False decimal point in srcset when locale is not English to Thumbnails are broken (False decimal point in srcset when locale is not English).Dec 2 2019, 2:45 AM
Chealer updated the task description. (Show Details)

Today a user on IRC came with a similar problem on 1.34, but this time an exception when saving an edit, where a timestamp was being represented with a comma instead of a dot: T241533

The solution was to set $wgShellLocale = "C.UTF-8"; the same as this problem.

Resolving the core issue will result both problems

For the current 1.35 we experienced the same problem as in the original description above. At the same time, we have a very similar locale-related issue with Cirrussearch which should have been solved already (T189877).
We are currently experimenting with the suggested workarounds. But anyway, it would be desirable to have a general solution for all these locale-related problems.

	static function srcSet( array $urls ) {
		$candidates = [];
		foreach ( $urls as $density => $url ) {
			// Cast density to float to strip 'x', then back to string to serve
			// as array index.
			$density = (string)(float)$density;
			$candidates[$density] = $url;
		}

		// Remove duplicates that are the same as a smaller value
		ksort( $candidates, SORT_NUMERIC );
		$candidates = array_unique( $candidates );

		// Append density info to the url
		foreach ( $candidates as $density => $url ) {
			$candidates[$density] = $url . ' ' . $density . 'x';
		}

		return implode( ", ", $candidates );
	}

Does casting to a float if local is de cause this problem?

Not casting to a float per se, but casting back to a string. It would be best to simply strip non-alphabetic characters, as done in the following commit: https://github.com/wikimedia/mediawiki/pull/152/commits/01596cdc19c660a7f26d30098e057b9946c5db45