Search code examples
c#asp.net-corenancy

Static Content in NancyFX with ASP.Net Core


I'm using Nancy 2.0.0 with ASP.Net Core 2.0.0 and I can't get my application to return static content (in this case, a zip file) from a route defined in a Nancy module.

The Nancy convention is to store static content in /Content and the ASP.Net Core convention is to store it in /wwwroot, but I can't get my app to recognize either.

My Startup.Configure method looks like this:

public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
    app.UseStaticFiles();            
    app.UseOwin(b => b.UseNancy());
}

And my module route looks like this:

Get("/big_file", _ => {
    return Response.AsFile("wwwroot/test.zip");
});

But Nancy always returns a 404 when I hit this route. I've also tried directing ASP.Net Core to the static directory expected by Nancy, like this:

app.UseStaticFiles(new StaticFileOptions()
{
    FileProvider = new PhysicalFileProvider(Path.Combine(Directory.GetCurrentDirectory(), @"Content")),
    RequestPath = new PathString("/Content")
});

But this didn't work either. I've tried putting the file in /Content and in /wwwroot with the same result. And I've tried different casing of Content, but nothing seems to work. What am I missing?


Solution

  • I figured it out. The issue was that I needed to let Nancy know what I wanted to use as the root path for the application. I did this by creating a class that inherits from IRootPathProvider. Nancy will discover any class that inherits from this on Startup, so you can put it wherever you want.

    public class DemoRootPathProvider : IRootPathProvider
    {
      public string GetRootPath()
      {
        return Directory.GetCurrentDirectory();
      }
    }
    

    Once this was in place I was able to access static content in /Content. Additionally, I was able to add additional static directories (for example, if I wanted to stick with /wwwroot) by adding a class that inherits from DefaultNancyBootstrapper. Again, Nancy will find this on Startup, so you can put it anywhere.

    public class DemoBootstrapper : DefaultNancyBootstrapper
    {
      protected override void ConfigureConventions(NancyConventions conventions)
      {
        base.ConfigureConventions(conventions);
    
        conventions.StaticContentsConventions.Add(
            StaticContentConventionBuilder.AddDirectory("wwwroot")
        );
      }
    }