app_offline.htm выбрасывает ошибки HTTP 500 на рабочий ящик

Я создал файл app_offline.htm для приложения ASP.NET MVC2, работающего на 64-разрядной IIS7 / Win2008, и убедился, что его размер превышает 512 байт (сейчас это 2 КБ). На моем компьютере разработчика, работающем под управлением Visual Studio 2010, он работает как чудо, но когда я помещаю его в рабочий ящик, все, что я получаю, это общая ошибка HTTP 500, говорящая "Страница не может быть отображена, потому что произошла внутренняя ошибка сервера".

Что особенно странно, так это то, что я ничего не регистрирую в журнале событий приложений, и при этом ELMAH ничего не обнаруживает. Я отключил пользовательские ошибки, поместил исключения местоположения FormsAuthentication для файла, убедился, что я не ссылаюсь на другие файлы (изображения и т. Д.), Но ничто не исправляет это.

Я читал каждый пост на SO и Googled часами и не могу понять это. Есть идеи, что может быть не так? Я дергаю себя за волосы здесь...

2 ответа

ОБНОВИТЬ:
У вас есть это в вашем web.config?

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
    <system.web>
        <httpRuntime waitChangeNotification="300" maxWaitChangeNotification="300"/>
    </system.web>
    <system.webServer>
        <modules runAllManagedModulesForAllRequests="true" />
    </system.webServer>
</configuration>

Но есть еще один улов.

ASP.NET выгрузит приложение, как только изменится web.config, но на самом деле не перезагрузит его и не применит настройки "waitChange…", пока не будет сделан запрос. Таким образом, вы все равно можете оставить app_offline.htm и web.config, и если первое требование произойдет, когда dll будет скопирован только наполовину, возникнет исключение. Чтобы добавить оскорбление травмы, исключение будет сохраняться до тех пор, пока вы не замените временный файл web.config или пока не истечет общая продолжительность вашего времени "waitChange…"!

Чтобы обойти это последнее препятствие, вам необходимо сделать запрос к приложению после загрузки временного файла web.config, но до того, как вы начнете развертывать файлы приложения. Полный процесс выглядит следующим образом:

  1. Добавить app_offline.htm
  2. Замените web.config приложения временным web.config (как указано выше)
  3. Запросите любой ресурс ASP.NET на сайте, чтобы новое "waitChangeNotification" было "применено" *
  4. Внесите необходимые изменения в файловую систему (разверните bin-файлы, другие файлы сайта)
  5. Замените временный web.config исходным приложением web.config
  6. Удалить app_offline.htm

* Вы можете оспорить то, что происходит на шаге 2-3, так как ASP.NET закрывает приложение после шага 1. Действительно, из моего средства просмотра событий не видно, что изменение web.config зарегистрировано или "применено" в результате либо шаг 2 или 3, но, тем не менее, обновленные параметры waitChangeNotification применяются после шага 3.

Больше проблем app_offline.htm

App_offline.htm получил с ASP.NET MVC

Я придумал решение, которое работает на 100% для наших развертываний, поэтому я решил поделиться им.

Это решение добавляет раздел customErrors в web.config. Это поймает любые необработанные исключения. Он перенаправляет в App_Offline.htm, который обновляется до тех пор, пока приложение не вернется в оперативный режим. Таким образом, пользователь получает хороший загрузчик, который исчезает, когда приложение становится доступным.

Я надеюсь, что это полезно:)

Пакетный файл

copy "C:\www\_App_Offline.htm" "C:\www\App_Offline.htm"
copy /y "C:\www\App_Offline.config" "C:\www\Web.config"

Rem do deploy/publish actions

Rem Note: Our publish replaces/restores the Web.config. You should do that here.
del "C:\www\App_Offline.htm"

App_Offline.config

<?xml version="1.0"?>
<configuration>
  <system.web>
    <httpRuntime waitChangeNotification="100" maxWaitChangeNotification="100"/>
    <customErrors defaultRedirect="App_Offline.htm" mode="On">
    </customErrors>
  </system.web>
  <system.webServer>
    <modules runAllManagedModulesForAllRequests="true" />
  </system.webServer>
</configuration>

_App_Offline.htm

<!DOCTYPE html>
<html>
<head>
    <meta http-equiv="content-type" content="text/html; charset=UTF-8">
    <title>Application Offline</title>
    <meta charset="UTF-8">
    <style>
        .facebook_blockG { background-color: none; border: 3px solid #D6D6D6; float: left; height: 40px; margin-left: 7px; width: 24px; opacity: 0; -moz-animation-name: bounceG; -moz-animation-duration: 1.3s; -moz-animation-iteration-count: infinite; -moz-animation-direction: linear; -moz-transform: scale(0.7); -webkit-animation-name: bounceG; -webkit-animation-duration: 1.3s; -webkit-animation-iteration-count: infinite; -webkit-animation-direction: linear; -webkit-transform: scale(0.7); -ms-animation-name: bounceG; -ms-animation-duration: 1.3s; -ms-animation-iteration-count: infinite; -ms-animation-direction: linear; -ms-transform: scale(0.7); -o-animation-name: bounceG; -o-animation-duration: 1.3s; -o-animation-iteration-count: infinite; -o-animation-direction: linear; -o-transform: scale(0.7); animation-name: bounceG; animation-duration: 1.3s; animation-iteration-count: infinite; animation-direction: linear; transform: scale(0.7); }
        #blockG_1 { -moz-animation-delay: 0.39s; -webkit-animation-delay: 0.39s; -ms-animation-delay: 0.39s; -o-animation-delay: 0.39s; animation-delay: 0.39s; }
        #blockG_2 { -moz-animation-delay: 0.52s; -webkit-animation-delay: 0.52s; -ms-animation-delay: 0.52s; -o-animation-delay: 0.52s; animation-delay: 0.52s; }
        #blockG_3 { -moz-animation-delay: 0.65s; -webkit-animation-delay: 0.65s; -ms-animation-delay: 0.65s; -o-animation-delay: 0.65s; animation-delay: 0.65s; }

        @-moz-keyframes bounceG {
            0% { -moz-transform: scale(1.2); opacity: 0.6; }

            100% { -moz-transform: scale(0.7); opacity: 0; }
        }

        @-webkit-keyframes bounceG {
            0% { -webkit-transform: scale(1.2); opacity: 0.6; }

            100% { -webkit-transform: scale(0.7); opacity: 0; }
        }

        @-ms-keyframes bounceG {
            0% { -ms-transform: scale(1.2); opacity: 0.6; }

            100% { -ms-transform: scale(0.7); opacity: 0; }
        }

        @-o-keyframes bounceG {
            0% { -o-transform: scale(1.2); opacity: 0.6; }

            100% { -o-transform: scale(0.7); opacity: 0; }
        }

        @keyframes bounceG {
            0% { transform: scale(1.2); opacity: 0.6; }

            100% { transform: scale(0.7); opacity: 0; }
        }
    </style>
</head>
<body>

    <div id="overlay" class="trans">
        <div id="overlay-inner" class="trans login">
            <h1 style="line-height:1em; font-size:30pt">Application Offline</h1>
            <h2 style="line-height:1em; width:70%; margin:auto">application is offline for maintenance</h2>
            <div style="width: 128px; margin:40px auto">
                <div id="blockG_1" class="facebook_blockG">
                </div>
                <div id="blockG_2" class="facebook_blockG">
                </div>
                <div id="blockG_3" class="facebook_blockG">
                </div>
            </div>
        </div>
    </div>

    <script type="text/javascript">
        function getParameterByName(name) {
            name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]");
            var regex = new RegExp("[\\?&]" + name + "=([^&#]*)"),
                results = regex.exec(location.search);
            return results === null ? "" : decodeURIComponent(results[1].replace(/\+/g, " "));
        }
        setTimeout(function () {
            var loc = getParameterByName('aspxerrorpath');
            loc = (loc) ? window.location.protocol + '//' + window.location.host + loc : window.location.href;
            window.location.assign(loc);
        }, 1500);
    </script>
</body>
</html>
Другие вопросы по тегам