eadam
eadam

Reputation: 26061

Change the headers of static files in Asp.net Core

I am using package Microsoft.AspNet.StaticFiles and configuring it in Startup.cs as app.UseStaticFiles(). How can I change the headers of the delivered files ? I want to set cache expiry etc for images, css and js.

Upvotes: 17

Views: 12223

Answers (5)

Darkseal
Darkseal

Reputation: 9564

If you're looking for a solution allowing you to configure different behaviours for each environment (development, production & more), which is also the point of having these settings in the web.config file instead of hard-coding the whole stuff, you could consider the following approach.

Add the following key/value section in the appsettings.json file:

  "StaticFiles": {
    "Headers": {
      "Cache-Control": "no-cache, no-store",
      "Pragma": "no-cache",
      "Expires": "-1"
    }
  }

Then add the following in the Startup.cs file's Configure method accordingly:

app.UseStaticFiles(new StaticFileOptions()
{
    OnPrepareResponse = (context) =>
    {
        // Disable caching for all static files.
        context.Context.Response.Headers["Cache-Control"] = Configuration["StaticFiles:Headers:Cache-Control"];
        context.Context.Response.Headers["Pragma"] = Configuration["StaticFiles:Headers:Pragma"];
        context.Context.Response.Headers["Expires"] = Configuration["StaticFiles:Headers:Expires"];
    }
});

This will allow the developer to define different cache settings using different/multiple/cascading settings files (appsettings.json, appsettings.production.json and so on) - which is something that could be done with the old web.config configuration pattern - with the ASP.NET Core's new one.

For additional info regarding the topic I also suggest to read this post on my blog and/or these great articles from the official ASP.NET Core docs:

Upvotes: 5

Matt Lengenfelder
Matt Lengenfelder

Reputation: 739

Based on Josh Mouch's answer above, added code to determine if it's a pdf file

Startup.cs:

      app.UseStaticFiles(new StaticFileOptions
      {
        OnPrepareResponse = ctx =>
          {
            if(ctx.File.Name.ToLower().EndsWith(".pdf"))
            {
              ctx.Context.Response.Headers.Append("Cache-Control", "public,max-age=86400");
            }
            else
            {
              ctx.Context.Response.Headers.Append("Cache-Control", "public,max-age=31104000");
            }
          }
      });

Upvotes: 8

Josh Mouch
Josh Mouch

Reputation: 3558

You can use StaticFileOptions, which contains an event handler that is called on each request of a static file.

Your Startup.cs should look something like this:

// Add static files to the request pipeline.
app.UseStaticFiles(new StaticFileOptions()
{
    OnPrepareResponse = (context) =>
    {
        // Disable caching of all static files.
        context.Context.Response.Headers["Cache-Control"] = "no-cache, no-store";
        context.Context.Response.Headers["Pragma"] = "no-cache";
        context.Context.Response.Headers["Expires"] = "-1";
    }
});

You can, of course, modify the above code to check the content type and only modify headers for JS or CSS or whatever you want.

Upvotes: 27

Malgaur
Malgaur

Reputation: 1850

Under IIS, you can add a web.config file to your wwwroot folder with header configurations. An example that will control cache headers for all files:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.webServer>

    <!-- Disable caching -->
    <httpProtocol>
      <customHeaders>
        <add name="Cache-Control" value="no-cache" />
      </customHeaders>
    </httpProtocol>

  </system.webServer>
</configuration>

Upvotes: 1

agua from mars
agua from mars

Reputation: 17404

You have to write a middleware to do this, I've a sample that remove headers on my github https://github.com/aguacongas/chatle
Look at the ChatLe.HttpUtility project, it's a bit tricky. you can take a look of this question as well:

How to do remove some httpresponse headers on each response like Server and ETag?

However this will not work under IIS, because IIS manage statics files itself. It will work only on stand-alone application like kestrel or firefly

Upvotes: 2

Related Questions