diff --git a/internal/client/telegram.go b/internal/client/telegram.go index d381fee..eb50f2f 100644 --- a/internal/client/telegram.go +++ b/internal/client/telegram.go @@ -84,3 +84,11 @@ func (t *Telegram) SendVerification(data *models.Verification, url string, isUpd return nil } + +func (t *Telegram) Ping() error { + _, err := t.bot.GetMe() + if err != nil { + return fmt.Errorf("error pinging tg bot: %w", err) + } + return nil +} diff --git a/internal/controllers/admin/health_check/health_check.go b/internal/controllers/admin/health_check/health_check.go index 9ac31a4..7af4c0d 100644 --- a/internal/controllers/admin/health_check/health_check.go +++ b/internal/controllers/admin/health_check/health_check.go @@ -1,13 +1,34 @@ package health_check -import "github.com/gofiber/fiber/v2" +import ( + "context" + "fmt" + "gitea.pena/PenaSide/verification/internal/client" + "gitea.pena/PenaSide/verification/internal/repository" + "github.com/gofiber/fiber/v2" + "github.com/minio/minio-go/v7" + "go.mongodb.org/mongo-driver/mongo" + "time" +) -type Deps struct{} +type Deps struct { + TgClient *client.Telegram + MongoDB *mongo.Client + S3Client *minio.Client +} -type HealthCheck struct{} +type HealthCheck struct { + tgClient *client.Telegram + mongoDB *mongo.Client + s3Client *minio.Client +} func NewHealthCheck(deps Deps) *HealthCheck { - return &HealthCheck{} + return &HealthCheck{ + tgClient: deps.TgClient, + mongoDB: deps.MongoDB, + s3Client: deps.S3Client, + } } func (receiver *HealthCheck) Liveness(ctx *fiber.Ctx) error { @@ -15,6 +36,45 @@ func (receiver *HealthCheck) Liveness(ctx *fiber.Ctx) error { } func (receiver *HealthCheck) Readiness(ctx *fiber.Ctx) error { - // todo + if err := receiver.checkMongoDB(); err != nil { + return ctx.Status(fiber.StatusServiceUnavailable).SendString("mongoDB is unavailable: " + err.Error()) + } + + if err := receiver.tgClient.Ping(); err != nil { + return ctx.Status(fiber.StatusServiceUnavailable).SendString("could not connect to Telegram: " + err.Error()) + } + + if err := receiver.checkS3(); err != nil { + return ctx.Status(fiber.StatusServiceUnavailable).SendString("could not connect to S3: " + err.Error()) + } + return ctx.SendStatus(fiber.StatusOK) } + +func (receiver *HealthCheck) checkMongoDB() error { + ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) + defer cancel() + + if err := receiver.mongoDB.Ping(ctx, nil); err != nil { + return fmt.Errorf("failed to ping MongoDB: %v", err) + } + return nil +} + +func (receiver *HealthCheck) checkS3() error { + ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) + defer cancel() + + buckets, err := receiver.s3Client.ListBuckets(ctx) + if err != nil { + return fmt.Errorf("failed to list buckets: %v", err) + } + + for _, b := range buckets { + if b.Name == repository.VerificationBucket { + return nil + } + } + + return fmt.Errorf("failed to find verification bucket") +}