我正在使用Delphi 7和ICS组件与php脚本进行通信并在mysql数据库中插入一些数据...
如何使用http post发布unicode数据?
从tnt控件使用utf8encode后,我正在将其发布到PHP脚本
<?php
echo "Note = ". $_POST['note'];
if($_POST['action'] == 'i')
{
/*
* This code will add new notes to the database
*/
$sql = "INSERT INTO app_notes VALUES ('', '" . mysql_real_escape_string($_POST['username']) . "', '" . mysql_real_escape_string($_POST['note']) . "', NOW(), '')";
$result = mysql_query($sql, $link) or die('0 - Ins');
echo '1 - ' . mysql_insert_id($link);
?>
Delphi代码:
data := Format('date=%s&username=%s&password=%s&hash=%s¬e=%s&action=%s',
[UrlEncode(FormatDateTime('yyyymmddhh:nn',now)),
UrlEncode(edtUserName.Text),
UrlEncode(getMd51(edtPassword.Text)),
UrlEncode(getMd51(dataHash)),UrlEncode(Utf8Encode(memoNote.Text)),'i'
]);
// try function StrHtmlEncode (const AStr: String): String; from IdStrings
HttpCli1.SendStream := TMemoryStream.Create;
HttpCli1.SendStream.Write(Data[1], Length(Data));
HttpCli1.SendStream.Seek(0, 0);
HttpCli1.RcvdStream := TMemoryStream.Create;
HttpCli1.URL := Trim(ActionURLEdit.Text);
HttpCli1.PostAsync;
但是,当我发布的unicode值与我在Tnt Memo中看到的原始值完全不同时
有什么我想念的吗?!
还有人知道如何用Indy做到这一点吗?
谢谢。
参考方案
您的示例代码显示您的数据来自TNT Unicode控件。该值的类型为WideString
,因此要获取UTF-8数据,应调用Utf8Encode
,这将返回一个AnsiString
值。然后在该值上调用UrlEncode
。确保UrlEncode
的输入类型为AnsiString
。因此,如下所示:
var
data, date, username, passhash, datahash, note: AnsiString;
date := FormatDateTime('yyyymmddhh:nn',now);
username := Utf8Encode(edtUserName.Text);
passhash := getMd51(edtPassword.Text);
datahash := getMd51(data);
note := Utf8Encode(memoNote.Text);
data := Format('date=%s&username=%s&password=%s&hash=%s¬e=%s&action=%s',
[UrlEncode(date),
UrlEncode(username),
UrlEncode(passhash),
UrlEncode(datahash),
UrlEncode(note),
'i'
]);
由于MD5字符串值只是十六进制字符,因此无需对MD5值进行UTF-8编码。但是,您应该仔细检查getMd51
函数是否接受WideString
。否则,您可能会丢失数据,然后再将其发送到任何地方。
接下来,您将遇到在PHP中接收UTF-8数据的问题。我希望在那里或在MySQL中不需要执行任何特殊操作。不管您存储了什么,以后都应该同样返回。将其发送回您的Delphi程序,然后将UTF-8数据解码回WideString
。
换句话说,由于您将Unicode数据存储为UTF-8,因此Unicode数据在数据库中看起来将有所不同。在数据库中,您看到的是UTF-8编码的数据,但是在TNT控件中,您看到的是常规Unicode字符。
因此,例如,如果您在编辑框中键入字符“ش”,则这是Unicode字符U + 0634,阿拉伯字母sheen。作为UTF-8,这是两个字节的序列0xD8 0xB4。如果将这些字节存储在数据库中,然后查看该字段的原始内容,则可能会看到字符被解释为好像这些字节采用某种ANSI编码那样。这些字节的一种可能解释是两个字符的序列“Ø”,这是带大写字母并带有重音符号的拉丁大写字母o。
当您从数据库中加载该字符串时,它仍然编码为UTF-8,就像存储它时一样,因此您需要对其进行解码。据我所知,PHP和MySQL都不会对数据进行任何处理,因此,您给它们提供的任何UTF-8字符都会原样返回给您。如果在Delphi中使用数据,请调用Utf8Decode
,它是对先前调用的Utf8Encode
函数的补充。如果您使用PHP中的数据,那么您可能会对PHP的utf8_decode
函数感兴趣,尽管该函数会转换为ISO-8859-1,其中不包含示例阿拉伯字符。堆栈溢出已经存在一些与在PHP中使用UTF-8有关的问题,因此在这里我不会尝试添加它们。例如:
Best practices in PHP and MySQL
with international strings
UTF-8 all the way through…
我最近安装了WAMP服务器(分别安装模块):操作系统:Windows 7 x32Apache:httpd-2.2.17-win32-x86-openssl-0.9.8oMySQL:mysql-5.1.50-win32的PHP:php-5.2.17-Win32-VC6-x86我已经全部配置好了,当我运行phpinfo()时,它可以正常工作,但是当我使用php_…
php Singleton类实例将在多个会话中保留吗? - php举一个简单的例子,如果我想计算一个不使用磁盘存储的脚本的命中次数,我可以使用静态类成员来执行此操作吗?用户1:<?php $test = Example::singleton(); $test->visits++; ?> 用户2:<?php $test = Example::singleton(); $test->visits+…
PHP:填写数组中的“空白” - php我有一个php数组(通过表单中的复选框值获取-您知道复选框仅在未设置时显示在_POST变量中)。Array ( [2] => 0,2 [3] => 0,3 ) 我需要一种方法来“填补” 0-5之间的差距。所以上面看起来像(用'-1'填充空白。我尝试用填充有'-1'的数组array_merge(),但这没用。Array ( [0] => -1…
PHP:对数组排序 - php请如何排序以下数组Array ( 'ben' => 1.0, 'ken' => 2.0, 'sam' => 1.5 ) 至Array ( 'ken' => 2.0, 'sam' => 1.5, 'ben' =&…
PHP:检查谁看过发送的电子邮件? - php我正在向某些用户发送电子邮件,并且想知道是谁阅读的,这意味着如果有人阅读了该电子邮件,则将维护一个日志文件,其中包含该用户的电子邮件地址以及日期/时间/ IP。为此,我发送一个带有电子邮件(html模板)的javascript函数,当用户打开该电子邮件时,它仅会警告用户的电子邮件地址,例如:for($n=0; $n<sizeof($checkBox);…