Andrew
Andrew

Reputation: 339

Need to preserve HTTP status code when using httpErrors custom 404 error using responseMode executeURL on Azure App Service IIS

I want to have all missing content/"bad" URLs redirect to our custom 404.html error page. This is important for accurately recording 404 errors in Google Analytics.

The issue is that when the responseMode=ExecuteURL flag is set, then the custom error does not preserve the 404 status code, but always shows a 200 code. I can change this to responseMode=Redirect, but this then shows a 302 status code, before redirecting to the custom 404.html page.

All of this DOES work with a "File" flag set on the httpError… just not with the "ExecuteURL" flag which is required for our server-side Perl includes used to present Header/Footer page elements.

Ideally, we should be able to use the Azure App Service IIS web.config to set a custom error to:

The below code works to preserve the requested URL in address bar, correctly shows the custom 404.html page with server-side header/footer content, BUT loses the 404 status code in dev tools (and Google Analytics)...

<httpErrors>
      <remove statusCode="404" subStatusCode="-1" />
      <error statusCode="404" 
          responseMode="ExecuteURL" 
          path="/404.html" />
</httpErrors>

Changing to responseMode="Redirect" only changes the status code to 302 before redirecting to custom 404.html...

If I change to use responseMode="File" this all works fine, but I then lose the custom server-side header and footers which are handled with Perl server-side includes...

EDIT: To be clear, the custom 404 page is all HTML and Javascript, but also leverages some very old Perl server-side includes to add custom header and footer elements to the page. We are not using any .NET framework or .NET core pages...

This arrangement should be possible, but perhaps only with a different web server, not IIS? nginx, perhaps?

FINAL UPDATE: Not a full answer, but our near-term resolution was to use nginx proxy configuration (which was already present and could be altered in nginx.conf) to preserve 404 error codes and present the proper custom 404.html static file.

I was also able to do this with Docker and nginx, so I know it is possible for a web server to deal with this situation...

I've determined that AFAICT there is no way for IIS web.config to handle this without using server-side code as Jason Pan suggested. So while he may be correct, that answer was not helpful for our needs.

Upvotes: 4

Views: 1853

Answers (2)

Fabri Nu&#241;ez
Fabri Nu&#241;ez

Reputation: 11

Hi i found this workaround(ASP NET WebForms)

Web Config

<httpErrors errorMode="Custom" existingResponse="Replace">
      <remove statusCode="404" subStatusCode="-1" />
      <error statusCode="404" path="/ErrorDefault.aspx?httpcode=404" responseMode="ExecuteURL" />
      <remove statusCode="500" subStatusCode="-1" />
      <error statusCode="500" path="/ErrorDefault.aspx?httpcode=500" responseMode="ExecuteURL" />
</httpErrors>

ErrorDefault.cs > Page Load

var httpCode = Request.QueryString["httpcode"];

Upvotes: 1

Jason Pan
Jason Pan

Reputation: 22049

UPDATE

When you use httpErrors in web.config, it must have code in your project to handle 400 and 500 in server side.

Due to your project just static web app, and no sever side code. So I suggest you can use hard code in httpErrors.

Like,

<error statusCode="404" responseMode="ExecuteURL" path="/404.html?httpcode=404" />.

The tag of httpErrors is used in servers such as iis. The 404 and 500 errors you want can’t be displayed directly in the browser. Because the httpErrors tag is used, the server will process everything and return it to the browser, so the HttpStaus you get is always 200.

PRIVIOUS

I probably know your question. Your program is .net framework or .net core, it is not clear for the time being. But I see the configuration tags in the web.config file.

In principle, the wrong request arrives at IIS and other servers, and the code level has processed 404 and other errors, so the returned HttpStatus value must be 200. There is no way to change it, but when a 404 or 500 error occurs, we can Processing and recording in Application_Error can also achieve the purpose you want to analyze.

So I tested it and based on the .net framework, you can download my sample code on github and give the following suggestions.

1. Add the Application_Error method to the Global.asax.cs file.

enter image description here

2. According to the Application_Error method, add an Error Controller.

enter image description here

3. Perform the test and the result is shown in the screenshot.

enter image description here

After decode the message. The content is

The controller for path '/a/b' was not found or does not implement IController..

We can custom error msg in Application_Error function. We can append HttpCode and other info.

Upvotes: 1

Related Questions