Gah,我从不喜欢PHP,它是如此"不纯"......
现在我必须使用它,我有一个问题:主要是既不适合html_entity_decode也不htmlspecialchars_decode适合我.我看完了这个论坛,一无所获.它似乎无处不在,只是不会在这里工作......
我正在将一部电影的标题发送到一个数据库,所有数据都被编码,然后当我从数据库中获取它时,我正在解码它:
$title = html_entity_decode($row['Title']);
Run Code Online (Sandbox Code Playgroud)
然后:
"title":"'.$title.'"
Run Code Online (Sandbox Code Playgroud)
它是我用PHP创建的JSON对象的一部分.虽然当我查看该特定对象的属性时,它没有解码其标题,实际上根本没有任何变化.我尝试了问题标题中所述的两个函数,并尝试编码像UTF-8,还有一些选项,如ENT_QUOTES或ENT_COMPAT,但它仍然无效.
有人可以告诉我为什么PHP不会服从我?
编辑:这是我在那里做的全部内容:
echo 'var serverVideos = [';
while($row = mysql_fetch_array($result))
{
$currentRow++;
$data = array('posterSrc' => $row["Poster_name"],
'videoSrc' => $row["Video_name"],
'videoType' => $row["Type"]);
$title = html_entity_decode($row['Title']);
$poster = html_entity_decode($row['Poster_name']);
echo'{"id":"'.$row["ID"].'", "vimeoID":"'.$row["VimeoID"].'", "title":"'.$title.'" ,"client":"'.$row["Client"].'" , "production":"'.$row["Production"].'", "type":"'.$row["Type"].'", ';
if($row["Type"] != "vimeo")
{
echo '"href":"'.http_build_query($data).'"';
}
else
{
echo '"href":"'.$row["Video_name"].'"';
}
echo ', "poster":"'.$poster.'"}';
if($currentRow != $rowNumber)
{
echo ',';
}
}
echo '];';
Run Code Online (Sandbox Code Playgroud)
对不起,它有点乱,在记事本++中它看起来更好; /我实际上是在一个脚本标签中输出它来制作一个对象,我看了json_encode并且真的不明白它是如何帮助我的,因为我不知道如何使用这么多变量,抱歉.
此外,这是使用来自该JSON对象的变量使用javascript制作标记后来自源代码:
<a production=" " client=" " title="O.S.T.R &quot;Track #12&quot;" href="http://player.vimeo.com/video/43886787?title=1&amp;byline=1&amp;portrait=1" rel="shadowbox" class="box">
Run Code Online (Sandbox Code Playgroud)
Dar*_*ook 10
(我不能让这个符合评论,所以它必须是一个答案.)
这里真正的问题是数据放入数据库的方式.我们来看看你给出的示例字符串:
$raw="O.S.T.R &quot;Track #12&quot;";
echo html_entity_decode($raw);
// O.S.T.R "Track #12"
echo html_entity_decode(html_entity_decode($raw));
// O.S.T.R "Track #12"
Run Code Online (Sandbox Code Playgroud)
所以用户输入是OSTR"Track#12"
这里的关键概念是它应该如何存储在数据库中.因为那是实际数据.不要在数据库中存储修改后的版本.相反,适当地转义数据,但是您需要输出它.
以下是我将用于以下几个示例的示例数据:
$title='O.S.T.R "Track #12"';
$description='A&B or A\B ??';
Run Code Online (Sandbox Code Playgroud)
因此,当您在SQL语句中编写数据时使用addslashes(或准备好的语句,但我将在此处显示addslashes方法):
$sql="INSERT INTO xxx(title,description) VALUES('".addslashes($title)."','".addslashes($description)."')";
// INSERT INTO xxx(title,description) VALUES('O.S.T.R \"Track #12\"','A&B or A\\B ??')
Run Code Online (Sandbox Code Playgroud)
对于json编码,请使用json_encode:
$json=json_encode( array('title'=>$title,'description'=>$description) );
// {"title":"O.S.T.R \"Track #12\"","description":"A&B or A\\B ??"}
Run Code Online (Sandbox Code Playgroud)
要在csv中编码,请在日志文件中使用fputcsv:
$fp=fopen("my.csv","a");
fputcsv($fp, array($title,$description) );
fclose($fp);
// "O.S.T.R ""Track #12""","A&B or A\B ??"
Run Code Online (Sandbox Code Playgroud)
要输出为HTML,请使用htmlspecialchars()(或html_entity_encode()):
$html='<h3>'.htmlspecialchars($title).'</h3>';
$html.='<p>'.htmlspecialchars($description).'</p>';
// <h3>O.S.T.R "Track #12"</h3><p>A&B or A\B ??</p>
Run Code Online (Sandbox Code Playgroud)
现在,也许我仍然没有说服你,你仍然真的想在你的数据库中存储HTML就绪数据,并且每次你想要将它用于其他任何事情时都要经过额外的步骤来取消它的标记吗?在这种情况下,您的示例字符串应如下所示:
O.S.T.R "Track #12"
Run Code Online (Sandbox Code Playgroud)
而你的字符串看起来像:
O.S.T.R &quot;Track #12&quot;
Run Code Online (Sandbox Code Playgroud)
你看得到差别吗?第一个有html实体编码一次.呼叫html_entity_decode()将正确解码.第二个已经编码了两次.它不再编码为html实体.我们称之为双实体编码格式或简称DEEF.deef_decode()PHP中没有任何功能,或者我听过的任何计算机语言,甚至没有比PHP更纯粹的功能.原因是因为没有人需要这个功能.
摘要:您的代码中存在写入其数据库的错误.您正在接收已编码实体的字符串,但在将它们写入数据库之前,您将再次对它们进行编码.
结论:回到上面给出的关键概念,你应该在将这些html实体写入数据库之前解码它们,而不是第二次对它们进行编码.但是,当您进行此更改时,请确保从数据库获取数据并将其放入HTML或XML的所有代码都知道它现在必须对实体进行编码.