Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Relative url of resources in ASP.NET Core not working from development to production

I'm struggling with an issue in my ASP.NET Core & Angular 2 application, where it works just great in development, but when publishing to IIS and configuring IIS properly for ASP.NET Core it fails to load the required stylesheets and scripts.

I redirect all requests that don't map to my API routing back to index.html by returning a VirtualFileResult. The index.html has a

<!DOCTYPE html>
<html>
<head>
    <title>Data Platform</title>
    <meta name="description" content="Data Platform" />
    <meta charset="utf8" />

    <base href="/" />
    <link rel="stylesheet" href="lib/css/vendors.css" />
    <link rel="stylesheet" href="platform/content/css/base.css" />
    <link rel="stylesheet" href="platform/content/css/bootstrap-overrides.css" />
    <link rel="shortcut icon" type="image/x-icon" href="favicon.ico" />

    <script src="lib/vendors.js"></script>
    <script>
        System.config({
            packages: {
                "/platform/": { defaultExtension: "js" }
            }
        });

        System.import("/platform/boot");
    </script>
</head>
<body>
    <data-platform>Initializing...</data-platform>
</body>
</html>

The Startup.cs configuration is pretty basic:

app.UseIISPlatformHandler();

if (string.Equals(env.EnvironmentName, "Development", StringComparison.OrdinalIgnoreCase))
{
    app.UseDeveloperExceptionPage();
}

app.UseFileServer(false);
app.UseStatusCodePages();
app.UseMvc(routeBuilder =>
{
    routeBuilder.MapRoute(
        name: "Api",
        template: "api/{controller}/"
    );
    routeBuilder.MapRoute(
        name: "Client Passthrough",
        template: "{*any}",
        defaults: new { Controller = "ClientPassthrough", Action = "Index" }
    );
});

The ClientPassthrough controller action is very basic:

public IActionResult Index()
{
    return new VirtualFileResult("~/index.html", "text/html");
}

Works fine in development, fails miserably in production. I've tried changing the base href to be ~/ which will point the subsequent urls to the proper application root instead of the server root... but it still can't seem to find those css files or scripts in the /wwwroot/ folder.

like image 371
Cowman Avatar asked Oct 18 '22 16:10

Cowman


1 Answers

If you are using .NET Core with Razor you can add the following code to set your base URL to the URL of the IIS app you are publishing to.

<base href="@(Url.Content("~"))" />

This code should go in the <head> just below the <title> element.

Then when you reference the root use

<link rel="stylesheet" href="lib/css/vendors.css" />

Without the slash in front of the path. This is what worked for me.

If you try to use <base href="/" /> or <base href="~/" />, IIS won't know what to do with it because the tilde has no meaning unless it gets parsed by .NET as opposed to served up as text in a page.

Hope that this helps someone.

like image 144
user7648679 Avatar answered Oct 21 '22 10:10

user7648679