ServiceStack是否支持普通html的POST?

时间:2014-04-30 02:43:49

标签: servicestack servicestack-razor

基本上是这样,但我在POST数据中遇到国家符号问题。他们被服务破坏了。

我有非常基本的标记:

<!DOCTYPE html>
<html>
    <head>
        <title></title>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
</head>
<body>
    <form action="/hello" method="POST">
        <input name="Name" id="Name"/>
        <input type="submit" value="Send"/>
    </form>
</body>
</html>

浏览器发送以下内容:

接头:

Accept:text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Encoding:gzip,deflate,sdch
Accept-Language:uk,ru;q=0.8,en;q=0.6 Cache-Control:max-age=0
Connection:keep-alive Content-Length:41
Content-Type:application/x-www-form-urlencoded
Cookie:ss-pid=s2uF57+2p07xnT9nUcpw; X-UAId= 
Host:localhost:2012
Origin:http://localhost:2012 
Referer:http://localhost:2012/Great
User-Agent:Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/34.0.1847.116 Safari/537.36

表格数据:

Name=%D0%BF%D1%80%D0%B8%D0%B2%D1%96%D1%82

在服务中,我收到以下内容:

РїСЂРёРІС–С

和this.Request.OriginalRequest.EncodingName是“Cyrillic(Windows)”。我认为这应该是UTF-8。预期结果是

привіт

PS。 App.config(我正在使用自托管)默认来自http://www.ienablemuch.com/2012/12/self-hosting-servicestack-serving.html

1 个答案:

答案 0 :(得分:2)

我已经看过这个,问题是HTTP Listener推断请求的字符编码为Windows-1251而不是UTF-8,因为字符编码为请求在Content-Type HTTP标头上指定,因此如果要将fiddler中的Content-Type更改为:

,它将按预期工作
Content-Type: application/x-www-form-urlencoded; charset=utf-8

不幸的是,HTML表单不允许您使用charset指定Content-Type,如下所示:

<form action="/hello" method="POST" 
      enctype="application/x-www-form-urlencoded; charset=utf-8">
    <input name="Name" id="Name"/>
    <input type="submit" value="Send"/>
</form>

但是浏览器会有效地忽略它并发送默认的Form Content-Type,例如:

Content-Type: application/x-www-form-urlencoded

由于缺少Content-Type,HTTP Listener会尝试在这种情况下从POST&#39; ed数据中推断出Content-Type:

Name=%D0%BF%D1%80%D0%B8%D0%B2%D1%96%D1%82

它推断为Windows-1251并使用该编码解析值。

有一些解决方案,第一个是覆盖具有just been enabled in this commit并强制执行UTF-8编码的内容编码,例如:

public override ListenerRequest CreateRequest(HttpListenerContext httpContext, 
    string operationName)
{
    var req = new ListenerRequest(httpContext, 
        operationName, 
        RequestAttributes.None)
    {
        ContentEncoding = Encoding.UTF8
    };
    //Important: Set ContentEncoding before parsing attrs as it parses FORM Body
    req.RequestAttributes = req.GetAttributes(); 
    return req;
}

此功能将在v4.0.19版本中发布now available on MyGet

第二个解决方案是有效地向HTTP请求提供一个提示,以便将请求推断为UTF-8,您可以通过指定英语中的第一个字段来完成,例如:

<form action="/hello" method="POST">
    <input type="hidden" name="force" value="UTF-8"/>
    <input name="Name" id="Name"/>
    <input type="submit" value="Send"/>
</form>

force=UTF-8除了英语之外没有什么特别之处,并使用ASCII字符集。