private void ReportMessage(HealthState healthState, string description) { HealthInformation healthInformation = new HealthInformation(this.entityIdentifier, "Connectivity", healthState); healthInformation.Description = description; DeployedServicePackageHealthReport healthReport = new DeployedServicePackageHealthReport( this.applicatioName, this.serviceManifestName, this.nodeName, healthInformation); try { this.fabricClient.HealthManager.ReportHealth(healthReport); } catch (FabricException e) { // A stale report exception indicates a newer report was submitted for the same entity. // Because we are reporting health for deployed service package, this can happen if multiple instances or replicas // of the same service are deployed on the same cluster node. We could report on service instances/replicas instead, // and that would make health reports unique, but would also significantly complicate EventFlow setup, // so we just suppress the error instead. if (e.ErrorCode != FabricErrorCode.FabricHealthStaleReport) { throw; } } }
protected override async Task RunAsync(CancellationToken cancellationToken) { int failedCount = 0; while (!cancellationToken.IsCancellationRequested) { using (WebClient client = new WebClient()) { try { string payload = client.DownloadString(new Uri("http://localhost:8080/")); if (!string.IsNullOrEmpty(payload)) { if (payload == "something wrong") { failedCount++; ServiceEventSource.Current.Write("Watchdog had detected " + failedCount + " failures."); if (failedCount >= 5) { var deployedServicePackageHealthReport = new DeployedServicePackageHealthReport( applicationName, serviceManifestName, nodeName, new HealthInformation("CustomWatchDog", "MyServiceHealth", HealthState.Warning)); Client.HealthManager.ReportHealth(deployedServicePackageHealthReport); ServiceEventSource.Current.Write("Watchdog is sad."); } } else { failedCount = 0; var deployedServicePackageHealthReport = new DeployedServicePackageHealthReport( applicationName, serviceManifestName, nodeName, new HealthInformation("CustomWatchDog", "MyServiceHealth", HealthState.Ok)); Client.HealthManager.ReportHealth(deployedServicePackageHealthReport); ServiceEventSource.Current.Write("Watchdog is happy"); } } } catch (WebException) { failedCount++; ServiceEventSource.Current.Write("Watchdog had detected " + failedCount + " failures."); if (failedCount >= 5) { var deployedServicePackageHealthReport = new DeployedServicePackageHealthReport( applicationName, serviceManifestName, nodeName, new HealthInformation("CustomWatchDog", "MyServiceHealth", HealthState.Warning)); Client.HealthManager.ReportHealth(deployedServicePackageHealthReport); ServiceEventSource.Current.Write("Watchdog is sad."); } } } await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken); } }
/// <summary> /// Returns a health report /// </summary> /// <param name="context">The service fabric context that the health report is for</param> /// <param name="reportSourceId">The unique reporting source id</param> /// <param name="propertyName">The name of the health property being reported on</param> /// <param name="state">The current state of the health property</param> /// <param name="timeToLive">The time to live of the health report</param> /// <param name="reportType">The entity type the report is for</param> /// <returns>A health report for the appropriate reporting entity</returns> public static HealthReport GetHealthReport(ServiceContext context, string reportSourceId, string propertyName, HealthState state, ReportTypes reportType, TimeSpan timeToLive) { HealthReport report; var information = new HealthInformation(reportSourceId, propertyName, state); information.Description = $"{ propertyName } health state { Enum.GetName(typeof(HealthState), state) }"; information.RemoveWhenExpired = true; information.TimeToLive = timeToLive; information.SequenceNumber = HealthInformation.AutoSequenceNumber; switch (reportType) { case ReportTypes.Cluster: report = new ClusterHealthReport(information); break; case ReportTypes.Application: report = new ApplicationHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), information); break; case ReportTypes.DeployedApplication: report = new DeployedApplicationHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), context.NodeContext.NodeName, information); break; case ReportTypes.Service: report = new ServiceHealthReport(context.ServiceName, information); break; case ReportTypes.DeployedService: report = new DeployedServicePackageHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), context.CodePackageActivationContext.GetServiceManifestName(), context.NodeContext.NodeName, information); break; case ReportTypes.Node: report = new NodeHealthReport(context.NodeContext.NodeName, information); break; case ReportTypes.Instance: if (context is StatelessServiceContext) { report = new StatelessServiceInstanceHealthReport(context.PartitionId, context.ReplicaOrInstanceId, information); } else { report = new StatefulServiceReplicaHealthReport(context.PartitionId, context.ReplicaOrInstanceId, information); } break; default: throw new ArgumentException("Unknown health type", nameof(reportType)); } return(report); }
private void ReportHealth(HealthState healthState, string problemDescription) { HealthInformation healthInformation = new HealthInformation(this.entityIdentifier, "Connectivity", healthState); healthInformation.Description = problemDescription; DeployedServicePackageHealthReport healthReport = new DeployedServicePackageHealthReport( this.applicatioName, this.serviceManifestName, this.nodeName, healthInformation); this.fabricClient.HealthManager.ReportHealth(healthReport); }
//works only as admin public static void SendReport(bool good, string component) { // Test whether the resource can be accessed from the node HealthState healthState = good ? HealthState.Ok : HealthState.Warning; // Send report on deployed service package, as the connectivity is needed by the specific service manifest // and can be different on different nodes var deployedServicePackageHealthReport = new DeployedServicePackageHealthReport( ApplicationName, ServiceManifestName, NodeName, new HealthInformation("SFPubSubAdmin", component, healthState)); // TODO: handle exception. Code omitted for snippet brevity. // Possible exceptions: FabricException with error codes // FabricHealthStaleReport (non-retryable, the report is already queued on the health client), // FabricHealthMaxReportsReached (retryable; user should retry with exponential delay until the report is accepted). Client.HealthManager.ReportHealth(deployedServicePackageHealthReport); }
/// <summary> /// Returns a health report /// </summary> /// <param name="context">The service fabric context that the health report is for</param> /// <param name="reportSourceId">The unique reporting source id</param> /// <param name="propertyName">The name of the health property being reported on</param> /// <param name="state">The current state of the health property</param> /// <param name="timeToLive">The time to live of the health report</param> /// <param name="reportType">The entity type the report is for</param> /// <returns>A health report for the appropriate reporting entity</returns> public static HealthReport GetHealthReport(ServiceContext context, string reportSourceId, string propertyName, HealthState state, ReportTypes reportType, TimeSpan timeToLive) { HealthReport report; var information = new HealthInformation(reportSourceId, propertyName, state); information.Description = $"{ propertyName } health state { Enum.GetName(typeof(HealthState), state) }"; information.RemoveWhenExpired = true; information.TimeToLive = timeToLive; information.SequenceNumber = HealthInformation.AutoSequenceNumber; switch (reportType) { case ReportTypes.Cluster: report = new ClusterHealthReport(information); break; case ReportTypes.Application: report = new ApplicationHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), information); break; case ReportTypes.DeployedApplication: report = new DeployedApplicationHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), context.NodeContext.NodeName, information); break; case ReportTypes.Service: report = new ServiceHealthReport(context.ServiceName, information); break; case ReportTypes.DeployedService: report = new DeployedServicePackageHealthReport(new Uri(context.CodePackageActivationContext.ApplicationName), context.CodePackageActivationContext.GetServiceManifestName(), context.NodeContext.NodeName, information); break; case ReportTypes.Node: report = new NodeHealthReport(context.NodeContext.NodeName, information); break; case ReportTypes.Instance: if (context is StatelessServiceContext) { report = new StatelessServiceInstanceHealthReport(context.PartitionId, context.ReplicaOrInstanceId, information); } else { report = new StatefulServiceReplicaHealthReport(context.PartitionId, context.ReplicaOrInstanceId, information); } break; default: throw new ArgumentException("Unknown health type", nameof(reportType)); } return report; }