4

我有一个由 GoDaddy 托管的网站,包括后端的 MySQL 数据库。该站点是斯洛文尼亚站点,因此使用了特殊字符。

该网站是用经典的 ASP 构建的,我在 Notepad++ 中创建了所有使用 utf-8 编码的页面。在每一页的顶部,我还有 Session.CodePage=65001、Session.LCID=1060 和 Response.Charset="utf-8"。MySQL db 和所有表也是 utf8 编码的。

如果我通过 Workbench 界面直接查看 db 中的数据,一切正常,包括我使用的一些特殊的斯洛文尼亚语字符,例如:č

如果我去我的网站,斯洛文尼亚字符也打印得很好,包括 č

唯一的问题是,在同一页面上,从 MySQL 检索的数据没有正确编码,所以字母 č 变成了?

可能是什么问题以及如何解决?

首先我认为是 MySQL ODBC 3.51 驱动程序,我用它来连接数据库。我尝试将 charset=utf8 添加到连接字符串,但没有奏效。我也尝试将 charset=ucs2 添加到连接字符串,这是我在另一个网站上找到的提示,但它也没有帮助。GoDaddy 不支持 MySQL ODBC 5.1 驱动程序,这可能是一个解决方案。

我的选项不多了,所以请帮忙。

4

1 回答 1

2

根据此映射和Windows-1252 wiki 文章的摘录,您有机会获得斯洛文尼亚语字母:

根据 Microsoft 和 Unicode Consortium 网站上的信息,位置 81、8D、8F、90 和 9D 未使用;但是,Windows API MultiByteToWideChar将这些映射到相应的C1 控制代码

在此代码页的早期版本中,第 80 位的欧元字符不存在,带有 caron (háček) 的 S、s、Z 和 z 也不存在。

以下是要做的事情:

  1. 使用 UTF-8(无 BOM)编码文件以防止包含硬编码文本。(✔已经完成)

  2. 在服务器端使用 ASP 或在客户端使用元标记为响应字符集指定 UTF-8。(✔已经完成)

  3. 告诉 MySQL 服务器您的命令在 charset utf-8 中,并且您期望 utf-8 编码的结果集。将初始语句添加到连接字符串:...;stmt=SET NAMES 'utf8';...

  4. 将 Response.CodePage 设置为 1252。

我已经测试了以下脚本,它就像一个魅力。

DDL: http ://sqlfiddle.com/#!8/c2c35/1

ASP:

<%@Language=VBScript%>
<% 
Option Explicit

Response.CodePage = 1252
Response.LCID = 1060
Response.Charset = "utf-8"

Const adCmdText = 1, adVarChar = 200, adParamInput = 1, adLockOptimistic = 3

Dim Connection
Set Connection = Server.CreateObject("Adodb.Connection")
    Connection.Open "Driver={MySQL ODBC 3.51 Driver};Server=localhost;Database=myDb;User=myUsr;Password=myPwd;stmt=SET NAMES 'utf8';"
    
If Request.Form("name").Count = 1 And Len(Request.Form("name")) Then 'add new
    Dim rsAdd
    Set rsAdd = Server.CreateObject("Adodb.Recordset")
        rsAdd.Open "names", Connection, ,adLockOptimistic
        rsAdd.AddNew
        rsAdd("name").Value = Left(Request.Form("name"), 255)
        rsAdd.Update
        rsAdd.Close
    Set rsAdd = Nothing
End If

Dim Command
Set Command = Server.CreateObject("Adodb.Command")
    Command.CommandType = adCmdText
    Command.CommandText = "Select name From `names` Order By id Desc"
    
    If Request.QueryString("name").Count = 1 And Len(Request.QueryString("name")) Then
        Command.CommandText = "Select name From `names` Where name = ? Order By id Desc"
        Command.Parameters.Append Command.CreateParameter(, adVarChar, adParamInput, 255, Left(Request.QueryString("name"), 255))
    End If
    
    Set Command.ActiveConnection = Connection
    With Command.Execute
        While Not .Eof
            Response.Write "<a href=""?name=" & .Fields("name").Value & """>" & .Fields("name").Value & "</a><br />"
            .MoveNext
        Wend
        .Close
    End With
    
    Set Command.ActiveConnection = Nothing
    Set Command = Nothing
    
Connection.Close
%><hr />
<a href="?">SHOW ALL</a><hr />
<form method="post" action="<%=Request.ServerVariables("SCRIPT_NAME")%>">
Name : <input type="text" name="name" maxlength="255" /> <input type="submit" value="Add" />
</form>

最后一句话:

当您需要对从数据库中获取的字符串应用 html 编码时,您不应再使用 Server.HTMLEncode,因为 Response.Codepage 在服务器端是 1252,并且由于 Server.HTMLEncode 是依赖上下文代码页,这将导致乱码输出。
因此,您需要编写自己的 html 编码器来处理这种情况。

Function MyOwnHTMLEncode(ByVal str)
    str = Replace(str, "&", "&amp;")
    str = Replace(str, "<", "&lt;")
    str = Replace(str, ">", "&gt;")
    str = Replace(str, """", "&quot;")
    MyOwnHTMLEncode = str
End Function
'Response.Write MyOwnHTMLEncode(rs("myfield").value)
于 2013-08-19T00:43:18.297 回答