// // ------------------------------------------------------------------------ // // This program is free software; you can redistribute it and/or modify // // it under the terms of the GNU General Public License as published by // // the Free Software Foundation; either version 2 of the License, or // // (at your option) any later version. // // // // You may not change or alter any portion of this comment or credits // // of supporting developers from this source code or any supporting // // source code which is considered copyrighted (c) material of the // // original comment or credit authors. // // // // This program is distributed in the hope that it will be useful, // // but WITHOUT ANY WARRANTY; without even the implied warranty of // // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // // GNU General Public License for more details. // // // // You should have received a copy of the GNU General Public License // // along with this program; if not, write to the Free Software // // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA // // ------------------------------------------------------------------------ // // Author: Kazumi Ono (http://www.myweb.ne.jp/, http://jp.xoops.org/) // // Goghs Cheng (http://www.eqiao.com, http://www.devbeez.com/) // // Project: The XOOPS Project (http://www.xoops.org/) // // ------------------------------------------------------------------------- // /** * Class to "clean up" text for various uses * * Singleton * * @package kernel * @subpackage core * * @author Kazumi Ono * @author Goghs Cheng * @copyright (c) 2000-2003 The Xoops Project - www.xoops.org */ class MyTextSanitizer { /** * @var array */ var $smileys = array(); /** * */ var $censorConf; /* * Constructor of this class * * Gets allowed html tags from admin config settings *
should not be allowed since nl2br will be used * when storing data. * * @access private * * @todo Sofar, this does nuttin' ;-) */ function MyTextSanitizer() { } /** * Access the only instance of this class * * @return object * * @static * @staticvar object */ function &getInstance() { static $instance; if (!isset($instance)) { $instance = new MyTextSanitizer(); } return $instance; } /** * Get the smileys * * @return array */ function getSmileys() { return $this->smileys; } /** * Replace emoticons in the message with smiley images * * @param string $message * * @return string */ function &smiley($message) { $db =& Database::getInstance(); if (count($this->smileys) == 0) { if ($getsmiles = $db->query("SELECT * FROM ".$db->prefix("smiles"))){ while ($smiles = $db->fetchArray($getsmiles)) { $message = str_replace($smiles['code'], '', $message); array_push($this->smileys, $smiles); } } } elseif (is_array($this->smileys)) { foreach ($this->smileys as $smile) { $message = str_replace($smile['code'], '', $message); } } return $message; } /** * Make links in the text clickable * * @param string $text * @return string **/ function &makeClickable(&$text) { $patterns = array("/(^|[^]_a-z0-9-=\"'\/])([a-z]+?):\/\/([^, \r\n\"\(\)'<>]+)/i", "/(^|[^]_a-z0-9-=\"'\/])www\.([a-z0-9\-]+)\.([^, \r\n\"\(\)'<>]+)/i", "/(^|[^]_a-z0-9-=\"'\/])ftp\.([a-z0-9\-]+)\.([^, \r\n\"\(\)'<>]+)/i", "/(^|[^]_a-z0-9-=\"'\/:\.])([a-z0-9\-_\.]+?)@([^, \r\n\"\(\)'<>\[\]]+)/i"); $replacements = array("\\1\\2://\\3", "\\1www.\\2.\\3", "\\1ftp.\\2.\\3", "\\1\\2@\\3"); $ret = preg_replace($patterns, $replacements, $text); return $ret; } /** * Replace XoopsCodes with their equivalent HTML formatting * * @param string $text * @param bool $allowimage Allow images in the text? * On FALSE, uses links to images. * @return string **/ function &xoopsCodeDecode(&$text, $allowimage = 1) { $imgCallbackPattern = "/\[img( align=\w+)]([^\"\(\)\?\&'<>]*)\[\/img\]/sU"; $text = preg_replace_callback($imgCallbackPattern, array($this, '_filterImgUrl'), $text); // Extension of BB code //----------------------------------------------- $text =& $this->xoopsCodeImage($text, $allowimage); $text =& $this->xoopsCodeSiteImage($text, $allowimage); // flash maybe become a security hole. // $text =& $this->xoopsCodeFlash($text); //----------------------------------------------- $patterns = array(); $replacements = array(); // RMV: added new markup for intrasite url (allows easier site moves) // TODO: automatically convert other URLs to this format if XOOPS_URL matches?? // Extension of BB code //----------------------------------------------- // $patterns[] = "/\[siteurl=(['\"]?)([^\"'<>]*)\\1](.*)\[\/siteurl\]/sU"; // $replacements[] = '\\3'; $patterns[] = "/\[siteurl=(['\"]?)([^\"'<>]*)\\1](.*)\[\/siteurl\]/sU"; $replacements[] = '\\3'; //----------------------------------------------- $patterns[] = "/\[url=(['\"]?)(http[s]?:\/\/[^\"'<>]*)\\1](.*)\[\/url\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[url=(['\"]?)(ftp?:\/\/[^\"'<>]*)\\1](.*)\[\/url\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[url=(['\"]?)([^\"'<>]*)\\1](.*)\[\/url\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[color=(['\"]?)([a-zA-Z0-9]*)\\1](.*)\[\/color\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[size=(['\"]?)([a-z0-9-]*)\\1](.*)\[\/size\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[font=(['\"]?)([^;<>\*\(\)\"']*)\\1](.*)\[\/font\]/sU"; $replacements[] = '\\3'; $patterns[] = "/\[email]([^;<>\*\(\)\"']*)\[\/email\]/sU"; $replacements[] = '\\1'; $patterns[] = "/\[b](.*)\[\/b\]/sU"; $replacements[] = '\\1'; $patterns[] = "/\[i](.*)\[\/i\]/sU"; $replacements[] = '\\1'; $patterns[] = "/\[u](.*)\[\/u\]/sU"; $replacements[] = '\\1'; $patterns[] = "/\[d](.*)\[\/d\]/sU"; $replacements[] = '\\1'; //$patterns[] = "/\[li](.*)\[\/li\]/sU"; //$replacements[] = '
  • \\1
  • '; // Extension of BB code //----------------------------------------------- // $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1]([^\"\(\)\?\&'<>]*)\[\/img\]/sU"; // $patterns[] = "/\[img]([^\"\(\)\?\&'<>]*)\[\/img\]/sU"; // $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1 id=(['\"]?)([0-9]*)\\3]([^\"\(\)\?\&'<>]*)\[\/img\]/sU"; // $patterns[] = "/\[img id=(['\"]?)([0-9]*)\\1]([^\"\(\)\?\&'<>]*)\[\/img\]/sU"; // if ($allowimage != 1) { // $replacements[] = '\\3'; // $replacements[] = '\\1'; // $replacements[] = '\\5'; // $replacements[] = '\\3'; // } else { // $replacements[] = ''; // $replacements[] = ''; // $replacements[] = '\\5'; // $replacements[] = '\\3'; // } //----------------------------------------------- $patterns[] = "/\[quote]/sU"; $replacements[] = _QUOTEC.'
    '; //$replacements[] = 'Quote:
    '; $patterns[] = "/\[\/quote]/sU"; $replacements[] = '
    '; $patterns[] = "/javascript:/si"; $replacements[] = "java script:"; $patterns[] = "/about:/si"; $replacements[] = "about :"; $ret = preg_replace($patterns, $replacements, $text); return $ret; } //----------------------------------------------- // Extension of BB code // img tag //----------------------------------------------- function &xoopsCodeImage(&$text, $allowimage = 1) { $patterns = array(); $replacements = array(); $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*),(\d+),(\d+)\[\/img\]/sU"; $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*),(\d+)\[\/img\]/sU"; $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*)\[\/img\]/sU"; $patterns[] = "/\[img]([^\[\]\"\(\)\?\&'<>,]*),(\d+),(\d+)\[\/img\]/sU"; $patterns[] = "/\[img]([^\[\]\"\(\)\?\&'<>,]*),(\d+)\[\/img\]/sU"; $patterns[] = "/\[img]([^\[\]\"\(\)\?\&'<>,]*)\[\/img\]/sU"; $patterns[] = "/\[img align=(['\"]?)(left|center|right)\\1 id=(['\"]?)([0-9]*)\\3]([^\[\]\"\(\)\?\&'<>,]*)\[\/img\]/sU"; $patterns[] = "/\[img id=(['\"]?)([0-9]*)\\1]([^\[\]\"\(\)\?\&'<>,]*)\[\/img\]/sU"; if ($allowimage != 1) { $replacement1 = '\\3'; $replacement2 = '\\1'; $replacements[] = $replacement1; $replacements[] = $replacement1; $replacements[] = $replacement1; $replacements[] = $replacement2; $replacements[] = $replacement2; $replacements[] = $replacement2; $replacements[] = '\\5'; $replacements[] = '\\3'; } else { $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = '\\5'; $replacements[] = '\\3'; } $text = preg_replace($patterns, $replacements, $text); return $text; } //----------------------------------------------- //----------------------------------------------- // Extension of BB code // siteimg tag //----------------------------------------------- function &xoopsCodeSiteImage(&$text, $allowimage = 1) { $patterns = array(); $replacements = array(); $patterns[] = "/\[siteimg align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*),(\d+),(\d+)\[\/siteimg\]/sU"; $patterns[] = "/\[siteimg align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*),(\d+)\[\/siteimg\]/sU"; $patterns[] = "/\[siteimg align=(['\"]?)(left|center|right)\\1]([^\[\]\"\(\)\?\&'<>,]*)\[\/siteimg\]/sU"; $patterns[] = "/\[siteimg]([^\[\]\"\(\)\?\&'<>,]*),(\d+),(\d+)\[\/siteimg\]/sU"; $patterns[] = "/\[siteimg]([^\[\]\"\(\)\?\&'<>,]*),(\d+)\[\/siteimg\]/sU"; $patterns[] = "/\[siteimg]([^\[\]\"\(\)\?\&'<>,]*)\[\/siteimg\]/sU"; // if ($allowimage != 1) // { // $replacement1 = '\\3'; // $replacement2 = '\\1'; // $replacements[] = $replacement1; // $replacements[] = $replacement1; // $replacements[] = $replacement1; // $replacements[] = $replacement2; // $replacements[] = $replacement2; // $replacements[] = $replacement2; // } // else // { $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; $replacements[] = ''; // } $text = preg_replace($patterns, $replacements, $text); return $text; } //----------------------------------------------- //----------------------------------------------- // Extension of BB code // flash tag //----------------------------------------------- function &xoopsCodeFlash(&$text) { $patterns = array(); $replacements = array(); $patterns[] = "/\[flash]([^\[\]\"\(\)\?\&'<>,]*),(\d+),(\d+)\[\/flash\]/sU"; $patterns[] = "/\[flash]([^\[\]\"\(\)\?\&'<>,]*),(\d+)\[\/flash\]/sU"; $patterns[] = "/\[flash]([^\[\]\"\(\)\?\&'<>,]*)\[\/flash\]/sU"; $object_1 = ''; $object_2 = ''; $object_3 = ''; $embed_1 = ''; $embed_2 = ''; $embed_3 = ''; $param_movie = ''; $param_quality = ''; $object_end = ''; $replacements[] = $object_1.$param_movie.$param_quality.$embed_1.$object_end; $replacements[] = $object_2.$param_movie.$param_quality.$embed_2.$object_end; $replacements[] = $object_3.$param_movie.$param_quality.$embed_3.$object_end; $text = preg_replace($patterns, $replacements, $text); return $text; } /** * Filters out invalid strings included in URL, if any * * @param array $matches * @return string */ function _filterImgUrl($matches) { if ($this->checkUrlString($matches[2])) { return $matches[0]; } else { return ""; } } /** * Checks if invalid strings are included in URL * * @param string $text * @return bool */ function checkUrlString($text) { // Check control code if (preg_match("/[\\0-\\31]/", $text)) { return false; } // check black pattern(deprecated) return !preg_match("/^(javascript|vbscript|about):/i", $text); } /** * Convert linebreaks to
    tags * * @param string $text * * @return string */ function &nl2Br($text) { $ret = preg_replace("/(\015\012)|(\015)|(\012)/","
    ",$text); return $ret; } /** * Add slashes to the text if magic_quotes_gpc is turned off. * * @param string $text * @return string **/ function &addSlashes($text) { if (!get_magic_quotes_gpc()) { $text = addslashes($text); } return $text; } /* * if magic_quotes_gpc is on, stirip back slashes * * @param string $text * * @return string */ function &stripSlashesGPC($text) { if (get_magic_quotes_gpc()) { $text = stripslashes($text); } return $text; } /* * for displaying data in html textbox forms * * @param string $text * * @return string */ function &htmlSpecialChars($text) { //return preg_replace("/&/i", '&', htmlspecialchars($text, ENT_QUOTES)); $ret = preg_replace(array("/&/i", "/ /i"), array('&', '&nbsp;'), htmlspecialchars($text, ENT_QUOTES)); return $ret; } /** * Reverses {@link htmlSpecialChars()} * * @param string $text * @return string **/ function &undoHtmlSpecialChars(&$text) { return preg_replace(array("/>/i", "/</i", "/"/i", "/'/i"), array(">", "<", "\"", "'"), $text); } function &renderWikistyle($text, $html = 0, $smiley = 1, $xcode = 1, $image = 1, $br = 1, $use_cache = 0, $wikidir = 'xpwiki') { $br = ($br)? 1 : 0; $use_cache = ($use_cache)? 1 : 0; $smiley = ($smiley)? 1 : 0; // xpWiki include_once XOOPS_TRUST_PATH."/modules/xpwiki/include.php"; $render =& XpWiki::getSingleton( $wikidir ); // pukiwiki.ini.php setting $render->setIniRoot('line_break', $br); $render->setIniRoot('render_use_cache', $use_cache); $render->setIniRoot('use_extra_facemark', 1); $render->setIniRoot('usefacemark', $smiley); $render->setIniRoot('render_cache_min', 1440); // 1day $render->setIniRoot('link_target', '_blank'); $render->setIniRoot('nowikiname', 1); $render->setIniRoot('show_passage', 0); $render->setIniRoot('no_slashes_commentout', 1); if ($xcode) { // BB Code code $text = preg_replace( "/(?:\r\n|\r|\n)?\[code](?:\r\n|\r|\n)?(.*)(?:\r\n|\r|\n)?\[\/code\](?:\r\n|\r|\n)?/sU", "\n#code(){{{\n$1\n}}}\n", $text); // BB Code email $text = preg_replace("/\[email](.+?)\[\/email]/i","$1",$text); // BB Code url $text = preg_replace( "/\[url=(['\"]?)((?:ht|f)tp[s]?:\/\/[!~*'();\/?:\@&=+\$,%#\w.-]+)\\1\](.+)\[\/url\]/esU", "'[['.MyTextSanitizer::ret2br('$3').':$2]]'" ,$text); $text = preg_replace( "/\[url=(['\"]?)([!~*'();\/?:\@&=+\$,%#\w.-]+)\\1\](.+)\[\/url\]/esU", "'[['.MyTextSanitizer::ret2br('$3').':http://$2]]'", $text); // BB Code image $text = preg_replace("/(\[img(?:[^\]]+)?])(.+?)(\[\/img])/ie","'$1'.base64_encode('$2').'$3'",$text); } // disable comment out //$text = preg_replace('#((?:^|\n)\#[^{]+(\{\{+).+?\\2)?(.*?)(^|\n)//#s', '$1$2$3//', $text); // $text = preg_replace('#^//#m', '//', $text); $text = $render->transform($text, $wikidir); // BB Code image $text = preg_replace("/(\[img(?:[^\]]+)?])(.+?)(\[\/img])/ie","'$1'.base64_decode('$2').'$3'",$text); // XOOPS Quote style $text = str_replace( array('
    ','
    '), array(_QUOTEC.'
    ','
    '),$text ); return $text; } function ret2br($text) { $text = str_replace('\"','"',$text); return str_replace(array("\r\n","\r","\n"),"&br;",$text); } /** * Filters textarea data for display * (This method makes overhead but needed for compatibility) * * @param string $text * @param bool $html allow html? * @param bool $smiley allow smileys? * @param bool $xcode allow xoopscode? * @param bool $image allow inline images? * @param bool $br convert linebreaks? * @return string **/ function _ToShowTarea($text, $html = 0, $smiley = 1, $xcode = 1, $image = 1, $br = 1, $use_cache = 0) { if ($html != 1) { $text = $this->renderWikistyle($text, $html, $smiley, $xcode, $image, $br, $use_cache); } else { $text = $this->codePreConv($text, $xcode); $text = $this->makeClickable($text); if ($smiley != 0) $text = $this->smiley($text); } if ($xcode != 0) $text = $this->xoopsCodeDecode($text, $image); if ($html && $br != 0) $text = $this->nl2Br($text); if ($html) $text = $this->codeConv($text, $xcode, $image); return $text; } /** * Filters textarea form data in DB for display * * @param string $text * @param bool $html allow html? * @param bool $smiley allow smileys? * @param bool $xcode allow xoopscode? * @param bool $image allow inline images? * @param bool $br convert linebreaks? * @return string **/ function &displayTarea(&$text, $html = 0, $smiley = 1, $xcode = 1, $image = 1, $br = 1) { $text = $this->_ToShowTarea($text, $html, $smiley, $xcode, $image, $br, 1); return $text; } /** * Filters textarea form data submitted for preview * * @param string $text * @param bool $html allow html? * @param bool $smiley allow smileys? * @param bool $xcode allow xoopscode? * @param bool $image allow inline images? * @param bool $br convert linebreaks? * @return string **/ function &previewTarea(&$text, $html = 0, $smiley = 1, $xcode = 1, $image = 1, $br = 1) { $text =& $this->stripSlashesGPC($text); $text = $this->_ToShowTarea($text, $html, $smiley, $xcode, $image, $br, 0); return $text; } /** * Replaces banned words in a string with their replacements * * @param string $text * @return string * * @deprecated **/ function &censorString(&$text) { if (!isset($this->censorConf)) { $config_handler =& xoops_gethandler('config'); $this->censorConf =& $config_handler->getConfigsByCat(XOOPS_CONF_CENSOR); } if ($this->censorConf['censor_enable'] == 1) { $replacement = $this->censorConf['censor_replace']; foreach ($this->censorConf['censor_words'] as $bad) { if ( !empty($bad) ) { $bad = quotemeta($bad); $patterns[] = "/(\s)".$bad."/siU"; $replacements[] = "\\1".$replacement; $patterns[] = "/^".$bad."/siU"; $replacements[] = $replacement; $patterns[] = "/(\n)".$bad."/siU"; $replacements[] = "\\1".$replacement; $patterns[] = "/]".$bad."/siU"; $replacements[] = "]".$replacement; $text = preg_replace($patterns, $replacements, $text); } } } return $text; } /**#@+ * Sanitizing of [code] tag */ function codePreConv($text, $xcode = 1) { if($xcode != 0){ $patterns = "/\[code](.*)\[\/code\]/esU"; $replacements = "'[code]'.base64_encode('$1').'[/code]'"; $text = preg_replace($patterns, $replacements, $text); } return $text; } function codeConv($text, $xcode = 1, $image = 1){ if($xcode != 0){ $patterns = "/\[code](.*)\[\/code\]/esU"; if ($image != 0) { // image allowed $replacements = "'
    '.MyTextSanitizer::codeSanitizer('$1').'
    '"; //$text =& $this->xoopsCodeDecode($text); } else { // image not allowed $replacements = "'
    '.MyTextSanitizer::codeSanitizer('$1', 0).'
    '"; //$text =& $this->xoopsCodeDecode($text, 0); } $text = preg_replace($patterns, $replacements, $text); } return $text; } function codeSanitizer($str, $image = 1){ if($image != 0){ $str = $this->xoopsCodeDecode( $this->htmlSpecialChars(str_replace('\"', '"', base64_decode($str))) ); }else{ $str = $this->xoopsCodeDecode( $this->htmlSpecialChars(str_replace('\"', '"', base64_decode($str))),0 ); } return $str; } /**#@-*/ ##################### Deprecated Methods ###################### /**#@+ * @deprecated */ function sanitizeForDisplay($text, $allowhtml = 0, $smiley = 1, $bbcode = 1) { $text =& displayTarea($text, $allowhtml, $smiley, $bbcode, 1, 1); return $text; } function sanitizeForPreview($text, $allowhtml = 0, $smiley = 1, $bbcode = 1) { $text =& previewTarea($text, $allowhtml, $smiley, $bbcode, 1, 1); return $text; } function makeTboxData4Save($text) { //$text = $this->undoHtmlSpecialChars($text); return $this->addSlashes($text); } function makeTboxData4Show($text, $smiley=0) { $text = $this->htmlSpecialChars($text); return $text; } function makeTboxData4Edit($text) { return $this->htmlSpecialChars($text); } function makeTboxData4Preview($text, $smiley=0) { $text = $this->stripSlashesGPC($text); $text = $this->htmlSpecialChars($text); return $text; } function makeTboxData4PreviewInForm($text) { $text = $this->stripSlashesGPC($text); return $this->htmlSpecialChars($text); } function makeTareaData4Save($text) { return $this->addSlashes($text); } function &makeTareaData4Show(&$text, $html=1, $smiley=1, $xcode=1) { $ret = $this->displayTarea($text, $html, $smiley, $xcode); return $ret; } function makeTareaData4Edit($text) { return $this->htmlSpecialChars($text); } function &makeTareaData4Preview(&$text, $html=1, $smiley=1, $xcode=1) { $ret = $this->previewTarea($text, $html, $smiley, $xcode); return $ret; } function makeTareaData4PreviewInForm($text) { //if magic_quotes_gpc is on, do stipslashes $text = $this->stripSlashesGPC($text); return $this->htmlSpecialChars($text); } function makeTareaData4InsideQuotes($text) { return $this->htmlSpecialChars($text); } function &oopsStripSlashesGPC($text) { $ret = $this->stripSlashesGPC($text); return $ret; } function &oopsStripSlashesRT($text) { if (get_magic_quotes_runtime()) { $text =& stripslashes($text); } return $text; } function &oopsAddSlashes($text) { $ret = $this->addSlashes($text); return $ret; } function &oopsHtmlSpecialChars($text) { $ret = $this->htmlSpecialChars($text); return $ret; } function &oopsNl2Br($text) { $ret = $this->nl2br($text); return $ret; } /**#@-*/ } ?>