Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Peter S 169 posts 587 karma points
    Nov 14, 2014 @ 10:21
    Peter S
    0

    404 for files

    I've been looking for a full proof error handler but I can't seem to find a way that includes missing files. Adding node ID of 404 and 500 in the umbracoSettings.config works but not for files. By adding the code below that includes a dummy 404 page that THEN throws an Umbraco 404 can get it working but you then loose the support for 500 errors.

    <httpErrors errorMode="Custom" existingResponse="Replace">
      <remove statusCode="404" subStatusCode="-1" />
      <remove statusCode="500" subStatusCode="-1" />
      <error statusCode="404" path="/non-existing-page.aspx" responseMode="ExecuteURL" />
      <error statusCode="500" path="error.html" responseMode="File" />
    </httpErrors>

    Are there any other ways to go around this? The best way would be if Umbraco could handle missing files but I guess that's going to be hard. If not, where do I find the stock 404 page so that I can make it a bit less "sarcastic"...? :)

  • Dan Lister 416 posts 1974 karma points c-trib
    Nov 14, 2014 @ 13:14
    Dan Lister
    102

    Hi Peter,

    To handle all 404 and 500 errors, I use the following section like yourself.

    <system.webServer>
        <httpErrors errorMode="Custom" existingResponse="Replace">
        <remove statusCode="404" subStatusCode="-1" />
        <remove statusCode="500" subStatusCode="-1" />
        <error statusCode="404" path="404.html" responseMode="File" />
        <error statusCode="500" path="500.html" responseMode="File" />
    </httpErrors>
    

    To allow editors to edit the contents of error pages, I usually have an Error Page document type. On publish of an Error Page, a separate web request is made to the Umbraco error page (for example, http://domain/404/). The contents of the web request are saved to disk at http://domain/404.html. This allows IIS to handle all 404 and 500 exceptions. I've tested the above section with missing files and the correct path is displayed to the user. This method should allow you to create a content manageable, static error page.

    Hope that helps.

    Thanks, Dan.

  • Peter S 169 posts 587 karma points
    Nov 17, 2014 @ 11:28
    Peter S
    0

    Ahaa, interesting. Thanks for the tip! I'll try that out!

  • Dan Lister 416 posts 1974 karma points c-trib
    Nov 17, 2014 @ 11:30
    Dan Lister
    0

    I can post a sample event if you require more information?

    Thanks. Dan.

  • Graham Carr 277 posts 389 karma points
    Aug 24, 2015 @ 10:13
    Graham Carr
    0

    Hi Dan,

    Old post I know, but would you be able to post a sample event showing how you got this to work for non-existent files?

    Thanks. Graham

  • Dan Lister 416 posts 1974 karma points c-trib
    Aug 24, 2015 @ 10:33
    Dan Lister
    0

    Hey Graham,

    Something like the following should do the trick:

    using System;
    using System.IO;
    using System.Net;
    using System.Text;
    using System.Threading;
    using System.Web;
    using System.Linq;
    using System.Net.Security;
    using Umbraco.Core;
    using Umbraco.Core.Events;
    using Umbraco.Core.Models;
    using Umbraco.Core.Publishing;
    using Umbraco.Core.Services;
    using Umbraco.Web;
    
    namespace MyApplication.Events
    {
        public class SaveErrorPageToFile : IApplicationEventHandler
        {
            private static readonly object s_LockObj = new object();
            private static bool s_Ran; 
    
            public void OnApplicationStarted(UmbracoApplicationBase umbracoApplication, ApplicationContext applicationContext)
            {
                if (s_Ran) 
                    return;
    
                lock (s_LockObj)
                {
                    if (s_Ran) 
                        return;
    
                    ContentService.Published += ContentServiceOnPublished;
    
                    s_Ran = true;
                }
            }
    
            private static void ContentServiceOnPublished(IPublishingStrategy sender, PublishEventArgs<IContent> e)
            {
                var umbracoHelper = new UmbracoHelper(UmbracoContext.Current);
    
                foreach (var content in e.PublishedEntities.Where(c => c.ContentType.Alias.Equals(“ErrorPage”)))
                {
                    var url = umbracoHelper.NiceUrlWithDomain(content.Id);
                    var name = content.Name;
    
                    var file = HttpContext.Current.Server.MapPath(string.Concat("/", name, ".html"));
    
                    var thread = new Thread(() => SaveErrorPageToDisk(url, file));
                    thread.Start();
                }
            }
    
            private static void SaveErrorPageToDisk(string url, string file)
            {
                // Gives the page time to publish
                Thread.Sleep(15000);
    
                try
                {
                    using (var client = new WebClient())
                    {
                        var html = client.DownloadString(url);
    
                        using (var stream = new StreamWriter(file, false, Encoding.UTF8))
                        {
                            stream.Write(html);
                            stream.Close();
                        }
                    }
                }
                catch (Exception ex)
                {
                }
            }
    
            public void OnApplicationInitialized(UmbracoApplicationBase umbracoApplication, ApplicationContext applicationContext)
            {
            }
    
            public void OnApplicationStarting(UmbracoApplicationBase umbracoApplication, ApplicationContext applicationContext)
            {
            }
        }
    }
    

    I hope that helps.

    Thanks, Dan.

Please Sign in or register to post replies

Write your reply to:

Draft