Skip to content

Commit fe7678b

Browse files
committed
[增加] 心跳检查接口
1 parent 1aacf37 commit fe7678b

File tree

2 files changed

+119
-22
lines changed

2 files changed

+119
-22
lines changed

GameFrameX.StartUp/AppStartUpByHTTPServer.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,9 @@ private async Task StartHttpServer(List<BaseHttpHandler> baseHandler, Func<strin
119119
}
120120
}
121121

122+
// 配置健康检查端点
123+
app.UseGameFrameXHealthChecks(Setting, ipList);
124+
122125
// 配置全局异常处理
123126
app.UseExceptionHandler(ExceptionHandler);
124127

GameFrameX.StartUp/Extensions/HealthChecksExtensions.cs

Lines changed: 116 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,13 @@
55
// 不得利用本项目从事危害国家安全、扰乱社会秩序、侵犯他人合法权益等法律法规禁止的活动!任何基于本项目二次开发而产生的一切法律纠纷和责任,我们不承担任何责任!
66

77
using GameFrameX.Utility.Setting;
8+
using Microsoft.AspNetCore.Builder;
9+
using Microsoft.AspNetCore.Diagnostics.HealthChecks;
10+
using Microsoft.AspNetCore.Http;
811
using Microsoft.Extensions.DependencyInjection;
912
using Microsoft.Extensions.Diagnostics.HealthChecks;
13+
using GameFrameX.Foundation.Json;
14+
using GameFrameX.Foundation.Logger;
1015

1116
namespace GameFrameX.StartUp.Extensions;
1217

@@ -15,6 +20,24 @@ namespace GameFrameX.StartUp.Extensions;
1520
/// </summary>
1621
public static class HealthChecksExtensions
1722
{
23+
private const string JsonContentType = "application/json; charset=utf-8";
24+
25+
/// <summary>
26+
/// 默认健康检查端点路径
27+
/// </summary>
28+
/// <value>返回默认的健康检查端点路径 "/health"</value>
29+
public const string DefaultHealthCheckPath = "/health";
30+
31+
/// <summary>
32+
/// 简单健康检查端点路径(兼容性端点)
33+
/// </summary>
34+
public const string SimpleHealthCheckPath = $"{DefaultHealthCheckPath}/simple";
35+
36+
/// <summary>
37+
/// OpenTelemetry 健康检查端点路径
38+
/// </summary>
39+
public const string OpenTelemetryHealthCheckPath = $"{DefaultHealthCheckPath}/opentelemetry";
40+
1841
/// <summary>
1942
/// 添加 GameFrameX 健康检查服务(包含多种检查项目)
2043
/// </summary>
@@ -23,44 +46,115 @@ public static class HealthChecksExtensions
2346
/// <returns>服务集合</returns>
2447
public static IServiceCollection AddGameFrameXHealthChecks(this IServiceCollection services, AppSetting setting)
2548
{
26-
var healthChecksBuilder = services.AddHealthChecks()
27-
// 基础应用程序健康检查
28-
.AddCheck("self", () => HealthCheckResult.Healthy("应用程序运行正常"));
49+
var healthChecksBuilder = services.AddHealthChecks();
50+
// 基础应用程序健康检查
51+
healthChecksBuilder.AddCheck(DefaultHealthCheckPath, () => HealthCheckResult.Healthy("应用程序运行正常"));
52+
healthChecksBuilder.AddCheck(SimpleHealthCheckPath, () => HealthCheckResult.Healthy("应用程序运行正常"));
2953

3054
// OpenTelemetry相关检查
3155
if (setting.IsOpenTelemetry)
3256
{
33-
healthChecksBuilder.AddCheck("opentelemetry", () => HealthCheckResult.Healthy("OpenTelemetry 配置正常"));
57+
healthChecksBuilder.AddCheck(OpenTelemetryHealthCheckPath, () => HealthCheckResult.Healthy("OpenTelemetry 配置正常"));
3458
}
3559

36-
// 配置检查
37-
healthChecksBuilder.AddCheck("configuration", () =>
38-
{
39-
var issues = new List<string>();
60+
return services;
61+
}
4062

41-
if (string.IsNullOrEmpty(setting.ServerName))
63+
/// <summary>
64+
/// 使用 GameFrameX 健康检查中间件
65+
/// </summary>
66+
/// <param name="app">应用程序构建器,用于配置HTTP请求管道</param>
67+
/// <param name="setting">应用设置对象,包含应用程序的配置信息</param>
68+
/// <param name="ipList"></param>
69+
/// <returns>返回配置了健康检查端点的应用程序构建器</returns>
70+
/// <remarks>
71+
/// 此方法会配置以下健康检查端点:
72+
/// <list type="bullet">
73+
/// <item><description><c>/health</c> - 详细的JSON格式健康检查报告</description></item>
74+
/// <item><description><c>/health/simple</c> - 简单的"OK"响应(兼容性端点)</description></item>
75+
/// </list>
76+
/// 健康检查响应包含状态、检查项详情、持续时间、服务器信息和时间戳。
77+
/// </remarks>
78+
/// <example>
79+
/// <code>
80+
/// // 使用默认路径
81+
/// app.UseGameFrameXHealthChecks(appSetting);
82+
///
83+
/// // 使用自定义路径
84+
/// app.UseGameFrameXHealthChecks(appSetting, "/api/health");
85+
/// </code>
86+
/// </example>
87+
/// <seealso cref="AddGameFrameXHealthChecks"/>
88+
/// <seealso cref="AppSetting"/>
89+
public static IApplicationBuilder UseGameFrameXHealthChecks(this IApplicationBuilder app, AppSetting setting, List<string> ipList)
90+
{
91+
var defaultHealthCheckOptions = new HealthCheckOptions
92+
{
93+
ResponseWriter = async (context, report) =>
4294
{
43-
issues.Add("ServerName未配置");
95+
context.Response.ContentType = JsonContentType;
96+
97+
var response = new
98+
{
99+
status = report.Status.ToString(),
100+
checks = report.Entries.Select(entry => new
101+
{
102+
name = entry.Key,
103+
status = entry.Value.Status.ToString(),
104+
description = entry.Value.Description,
105+
duration = entry.Value.Duration.TotalMilliseconds
106+
}),
107+
totalDuration = report.TotalDuration.TotalMilliseconds,
108+
serverName = setting.ServerName ?? "Unknown",
109+
tagName = setting.TagName ?? "Unknown",
110+
timestamp = DateTime.UtcNow
111+
};
112+
113+
await context.Response.WriteAsync(JsonHelper.Serialize(response));
44114
}
115+
};
116+
117+
// 配置详细的健康检查端点
118+
app.UseHealthChecks(DefaultHealthCheckPath, defaultHealthCheckOptions);
45119

46-
if (string.IsNullOrEmpty(setting.TagName))
120+
var simpleHealthCheckOptions = new HealthCheckOptions
121+
{
122+
Predicate = _ => false, // 不执行任何检查,直接返回成功
123+
ResponseWriter = async (context, _) =>
47124
{
48-
issues.Add("TagName未配置");
49-
}
125+
context.Response.ContentType = JsonContentType;
126+
await context.Response.WriteAsync("OK");
127+
},
128+
};
50129

51-
if (setting.SaveDataInterval <= 0)
130+
// 配置简单的健康检查端点(兼容性)
131+
app.UseHealthChecks(SimpleHealthCheckPath, simpleHealthCheckOptions);
132+
// OpenTelemetry相关检查
133+
if (setting.IsOpenTelemetry)
134+
{
135+
var openTelemetryHealthCheckOptions = new HealthCheckOptions
52136
{
53-
issues.Add("SaveDataInterval配置无效");
54-
}
137+
Predicate = _ => false, // 不执行任何检查,直接返回成功
138+
ResponseWriter = async (context, _) =>
139+
{
140+
context.Response.ContentType = JsonContentType;
141+
await context.Response.WriteAsync("OpenTelemetry 配置正常");
142+
},
143+
};
144+
app.UseHealthChecks(OpenTelemetryHealthCheckPath, openTelemetryHealthCheckOptions);
145+
}
55146

56-
if (issues.Any())
147+
LogHelper.InfoConsole("健康检查端点已启用:");
148+
foreach (var ip in ipList)
149+
{
150+
LogHelper.InfoConsole($"- 详细健康检查: http://{ip}:{setting.HttpPort}{DefaultHealthCheckPath}");
151+
LogHelper.InfoConsole($"- 简单健康检查: http://{ip}:{setting.HttpPort}{SimpleHealthCheckPath}");
152+
if (setting.IsOpenTelemetry)
57153
{
58-
return HealthCheckResult.Degraded($"配置问题: {string.Join(", ", issues)}");
154+
LogHelper.InfoConsole($"- OpenTelemetry 检查: http://{ip}:{setting.HttpPort}{OpenTelemetryHealthCheckPath}");
59155
}
156+
}
60157

61-
return HealthCheckResult.Healthy("配置检查通过");
62-
});
63-
64-
return services;
158+
return app;
65159
}
66160
}

0 commit comments

Comments
 (0)