|
If you are running PHP5 and have the php-tidy extension installed, this bug can also fixed in the forum_shorten_post() function in mod/forum/lib.php:
- return substr($message, 0, $truncate);
+ $truncatedpost = substr($message, 0, $truncate);
+ if (function_exists('tidy_repair_string')) { // requires php-tidy extension
+ return tidy_repair_string($truncatedpost);
+ } else {
+ return $truncatedpost;
+ }
Applies cleanly to CVS HEAD (2.0), MOODLE_19_STABLE, and MOODLE_18_STABLE.
Fix relies on the php-tidy extension, falls back to normal (broken) behaviour if the extension is absent. This is a silent dependence on php-tidy, so I'm not sure whether to add it to admin/environment.xml as an optional module, or fix it permanently by making it required (I imagine on HEAD only as we probably don't want to clobber existing 1.8 and 1.9 hosting environments).
Comments on the above please - I'd like to commit this soon Cheers, J I think putting it in environment checks as optional is a good idea, and keep the code exactly as you have it. Great, thanks!
Hi Jonathan,
Just an idea but maybe we should think about creating a truncate function that respects HTML tags and does some other nice stuff at the same time. I've had think about how this function would, or could operate and came up with the solution in the attached truncate.php file. Cheers Looks good Sam. Perhaps we could use a function like this when HTML tidy isn't present, Jonathan?
Ah, true enough
Sorry I've been swamped - I'll try to get on to committing it this week.
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||
I've been working on a project that ran into this same problem....this is how I fixed it. I ran this function after I truncated the posts. It might not be perfect, but it is definately better than the entire page being screwed up because of open table tags.
function closetags($html)
{
$selfclosing = ',img,input,br,hr,';
//put all opened tags into an array
preg_match_all("#<([a-z]+)(?: .*)?(?<![/|/ ])>#iU", $html, $result);
$openedtags=$result[1];
//put all closed tags into an array
preg_match_all("#</([a-z]+)>#iU",$html,$result);
$closedtags=$result[1];
$len_opened = count($openedtags);
//all tags are closed
{ return $html; }if(count($closedtags) == $len_opened)
$openedtags = array_reverse($openedtags);
//close tags
{ $html .= '</'.$openedtags[$i].'>'; }for($i=0;$i < $len_opened;$i++)
{
$temp = $openedtags[$i];
switch ($openedtags[$i])
{
case strstr($selfclosing,",$temp,"):
break;
default:
if (!in_array($openedtags[$i],$closedtags))
else
{ unset($closedtags[array_search($openedtags[$i],$closedtags)]); }}
}
return $html;
}