题
有没有办法返回经典对象,而不是返回普通字符串?如果不:最佳做法是什么?您是否将对象转置为 xml 并在另一侧重建对象?还有哪些其他可能性?
解决方案
如前所述,您可以通过序列化在 .net 中执行此操作。默认情况下,所有本机类型都是可序列化的,因此这会自动为您发生。
但是,如果您有复杂类型,则需要使用 [Serializable] 属性来标记对象。复杂类型作为属性也是如此。
例如,您需要:
[Serializable]
public class MyClass
{
public string MyString {get; set;}
[Serializable]
public MyOtherClass MyOtherClassProperty {get; set;}
}
其他提示
如果对象可以序列化为 XML 并可以用 WSDL 进行描述,那么可以从 Web 服务返回对象。
是的:在 .NET 中,他们将此称为序列化,其中对象被序列化为 XML,然后由使用服务将其重建回其原始对象类型或具有相同数据结构的代理。
在可能的情况下,我将对象转置为 XML - 这意味着 Web 服务更具可移植性 - 然后我可以用任何语言访问该服务,我只需要用该语言创建解析器/对象转置器。
因为我们有描述服务的 WSDL 文件,所以这在某些系统中几乎是自动化的。
(例如,我们有一个用纯 python 编写的服务器,它正在取代用 C 编写的服务器,一个用 C++/gSOAP 编写的客户端,以及一个用 Cocoa/Objective-C 编写的客户端。我们使用soapUI作为测试框架,它是用Java编写的)。
可以使用 XML 从 Web 服务返回对象。但 Web 服务应该与平台和操作系统无关。序列化对象仅允许您从字节流(例如文件)存储和检索对象。例如,您可以序列化 Java 对象,转换该二进制流(可能通过 Base 64 编码转换为 CDATA 字段)并将其传输到服务的客户端。
但客户端只能恢复基于 Java 的对象。此外,需要深拷贝来序列化对象并准确恢复它。深拷贝可能会很昂贵。
最好的方法是创建一个表示文档的 XML 模式,并使用对象细节创建该模式的实例。
.NET 自动对可序列化的对象执行此操作。我很确定 Java 也以同样的方式工作。
这是一篇讨论 .NET 中对象序列化的文章:http://www.codeguru.com/Csharp/Csharp/cs_syntax/serialization/article.php/c7201
@布莱恩:我不知道 Java 中的工作原理,但在 .net 中,对象被序列化为 XML,而不是 base64 字符串。Web 服务发布一个 wsdl 文件,其中包含 Web 服务所需的方法和对象定义。
我希望没有人创建简单地创建 Base64 字符串的 Web 服务
丹尼尔·奥格:
正如其他人所说,这是可能的。但是,如果服务和客户端都使用在双方都具有完全相同域行为的对象,则首先您可能不需要服务。洛马克斯:我必须不同意这一点,因为这是一个狭窄的评论。使用可以将域对象序列化为XML的Web服务意味着它使使用相同域对象的客户变得容易,但这也意味着这些客户端仅限于使用您所曝光的特定Web服务,并且也可以在通过允许其他客户不了解您的域对象,但仍然通过XML与您的服务进行交互,反转。
@洛马克斯:您描述了两种情况。 场景一: 客户端正在将 xml 消息重新恢复到完全相同的域对象中。我认为这是“返回一个对象”。根据我的经验,这是一个糟糕的选择,我将在下面解释这一点。 场景2: 客户端将 xml 消息重新水合为除完全相同的域对象之外的其他内容:我 100% 支持这一点,但是我不认为这会返回域对象。它实际上是在发送消息或DTO。
现在让我解释为什么跨 Web 服务的真实/纯/非 DTO 对象序列化是 通常 一个坏主意。一个断言:为了首先做到这一点,您要么必须是客户端和服务的所有者,要么为客户端提供一个要使用的库,以便他们可以将对象重新恢复到其真实类型。问题:该域对象作为一种类型现在存在于并属于两个半相关的域。随着时间的推移,可能需要在一个领域添加在另一个领域没有意义的行为,这会导致污染和潜在的痛苦问题。
我通常默认场景2。我只在有压倒性理由时才使用场景 1。
对于我最初的回复如此简洁,我深表歉意。我希望这能在一定程度上澄清我的观点。Lomax,看来我们一半同意;)。
正如其他人所说,这是可能的。但是,如果服务和客户端都使用双方具有完全相同的域行为的对象,那么您可能一开始就不需要服务。
正如其他人所说,这是可能的。但是,如果服务和客户端都使用在双方都具有完全相同域行为的对象,则首先您可能不需要服务。
我不得不不同意这一点,因为这是一个有点狭隘的评论。使用可以将域对象序列化为 XML 的 Web 服务意味着它使使用相同域对象的客户端变得容易,但这也意味着这些客户端仅限于使用您公开的特定 Web 服务,并且它也可以在相反,允许其他客户端不了解您的域对象,但仍然通过 XML 与您的服务交互。