aspnetcore: 404 when publicPath is set to "/"

The bug appears to be related to this this line:

https://github.com/aspnet/JavaScriptServices/blob/5f6f288056b3263a61a55631257db14314a02795/src/Microsoft.AspNetCore.SpaServices/Webpack/WebpackDevMiddleware.cs#L114

My webpack config has the following output:

        "output": {
            "filename": "js/[name].js",
            "path": OutputPath,
            "publicPath": "/"
        },

If I set the and the WebpackDevMiddleware like such:

                    .UseWebpackDevMiddleware(new WebpackDevMiddlewareOptions
                    {
                        HotModuleReplacement = true
                    });

Then the hmrEndpoint defaults to “/__webpack_hmr” and the SpaProxy url ends up as “//__webpack_url”. Every request to [xxx].hot-update.json (e.g.: http://localhost:5000/7d73bb05e2e2c47519ea.hot-update.json) fails with a 404.

However, if I set up my webpack config like this:

        "output": {
            "filename": "js/[name].js",
            "path": OutputPath,
            "publicPath": "/dist/"
        },

Then the SpaProxy url is set to “/dist//__webpack_url” and any request to find the hot-update config (e.g.: http://localhost:5000/dist/7d73bb05e2e2c47519ea.hot-update.json) works.

FWIW: overriding the HmrEndpoint to “__webpack_hmr” does not seem to get around the problem:

                    .UseWebpackDevMiddleware(new WebpackDevMiddlewareOptions
                    {
                        HotModuleReplacement = true,
                        HotModuleReplacementEndpoint = "__webpack_hmr"
                    });

Also, leaving the publicPath blank (“”) results in an error.

EDIT: if this is the expected behavior (that publicPath is required to be set to “/dist/”) then the documentation should reflect this. Otherwise, this is a bug likely due to oversimplification of the logic that builds the proxy server URLs.

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Comments: 17 (5 by maintainers)

Most upvoted comments

crhairr

I’m guessing that this has to do with how the SpaProxy intercepts GET requests at the primary url in order to redirect to the SPA fallback route. Since it’s a get request on “~/”, it just bombs. At least, that’s what seems to be going on.

that’s not the case. I placed sample *.hot-update.json file in the root ditectory and was able to retrieve the file with get http://localhost:5000/*.hot-update.json .

@SkeletonSkelettron Ah ok, well thats another problem I think. In my project setup, I actually have a windows service running as a console app which self-hosts a WebApi and my app (with webpack in dev mode) so i have to manually go to localhost:5000 (in my case) in a browser window anyway. I dont really mind this for the initial load as long as HMR picks up from there.

FWIW: the workaround is to set publicPath to “/dist/” (I presume any subdirectory of the output folder will work, but I haven’t verified that yet). This is annoying only because I don’t like unnecessary folders, and this is just a really silly gotcha to have to remember whenever using ASP.NET Core and Webpack.

Yes, like i already said:

I still get 404’s on the hot-module.js and json’s. Changing publicPath to something (in my case “/debug/”) fixes the issue.

This actually works for ANY value of the publicPath EXCEPT “/”. You can even put-non-existing (aka paths not on your drive) in there, it does not matter since the “path” is really just something that only exists in the webpack server’s memory.

However, i agree with @crhairr , I also do not like the fact this bug causes the website to be REQUIRED to be served from something else then “/”. In production, my SPA resides at “/” and I want as little difference between production and development modes as possible. This should be fixed.

You could retrieve that file thanks to the StaticFiles middleware, which I assume you have active if you used the template. The hot-update.json “files” do not actually go into the file system. They’re generated by the HMR service on-demand to describe updated resources. The SpaProxy has trouble mapping requests for the *hot-update.json files when they’re served from “/” instead of a different subfolder.

The bug appears to be that SpaProxy just doesn’t look for HMR requests of the form “*.hot-update.json”, but instead attempts to map any request to a resource under the Webpack publicPath, and thus can’t handle anything under “/” due to route conflicts.

From what I’ve seen in the code, it appears to do with the way the SpaProxy attempts to intercept requests, and how this relates to the URL used by the [xxx].hot-update.json requests. If publicPath is set to “/”, then the hot-update request is issued on the application base URL, e.g.: http://localhost:5000/7d73bb05e2e2c47519ea.hot-update.json. This always results in a 404.

But if publicPath is set to a subdirectory like “/dist/” then the hot-update request goes to a subdirectory of the primary app, e.g.: http://localhost:5000/dist/7d73bb05e2e2c47519ea.hot-update.json.

I’m guessing that this has to do with how the SpaProxy intercepts GET requests at the primary url in order to redirect to the SPA fallback route. Since it’s a get request on “~/”, it just bombs. At least, that’s what seems to be going on.

I think that the SpaProxy just needs a little tweaking so that it can interpret and intercept the hot-update.json requests when its URL is essentially “~/”.

It might be a few days before I get the time to create a repro project.