尝试通过 WCF 传递位图时出现“System.ServiceModel.CommunicationException”

Posted

技术标签:

【中文标题】尝试通过 WCF 传递位图时出现“System.ServiceModel.CommunicationException”【英文标题】:"System.ServiceModel.CommunicationException" when trying to pass a bitmap through WCF 【发布时间】:2011-04-15 19:19:42 【问题描述】:

我正在尝试通过 WCF 传递位图,但它会抛出

System.ServiceModel.CommunicationException 未被用户代码处理 Message=套接字连接是 中止。这可能是由 处理您的消息时出错或 接收超时被超过 远程主机或底层网络 资源问题。本地套接字超时 是“00:00:59.9650000”。

知道是什么原因造成的吗?

谢谢!

【问题讨论】:

【参考方案1】:

原因是 Bitmap 类型是 .NET 特定类型(其中也包含许多 Win32 细节),它不能序列化为 XML。您不能真正将其作为方法的参数传回 - 您可以做的是将其流式传输回 Stream 类型的参数并使用 streamed transfer in WCF。

或者另一种方法(如果您的位图不是太大)将使用 Base64 编码将Bitmap 转换为字符串,将其作为字符串发送回,然后在客户端重新编码。

【讨论】:

谢谢! Base64 编码看起来很有希望,我明天试试。 Auch... 不,它只适用于非常小的图像。转换一张 0.5mb 的图片花了一分钟多的时间。【参考方案2】:

假设您在 IIS 中托管 WCF 服务(您没有提及任何细节)。

尝试在客户端和服务器配置文件中增加一些数字(记住设置必须匹配)。

<binding name="Binding_ISomeervice" closeTimeout="00:01:00"
    openTimeout="00:01:00" receiveTimeout="00:10:00" sendTimeout="00:10:00"
    transactionFlow="false" transferMode="Buffered" transactionProtocol="OleTransactions"
    hostNameComparisonMode="StrongWildcard" listenBacklog="1000"
    maxBufferPoolSize="524288" maxBufferSize="2147483647" maxConnections="100"
    maxReceivedMessageSize="2147483647">
  <readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="2147483647"
    maxBytesPerRead="4096" maxNameTableCharCount="16384" />
</binding>

同时在服务器的 web 配置文件中启用调试:

<system.web>
  <compilation debug="true" />
</system.web>

如果可以的话,将 try/catch(带有日志记录)放在您的服务调用实现中,这将告诉您是执行正在抛出还是托管环境正在抛出。

【讨论】:

【参考方案3】:

嘿,这是来自 WCF 的更令人恼火的消息之一。我的猜测是消息大小太大。我发现解决这些问题的最可靠方法是使用 WCF 跟踪,如 http://msdn.microsoft.com/en-us/library/ms733025.aspx 和 SvcTraceViewer.exe 中所述。

【讨论】:

【参考方案4】:

我的回答分为两部分:针对这种情况的建议,以及对未来更好的错误报告和跟踪的建议。

由于您正在处理位图,您是否考虑过使用 WCF 的原始编程模型? This blog post details如何在服务端使用编程模型,this follow-up blog post详细说明如何在客户端使用。我已经看到它在文件上传和图像传输场景中使用了很多,所以它也可能对您的情况有所帮助!

CommunicationException 是通用的,不会揭示底层异常。以后报错的时候,建议在服务端开启IncludeExceptionDetailInFaults(无论是从ServiceBehaviorAttribute还是从配置行为),以便将异常信息发送回客户端,然后在Detail中报告你得到的嵌套异常.

例如:

<behaviors> 
            <serviceBehaviors> 
                <behavior 
                    <serviceMetadata httpGetEnabled="true" /> 
                    <serviceDebug includeExceptionDetailInFaults="true" /> 
                </behavior> 
            </serviceBehaviors> 
        </behaviors> 

至于开启追踪,以下是我的建议,我已经在其他一些答案中粘贴了这些建议。

在服务端启用跟踪,生成跟踪日志,并使用 SvcTraceViewer 进行分析。为此,请按照this MSDN article on using the service trace viewer 的说明进行操作。

使用Fiddler 监控客户端和服务端的有线流量。

一般来说,一旦你这样做了,你应该得到更多关于服务端出现问题的更多信息,并且可以很快诊断出问题。

【讨论】:

以上是关于尝试通过 WCF 传递位图时出现“System.ServiceModel.CommunicationException”的主要内容,如果未能解决你的问题,请参考以下文章

尝试 GET 时出现 WCF REST 404

为啥我尝试裁剪位图时出现空白 TImage?

在部分受信任的 AppDomain 中调用 WCF 操作时出现“请求失败”

BitmapRegionDecode.decodeRegion,尝试从位图创建图块时出现skia错误

尝试在 ASP.NET 网站中托管时出现 WCF 服务异常错误

尝试使用 XHR 联系 WCF 服务时出现 400 错误请求