feat(ops): add usage_logs partition status to ops dashboard
Add partition management integration to the smart ops system: - Backend: Add GetUsageLogsPartitionStatus endpoint in OpsHandler - Backend: Add partition query methods in OpsRepository - Backend: Add UsageLogsPartitionStatus type in OpsService - Frontend: Add OpsPartitionStatusCard component - Frontend: Add partition status display in OpsDashboard - i18n: Add Chinese and English translations The partition status card shows: - Whether usage_logs is partitioned - Current row count vs threshold (100K) - Partition count (if partitioned) - Warning message when partitioning is recommended This allows administrators to monitor partition status directly from the ops dashboard without checking server logs.
This commit is contained in:
@@ -63,6 +63,11 @@ type OpsRepository interface {
|
||||
UpsertDailyMetrics(ctx context.Context, startTime, endTime time.Time) error
|
||||
GetLatestHourlyBucketStart(ctx context.Context) (time.Time, bool, error)
|
||||
GetLatestDailyBucketDate(ctx context.Context) (time.Time, bool, error)
|
||||
|
||||
// Usage logs partition management
|
||||
IsUsageLogsPartitioned(ctx context.Context) (bool, error)
|
||||
GetUsageLogsRowCount(ctx context.Context) (int64, error)
|
||||
GetUsageLogsPartitionCount(ctx context.Context) (int, error)
|
||||
}
|
||||
|
||||
type OpsInsertErrorLogInput struct {
|
||||
|
||||
@@ -724,3 +724,72 @@ func sanitizeErrorBodyForStorage(raw string, maxBytes int) (sanitized string, tr
|
||||
}
|
||||
return raw, false
|
||||
}
|
||||
|
||||
// ==================== Usage Logs Partition Management ====================
|
||||
|
||||
// UsageLogsPartitionStatus represents the partition status of usage_logs table.
|
||||
type UsageLogsPartitionStatus struct {
|
||||
IsPartitioned bool `json:"is_partitioned"`
|
||||
RowCount int64 `json:"row_count"`
|
||||
PartitionCount int `json:"partition_count"`
|
||||
ThresholdRows int64 `json:"threshold_rows"` // 100000
|
||||
NeedsPartitioning bool `json:"needs_partitioning"` // rowCount >= threshold && !isPartitioned
|
||||
WarningLevel string `json:"warning_level"` // "none", "info", "warning"
|
||||
LastCheckedAt string `json:"last_checked_at"`
|
||||
}
|
||||
|
||||
// GetUsageLogsPartitionStatus returns the current partition status of usage_logs table.
|
||||
func (s *OpsService) GetUsageLogsPartitionStatus(ctx context.Context) (*UsageLogsPartitionStatus, error) {
|
||||
if s.opsRepo == nil {
|
||||
return nil, errors.New("ops repository not available")
|
||||
}
|
||||
|
||||
status := &UsageLogsPartitionStatus{
|
||||
ThresholdRows: 100000,
|
||||
LastCheckedAt: time.Now().UTC().Format(time.RFC3339),
|
||||
}
|
||||
|
||||
// Check if usage_logs is partitioned
|
||||
isPartitioned, err := s.opsRepo.IsUsageLogsPartitioned(ctx)
|
||||
if err != nil {
|
||||
log.Printf("[Ops] GetUsageLogsPartitionStatus check partitioned failed: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
status.IsPartitioned = isPartitioned
|
||||
|
||||
// Get row count
|
||||
rowCount, err := s.opsRepo.GetUsageLogsRowCount(ctx)
|
||||
if err != nil {
|
||||
log.Printf("[Ops] GetUsageLogsPartitionStatus get row count failed: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
status.RowCount = rowCount
|
||||
|
||||
// Determine partition count if partitioned
|
||||
if isPartitioned {
|
||||
count, err := s.opsRepo.GetUsageLogsPartitionCount(ctx)
|
||||
if err != nil {
|
||||
log.Printf("[Ops] GetUsageLogsPartitionStatus get partition count failed: %v", err)
|
||||
// Non-critical, continue
|
||||
} else {
|
||||
status.PartitionCount = count
|
||||
}
|
||||
}
|
||||
|
||||
// Determine warning level and needs_partitioning
|
||||
if isPartitioned {
|
||||
status.WarningLevel = "none"
|
||||
status.NeedsPartitioning = false
|
||||
} else if rowCount >= status.ThresholdRows {
|
||||
status.WarningLevel = "warning"
|
||||
status.NeedsPartitioning = true
|
||||
} else if rowCount >= 50000 {
|
||||
status.WarningLevel = "info"
|
||||
status.NeedsPartitioning = false
|
||||
} else {
|
||||
status.WarningLevel = "none"
|
||||
status.NeedsPartitioning = false
|
||||
}
|
||||
|
||||
return status, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user