我试图让ServiceStack将对象列表返回给C#客户端,但我一直得到这个例外:
"... System.Runtime.Serialization.SerializationException: Type definitions should start with a '{' ...."
我想要回归的模型:
public class ServiceCallModel
{
public ServiceCallModel()
{
call_uid = 0;
}
public ServiceCallModel(int callUid)
{
this.call_uid = callUid;
}
public int call_uid { get; set; }
public int store_uid { get; set; }
...... <many more properties> ......
public bool cap_expense { get; set; }
public bool is_new { get; set; }
// An array of properties to exclude from property building
public string[] excludedProperties = { "" };
}
回应:
public class ServiceCallResponse
{
public List<ServiceCallModel> Result { get; set; }
public ResponseStatus ResponseStatus { get; set; } //Where Exceptions get auto-serialized
}
服务:
public class ServiceCallsService : Service
{
// An instance of model factory
ModelFactory MyModelFactory = new ModelFactory();
public object Any(ServiceCallModel request)
{
if (request.call_uid != 0)
{
return MyModelFactory.GetServiceCalls(request.call_uid);
} else {
return MyModelFactory.GetServiceCalls() ;
}
}
}
客户端使用以下方式访问服务:
JsonServiceClient client = new ServiceStack.ServiceClient.Web.JsonServiceClient("http://172.16.0.15/");
client.SetCredentials("user", "1234");
client.AlwaysSendBasicAuthHeader = true;
ServiceCallResponse response = client.Get<ServiceCallResponse>("/sc");
“model factory”类是一个返回列表的DB访问类。当我通过Web浏览器访问服务时,一切似乎都运行正常。从服务返回的JSON开始:
"[{"call_uid":70...."
结束于:
"....false,"is_new":true}]"
我的问题是,这可能会导致序列化/反序列化失败?
解决方案
感谢mythz的回答,我能够弄清楚我做错了什么。我的误解在于究竟有多少DTO类型,以及它们究竟是做什么的。在我看来,我把它们以某种不正确的方式合并在一起。所以现在我明白了:
要返回的对象(在我的例子中,称为“ServiceCallModel”:一旦ServiceStack完成其工作,您希望客户端拥有的实际类。在我的例子中,ServiceCallModel是我的程序中的一个关键类,许多其他类消耗并创造。
请求DTO:这是客户端发送到服务器的内容,包含与发出请求相关的任何内容。变量等
响应DTO:服务器发送回请求客户端的响应。这个包含单个数据对象(ServiceCallModel),或者在我的情况下......包含ServiceCallModel列表。
此外,正如Mythz所说,我现在理解在请求DTO中添加“IReturn”的原因是客户端将准确知道服务器将发回给它的内容。在我的例子中,我使用ServiceCallModel列表作为Android中ListView的数据源。因此能够告诉ListViewAdapter“response.Result”实际上已经是一个有用的列表了。
感谢Mythz的帮助。
答案 0 :(得分:2)
此错误:
Type definitions should start with a '{'
当JSON的形状与预期的形状不匹配时会发生这种情况,例如:
ServiceCallResponse response = client.Get<ServiceCallResponse>("/sc");
客户希望服务返回ServiceCallResponse
,但是从提供的信息中发现这种情况并不清楚 - 虽然错误表明它不是。
虽然它不会改变行为,但如果在服务中指定类型,则可以断言它返回预期类型,例如将object
更改为ServiceCallResponse
,例如:
public ServiceCallResponse Any(ServiceCallModel request)
{
...
}
为了保存客户猜测服务返回的内容,您可以在Request DTO上使用以下命令指定它:
public class ServiceCallModel : IReturn<ServiceCallResponse>
{
...
}
这可以让您的客户拥有更简洁和类型化的API,例如:
ServiceCallResponse response = client.Get(new ServiceCallModel());
而不是:
ServiceCallResponse response = client.Get<ServiceCallResponse>("/sc");
有关详细信息,请参阅New API和C# Clients文档。