ヘルスチェック

ヘルスチェック

ヘルスチェックは、プロダクション環境でアプリケーションが健全な状態で実行されていることを確認するために行われます。これには、サーバー上の利用可能なディスクスペース、アプリケーションが消費するメモリ、またはデータベース接続のテストなどが含まれる場合があります。

AdonisJSでは、いくつかの組み込みのヘルスチェックカスタムヘルスチェックの作成と登録の機能が提供されています。

ヘルスチェックの設定

次のコマンドを実行することで、アプリケーションでヘルスチェックを設定できます。このコマンドはstart/health.tsファイルを作成し、メモリ使用量使用済みディスクスペースのヘルスチェックを設定します。このファイルを自由に編集して、追加のヘルスチェックを削除または追加してください。

以下のコマンドを使用する前に、@adonisjs/core@6.12.1がインストールされていることを確認してください。

node ace configure health_checks
start/health.ts
import { HealthChecks, DiskSpaceCheck, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
])

エンドポイントの公開

ヘルスチェックを実行するための一般的な方法は、外部のモニタリングサービスがヘルスチェック結果を収集するためにpingできるHTTPエンドポイントを公開することです。

そこで、start/routes.tsファイル内にルートを定義し、HealthChecksControllerをバインドしましょう。health_checks_controller.tsファイルは初期セットアップ時に作成され、app/controllersディレクトリ内に存在します。

start/routes.ts
import router from '@adonisjs/core/services/router'
const HealthChecksController = () => import('#controllers/health_checks_controller')
router.get('/health', [HealthChecksController])

サンプルレポート

healthChecks.runメソッドは、すべてのチェックを実行し、詳細なJSONオブジェクトとしてのレポートを返します。レポートには以下のプロパティが含まれます。

{
"isHealthy": true,
"status": "warning",
"finishedAt": "2024-06-20T07:09:35.275Z",
"debugInfo": {
"pid": 16250,
"ppid": 16051,
"platform": "darwin",
"uptime": 16.271809083,
"version": "v21.7.3"
},
"checks": [
{
"name": "ディスクスペースチェック",
"isCached": false,
"message": "ディスク使用量は75%を超えており、しきい値を超えています",
"status": "warning",
"finishedAt": "2024-06-20T07:09:35.275Z",
"meta": {
"sizeInPercentage": {
"used": 76,
"failureThreshold": 80,
"warningThreshold": 75
}
}
},
{
"name": "メモリヒープチェック",
"isCached": false,
"message": "ヒープ使用量は定義されたしきい値を下回っています",
"status": "ok",
"finishedAt": "2024-06-20T07:09:35.265Z",
"meta": {
"memoryInBytes": {
"used": 41821592,
"failureThreshold": 314572800,
"warningThreshold": 262144000
}
}
}
]
}

isHealthy

すべてのチェックが成功したかどうかを示すブール値です。1つ以上のチェックが失敗した場合、値はfalseに設定されます。

status

すべてのチェックを実行した後のレポートのステータスです。次のいずれかになります。

  • ok:すべてのチェックが正常に完了しました。
  • warning:1つ以上のチェックが警告を報告しました。
  • error:1つ以上のチェックが失敗しました。

finishedAt

テストが完了した日時。

checks

実行されたすべてのチェックの詳細なレポートを含むオブジェクトの配列です。

debugInfo

デバッグ情報は、プロセスとその実行時間を識別するために使用できます。次のプロパティが含まれます。

  • pid:プロセスID。
  • ppid:AdonisJSアプリケーションプロセスを管理する親プロセスのプロセスID。
  • platform:アプリケーションが実行されているプラットフォーム。
  • uptime:アプリケーションの実行時間(秒単位)。
  • version:Node.jsのバージョン。

エンドポイントの保護

/healthエンドポイントを公開アクセスから保護するには、認証ミドルウェアを使用するか、リクエストヘッダー内の特定のAPIシークレットをチェックするカスタムミドルウェアを作成できます。

例:

import router from '@adonisjs/core/services/router'
const HealthChecksController = () => import('#controllers/health_checks_controller')
router
.get('/health', [HealthChecksController])
.use(({ request, response }, next) => {
if (request.header('x-monitoring-secret') === 'some_secret_value') {
return next()
}
response.unauthorized({ message: 'Unauthorized access' })
})

利用可能なヘルスチェック

start/health.tsファイル内で設定できる利用可能なヘルスチェックのリストは以下の通りです。

ディスクスペースチェック

DiskSpaceCheckは、サーバー上の使用済みディスクスペースを計算し、特定のしきい値を超えた場合に警告/エラーを報告します。

import { HealthChecks, DiskSpaceCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck()
])

デフォルトでは、警告のしきい値は75%に設定され、エラーのしきい値は80%に設定されています。ただし、カスタムのしきい値を定義することもできます。

export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck()
.warnWhenExceeds(80) // 80%を超えた場合に警告
.failWhenExceeds(90), // 90%を超えた場合にエラー
])

メモリヒープチェック

MemoryHeapCheckは、process.memoryUsage()メソッドによって報告されるヒープサイズを監視し、特定のしきい値を超えた場合に警告/エラーを報告します。

import { HealthChecks, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new MemoryHeapCheck()
])

デフォルトでは、警告のしきい値は250MBに設定され、エラーのしきい値は300MBに設定されています。ただし、カスタムのしきい値を定義することもできます。

export const healthChecks = new HealthChecks().register([
new MemoryHeapCheck()
.warnWhenExceeds('300 mb')
.failWhenExceeds('700 mb'),
])

メモリRSSチェック

MemoryRSSCheckは、process.memoryUsage()メソッドによって報告されるResident Set Sizeを監視し、特定のしきい値を超えた場合に警告/エラーを報告します。

import { HealthChecks, MemoryRSSCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new MemoryRSSCheck()
])

デフォルトでは、警告のしきい値は320MBに設定され、エラーのしきい値は350MBに設定されています。ただし、カスタムのしきい値を定義することもできます。

export const healthChecks = new HealthChecks().register([
new MemoryRSSCheck()
.warnWhenExceeds('600 mb')
.failWhenExceeds('800 mb'),
])

DbCheck

DbCheckは、SQLデータベースとの接続を監視するために@adonisjs/lucidパッケージによって提供されます。以下のようにインポートして使用できます。

import db from '@adonisjs/lucid/services/db'
import { DbCheck } from '@adonisjs/lucid/database'
import { HealthChecks, DiskSpaceCheck, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new DbCheck(db.connection()),
])

以下は、データベースヘルスチェックの例のレポートです。

サンプルレポート
{
"name": "データベースヘルスチェック (postgres)",
"isCached": false,
"message": "データベースサーバーへの接続に成功しました",
"status": "ok",
"finishedAt": "2024-06-20T07:18:23.830Z",
"meta": {
"connection": {
"name": "postgres",
"dialect": "postgres"
}
}
}

DbCheckクラスは、監視するためのデータベース接続を受け入れます。複数の接続を監視する場合は、各接続ごとにこのチェックを複数回登録してください。例:

複数の接続の監視
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new DbCheck(db.connection()),
new DbCheck(db.connection('mysql')),
new DbCheck(db.connection('pg')),
])

DbConnectionCountCheck

DbConnectionCountCheckは、データベースサーバー上のアクティブな接続を監視し、特定のしきい値を超えた場合に警告/エラーを報告します。このチェックはPostgreSQLMySQLデータベースのみサポートされています。

import db from '@adonisjs/lucid/services/db'
import { DbCheck, DbConnectionCountCheck } from '@adonisjs/lucid/database'
import { HealthChecks, DiskSpaceCheck, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new DbCheck(db.connection()),
new DbConnectionCountCheck(db.connection())
])

以下は、データベース接続数のヘルスチェックの例のレポートです。

サンプルレポート
{
"name": "接続数ヘルスチェック (postgres)",
"isCached": false,
"message": "アクティブな接続は6つあり、定義されたしきい値を下回っています",
"status": "ok",
"finishedAt": "2024-06-20T07:30:15.840Z",
"meta": {
"connection": {
"name": "postgres",
"dialect": "postgres"
},
"connectionsCount": {
"active": 6,
"warningThreshold": 10,
"failureThreshold": 15
}
}
}

デフォルトでは、警告のしきい値は10接続に設定され、エラーのしきい値は15接続に設定されています。ただし、カスタムのしきい値を定義することもできます。

new DbConnectionCountCheck(db.connection())
.warnWhenExceeds(4)
.failWhenExceeds(10)

RedisCheck

RedisCheckは、Redisデータベース(クラスターを含む)との接続を監視するために@adonisjs/redisパッケージによって提供されます。以下のようにインポートして使用できます。

import redis from '@adonisjs/redis/services/main'
import { RedisCheck } from '@adonisjs/redis'
import { HealthChecks, DiskSpaceCheck, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new RedisCheck(redis.connection()),
])

以下は、Redisデータベースのヘルスチェックの例のレポートです。

サンプルレポート
{
"name": "Redisヘルスチェック (main)",
"isCached": false,
"message": "Redisサーバーへの接続に成功しました",
"status": "ok",
"finishedAt": "2024-06-22T05:37:11.718Z",
"meta": {
"connection": {
"name": "main",
"status": "ready"
}
}
}

RedisCheckクラスは、モニタリングするためのredis接続を受け入れます。複数の接続を監視する場合は、各接続ごとにこのチェックを複数回登録してください。例:

複数の接続の監視
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new RedisCheck(redis.connection()),
new RedisCheck(redis.connection('cache')),
new RedisCheck(redis.connection('locks')),
])

RedisMemoryUsageCheck

RedisMemoryUsageCheckは、redisサーバーのメモリ消費量を監視し、特定のしきい値を超えた場合に警告/エラーを報告します。

import redis from '@adonisjs/redis/services/main'
import { RedisCheck, RedisMemoryUsageCheck } from '@adonisjs/redis'
import { HealthChecks, DiskSpaceCheck, MemoryHeapCheck } from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck(),
new MemoryHeapCheck(),
new RedisCheck(redis.connection()),
new RedisMemoryUsageCheck(redis.connection())
])

以下は、redisメモリ使用量のヘルスチェックの例のレポートです。

サンプルレポート
{
"name": "Redisメモリ消費量のヘルスチェック (main)",
"isCached": false,
"message": "Redisメモリ使用量は1.06MBで、定義されたしきい値を下回っています",
"status": "ok",
"finishedAt": "2024-06-22T05:36:32.524Z",
"meta": {
"connection": {
"name": "main",
"status": "ready"
},
"memoryInBytes": {
"used": 1109616,
"warningThreshold": 104857600,
"failureThreshold": 125829120
}
}
}

デフォルトでは、警告のしきい値は100MBに設定され、エラーのしきい値は120MBに設定されています。ただし、カスタムのしきい値を定義することもできます。

new RedisMemoryUsageCheck(db.connection())
.warnWhenExceeds('200MB')
.failWhenExceeds('240MB')

結果のキャッシュ

ヘルスチェックは、healthChecks.runメソッド(つまり/healthエンドポイントへのアクセス)を呼び出すたびに実行されます。/healthエンドポイントを頻繁にpingしたい場合でも、特定のチェックを毎回実行するのを避けることができます。

たとえば、ディスクスペースを1分ごとに監視することはあまり役に立ちませんが、メモリを1分ごとに追跡することは役に立ちます。

したがって、登録する個々のヘルスチェックの結果をキャッシュできます。

例:

import {
HealthChecks,
MemoryRSSCheck,
DiskSpaceCheck,
MemoryHeapCheck,
} from '@adonisjs/core/health'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck().cacheFor('1 hour'),
new MemoryHeapCheck(), // キャッシュしない
new MemoryRSSCheck(), // キャッシュしない
])

カスタムヘルスチェックの作成

HealthCheckContractインターフェイスに準拠するJavaScriptクラスとしてカスタムヘルスチェックを作成できます。プロジェクトまたはパッケージ内の任意の場所でヘルスチェックを定義し、start/health.tsファイル内でインポートして登録できます。

import { Result, BaseCheck } from '@adonisjs/core/health'
import type { HealthCheckResult } from '@adonisjs/core/types/health'
export class ExampleCheck extends BaseCheck {
async run(): Promise<HealthCheckResult> {
/**
* 以下のチェックは参考用です
*/
if (checkPassed) {
return Result.ok('表示する成功メッセージ')
}
if (checkFailed) {
return Result.failed('エラーメッセージ', errorIfAny)
}
if (hasWarning) {
return Result.warning('警告メッセージ')
}
}
}

上記の例のように、Resultクラスを使用してヘルスチェック結果を作成できます。オプションで、以下のように結果のメタデータをマージすることもできます。

Result.ok('データベース接続は正常です').mergeMetaData({
connection: {
dialect: 'pg',
activeCount: connections,
},
})

カスタムヘルスチェックの登録

start/health.tsファイル内でカスタムヘルスチェッククラスをインポートし、新しいクラスインスタンスを作成して登録できます。

import { ExampleCheck } from '../app/health_checks/example.js'
export const healthChecks = new HealthChecks().register([
new DiskSpaceCheck().cacheFor('1 hour'),
new MemoryHeapCheck(),
new MemoryRSSCheck(),
new ExampleCheck()
])