You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现Azure Web App实例优雅重启?解决.NET大字符串内存问题

实现Azure Web App实例的优雅重启(针对.NET应用)

Hey there! Let's tackle this graceful restart scenario for your Azure Web App running a .NET app—great question, since handling large strings and memory constraints makes this super important. Here's a step-by-step approach to get this working:

1. 先配置Azure层面的优雅关闭基础

Azure Web App has built-in graceful shutdown settings you should enable first:

  • Head to your Web App in the Azure Portal → Configuration → General Settings
  • Look for the "Graceful shutdown timeout" option, set a value that matches your longest typical request processing time (e.g., 300 seconds)
    This tells Azure to stop routing new requests to the instance when a restart is triggered, while giving existing requests time to finish before forcing a shutdown.

2. 在.NET应用中监听关闭信号并拒绝新请求

Azure's default settings help, but you'll need to add code to your ASP.NET Core app to explicitly block new requests during shutdown and wrap up ongoing work. Here's how:

示例:注册优雅关闭服务

Create a hosted service to track shutdown state and handle cleanup:

public class GracefulShutdownService : IHostedService
{
    private readonly ILogger<GracefulShutdownService> _logger;
    private readonly IHostApplicationLifetime _appLifetime;
    private bool _isShuttingDown = false;
    private int _activeRequests = 0;

    public GracefulShutdownService(ILogger<GracefulShutdownService> logger, 
                                  IHostApplicationLifetime appLifetime)
    {
        _logger = logger;
        _appLifetime = appLifetime;
    }

    public Task StartAsync(CancellationToken cancellationToken)
    {
        _appLifetime.ApplicationStopping.Register(InitiateShutdown);
        return Task.CompletedTask;
    }

    private void InitiateShutdown()
    {
        _isShuttingDown = true;
        _logger.LogInformation("Instance entering graceful shutdown mode—no new requests accepted.");

        // Wait for active requests to finish (adjust timeout as needed)
        var waitTime = TimeSpan.FromSeconds(45);
        var startTime = DateTime.UtcNow;
        while (_activeRequests > 0 && DateTime.UtcNow - startTime < waitTime)
        {
            Thread.Sleep(500);
        }
    }

    public void IncrementActiveRequests() => Interlocked.Increment(ref _activeRequests);
    public void DecrementActiveRequests() => Interlocked.Decrement(ref _activeRequests);
    public bool IsShuttingDown() => _isShuttingDown;

    public Task StopAsync(CancellationToken cancellationToken) => Task.CompletedTask;
    }

示例:添加中间件拦截新请求

Register the service and add a middleware to block new requests during shutdown:

var builder = WebApplication.CreateBuilder(args);

// Register required services
builder.Services.AddHostedService<GracefulShutdownService>();

var app = builder.Build();

// Middleware to reject new requests when shutting down
app.Use(async (context, next) =>
{
    var shutdownService = context.RequestServices.GetRequiredService<GracefulShutdownService>();
    
    if (shutdownService.IsShuttingDown())
    {
        context.Response.StatusCode = StatusCodes.Status503ServiceUnavailable;
        await context.Response.WriteAsync("Instance is restarting. Please try again shortly.");
        return;
    }

    // Track active requests
    shutdownService.IncrementActiveRequests();
    try
    {
        await next();
    }
    finally
    {
        shutdownService.DecrementActiveRequests();
    }
});

// Your existing middleware/routing setup here...

app.Run();

3. 触发优雅重启的正确方式

  • Manual restart via Portal: Go to your Web App → Instances, select the target instance, then click "Restart". Azure will trigger the graceful shutdown flow before restarting.
  • Automated restart via CLI: Use this command to restart a specific instance (follows graceful shutdown rules):
az webapp restart --name <your-webapp-name> --resource-group <your-resource-group> --instance <instance-id>

4. Bonus: Fix that large string memory issue

Since you mentioned oversized strings causing memory problems, here are quick fixes to reduce pressure:

  • Use Stream instead of strings for handling large content (avoids loading entire payloads into memory)
  • Enable server-side GC in your runtimeconfig.json:
{
  "runtimeOptions": {
    "configProperties": {
      "System.GC.Server": true
    }
  }
}
  • Offload large string processing to background tasks (like Azure Functions) to keep your Web App instances lean.

内容的提问来源于stack exchange,提问作者Minh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 06:40:51