我正在写一个 Nancy 端点,我想做一些我认为应该非常简单的事情。我想支持以 json 或 xml 格式返回内容,但是当请求 html 或任何其他类型时返回 406 Not supported。我可以轻松地仅强制使用 XML 或 JSON,我想我可以这样做,如果(接受为 html)返回 406,但我认为在内容协商支持中对此有一些支持。
任何人都可以解释一下吗?
我正在写一个 Nancy 端点,我想做一些我认为应该非常简单的事情。我想支持以 json 或 xml 格式返回内容,但是当请求 html 或任何其他类型时返回 406 Not supported。我可以轻松地仅强制使用 XML 或 JSON,我想我可以这样做,如果(接受为 html)返回 406,但我认为在内容协商支持中对此有一些支持。
任何人都可以解释一下吗?
实现你自己的 IResponseProcessor,Nancy 将把它捡起来并挂在引擎中。
public sealed class NoJsonOrXmlProcessor : IResponseProcessor
{
public ProcessorMatch CanProcess(MediaRange requestedMediaRange, dynamic model, NancyContext context)
{
if (requestedMediaRange.Matches("application/json") || requestedMediaRange.Matches("aaplication/xml"))
{
//pass on, so the real processors can handle
return new ProcessorMatch{ModelResult = MatchResult.NoMatch, RequestedContentTypeResult = MatchResult.NoMatch};
}
return new ProcessorMatch{ModelResult = MatchResult.ExactMatch, RequestedContentTypeResult = MatchResult.ExactMatch};
}
public Response Process(MediaRange requestedMediaRange, dynamic model, NancyContext context)
{
return new Response{StatusCode = HttpStatusCode.NotAcceptable};
}
public IEnumerable<Tuple<string, MediaRange>> ExtensionMappings { get; private set; }
}
我们避免使用ResponseProcessor
的全部原因是请求仍在通过我们的身份验证层、域层等一直运行。我们想要一种方法来尽快终止请求。
我们最终做的是在我们自己的内部进行检查Boostrapper
public class Boostrapper : DefaultNancyBootstrapper
{
protected override void RequestStartup(TinyIoCContainer requestContainer, IPipelines pipelines, NancyContext context)
{
base.RequestStartup(requestContainer, pipelines, context);
pipelines.BeforeRequest += nancyContext =>
{
RequestHeaders headers = nancyContext.Request.Headers
if (!IsAcceptHeadersAllowed(headers.Accept))
{
return new Response() {StatusCode = HttpStatusCode.NotAcceptable};
}
return null;
}
}
private bool IsAcceptHeadersAllowed(IEnumerable<Tuple<string, decimal>> acceptTypes)
{
return acceptTypes.Any(tuple =>
{
var accept = new MediaRange(tuple.Item1);
return accept.Matches("application/json") || accept.Matches("application/xml");
});
}
}