通过WCF流传输文件时出现的“ArgumentNullException”错误

3

我有一个WCF流式传输二进制文件。以下是合同的缩短版。

[MessageContract()]
public class DocumentTransfer
{
    [MessageHeader(MustUnderstand = true)]
    public string Title { get; set; }

    [MessageHeader(MustUnderstand = true)]
    public string FileName { get; set; }

    [MessageBodyMember(Order = 1)]
    public System.IO.Stream Data;
}

一切都运行良好,但是有些情况下只需要更新与文件相关的其他值,而不是文件本身。在这种情况下,客户端将Data设置为null。然后无法解释/序列化Data属性,从而引发此异常:

System.ServiceModel.Dispatcher.StreamFormatter.Serialize(XmlDictionaryWriter writer, Object[] parameters, Object returnValue)
System.ServiceModel.Dispatcher.OperationFormatter.SerializeBodyContents(XmlDictionaryWriter writer, MessageVersion version, Object[] parameters, Object returnValue, Boolean isRequest)
System.ServiceModel.Dispatcher.OperationFormatter.OperationFormatterMessage.OperationFormatterBodyWriter.OnWriteBodyContents(XmlDictionaryWriter writer)
System.ServiceModel.Channels.BodyWriter.WriteBodyContents(XmlDictionaryWriter writer)
System.ServiceModel.Channels.BodyWriterMessage.OnWriteBodyContents(XmlDictionaryWriter writer)
System.ServiceModel.Channels.Message.OnWriteMessage(XmlDictionaryWriter writer)
System.ServiceModel.Channels.Message.WriteMessage(XmlDictionaryWriter writer)
System.ServiceModel.Channels.TextMessageEncoderFactory.TextMessageEncoder.WriteMessage(Message message, Stream stream)
System.ServiceModel.Channels.HttpOutput.WriteStreamedMessage(TimeSpan timeout)
System.ServiceModel.Channels.HttpOutput.Send(TimeSpan timeout)
System.ServiceModel.Channels.HttpChannelFactory.HttpRequestChannel.HttpChannelRequest.SendRequest(Message message, TimeSpan timeout)
System.ServiceModel.Channels.RequestChannel.Request(Message message, TimeSpan timeout)
System.ServiceModel.Dispatcher.RequestChannelBinder.Request(Message message, TimeSpan timeout)
System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs, TimeSpan timeout)
System.ServiceModel.Channels.ServiceChannel.Call(String action, Boolean oneway, ProxyOperationRuntime operation, Object[] ins, Object[] outs)
System.ServiceModel.Channels.ServiceChannelProxy.InvokeService(IMethodCallMessage methodCall, ProxyOperationRuntime operation)
System.ServiceModel.Channels.ServiceChannelProxy.Invoke(IMessage message)
System.Runtime.Remoting.Proxies.RealProxy.HandleReturnMessage(IMessage reqMsg, IMessage retMsg)
System.Runtime.Remoting.Proxies.RealProxy.PrivateInvoke(MessageData& msgData, Int32 type)
...UploadDocument(DocumentTransfer request)
...UploadDocument(DocumentTransfer request) in ...

有什么想法吗?

1
使用另一种类型,比如DocumentMetadataTransfer。这是有道理的,因为正如你所解释的那样,它们适用于不同的目的。仅带有标题的消息并不完全是一条消息,对吧?此外,TitleFileName不应该是MessageHeader项,因为它们实际上是消息的一部分,而不一定是消息元数据,而是操作数据。 - Grant Thomas
2个回答

2

当body为空时,您会在SerializeBodyContents中遇到错误。

您可以为没有文件的情况创建不同的操作,或者在流中放入一个字节以避免异常。如果您无法更改合同,则最好选择前面的选项,否则选择后面的选项。


2
另一个选择是返回Stream.Null。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接