feat: 인프라 개선 — 헬스체크, 로깅, 보안, CI 검증
- /health + /ready 엔드포인트 추가 (DB/Redis 상태 확인) - RequestID 미들웨어 + 구조화 JSON 로깅 - 체인 트랜잭션 per-user rate limit (20 req/min) - DB 커넥션 풀 설정 (MaxOpen 25, MaxIdle 10, MaxLifetime 5m) - Graceful Shutdown 시 Redis/MySQL 연결 정리 - Dockerfile HEALTHCHECK 추가 - CI에 go vet + 빌드 검증 단계 추가 (deploy 전 실행) - 보스 레이드 클라이언트 입장 API (JWT 인증) - Player 프로필 모듈 추가 Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -6,6 +6,7 @@ import (
|
||||
"a301_server/internal/bossraid"
|
||||
"a301_server/internal/chain"
|
||||
"a301_server/internal/download"
|
||||
"a301_server/internal/player"
|
||||
"a301_server/pkg/middleware"
|
||||
"github.com/gofiber/fiber/v2"
|
||||
)
|
||||
@@ -17,9 +18,17 @@ func Register(
|
||||
dlH *download.Handler,
|
||||
chainH *chain.Handler,
|
||||
brH *bossraid.Handler,
|
||||
playerH *player.Handler,
|
||||
authLimiter fiber.Handler,
|
||||
apiLimiter fiber.Handler,
|
||||
healthCheck fiber.Handler,
|
||||
readyCheck fiber.Handler,
|
||||
chainUserLimiter fiber.Handler,
|
||||
) {
|
||||
// Health / Ready (rate limiter 밖)
|
||||
app.Get("/health", healthCheck)
|
||||
app.Get("/ready", readyCheck)
|
||||
|
||||
api := app.Group("/api", apiLimiter)
|
||||
|
||||
// Auth
|
||||
@@ -63,14 +72,14 @@ func Register(
|
||||
ch.Get("/market", chainH.GetMarketListings)
|
||||
ch.Get("/market/:id", chainH.GetMarketListing)
|
||||
|
||||
// Chain - User Transactions (authenticated, idempotency-protected)
|
||||
ch.Post("/transfer", middleware.Idempotency, chainH.Transfer)
|
||||
ch.Post("/asset/transfer", middleware.Idempotency, chainH.TransferAsset)
|
||||
ch.Post("/market/list", middleware.Idempotency, chainH.ListOnMarket)
|
||||
ch.Post("/market/buy", middleware.Idempotency, chainH.BuyFromMarket)
|
||||
ch.Post("/market/cancel", middleware.Idempotency, chainH.CancelListing)
|
||||
ch.Post("/inventory/equip", middleware.Idempotency, chainH.EquipItem)
|
||||
ch.Post("/inventory/unequip", middleware.Idempotency, chainH.UnequipItem)
|
||||
// Chain - User Transactions (authenticated, per-user rate limited, idempotency-protected)
|
||||
ch.Post("/transfer", chainUserLimiter, middleware.Idempotency, chainH.Transfer)
|
||||
ch.Post("/asset/transfer", chainUserLimiter, middleware.Idempotency, chainH.TransferAsset)
|
||||
ch.Post("/market/list", chainUserLimiter, middleware.Idempotency, chainH.ListOnMarket)
|
||||
ch.Post("/market/buy", chainUserLimiter, middleware.Idempotency, chainH.BuyFromMarket)
|
||||
ch.Post("/market/cancel", chainUserLimiter, middleware.Idempotency, chainH.CancelListing)
|
||||
ch.Post("/inventory/equip", chainUserLimiter, middleware.Idempotency, chainH.EquipItem)
|
||||
ch.Post("/inventory/unequip", chainUserLimiter, middleware.Idempotency, chainH.UnequipItem)
|
||||
|
||||
// Chain - Admin Transactions (admin only, idempotency-protected)
|
||||
chainAdmin := api.Group("/chain/admin", middleware.Auth, middleware.AdminOnly)
|
||||
@@ -78,6 +87,11 @@ func Register(
|
||||
chainAdmin.Post("/reward", middleware.Idempotency, chainH.GrantReward)
|
||||
chainAdmin.Post("/template", middleware.Idempotency, chainH.RegisterTemplate)
|
||||
|
||||
// Boss Raid - Client entry (JWT authenticated)
|
||||
bossRaid := api.Group("/bossraid", middleware.Auth)
|
||||
bossRaid.Post("/entry", brH.RequestEntryAuth)
|
||||
bossRaid.Get("/my-entry-token", brH.GetMyEntryToken)
|
||||
|
||||
// Internal - Boss Raid (API key auth)
|
||||
br := api.Group("/internal/bossraid", middleware.ServerAuth)
|
||||
br.Post("/entry", brH.RequestEntry)
|
||||
@@ -85,6 +99,17 @@ func Register(
|
||||
br.Post("/complete", middleware.Idempotency, brH.CompleteRaid)
|
||||
br.Post("/fail", brH.FailRaid)
|
||||
br.Get("/room", brH.GetRoom)
|
||||
br.Post("/validate-entry", brH.ValidateEntryToken)
|
||||
|
||||
// Player Profile (authenticated)
|
||||
p := api.Group("/player", middleware.Auth)
|
||||
p.Get("/profile", playerH.GetProfile)
|
||||
p.Put("/profile", playerH.UpdateProfile)
|
||||
|
||||
// Internal - Player (API key auth)
|
||||
internalPlayer := api.Group("/internal/player", middleware.ServerAuth)
|
||||
internalPlayer.Get("/profile", playerH.InternalGetProfile)
|
||||
internalPlayer.Post("/save", playerH.InternalSaveGameData)
|
||||
|
||||
// Internal - Game server endpoints (API key auth, username-based, idempotency-protected)
|
||||
internal := api.Group("/internal/chain", middleware.ServerAuth)
|
||||
|
||||
Reference in New Issue
Block a user