Проблема с кодировкой

Статус
В этой теме нельзя размещать новые ответы.

Rabben

Старатель
Регистрация
26 Мар 2009
Сообщения
159
Реакции
10
Bсем доброго вечера. Опыта в программирование очень мало, и как на зло столкнулся с проблемой, нашел на сайте cms она была полностью на немецком, я ее перевел, сменил кодировку в бд, стояла latin1 поменял на utf8, но русского так и не увидел, т.е перевод отображается нормально, но при добавлении контента вместо русского пишет "Ñ"
в дб контент сохраняет примерно так "Ñ"
кодировка страницы <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
По всей видимости в бд уже заливается не в правильной кодировки а как исправить я не знаю.
mysql.php
PHP:
<?php

// to increase security, move password.php to a save directory which
// is not accessible for web users and change the path in require_once
// accordingly


class MyDb {
  	var $mysqli;
  	var $showerror = false;   // set FALSE if you don't want to see error messages
  	var $showsql   = false;  // set TRUE if you want to see all SQL queries for debugging purposes
  	var $sqlcounter = 0;     // counter for SQL commands
  	var $rowcounter = 0;     // counter for returned SELECT rows
  	var $dbtime     = 0;     // counter for time needed to execute queries
  	var $starttime;

  	// constructor
	function MyDb($path = "") {
    	require_once($path.'inc/config.php');
		$link = @mysql_connect(MYSQL_HOST, MYSQL_USER, MYSQL_PASS) OR die(mysql_error());
		mysql_query('SET NAMES utf8');
		mysql_query('SET CHARACTER_SET utf8');
		mysql_select_db(MYSQL_DATABASE) OR die(mysql_error());
    	if(!$link) 
    	{
      		$this->printerror("Sorry, no connection! (" . mysql_error() . ")");
      		// you might add output for HTML code to close the page
      		// here (</body></html> etc.)
      		$this->mysqli = $link;
      		exit();
    	}
    	$this->starttime = $this->microtime_float();    	
  	}	
	
  	// destructor
  	function __destruct() 
  	{
  		$this->close();
   	}

  	// explicit close
  	function close() 
  	{
    	if($this->mysqli)
    	{
      		mysql_close($this->mysqli);
    	}
      	$this->mysqli = FALSE;
  	}

  	function getMysqli() 
  	{
    	return $this->mysqli; 
    }

  	// execute SELECT query, return array
	function queryObjectArray($sql) 
	{ 	
		$this->sqlcounter++;
	    $this->printsql($sql);
	    $time1  = $this->microtime_float();
	    //$result = $this->mysqli->query($sql);
	    $result = mysql_query($sql);
	    $time2  = $this->microtime_float();
	    $this->dbtime += ($time2 - $time1);
	    if($result) {
	      	if(mysql_num_rows($result)) 
	      	{
	        	while($row = mysql_fetch_object($result))
	         	{
	          		$result_array[] = $row;
	         	}
	        	$this->rowcounter += sizeof($result_array);
	        	return $result_array; 
	        }
	     	else
	     	{
	        	return FALSE;    
	     	}
	    } 
	    else 
	    {
	      	$this->printerror(mysql_error());
	      	return FALSE;
	    }
	}
  
	function queryMYSQL($sql) 
	{
	    $this->sqlcounter++;
	    $this->printsql($sql);
	    $time1  = $this->microtime_float();
	    $result = mysql_query($sql);
	    $time2  = $this->microtime_float();
	    $this->dbtime += ($time2 - $time1);
	    return $result;
	  }

  	// execute SELECT query, return array
	function queryArray($sql) 
	{
		$this->sqlcounter++;
	    $this->printsql($sql);
	    $time1  = $this->microtime_float();
	    $result = mysql_query($sql);
	    $time2  = $this->microtime_float();
	    $this->dbtime += ($time2 - $time1);
	    if($result) 
	    {
	    	if(mysql_num_rows($result)) 
	      	{
	        	while($row = mysql_fetch_array($result))
	        	{
	          		$result_array[] = $row;
	        	}
	        	$this->rowcounter += sizeof($result_array);
	        return $result_array; 
	        }
	      	else
	      	{
	        	return FALSE;
	      	}
		} 
		else 
		{
	    	$this->printerror(mysql_error());
	      	return FALSE;
	    }
	}


  	// execute a SELECT query which returns only a single
  	// item (i.e. SELECT COUNT(*) FROM table); return
  	// this item
  	// beware: this method return -1 for errors (not 0)!
	function querySingleItem($sql) 
	{
	    $this->sqlcounter++;
	    $this->printsql($sql);
	    $time1  = $this->microtime_float();
	    $result = mysql_query($sql);
	    $time2  = $this->microtime_float();
	    $this->dbtime += ($time2 - $time1);
	    if($result) {
	      	if ($row = mysql_fetch_array($result)) 
	      	{
	        	unset($result);
	        	$this->rowcounter++;
	        	return $row[0];
	      	} 
	      	else 
	      	{
	        	// query returned no data
	        	return -1;
	      	}
	    } 
	    else 
	    {
	      	$this->printerror(mysql_error());
	      	return -1;
	    }
	}
  
  //Count Table
	function quereyCount($table,$key = "",$value = "")
  	{
	  	if(empty($key) or empty($value))
	  	{
	  		$sql = "SELECT COUNT(*) FROM ".$table;
	  	}
	  	else
	  	{
	  		$sql = "SELECT COUNT(*) FROM ".$table." WHERE ".$key." = '".$value."'";
	  	}
	  	return $this->querySingleItem($sql);
  }

  // execute a SQL command without results (no query)
  	function execute($sql) 
  	{
	    $this->sqlcounter++;
	    $this->printsql($sql);
	    $time1  = $this->microtime_float();
	    $result = mysql_query($sql);
	    $time2  = $this->microtime_float();
	    $this->dbtime += ($time2 - $time1);
	    if($result)
	    {
	      	return TRUE;
	    }
	    else 
	    {
	      	$this->printerror(mysql_error());
	      	return FALSE;
	   	}
  	}

  	// get insert_id after an INSERT command
  	function insertId() 
  	{
    	return mysql_insert_id(); 
   	}

  	// insert \ before ', " etc.
  	function escape($txt) 
  	{
    	return trim(stripslashes($txt)); 
    }

  	// return 'NULL' or '<quoted string>'
  	function sql_string($txt) 
  	{
    	if(!$txt || trim($txt)=="")
    	{
      		return 'NULL';
    	}
    	else
    	{
      		return "'".mysql_real_escape_string(trim($txt))."'";  
      	}
  	}

  	function error() 
  	{
    	return  mysql_errno(); 
    }

	function printsql($sql) 
	{
	    if($this->showsql)
	    {
	      	printf("<p><font color=\"#0000ff\">%s</font></p>\n",htmlspecialchars($sql));    
	    }
	} 

	function printerror($txt) 
	{
		if($this->showerror)
	    {
	      		printf("<p><font color=\"#ff0000\">%s</font></p>\n",htmlspecialchars($txt));  
	   	}
	}

 	function showStatistics() 
 	{
    	$totalTime = $this->microtime_float() - $this->starttime;
    	printf("<p><font color=\"#0000ff\">SQL commands: %d\n",
      	$this->sqlcounter);
    	printf("<br />Sum of returned rows: %d\n",
      	$this->rowcounter);
    	printf("<br />Sum of query time (MySQL): %f\n",
      	$this->dbtime);
    	printf("<br />Processing time (PHP): %f\n",
      	$totalTime - $this->dbtime);
    	printf("<br />Total time since MyDB creation / last reset: %f</font></p>\n",
      	$totalTime);    
  	}

	function resetStatistics() 
	{
	 	$this->sqlcounter = 0;
	 	$this->rowcounter = 0;
	    $this->dbtime     = 0;
	    $this->starttime = $this->microtime_float();  
	}

  	function microtime_float() 
  	{
    	list($usec, $sec) = explode(" ", microtime());
    	return ((float)$usec + (float)$sec); 
  	}

}
?>
Ну и заодно скрипт комментария.
PHP:
<?

class Comment
{
   	var $modulID;
   	var $contentID;
   	var $showSize;
   	var $points;
   	var $nologin;
   	var $url;
   	var $error;
	
	
		
   	function Comment($modulIDx,$contentIDx,$urlx,$pointsx = true,$showSizex = 10,$loginx = false)
   	{
       	$this->modulID = intval($modulIDx);
       	$this->contentID = intval($contentIDx);
       	$this->points = $pointsx;
       	$this->showSize = intval($showSizex);
       	$this->nologin = $loginx;
       	$this->url = $urlx;
       	$this->error = "NOERR";
   	}
   	
   	function allowed()
   	{
   		global $db,$life_h_config;
   		if(cookie_auth())
   		{
   			$sql = "SELECT * FROM espcms_comment_main WHERE userID = '".$_SESSION['id']."' and modulID = '".$this->modulID."' and contentID = '".$this->contentID."' and DATE_SUB(NOW(), INTERVAL ".$life_h_config['comment_span_time']." MINUTE) < Datum";
   			if(!$db->queryObjectArray($sql))
   			{
   				return true;	
   			}   			
   			else
   			{
   				return false;
   			}
   		}
   		else
   		{
   			return false;
   		}
   	}
   	
   	function control()
	{
		global $db, $lhl,$life_h_config;
		if($_GET['com_a'] == "done")
		{
			if(!convert_vars($_POST['eintrag'],'string',true,'clallback_security'))
			{
				$this->error = return_achtung($lhl['comment_achtung']);
			}	
			convert_vars($_POST['points'],'int');
			if($this->allowed() and ($this->error == "NOERR") and cookie_auth() and !($db->queryObjectArray("SELECT * FROM espcms_comment_main WHERE userID = '".$_SESSION['id']."' and modulID = '".$this->modulID."' and contentID = '".$this->contentID."' and comment = '".$_POST['eintrag']."'")))
			{
				$sql = "INSERT INTO espcms_comment_main (userID,modulID,contentID,datum,comment,points) VALUES" .
						"('".$_SESSION['id']."','".$this->modulID."','".$this->contentID."',NOW(),'".$_POST['eintrag']."','".intval($_POST['points'])."')";
				if($db->execute($sql))
				{
					userrank_setze_punkte($this->modulID,$_SESSION['id']);
					top($lhl['comment_head_done']);
					erfolg($lhl['comment_erfolg']);
					nop();			
				}
			}
		}
		
		if($_GET['com_a'] == "del")
		{
			
			if(cookie_auth())
			{
				if($result = $db->queryObjectArray("SELECT * FROM espcms_comment_main WHERE userID = '".intval($_SESSION['id'])."' and ID = '".intval($_GET['com_id'])."'"))
				{
					$row = $result[0];
					$now = time();
					$datum = strtotime($row->datum);
					$zeit = 60*60*2;
					if($datum > ($now-$zeit))
					{
						$db->execute("DELETE FROM espcms_comment_main WHERE ID = '".$row->ID."'");
						top($lhl['comment_head_done']);
						erfolg("Deleted!");
						nop();
					}
					else
					{
						echo $this->error ="You are not allowed to do this!";	
					}
				}
				else
				{
					echo $this->error ="Dont try this...";
				}
			}
			else
			{
				echo $this->error ="Login!";
			}
		}
	
		if($_GET['com_a'] == "edit")
		{
			if(!convert_vars($_POST['eintrag'],'string',true,'clallback_security'))
			{
				$this->error = return_achtung($lhl['comment_achtung']);
			}	
			
			if(cookie_auth() and ($this->error == "NOERR"))
			{
				if($result = $db->queryObjectArray("SELECT * FROM espcms_comment_main WHERE userID = '".intval($_SESSION['id'])."' and ID = '".intval($_GET['com_id'])."'"))
				{
					$row = $result[0];
					$now = time();
					$datum = strtotime($row->datum);
					$zeit = 60*60*2;
					if($datum > ($now-$zeit))
					{
						$db->execute("UPDATE espcms_comment_main SET comment = '".$_POST['eintrag']."' WHERE ID = '".intval($_GET['com_id'])."'");
						top($lhl['comment_head_done']);
						erfolg("Saved!");
						nop();
					}
					else
					{
						echo $this->error ="You are not allowed to do this!";	
					}
				}
				else
				{
					echo $this->error ="Dont try this...";
				}
			}
			else
			{
				echo $this->error ="Login!";
			}
		}	
	}
   
	function ausgabe()
   	{
   		global $db, $lhl,$life_h_config;
   		top($lhl['comment_head'],"Below you can read the comments");
   		
		$count = $db->querySingleItem("SELECT COUNT(*) as anzahl FROM espcms_comment_main WHERE modulID = '".$this->modulID."' and contentID = '".$this->contentID."'");
		$get_v = intval($_GET['com_v']);
		$show_max = $this->showSize;
		if($count > $this->$show_max)
		{		
			$anz_page=ceil($count/$show_max);		
		}
		else
		{
			$anz_page = 1;	
		}
		
		if(convert_vars($get_v,'int',true))
		{
			$akt_page = $get_v;
		}
		else
		{
			$akt_page = 1;
		}
		
		$count_ausgabe = $count." ".$lhl['comment_site'].": [ ";
		for($i = 1; $i <= $anz_page;$i++)
		{
			if($i == $akt_page)
			{
				$count_ausgabe .= "<b><u>".$i."</u></b>&nbsp;";		
			}
			else
			{					
				$count_ausgabe .=  "<a href=\"".$this->url."&com_v=".$i."\">".$i."</a>&nbsp;";	
			}
		}
		$count_ausgabe .=  "]";
		$von = (ceil($akt_page-1)*$show_max);
		if($von>0)
		{
			$von = $von-1;
		}
		$ausgabe['html'] = $count_ausgabe;
		$ausgabe['von'] = $von;
		$ausgabe['count'] = $count;
		
		
		if($result = $db->queryObjectArray("SELECT * FROM espcms_comment_main WHERE modulID = '".$this->modulID."' and contentID = '".$this->contentID."' ORDER BY datum asc LIMIT ".$ausgabe['von'].",".$this->showSize))
   		{
   			foreach($result as $row)
			{
				if($this->points)
				{
					//$points = $row->points." Points";
				}
				else
				{
					$points = "";
				}
				if(($row->userID == $_SESSION['id']) and cookie_auth())
				{
					$now = time();
					$datum = strtotime($row->datum);
					$zeit = 60*60*2;
					if($datum > ($now-$zeit))
					{
						$control = '<div style="float:right;"><a href="'.$this->url.'&com_id='.$row->ID.'&com_a=show_edit#edit"><img src="Images/icon/edit.png" border="0"></a> <a href="'.$this->url.'&com_id='.$row->ID.'&com_a=del"><img src="Images/icon/del.png" border="0"></a></div>
						';
					} 
					else
					{
						$control = '';
					}
				}
				else
				{
					$control = "";
				}
				
				echo '
				<table style="border:1px solid #ececec;margin:3px;" width="100%" border="0" cellspacing="3" cellpadding="1">
					<tr>
						<td align="left" valign="top" bgcolor="#ececec">
                        	<div style="float:left;"><strong><a href="?section=user_profile&user_id= '.$row->userID.'"><img src="'.get_location_r($row->userID).'" alt=""  border="0"> '.get_nick($row->userID).'</a></strong> &bull; '.strftime("%d.%m.%Y at %H.%M", strtotime($row->datum)).'</font></div> 
                        	'.$control.'
						</td>
					</tr>
					<tr>
						<td align="left" valign="top" bgcolor="">'.bbcode($row->comment).'</td>
					</tr>
				</table>';
			}
			echo "<div style=\"margin:3px;text-align:right;\">".$ausgabe['html']."</div>";	
   		}
   		else
   		{
   			//hinweis($lhl['comment_no_comment']);
   		}
   		nop();
   	}
   	
   	function eingabe()
   	{
   		global $lhl,$life_h_config;
   		if(cookie_auth() or $this->nologin)
   		{
   			if($_GET['com_a'] == "show_edit")
   			{
   				top();
	   			if($this->error != "NOERR"){ echo $this->error; }
	   			$editor = bbcode_editor("comment_add","eintrag",true);
	   			echo '
	   			<form action="'.$this->url.'&com_a=edit&com_id='.intval($_GET['com_id']).'" method="POST" name="comment_add">
					<table width="100%" border="0" cellspacing="2" cellpadding="1" id="edit" name="edit">
						<tr>
							<td align="left" valign="top" width="100"><strong>'.$lhl['comment_comment'].':</strong></td>
							<td align="left" valign="top"><textarea name="eintrag" rows="6" cols="50" style="width:460px;">'.get("espcms_comment_main","comment","ID",intval($_GET['com_id'])).'</textarea><br>'.$editor.'</td>
						</tr>
						<tr height="2">
	                        <td align="left" valign="top" width="100"></td>
							<td colspan="1" align="left" valign="top" height="2"><input type="submit" value="'.$lhl['comment_send'].'"></td>
						</tr>
					</table>
				</form>';
	   			nop();
				
			}
			else
			{
	   			top();
	   			if($this->error != "NOERR"){ echo $this->error; }
	   			$editor = bbcode_editor("comment_add","eintrag",true);
	   			if($this->allowed())
		   		{
		   			echo '
		   			<form action="'.$this->url.'&com_a=done" method="POST" name="comment_add">
						<table width="100%" border="0" cellspacing="2" cellpadding="1">
							<tr>
								<td align="left" valign="top" width="100"><strong>'.$lhl['comment_comment'].':</strong></td>
								<td align="left" valign="top"><textarea name="eintrag" rows="6" cols="50" style="width:460px;"></textarea><br>'.$editor.'</td>
							</tr>
							<tr height="2">
		                        <td align="left" valign="top" width="100"></td>
								<td colspan="1" align="left" valign="top" height="2"><input type="submit" value="'.$lhl['comment_send'].'"></td>
							</tr>
						</table>
					</form>';
		   			}
		   			else
		   			{
		   				achtung("Sie haben erst einen Beitag geschrieben. Sie m&uuml;ssen nach einem Post mindestens ".$life_h_config['comment_span_time']." Minuten warten, bis Sie hier wieder etwas schreiben d&uuml;rfen.");
		   			}
	   			nop();
	   		}			  	
   		}
   		else
   		{
   			top();
   			hinweis($lhl['comment_no_login']);
   			nop();
   		}
   	}
}
ЗЫ Если в бд написать русский контент, то отображается все нормально.
Следовательно, где то подправить надо скрипт.
 
Файлы скрипта перекодируй в UTF-8.
 
может у базы и текстовых полей в настройках сравнение не utf8, надо поставить utf8_general_ci.
Ещё иногда хостер кодировку меняет, если да то создать файл .htaccess с текстом:
AddDefaultCharset utf-8

Похоже контент сохраняется в дб перекодированный с функцией htmlentities, если эта функция используется для utf8 текста то это надо указать в функции:
PHP:
htmlentities('текст', ENT_QUOTES, 'UTF-8');
наверное проблемы в функции convert_vars.
 
Файлы скрипта перекодируй в UTF-8.
то есть? Сохранить в редакторе как utf8?

Добавлено через 3 минуты
может у базы и текстовых полей в настройках сравнение не utf8, надо поставить utf8_general_ci.
Ещё иногда хостер кодировку меняет, если да то создать файл .htaccess с текстом:
AddDefaultCharset utf-8
Похоже контент сохраняется в дб перекодированный с функцией htmlentities, если эта функция используется для utf8 текста то это надо указать в функции:
PHP:
htmlentities('текст', ENT_QUOTES, 'UTF-8');
наверное проблемы в функции convert_vars.
в mysql.php сделал так
Код:
		mysql_query("SET NAMES 'utf8'");
		mysql_query("SET collation_connection='utf8_general_ci'");
		mysql_query("SET collation_server='utf8_general_ci'");
		mysql_query("SET character_set_client='utf8'");
		mysql_query("SET character_set_connection='utf8'");
		mysql_query("SET character_set_results='utf8'");
		mysql_query("SET character_set_server='utf8'");
.htaccess
Код:
AddDefaultCharset utf-8
<IfModule mod_charset.c>
   CharsetRecodeMultipartForms Off
   CharsetSourceEnc utf-8
</IfModule>
P.S. Насчет htmlentities не понял
 
P.S. Насчет htmlentities не понял

если htmlentities("Ñ") даёт результат &Ntilde; так может где-то эта функция используется перед сохранением коментариев. Что делает функция convert_var() ?
Для тестирования вывести из разных мест кода перед сохранением коментария его текст и можно найти место где текст изменяется. Потому что похоже с базой всё нормально это в коде где-то текст изменяется до сохранения.
 
То есть нужно вставить перед
Код:
convert_vars($_POST['points'],'int');
вот это
Код:
echo htmlentities('текст', ENT_QUOTES, 'UTF-8');
я правильно понял?
 
похоже это e-sports cms, чтоб вылечить в utf8 надо сначала изменить кодировку всех страниц это во всех файлах изменить текст "charset=iso-8859-1" на "charset=utf-8".

Дальше надо всю базу установить в utf8, выше настройки были только для соединения с базой но надо ещё базу конвертировать, по умолчанию стоит latin1_swedish_ci. Простой способ это экспортировать всю базу и в дампе базы стереть все "DEFAULT CHARSET=latin1". Дальше стереть таблицы в базе, а в настройках базы (Operations) установить сравнение (Collation) utf8_general_ci, после этого импортировать изменённый дамп, после импорта у все таблиц и текстовых полей будет utf8 кодировка.

И последнее надо сделать поиск по всем файлам на слово "htmlentities(" и везде добавить в эту функцию ",ENT_QUOTES,'UTF-8')":
например:
PHP:
$string =  htmlentities(strip_tags($string),ENT_QUOTES);
должно быть:
PHP:
$string =  htmlentities(strip_tags($string),ENT_QUOTES,'UTF-8');
после всех изменений будет работать на русском и других языках. Ещё могут быть проблемы с текстовыми функциями: strlen, substr, preg_match тогда надо искать подробнее.
 
Спасибо, покуда работает. Буду тестить, появятся проблемы напишу в этой теме.
ЗЫ Не закрывайте покуда тему.
ЗЫЫ Еще раз спасибо.
 
Статус
В этой теме нельзя размещать новые ответы.
Назад
Сверху