Question

Is there a built-in Magento helper to escape outputted template data to prevent XSS?

Or should I just use the PHP htmlspecialchars or htmlentities functions?

Was it helpful?

Solution

There are several helper method depending on the context. All are defined in Mage_Core_Helper_Abstract but also in Mage_Core_Block_Abstract, so you can use them with $this->...() in every template:

  • escapeHtml(): It actually leverages htmlspecialchars with the recommended parameters to escape HTML: $result = htmlspecialchars($result, ENT_COMPAT, 'UTF-8', false); - additionally you can specify a whitelist of allowed tags and call the method on an array to escape all elements at once. Use this for any inline text.
  • quoteEscape(): a simpler version without whitelist and array processing but this one escapes single quotes as well as double quotes, useful for text within a HTML attribute.
  • jsQuoteEscape(): this one escapes single quotes with a backslash. It is used to escape string literals in JavaScript. But this is not secure. (Example by @Xorax: 'test\\\'+alert("powned");//'). Additional escaping of backslashes is necessary. Use quoteEscape() instead!
  • escapeUrl(): I don't know why this method exists, it's not URL encoding strings, it's just plain old htmlspecialchars() without any parameter. Don't use it. Ever.

    /**
     * Escape html entities in url
     *
     * @param string $data
     * @return string
     */
    public function escapeUrl($data)
    {
        return htmlspecialchars($data);
    }
    
  • On a related note, there is urlEncode() which also not applies URL encoding, but base64 instead... Don't use it, if you don't know exactly what you need.

    /**
     *  base64_encode() for URLs encoding
     *
     *  @param    string $url
     *  @return   string
     */
    public function urlEncode($url)
    {
        return strtr(base64_encode($url), '+/=', '-_,');
    }
    

Yes, the naming is inconsistent. Once all those method names were following the scheme somethingEscape() but then somebody decided to deprecate htmlEscape() and urlEscape() in favor of the new methods and forgot about quoteEscape() and jsQuoteEscape().

OTHER TIPS

Just translate it

You should always be using the standard translate function

In a block instance

<?php echo $this->__('Text goes here'); ?>

Anywhere else

<?php echo Mage::helper('core')->__('Text goes here'); ?>

And use it the same way you would use sprintf with PHP

Eg.

<?php $foo = 'rocks'; ?>
<?php echo $this->__('Sonassi %s', $foo); ?>

Or escape it

In a block instance

<?php echo $this->escapeHtml('HTML goes here'); ?>

Anywhere else

Using Mage/Core/Helper/Abstract.php

escapeHtml($data, $allowedTags = null)

Eg.

<?php echo Mage::helper('core')->escapeHtml('HTML goes here'); ?>

Classes Mage_Core_Block_Abstract and Mage_Core_Helper_Abstract both use the same function Mage_Core_Helper_Abstract::escapeHtml and it's implementation internaly uses PHP htmlspecialchars function besides implementing some aditional logic for arrays with HTML content.

The function can be accessed in all block and helper classes through $this and since the function is public you can use it through Mage::helper( 'core' ), or some other helper class, everywhere else.

For spanish convert:

$value = str_replace(array("&lt;", "&gt;"), array("<", ">"), htmlspecialchars("Lorem ipsum &gt;", ENT_COMPAT, "UTF-8", false));
Licensed under: CC-BY-SA with attribution
Not affiliated with magento.stackexchange
scroll top