Fix sheet name escaping (fixes #576)

This commit is contained in:
Tim Hunt 2018-07-03 16:41:43 +01:00
parent 799ad93d23
commit 22821d718f
6 changed files with 14 additions and 13 deletions

View File

@ -22,17 +22,17 @@ class ODS implements EscaperInterface
*/
public function escape($string)
{
// @NOTE: ODS files are basically XML, so we need to escape <, > and &.
// Mostly values are saved in element contents, but a few things (e.g. worksheet names)
// are stored in attributes, so we also need to escape " and ', hence ENT_QUOTES.
if (defined('ENT_DISALLOWED')) {
// 'ENT_DISALLOWED' ensures that invalid characters in the given document type are replaced.
// Otherwise control characters like a vertical tab "\v" will make the XML document unreadable by the XML processor
// @link https://github.com/box/spout/issues/329
$replacedString = htmlspecialchars($string, ENT_NOQUOTES | ENT_DISALLOWED, 'UTF-8');
$replacedString = htmlspecialchars($string, ENT_QUOTES | ENT_DISALLOWED, 'UTF-8');
} else {
// We are on hhvm or any other engine that does not support ENT_DISALLOWED.
//
// @NOTE: Using ENT_NOQUOTES as only XML entities ('<', '>', '&') need to be encoded.
// Single and double quotes can be left as is.
$escapedString = htmlspecialchars($string, ENT_NOQUOTES, 'UTF-8');
$escapedString = htmlspecialchars($string, ENT_QUOTES, 'UTF-8');
// control characters values are from 0 to 1F (hex values) in the ASCII table
// some characters should not be escaped though: "\t", "\r" and "\n".

View File

@ -42,9 +42,10 @@ class XLSX implements EscaperInterface
public function escape($string)
{
$escapedString = $this->escapeControlCharacters($string);
// @NOTE: Using ENT_NOQUOTES as only XML entities ('<', '>', '&') need to be encoded.
// Single and double quotes can be left as is.
$escapedString = htmlspecialchars($escapedString, ENT_NOQUOTES, 'UTF-8');
// @NOTE: Excel files are basically XML, so we need to escape <, > and &.
// Mostly values are saved in element contents, but a few things (e.g. worksheet names)
// are stored in attributes, so we also need to escape " and ', hence ENT_QUOTES.
$escapedString = htmlspecialchars($escapedString, ENT_QUOTES, 'UTF-8');
return $escapedString;
}

View File

@ -16,7 +16,7 @@ class ODSTest extends \PHPUnit_Framework_TestCase
{
return [
['test', 'test'],
['carl\'s "pokemon"', 'carl\'s "pokemon"'],
['carl\'s "pokemon"', 'carl&#039;s &quot;pokemon&quot;'],
["\n", "\n"],
["\r", "\r"],
["\t", "\t"],

View File

@ -16,7 +16,7 @@ class XLSXTest extends \PHPUnit_Framework_TestCase
{
return [
['test', 'test'],
['adam\'s "car"', 'adam\'s "car"'],
['adam\'s "car"', 'adam&#039;s &quot;car&quot;'],
["\n", "\n"],
["\r", "\r"],
["\t", "\t"],
@ -25,7 +25,7 @@ class XLSXTest extends \PHPUnit_Framework_TestCase
['_x0000_', '_x005F_x0000_'],
[chr(21), '_x0015_'],
['control '.chr(21).' character', 'control _x0015_ character'],
['control\'s '.chr(21).' "character"', 'control\'s _x0015_ "character"'],
['control\'s '.chr(21).' "character"', 'control&#039;s _x0015_ &quot;character&quot;'],
];
}

View File

@ -421,7 +421,7 @@ class WriterTest extends \PHPUnit_Framework_TestCase
$this->writeToODSFile($dataRows, $fileName);
$this->assertValueWasWritten($fileName, 'I\'m in "great" mood', 'Quotes should not be escaped');
$this->assertValueWasWritten($fileName, 'I&#039;m in &quot;great&quot; mood', 'Quotes should be escaped');
$this->assertValueWasWritten($fileName, 'This &lt;must&gt; be escaped &amp; tested', '<, > and & should be escaped');
}

View File

@ -473,7 +473,7 @@ class WriterTest extends \PHPUnit_Framework_TestCase
$this->writeToXLSXFile($dataRows, $fileName);
$this->assertInlineDataWasWrittenToSheet($fileName, 1, 'I\'m in "great" mood', 'Quotes should not be escaped');
$this->assertInlineDataWasWrittenToSheet($fileName, 1, 'I&#039;m in &quot;great&quot; mood', 'Quotes should be escaped');
$this->assertInlineDataWasWrittenToSheet($fileName, 1, 'This &lt;must&gt; be escaped &amp; tested', '<, > and & should be escaped');
}