【问题标题】:Disable IIS Idle Timeouts in Azure Web Role在 Azure Web 角色中禁用 IIS 空闲超时
【发布时间】:2013-08-06 20:07:30
【问题描述】:

为了防止 AppPool 每 20 分钟回收一次,我想在我的 Azure Web 角色启动时删除 IIS AppPool 空闲超时。我的网站是一个 Web 应用程序项目。

我该怎么做?

【问题讨论】:

    标签: c# azure web-deployment azure-web-roles


    【解决方案1】:

    创建启动任务禁用空闲超时:

    1. 在您的网络角色项目引用的网站项目中,将文件Startup.cmd添加到根文件夹。

    2. Startup.cmd 的属性中,将复制到输出目录设置为如果更新则复制

    3. 将此行添加到Startup.cmd:

      if exist %windir%\system32\inetsrv\appcmd.exe %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.processModel.idleTimeout:00:00:00
      

      if exist %windir%\system32\inetsrv\appcmd.exe 限定符是可选的。它允许您在 Azure Emulator Express 上使用相同的代码,因此您不需要安装 IIS 或需要以管理员身份运行 Visual Studio。

    4. 将文件另存为 UTF-8 不带签名。 (Visual Studio 中的文件 > 高级保存选项。)

    5. 在您的网络角色项目中,在ServiceDefinition.csdef 中,将其添加到WebRole

      <Startup>
        <Task commandLine="Startup.cmd" executionContext="elevated" />
      </Startup>
      

    【讨论】:

    • +1 非常有用的答案。但是您缺少第一个参数 -section:applicationPools
    • 因为角色没有在本地开始模拟,所以我必须找到原因。我找到这篇文章azure.microsoft.com/en-us/documentation/articles/… 并按照那里的提示进行操作。在命令的第二行添加EXIT /B 0 解决了这个问题。我怀疑,如果您运行未提升的 Visual Studio,该命令将失败,并阻止该角色启动。即使超时,我也更喜欢角色开始:-)。
    【解决方案2】:

    另一个选项是将 IIS 空闲超时操作配置为“暂停”。您可以将其作为 Web 角色启动脚本的一部分来执行。

    作为 IIS 设置的一部分,您需要的命令位于框中(请注意,这将适用于 Windows Server 2012 R2 及更高版本,您的代码针对 .NET 4.5.1 框架及更高版本)。

    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.processModel.idleTimeoutAction:Suspend
    

    您必须更新您的 Azure 云服务配置文件 (.cscfg) 才能使用 OS 系列 4,如 scottgu 在其blog post 中所述。

    由于启动操作是在配置您的实例时以及在将 Web 应用程序部署到 IIS 之前运行的,因此通过设置应用程序池默认值实际上会将您的应用程序应用程序池 idel 超时操作设置为暂停。

    【讨论】:

    • 请谨慎使用此解决方案,因为它会暂停整个过程(不像 Edward Brey 的解决方案?)。如果您有长时间运行的后台任务,它们将被暂停并在新的网络请求后首先执行。
    【解决方案3】:

    在您的 Web 应用程序项目的根目录中,使用以下代码创建一个名为 WebRole.cs 的文件:

    public class WebRole : RoleEntryPoint
    {
        public override void Run()
        {
            RemoveIISTimeouts();
            base.Run();
        }
    
        private void RemoveIISTimeouts()
        {
            Process.Start(
                String.Format(@"{0}\system32\inetsrv\appcmd", Environment.GetEnvironmentVariable("windir")),
                "set config -section:applicationPools -applicationPoolDefaults.processModel.idleTimeout:00:00:00");
        }
    }
    

    【讨论】:

    • 你也可以使用启动任务 .cmd 。
    • 通过将 config 命令放在 RoleEntryPoint.Run 覆盖中,这是否意味着您必须将 Web 角色标记为需要提升的权限?如果是这样,那将是使用启动任务的优势,正如@sharptooth 所建议的那样。
    • 我没有遇到这种方法的任何权限问题。无需修改权限。
    • @Albert:也许您的网络角色已经以提升的权限运行? Appcmd.exe 文档说“Appcmd.exe 位于 %windir%\system32\inetsrv 目录中,该目录仅供管理员帐户或计算机上属于管理员组成员的用户使用。”
    • 启动命令在提升的上下文中运行 - 而不是 Web 角色。 executionContext="elevated"
    【解决方案4】:

    不要打扰。无论如何,您确实应该为您的 Web 角色提供监控解决方案。现在它已内置到 Azure 仪表板中,开启监控比正确配置空闲超时更容易(尤其是如果您想保持最低权限)。

    【讨论】:

    • 我沿着端点监控路线走,但我发现当我有几个实例时问题仍然存在,所以我猜每个实例都没有被监控频繁地击中。有什么办法吗?
    • 很抱歉投了反对票,但该设置存在并且可以直接使用,因此我认为没有理由使用端点监控作为解决方法。正如 Ian 的评论中所展示的那样,解决方法并不总是理想的,并且可能存在其他不起作用的情况(例如,如果您没有使用循环负载平衡)。
    • @sham 请记住,这并不是一个通用的解决方案,只是在某些情况下可行的选择。由于基于设置的方法实施起来可能需要大量工作,因此监控甚至可能是“最佳”解决方案,如果这意味着无需增加工作量并且恰好可以完成这项工作。
    【解决方案5】:

    除了@Edward Brey 的回答,如果您想更改该启动脚本中的其他常用设置,请按照以下步骤操作

    rem Preload
    %windir%\system32\inetsrv\appcmd list app /xml | %windir%\system32\inetsrv\appcmd set site /in -applicationDefaults.preloadEnabled:True
    
    rem Disable idle
    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.processModel.idleTimeout:00:00:00
    
    rem Auto start
    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.autoStart:true
    
    rem Always running
    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.startMode:AlwaysRunning
    
    rem Disable recycling
    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -applicationPoolDefaults.recycling.periodicRestart.time:00:00:00
    

    要查看每个部分的可用选项列表,请执行

    %windir%\system32\inetsrv\appcmd set config -section:applicationPools -?
    

    【讨论】:

      【解决方案6】:

      这是我采取的方法:

      using (ServerManager iisManager = new ServerManager())
      {
          Application app = iisManager.Sites[RoleEnvironment.CurrentRoleInstance.Id + "_Web"].Applications[0];
      
          TimeSpan ts = new TimeSpan(0, 00, 00);
      
          iisManager.ApplicationPoolDefaults.ProcessModel.IdleTimeout = ts;
      
          iisManager.CommitChanges();
      }
      

      要求:

      using Microsoft.Web.Administration;
      using Microsoft.WindowsAzure.ServiceRuntime;
      

      【讨论】:

        猜你喜欢
        • 2017-08-27
        • 2013-07-06
        • 1970-01-01
        • 2013-11-27
        • 1970-01-01
        • 2013-06-09
        • 2016-06-07
        • 2014-09-29
        相关资源
        最近更新 更多