WCF服务中的文件上载(413)请求实体太大

时间:2015-10-13 11:50:39

标签: c# asp.net wcf

我试图在asp .net C#

中实现文件上传到我的WCF服务

以下是WCF服务器中用于文件上传的代码。

 public void FileUpload(string fileName, Stream fileStream)
       {
           FileStream fileToupload = new FileStream("D:\\FileUpload\\" + fileName, FileMode.Create);

        //   byte[] bytearray = new byte[10000];
           byte[] bytearray = new byte[1000];
           int bytesRead, totalBytesRead = 0;
           do
           {
               bytesRead = fileStream.Read(bytearray, 0, bytearray.Length);
               totalBytesRead += bytesRead;
               if(bytesRead > 0)
               fileToupload.Write(bytearray, 0, bytearray.Length);

           } while (bytesRead > 0);

         //  fileToupload.Write(bytearray, 0, bytearray.Length);
           fileToupload.Close();
           fileToupload.Dispose();



       }

以下是客户端上传文件的代码:(固定字节数组大小)

protected void bUpload_Click(object sender, EventArgs e)
{
    byte[] bytearray = null;
    Stream stream;
    string fileName = "";
    //throw new NotImplementedException();
    if (FileUpload1.HasFile)
    {
        fileName = FileUpload1.FileName;
        stream = FileUpload1.FileContent;
        stream.Seek(0, SeekOrigin.Begin);
        bytearray = new byte[stream.Length];
        int count = 0;
        while (count < stream.Length)
        {
            bytearray[count++] = Convert.ToByte(stream.ReadByte());
        }

    }

    string baseAddress = "http://localhost/WCFService/Service1.svc/FileUpload/";

    HttpWebRequest request = (HttpWebRequest)HttpWebRequest.Create(baseAddress + fileName);
    request.Method = "POST";
    request.ContentType = "text/plain";
    Stream serverStream = request.GetRequestStream();
    serverStream.Write(bytearray, 0, bytearray.Length);
    serverStream.Close();
    try
    {
        using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
        {
            int statusCode = (int)response.StatusCode;
            System.Diagnostics.Debug.WriteLine("statusCode: " + statusCode);

            StreamReader reader = new StreamReader(response.GetResponseStream());
            System.Diagnostics.Debug.WriteLine("reader: " + reader.ToString());

        }
    }
    catch (Exception ex)
    {
        System.Diagnostics.Debug.WriteLine("--- EXCEPTION ---");
        ex.ToString();
    }
}

这适用于小尺寸文件,当我尝试使用更大尺寸的文件时 我将固定大小的字节数组更改为动态字节数组写入流。 这是更新的代码:(用于发送数据的1024字节字节数组)

        request.Method = "POST";
        request.ContentType = "text/plain";
       // Stream serverStream = request.GetRequestStream();

        if (FileUpload1.HasFile)
        {
            fileName = FileUpload1.FileName;
            stream = FileUpload1.FileContent;
            stream.Seek(0, SeekOrigin.Begin);
            bytearray = new byte[1024];//stream.Length];


        }
        int TbyteCount = 0;
        Stream requestStream = request.GetRequestStream();

            int bufferSize = 1024;
            byte[] buffer = new byte[bufferSize];
            int byteCount = 0;
            while ((byteCount = stream.Read(buffer, 0, bufferSize)) > 0)
            {
                TbyteCount = TbyteCount + byteCount; 
                requestStream.Write(buffer, 0, byteCount);
            }

            requestStream.Close();


        try
        {
            using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
            {
                int statusCode = (int)response.StatusCode;
                System.Diagnostics.Debug.WriteLine("statusCode: " + statusCode);

                StreamReader reader = new StreamReader(response.GetResponseStream());
                System.Diagnostics.Debug.WriteLine("reader: " + reader.ToString());

            }
        }
        catch (Exception ex)
        {
            System.Diagnostics.Debug.WriteLine("--- EXCEPTION ---");
            ex.ToString();
        }
    }

但是在阅读回复时,我得到了例外 远程服务器返回错误:(413)请求实体太大。

我在请求流中多次写入是否正确!

我使用的文件大小为22.4 KB,使用第一个代码(固定大小的数组)成功上传 如果我将文件大小分成1024字节的倍数并尝试发送则存在问题。

Web.config文件

<?xml version="1.0"?>
<configuration>
  <appSettings>
    <add key="aspnet:UseTaskFriendlySynchronizationContext" value="true"/>
  </appSettings>
  <system.web>
    <compilation debug="true"/>
  </system.web>
  <system.serviceModel>
    <services>
      <service name="WcfServiceApp.Service1" behaviorConfiguration="ServiceBehavior">
        <endpoint address="" binding="webHttpBinding" contract="WcfServiceApp.IService1" behaviorConfiguration="webBehaviour"/>
        <host>
          <baseAddresses>
            <add baseAddress="http://localhost:50327/Service1.svc"/>
          </baseAddresses>
        </host>
      </service>
    </services>
    <behaviors>
      <serviceBehaviors>
        <behavior name="ServiceBehavior">
          <!-- To avoid disclosing metadata information, set the values below to false before deployment -->
          <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
          <!-- To receive exception details in faults for debugging purposes, set the value below to true.  Set to false before deployment to avoid disclosing exception information -->
          <serviceDebug includeExceptionDetailInFaults="false"/>
        </behavior>
      </serviceBehaviors>
      <endpointBehaviors>
        <behavior name="webBehaviour">
          <webHttp/>
        </behavior>
      </endpointBehaviors>
    </behaviors>
    <!--<protocolMapping>
      <add binding="basicHttpsBinding" scheme="https"/>
    </protocolMapping>-->
    <serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true"/>
  </system.serviceModel>
  <system.webServer>
    <httpProtocol>
      <customHeaders>
        <add name="Access-Control-Allow-Origin" value="*"/>
        <add name="Access-Control-Allow-Headers" value="Content-Type, Accept"/>
      </customHeaders>
    </httpProtocol>
    <directoryBrowse enabled="true"/>
  </system.webServer>
</configuration>

2 个答案:

答案 0 :(得分:1)

答案 1 :(得分:1)

当您尝试使用某种结构传输大型序列化对象时,此问题通常是由配置中maxItemsInObjectGraph的泄漏引起的。查看我的answer here

但在您的情况下,您尝试将简单数据文件作为字节流传输。要通过webHttpBinding执行此操作,您应指定正确的服务合同,该合同接受流消息作为输入。所有其他的东西,比如文件名,你可以在消息合约中指定为标题(实际上你可以用文件名作为参数来自URI)也可以。然后,您必须为绑定设置TransferMode = TransferMode.Streamed。一些code example is here还有一个with config samples is here

其他Google广告搜索的关键字是 webhttpbinding streaming