删除 Service Fabric 应用后,进程仍继续运行
Posted
技术标签:
【中文标题】删除 Service Fabric 应用后,进程仍继续运行【英文标题】:Processes still keep running after Service Fabric App is removed 【发布时间】:2017-09-07 04:30:39 【问题描述】:我在删除服务结构应用程序时看到了这一点。 应用程序内部服务的旧进程仍在运行。
应用中包含的服务类型
演员
无状态服务
ASP.NET 核心
我在重新部署应用程序时注意到了这个问题,并且 ASP.NET Core 服务为“EADDRINUSE 地址已在使用中”抛出错误
是否有适当的方法来彻底删除停止服务的所有内部进程的应用程序?
是否有任何可以在流程中捕获的取消事件?
我正在使用以下类将其注册为无状态服务。
/// <summary>
/// A specialized stateless service for hosting ASP.NET Core web apps.
/// </summary>
internal sealed class WebHostingService : StatelessService, ICommunicationListener
private readonly string _endpointName;
private IWebHost _webHost;
public WebHostingService(StatelessServiceContext serviceContext, string endpointName)
: base(serviceContext)
_endpointName = endpointName;
#region StatelessService
protected override IEnumerable<ServiceInstanceListener> CreateServiceInstanceListeners()
return new[] new ServiceInstanceListener(_ => this) ;
#endregion StatelessService
#region ICommunicationListener
void ICommunicationListener.Abort()
_webHost?.Dispose();
Task ICommunicationListener.CloseAsync(CancellationToken cancellationToken)
_webHost?.Dispose();
return Task.FromResult(true);
Task<string> ICommunicationListener.OpenAsync(CancellationToken cancellationToken)
var endpoint = FabricRuntime.GetActivationContext().GetEndpoint(_endpointName);
string serverUrl = $"endpoint.Protocol://FabricRuntime.GetNodeContext().IPAddressOrFQDN:endpoint.Port";
_webHost = new WebHostBuilder().UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.UseStartup<Startup>()
.UseUrls(serverUrl)
.Build();
_webHost.Start();
return Task.FromResult(serverUrl);
#endregion ICommunicationListener
并像这样注册它
ServiceRuntime.RegisterServiceAsync("WebApiType", context => new WebHostingService(context, "ServiceEndpoint")).GetAwaiter().GetResult();
Thread.Sleep(Timeout.Infinite);
【问题讨论】:
是的,它叫RunAsync。 你看到这篇关于托管 aspnet 核心的文章了吗? docs.microsoft.com/en-us/azure/service-fabric/… 如果您使用 'AspNetCoreCommunicationListener' 可能会有所帮助 @LoekD 确实查看了这篇文章。更新为使用 WebListenerCommunicationListener。但我仍然收到错误 “前缀 'http://+:8800/' 已注册。” 在升级或删除和安装时。 【参考方案1】:我从空 WebApi 开始,您可以从服务结构 .NET 核心 WebApi 模板中获得一个。 继续添加功能,直到我看到服务没有正常关闭。
我发现我们正在使用 Unity 注入控制器。
由于我们不应该注入控制器,我更新以删除它,并通过 Unity 更新了其他注入,以支持内置的 IServiceCollection 注入。
在进行这些更改后,我在升级时看不到端口已在使用中的错误。 我确实看到旧进程仍在运行,但没有使用任何 CPU 和内存(0.1M),然后在 10-15 分钟后消失。
【讨论】:
【参考方案2】:主机进程只有在其中仍有服务副本时才会挂起。如果所有服务副本都被删除,主机进程将退出。
如果您已删除整个应用程序并且主机进程仍在运行,这很可能意味着您的服务代码在被要求关闭时没有响应。您的 RunAsync 方法未侦听其取消令牌,或者您的 ICommunicationListener 在调用 CloseAsync 时未关闭(可能您有未完成的请求需要一段时间才能完成)。
【讨论】:
我没有覆盖 RunAsync,正如您在上面的问题中看到的那样。 现在我更新为使用 service-fabric-aspnetcore 包来初始化 IWebHost 并将它的管理留给包。查看 Git 存储库“AspNetCoreCommunicationListener.cs”,我也没有看到对 RunAsync 的任何处理,但我仍然看到相同的问题。现在作为一种解决方法,我使用随机端口并使用命名服务进行外部通信。 我与@viluMal 合作。我们在使用动态端口时遇到与端口冲突相关的差异升级错误。我们还通过任务管理器注意到 WebApi WebListener Stateless Service .exe 没有在合理的时间内关闭。我们正在使用您的示例和 AspNet Core VS2017 最新模板。关闭时似乎没有调用 RunAsync。除非集群与服务有某种开放式通信,否则这些服务没有未完成的请求。以上是关于删除 Service Fabric 应用后,进程仍继续运行的主要内容,如果未能解决你的问题,请参考以下文章
是否可以添加或删除 Service Fabric 有状态服务命名分区
Service Fabric 运行时未从 Actor 服务实例回收未使用的内存
Service Fabric 中的 actorevent 都有哪些限制?