WCF从客户端向服务器发送int []

时间:2012-05-22 21:21:19

标签: c# .net wcf visual-studio-2010

我遇到了这个问题:

我有一个WCF服务,它公开了这个操作合同:

[OperationContract]
void Index(int[] song, string fileName);

在我的客户上,我有:

AudioDetectionServiceReference.AudioDetectionServiceClient client = new AudioDetectionServiceReference.AudioDetectionServiceClient();
client.Index(max.ToArray(), mp3Files[i]);

其中max是2000个int值的数组,而mp3Files [i]是200个字符的字符串。

Web.config有这个:

<configuration>

  <system.web>
    <compilation debug="true" targetFramework="4.0" />
  </system.web>
  <system.serviceModel>
    <behaviors>
      <serviceBehaviors>
        <behavior>
          <!-- To avoid disclosing metadata information, set the value below to false and remove the metadata endpoint above before deployment -->
          <serviceMetadata httpGetEnabled="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>
    </behaviors>
    <serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
  </system.serviceModel>
  <system.webServer>
  <modules runAllManagedModulesForAllRequests="true"/>
  </system.webServer>

</configuration>

app.config有:

    <configuration>
        <system.serviceModel>

            <bindings>
                <basicHttpBinding>
                    <binding name="BasicHttpBinding_IAudioDetectionService" closeTimeout="00:01:00"
                        openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
                        allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
                        maxBufferSize="65536" maxBufferPoolSize="524288" maxReceivedMessageSize="65536"
                        messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
                        useDefaultWebProxy="true">
                        <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="16384"
                            maxBytesPerRead="4096" maxNameTableCharCount="16384" />
                        <security mode="None">
                            <transport clientCredentialType="None" proxyCredentialType="None"
                                realm="" />
                            <message clientCredentialType="UserName" algorithmSuite="Default" />
                        </security>
                    </binding>
                </basicHttpBinding>
            </bindings>
            <client>
                <endpoint address="http://localhost:15863/AudioDetectionService.svc"
                    binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IAudioDetectionService"
                    contract="AudioDetectionServiceReference.IAudioDetectionService"
                    name="BasicHttpBinding_IAudioDetectionService" />
            </client>
        </system.serviceModel>
    <startup><supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0"/></startup></configuration>

现在是棘手的部分:

右键单击服务引用时,转到配置服务引用,有一个名为Collection type的选项。如果我将集合类型设置为“Syste.Array”,我会收到错误

The remote server returned an unexpected response: (400) Bad Request.

使用堆栈跟踪:

    Server stack trace: 
       at System.ServiceModel.Channels.HttpChannelUtilities.ValidateRequestReplyResponse(HttpWebRequest request, HttpWebResponse response, HttpChannelFactory factory, WebException responseException, ChannelBinding channelBinding)
       at System.ServiceModel.Channels.HttpChannelFactory.HttpRequestChannel.HttpChannelRequest.WaitForReply(TimeSpan timeout)
       at System.ServiceModel.Channels.RequestChannel.Request(Message message, TimeSpan timeout)
       at System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout)
       at System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation)
       at System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)

    Exception rethrown at [0]: 
       at System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
       at System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
       at SqlTest.AudioDetectionServiceReference.IAudioDetectionService.Index(Int32[] song, String fileName)
       at SqlTest.AudioDetectionServiceReference.AudioDetectionServiceClient.Index(Int32[] song, String fileName) in blablabla\Service References\AudioDetectionServiceReference\Reference.cs:line 53
       at SqlTest.Program.Main(String[] args) in blablabla\Program.cs:line 46

当我将其更改为“System.Collection.Generic.List”时,错误会神奇地消失。

我的问题是:为什么?

第二个问题:

为什么这有效?

client.Index(max.Take(100).ToArray(), mp3Files[i]);

使用相同的上下文(app.config,web.config,以及与上面相同的代码,选择了System.Array)。

谢谢, Andrei Neagu

PS:我发布这个是因为我花了两天的时间尝试更改绑定设置,更改消息大小,更改readerQuotas和其他内容的值,当我只需做这个愚蠢的选择时。所以我很生气,我想至少从中学到一些东西。

1 个答案:

答案 0 :(得分:2)

经过多次挖掘后,我就改变了这一点:

的app.config

<bindings>
    <basicHttpBinding>
        <binding name="BasicHttpBinding_IAudioDetectionService" closeTimeout="00:01:00"
            openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
            allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
            maxBufferSize="655360" maxBufferPoolSize="5242880" maxReceivedMessageSize="655360"
            messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
            useDefaultWebProxy="true">
            <readerQuotas maxDepth="320" maxStringContentLength="81920" maxArrayLength="163840"
                maxBytesPerRead="40960" maxNameTableCharCount="163840" />
            <security mode="None">
                <transport clientCredentialType="None" proxyCredentialType="None"
                    realm="" />
                <message clientCredentialType="UserName" algorithmSuite="Default" />
            </security>
        </binding>
    </basicHttpBinding>
</bindings>
<client>
    <endpoint address="http://localhost:15863/AudioDetectionService.svc"
        binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IAudioDetectionService"
        contract="AudioDetectionServiceReference.IAudioDetectionService"
        name="BasicHttpBinding_IAudioDetectionService" />
</client>

并且对于服务器,请查看basicHttpBinding部分没有名称的事实。我认为如果此部分有名称,WCF生成的默认服务将忽略它。

<bindings>
  <basicHttpBinding>
    <binding closeTimeout="00:01:00"
        openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:01:00"
        allowCookies="false" bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
        maxBufferSize="655360" maxBufferPoolSize="5242880" maxReceivedMessageSize="655360"
        messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
        useDefaultWebProxy="true">
      <readerQuotas maxDepth="320" maxStringContentLength="81920" maxArrayLength="163840"
          maxBytesPerRead="40960" maxNameTableCharCount="163840" />
      <security mode="None">
        <transport clientCredentialType="None" proxyCredentialType="None"
            realm="" />
        <message clientCredentialType="UserName" algorithmSuite="Default" />
      </security>
    </binding>
  </basicHttpBinding>
</bindings>

对于其他值,我在末尾添加了一个0(乘以10)。增加它们我认为会让你更多地转移事件。但最重要的是,basicHttpBinding没有名字。如果它有一个名字,我认为它被忽略了。

我不会将其设置为已回答,因为问题是System.Array抛出异常而System.Generic.List没有抛出异常。