We use cookies to improve your experience. No personal information is gathered and we don't serve ads. Cookies Policy.

ExpressionEngine Logo ExpressionEngine
Features Pricing Support Find A Developer
Partners Upgrades
Blog Add-Ons Learn
Docs Forums University
Log In or Sign Up
Log In Sign Up
ExpressionEngine Logo
Features Pro new Support Find A Developer
Partners Upgrades
Blog Add-Ons Learn
Docs Forums University Blog
  • Home
  • Forums

LG Better Meta: Not escaping quotes in descriptions?

Development and Programming

Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

I have this on my template:

{exp:lg_better_meta_pi:template
 entry_id="{entry_id}"
 url_title=""
 title=""
 description=""
 keywords=""
 title_suffix=""
 hide_site_title=""}

Which is giving me this:

<title>A Journey Into 'The Second World'</title>

<meta name="description" content="In an excerpt from his book, "The Second World," Parag Khanna argues that real global understanding can only come from serious travel." />

The quotes in that title are causing all sorts of validation errors. Looks like the title may be being handled correctly. Anyone else experience this?

       
Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

Also seems to not be escaping quotes and apostrophes in the title_suffix or the title. I’m having a BEAR of a time passing a title with an apostrophe in it: title=”{somefield}” or title_suffix=”{segment_2_category_name}” (that last example using Low’s seg2cat extension). Every single time, no matter how I pass it, the apostroph gets converted to

’

.

       
Leevi Graham's avatar
Leevi Graham
1,143 posts
16 years ago
Leevi Graham's avatar Leevi Graham
The quotes in that title are causing all sorts of validation errors. Looks like the title may be being handled correctly. Anyone else experience this?

What DOCTYPE are you testing your validation against?

       
Leevi Graham's avatar
Leevi Graham
1,143 posts
16 years ago
Leevi Graham's avatar Leevi Graham

In my tests the following xhtml validates:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">

<html >
<head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    <title>" ' ' ’ ‘ “ ” « » … – — - EE Sandbox v1.6.4</title>

<meta name='description' content='"   ’ ‘ “ ” « » … – —' />
<meta name='keywords' content='test keywords, Site Keywords' />
<meta name='robots' content='index,nofollow,archive' />

<link rel='schema.DC' href='http://purl.org/dc/elements/1.1/' />
<link rel='schema.DCTERMS' href='http://purl.org/dc/terms/' />
<meta name='DC.title' content='"   ’ ‘ “ ” « » … – — - EE Sandbox v1.6.4' />

<meta name='DC.creator' content='Meta Author' />
<meta name='DC.subject' content='test keywords, Site Keywords' />
<meta name='DC.description' content='"   ’ ‘ “ ” « » … – —' />
<meta name='DC.publisher' content='Meta Publisher' />
<meta name='DC.date.created' scheme='DCTERMS.W3CDTF' content='2008-09-23T09:04:23+1000' />
<meta name='DC.date.modified' scheme='DCTERMS.W3CDTF' content='2008-12-13T12:20:24+1100' />
<meta name='DC.date.valid' scheme='DCTERMS.W3CDTF' content='2008-12-19T14:34:01+1100' />
<meta name='DC.type' scheme='DCTERMS.DCMIType' content='Text' />
<meta name='DC.rights' scheme='DCTERMS.URI' content='Meta Rights' />
<meta name='DC.format' content='text/html' />
<meta name='DC.identifier' scheme='DCTERMS.URI' content='http://ee.165.sandbox/tests/lg-better-meta/' />
</head>
<body>
</body>
</html>

I used the following meta title as a test:

" ' ' ’ ‘ “ ” « » … – —

I did make one small change to the extension file to encode all the outputted values not just the title.

Around line 338 change the code from:

// replace each of the {variables}
foreach ($params as $key => $value)
{
    if(strpos($params['template'], LD.$key.RD) !== FALSE)
    {
        $params['template'] = str_replace(LD.$key.RD, $value, $params['template']);
    }
}

to:

// replace each of the {variables}
foreach ($params as $key => $value)
{
    if(strpos($params['template'], LD.$key.RD) !== FALSE)
    {
        $params['template'] = str_replace(LD.$key.RD, $this->_encode($value), $params['template']);
    }
}
       
Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

Interesting. I just did this test:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" 
 "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html >
<head>
<title>New "Sample" for 'Ryan' Testing Quotes in the Meta title</title>
<meta name="description" content="New "Sample" for 'Ryan' Testing Quotes in the description" />

Looks like title was OK, but description was left alone, causing the errors.

1. An attribute value literal can occur in an attribute specification list only after a VI delimiter 2. End tag for “meta” omitted, but OMITTAG NO was specified 3. Character data is not allowed here

I’ll make your tweak and report back. Thanks!

EDIT: I think you meant to make the change to the plugin file, not the extension.

       
Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

In making that change, the title actually outputs:

New "Sample" for &#039;Ryan&#039; Testing Quotes in the Meta title

to the top title bar of the browser (that the user sees), but it was not doing that before the tweak. So it looks like the double quotes get rendered correctly, but the single quotes are outputting a numbered entity.

Changing the line back makes the title in the title bar look correct, but generates the validation errors. Madness!

Not sure why in the case of the title that single quotes would get rendered as

'

but when I’m trying to pass a variable to the title or title_suffix parameters, and that variable has a single quote/apostrophe in it, it outputs as:

’

.

I know there were some typography issues in the build of EE I have (at least a few of which were fixed in a tweaked typography file Derek Jones sent me (thanks, Derek)) - wonder if that might have anything to do with this.

       
Leevi Graham's avatar
Leevi Graham
1,143 posts
16 years ago
Leevi Graham's avatar Leevi Graham

I’m using the following method to encode all the html variables:

function _encode($str)
{
  global $PREFS;
  return htmlentities(html_entity_decode(str_replace(SLASH, '/', $str)), ENT_QUOTES, $PREFS->core_ini['charset']);
}

Basically it decodes all existing entities first so &amp; becomes &, &rsquo; becomes ’ etc.

Then with a fully decoded string htmlentities() is run on the string that converts all entities to their html encoded value including double and single quotes.

This function is identical to htmlspecialchars() in all ways, except with htmlentities(), all characters which have HTML character entity equivalents are translated into these entities.
       
Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

Might that fact that the charset for this site is iso-8859-1 and not utf-8 have anything to do with the output? I might have to get creative with the find/replace plugin or something.

       
Ryan Irelan's avatar
Ryan Irelan
444 posts
16 years ago
Ryan Irelan's avatar Ryan Irelan

Ryan, did you ever find a fix to this?

       
Ryan M.'s avatar
Ryan M.
1,511 posts
16 years ago
Ryan M.'s avatar Ryan M.

Ryan, I did not find a formal fix to this. Fortunately, we had to change the name of the section to a new phrase that didn’t include an apostrophe - which definitely isn’t a fix.

       
Ryan Irelan's avatar
Ryan Irelan
444 posts
16 years ago
Ryan Irelan's avatar Ryan Irelan

Ack. Yeah, that sucks.

Leevi? Any love on this problem?

       
Leevi Graham's avatar
Leevi Graham
1,143 posts
16 years ago
Leevi Graham's avatar Leevi Graham
Ack. Yeah, that sucks. Leevi? Any love on this problem?

TRY and force the charset to UTF-8 in the encode string method:

function _encode($str)
{
  global $PREFS;
  return htmlentities(html_entity_decode(str_replace(SLASH, '/', $str)), ENT_QUOTES, "UTF-8");
}
       
Ryan Irelan's avatar
Ryan Irelan
444 posts
16 years ago
Ryan Irelan's avatar Ryan Irelan

OK, that didn’t work, but what did was to set double_encode (the last param of htmlentities) to FALSE so it doesn’t encode already encoded entities.

return htmlentities(html_entity_decode(str_replace(SLASH, '/', $str)), ENT_QUOTES, $PREFS->core_ini['charset'], FALSE);

I haven’t tested this much further to see if it screws up anything else in the plugin. Leevi, I’ll be hanging out in the chatroom, if you want to discuss.

       
Ryan Irelan's avatar
Ryan Irelan
444 posts
16 years ago
Ryan Irelan's avatar Ryan Irelan

Yeah, not so sure about that now… 😊

       
Leevi Graham's avatar
Leevi Graham
1,143 posts
16 years ago
Leevi Graham's avatar Leevi Graham

Ok guys here is the quick fix… well quick to implement, ages to figure out.

In ext.lg_better_meta.php replace the _encode method with:

<?php
/**
* Encodes a string
* 
* @param $str string The unencoded or partially encoded string
* @return string A html encoded string
**/
function _encode($str)
{
  global $PREFS, $REGX;
  return str_replace(array("'","\""), array("'","""), $REGX->ascii_to_entities($REGX->_html_entity_decode($str, "UTF-8")));
}

I’m working this into the next release as we speak. ?>

       
1 2

Reply

Sign In To Reply

ExpressionEngine Home Features Pro Contact Version Support
Learn Docs University Forums
Resources Support Add-Ons Partners Blog
Privacy Terms Trademark Use License

Packet Tide owns and develops ExpressionEngine. © Packet Tide, All Rights Reserved.