Kestrelhttpserver: How to remove Response header server:krestel

Created on 20 May 2016  路  28Comments  路  Source: aspnet/KestrelHttpServer

From https://github.com/aspnet/Mvc/issues/4689

As a security concern how can we remove "Server:krestel" from Response Header?

3 - Done

Most helpful comment

How about making this an option on KestrelServerOptions?

All 28 comments

@sadjadbp context.Response.Headers.Remove("Server")

@benaadams that should work, I just need to add it somewhere at the end of startup.cs. But there should be a better way, maybe a built-in Middleware.

How about making this an option on KestrelServerOptions?

@blowdart

Yea I was just thinking that we should do this. Banks always want to be able to obfuscate the tech being used.

This can be mitigated by putting Kestrel behind a reverse proxy and configuring the reverse proxy to remove the header (e.g. server_tokens off; in nginx). This is a good one to think about but it's post 1.0.0.

cc @muratg

@cwe1ss add at the start of Startup.Configure rather than end e.g.

public void Configure(IApplicationBuilder app)
{
    app.Use((context, next) =>
    {
        context.Response.Headers.Remove("Server");
        return next();
    });

doesn't look nice! :) I'd prefer Kristian's PR since this is a common use-case.

since this is a common use-case.

So it shouldn't be in Kestrel, it should be somewhere common so it doesn't matter whether you are using Kestrel, WebListener, some other server or change server, it still works.

but why add it and then remove it again?

So it shouldn't be in Kestrel

I'm not so sure. I think it's a server concern since the server is the one adding the header.

The old RFC2068 Section 15.4 even mentions

Revealing the specific software version of the server may allow the
server machine to become more vulnerable to attacks against software
that is known to contain security holes. Implementers SHOULD make the
Server header field a configurable option.

(emphasis mine)

Though this has been removed in the newer RFCs (2616 and 7231):

An origin server SHOULD NOT generate a Server field containing
needlessly fine-grained detail and SHOULD limit the addition of
subproducts by third parties. Overly long and detailed Server field
values increase response latency and potentially reveal internal
implementation details that might make it (slightly) easier for
attackers to find and exploit known security holes.

[...]

Server (Section 7.4.2) header fields often reveal information about
the respective sender's software systems. In theory, this can make
it easier for an attacker to exploit known security holes; in
practice, attackers tend to try all potential holes regardless of the
apparent software versions being used.

I think this is something that should be configurable on the server level. If anything, you're just doing _less_ work by not adding it and then removing it again.

So it shouldn't be in Kestrel

I'm not so sure. I think it's a server concern since the server is the one adding the header.

I mean it should be a feature that is effective across all servers so you can do one thing and it will continue to work if you change server e.g.

app.RemoveServerHeader()

So if you move from .UseKestrel to .UseWebListener for Windows Authentication you aren't exposing the server header by default and what you did before still works.

Re: rfc2068 it is easy to remove as pointed out earlier and configurable so you can happily change it
context.Response.Headers["Server"] = "BenWeb";

Re: rfc2616/7231 it only says
Kestrel
it doesn't say
Kestrel 1.0.0-rc3-20957 ASP.NET Core Mvc Core 1.0.0-rc2-final Node.js 4.4.4 LTS

Suggestion: change IServerAddressesFeature into a more general IServerOptionsFeature that has a common model for server options, like bool AddServerHeader { get; set; } etc.

FYI: In WebListener Http.Sys adds the header for you after you start the response, calling Remove won't work. It has to be disabled with a reg key. I think you can replace it with your own value, but not remove it.

@khellang's PR is a good solution.

@khellang, there's no need to expand IServerAddressesFeature, we plan to add other feature interfaces as needed. That said this is not a good candidate.

For reference, if I remove the server header and then host behind IIS does IIS add its own?

@benaadams are there scenarios where you would conditionally remove the Server header per request? I'm not aware of any, it's usually on or off globally. As such I don't think middleware is appropriate.

Until RC2 the server was hard to directly configure so removing the header in middleware was a workaround.

On a related note we need to move setting the Server and Date headers from the start of the request to the start of the response, or else they can be removed unintentionally. https://github.com/aspnet/KestrelHttpServer/issues/223

@Tratcher There's also some duplication in setting the Server and Date headers right now. It's both in Frame and HttpComponentFactory+Headers.

Interestingly, Frame also sets the Content-Length header, while the other doesn't. Don't know why.

Should Kestrel check if Server and/or Date is present already, before setting them?

@khellang when we move them to the start of the response, yes, application values should be preferred over server defaults.

Not sure about the current duplication. @cesarbs?

when we move them to the start of the response, yes, application values should be preferred over server defaults.

@Tratcher You want to move them completely, or just have make sure they're present when starting the response? Does it make sense for the application to read them?

EDIT; Nevermind, if they're set up front, they won't be set on response start because of the checks.

Yea make it an option flag (says the person who used to fake IIS servers as Apache on Windows before that was an actual thing)

And of course you wouldn't be exposing Kestrel directly anyway, so you could do it at the forwarded level, but that's crappy.

I have a commit, https://github.com/aspnet/KestrelHttpServer/commit/ef35d2374f3bc591084a35866c60ac26da9b0ebb, that builds on top of #855, which moves the Date/Server headers to response start. I just have to figure out the tests before sending a PR.

What's up with setting the Content-Length? Does that need to stay in?

On error?

The Content-Length needs to stay in for empty 500 responses.

I had this working OK in RC2 by removing the header from some custom middleware, but since upgrading to RTM it has started being returned again.

Sorry, my bad. I didn't realise the option had been implemented and superseded the middleware workaround.

I doesn't want, that my server write this header. And doesn't want remove it after. This is a useless server operation. It makes me sad.

@nim This issue has been resolved by adding KestrelServerOptions.AddServerHeader which you can set to false during app startup.

Is there a way to remove the same header but when using HttpSys via server settings?

Was this page helpful?
0 / 5 - 0 ratings