简体   繁体   English

C#RESTful服务-HTTP 504 /连接重置

[英]C# RESTful service - HTTP 504 / Connection Reset

I have a C# application that takes and returns information via RESTful services. 我有一个C#应用程序,该应用程序通过RESTful服务获取并返回信息。 The way I handled these operations before, was the methods simply returned JSON strings, and these strings were then wrapped in XML. 我以前处理这些操作的方式是方法仅返回JSON字符串,然后将这些字符串包装为XML。

To prevent this, I changed the ResponseFormat to JSON and I am now returning DataContracts, which all derive from one abstract class: 为了防止这种情况,我将ResponseFormat更改为JSON,现在返回DataContracts,这些数据均源自一个抽象类:

using System.Runtime.Serialization;

/// <summary>
/// Abstract class for defining a standard definition of a command return result.
/// A command is not required to return a result, however it is recommended.
/// A return result must implement the properties defined in this abstract class.
/// A command may return an anonymous object instead of an instance of this abstract class.
/// </summary>
[DataContract(Namespace = "")]
public abstract class ICommandResult {
// Don't let the name disturb you, this used to be an interface.

    /// <summary>
    /// Gets or sets the message.
    /// </summary>

    [DataMember]
    public abstract string Message { get; set; }

}

To apply the DataContract attribute, I changed the above interface to a (now) abstract class. 为了应用DataContract属性,我将上述接口更改为一个(现在)抽象类。

Each derivative also applies the DataContract and DataMember attributes. 每个派生类还应用DataContract和DataMember属性。

When I call a route of the service, the command gets executed, and I can see output in the console. 当我调用服务的路由时,命令将被执行,并且可以在控制台中看到输出。 When returning the return value, however, I see following in the console, and the web browser stays empty. 但是,当返回返回值时,我在控制台中看到以下内容,并且Web浏览器保持空白。 Fiddler (on Windows) shows me a HTTP 504 error, whereas my Mac shows me a connection reset. Fiddler(在Windows上)向我显示HTTP 504错误,而在Mac上向我显示连接重置。

XmlException (Dropped Connection?): On JSON writer data type 'type' must be specified. Object string is 'object', server type string is '__type'.

The specific method I'm using to test this, is as follows: 我用来测试的具体方法如下:

IRestService: IRestService:

[OperationContract]
[WebGet(UriTemplate = Routing.GetRoutesRoute, ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Bare)]
ICommandResult GetAllRoutes();

RestService (implementation): RestService(实现):

public ICommandResult GetAllRoutes() {
    var results = ExecuteCommand("print-routes", "--no-output");
    // ExecuteCommand returns an ICommandResult object
    return results;
}

Actual command implementation (so it can be called via the console, too): 实际的命令实现(因此也可以通过控制台调用):

ICommandResult Command_PrintRoutes(Command sender, params string[] args) {
        var fields = typeof(Routing).GetFields();
        var fieldValues = new Dictionary<string, string>();
        var outputToConsole = true;

        if (args.Count(x => x.ToLowerInvariant().Equals("--no-output")) == 1)
            outputToConsole = false;

        foreach (var field in fields)
            fieldValues.Add(field.Name, (string)field.GetRawConstantValue());

        var output = JsonConvert.SerializeObject(fieldValues, Formatting.Indented);

        if (outputToConsole)
            WriteLine(output);

        //return new CommandResult<Dictionary<string, string>>("Found following routes", fieldValues);
        return new CommandResult<string>("Found following routes (JSON-encoded)", output); // Trying out different return types
    }

How can this be fixed and prevented? 如何解决和预防?

I think that this is a serialization problem, with your abstact DataContract. 我认为这是一个序列化问题,涉及您的Abstact DataContract。

Look this: KnownTypeAttribute - Serialization . 看一下: KnownTypeAttribute-序列化

I think that you need specify all your subclasses on the abstract base class using KnownType Attribute. 我认为您需要使用KnownType Attribute在抽象基类上指定所有子类。

In this way the DataContractSerializer can recognize all types when serialize and deserialize objects. 这样,DataContractSerializer可以在序列化和反序列化对象时识别所有类型。

 [DataContract]
 [KnownType(typeof(SubClassName1))] <-
 [KnownType(typeof(SubClassName2))] <-
 [KnownType(typeof(SubClassName3))] <-
 public abstract class ClassName
 {
      ...
 }

Sorry for my english. 对不起我的英语不好。 I hope I was helpful, 我希望我会有所帮助,

Stefano 斯特凡诺

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM