簡體   English   中英

如何使用docker優雅地關閉dotnet?

[英]How to do gracefully shutdown on dotnet with docker?

有沒有辦法優雅地關閉在DOCKER中運行的DOTNET CORE應用程序? 如果是的話,我應該聽哪個活動?

我想要的只是取消請求我想將我的取消令牌傳遞給當前的方法並在他們工作時推遲關閉。

尋找與dotnet核心相關的示例代碼,參考鏈接等,而不是通用信息

更新 即使在.net核心控制台應用程序中使用Console.ReadLine(),這個問題也不會立即與docker容器出口重復,因為我沒有立即退出問題。 我需要利用類似Windows.SystemsEvents.SessionEnding的事件並依賴於Console.CancelKeyPress和/或實現WebHostBuilder()不符合要求。

在.NET Core 2.0中,您可以使用AppDomain.CurrentDomain.ProcessExit事件,該事件在Docker中的Linux上運行良好。 AssemblyLoadContext.Default.Unloading可能也適用,甚至在.NET Core 2.0之前。

System.Console有一個名為CancelKeyPress的事件。 我相信當sigint事件傳遞到dotnet時會被觸發。

System.Console.CancelKeyPress += (s,e) => { /* do something here */};

使用2.0.0-preview2-006497我做了一些測試,現在當Docker將SIGTERM / SIGINT發送到容器時會觸發AssemblyLoadContext.Default.Unloading

示例代碼如下所示:

System.Runtime.Loader.AssemblyLoadContext.Default.Unloading += ctx =>
{
    // code here...
};

有關詳細信息,請參閱此問題: https//github.com/aspnet/Hosting/issues/870

如果您的容器在Linux中運行,那么Loader.AssemblyLoadContext.Default.Unloading可以捕獲SIGTERM信號,但是Windows沒有相應的機制( dotnet問題 )。 以下是使用最初來自gist的 SetConsoleCtrlHandler處理Windows中的關閉通知的答案

namespace Routeguide
{
    using System;
    using System.Threading;
    ...

    class Program
    {
        [DllImport("Kernel32")]
        internal static extern bool SetConsoleCtrlHandler(HandlerRoutine handler, bool Add);

        internal delegate bool HandlerRoutine(CtrlTypes ctrlType);

        internal enum CtrlTypes
        {
            CTRL_C_EVENT = 0,
            CTRL_BREAK_EVENT,
            CTRL_CLOSE_EVENT,
            CTRL_LOGOFF_EVENT = 5,
            CTRL_SHUTDOWN_EVENT
        }

        static void Main(string[] args)
        {
            // do the server starting code
            Start();
            ....

            var shutdown = new ManualResetEvent(false);
            var complete = new ManualResetEventSlim();
            var hr = new HandlerRoutine(type =>
            {
                Log.Logger.Information($"ConsoleCtrlHandler got signal: {type}");

                shutdown.Set();
                complete.Wait();

                return false;
            });
            SetConsoleCtrlHandler(hr, true);

            Console.WriteLine("Waiting on handler to trigger...");

            shutdown.WaitOne();

            Console.WriteLine("Stopping server...");

            // do the server stopping code
            Stop();

            complete.Set();
            GC.KeepAlive(hr);
        }
    }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM