mirror of
https://github.com/Noooste/garage-ui.git
synced 2026-07-26 07:48:13 +00:00
126 lines
3.1 KiB
Go
126 lines
3.1 KiB
Go
package main
|
|
|
|
import (
|
|
"flag"
|
|
"fmt"
|
|
"log"
|
|
"os"
|
|
"os/signal"
|
|
"syscall"
|
|
|
|
"Noooste/garage-ui/internal/auth"
|
|
"Noooste/garage-ui/internal/config"
|
|
"Noooste/garage-ui/internal/handlers"
|
|
"Noooste/garage-ui/internal/routes"
|
|
"Noooste/garage-ui/internal/services"
|
|
"github.com/gofiber/fiber/v3"
|
|
"github.com/gofiber/fiber/v3/middleware/logger"
|
|
"github.com/gofiber/fiber/v3/middleware/recover"
|
|
)
|
|
|
|
const version = "0.1.0"
|
|
|
|
func main() {
|
|
// Parse command-line flags
|
|
configPath := flag.String("config", "config.yaml", "Path to configuration file")
|
|
flag.Parse()
|
|
|
|
// Load configuration
|
|
log.Printf("Loading configuration from: %s", *configPath)
|
|
cfg, err := config.Load(*configPath)
|
|
if err != nil {
|
|
log.Fatalf("Failed to load configuration: %v", err)
|
|
}
|
|
|
|
log.Printf("Starting Garage UI Backend v%s in %s mode", version, cfg.Server.Environment)
|
|
|
|
// Initialize services
|
|
log.Println("Initializing S3 service...")
|
|
s3Service := services.NewS3Service(&cfg.Garage)
|
|
|
|
log.Printf("Initializing authentication service (mode: %s)...", cfg.Auth.Mode)
|
|
authService, err := auth.NewAuthService(&cfg.Auth)
|
|
if err != nil {
|
|
log.Fatalf("Failed to initialize auth service: %v", err)
|
|
}
|
|
|
|
// Initialize handlers
|
|
healthHandler := handlers.NewHealthHandler(version)
|
|
bucketHandler := handlers.NewBucketHandler(s3Service)
|
|
objectHandler := handlers.NewObjectHandler(s3Service)
|
|
userHandler := handlers.NewUserHandler()
|
|
|
|
// Create Fiber app with configuration
|
|
app := fiber.New(fiber.Config{
|
|
AppName: "Garage UI Backend v" + version,
|
|
DisableStartupMessage: false,
|
|
EnablePrintRoutes: cfg.IsDevelopment(),
|
|
ErrorHandler: customErrorHandler,
|
|
})
|
|
|
|
// Apply global middleware
|
|
app.Use(recover.New()) // Panic recovery
|
|
app.Use(logger.New(logger.Config{
|
|
Format: "[${time}] ${status} - ${method} ${path} (${latency})\n",
|
|
}))
|
|
|
|
// Setup routes
|
|
log.Println("Setting up routes...")
|
|
routes.SetupRoutes(
|
|
app,
|
|
cfg,
|
|
authService,
|
|
healthHandler,
|
|
bucketHandler,
|
|
objectHandler,
|
|
userHandler,
|
|
)
|
|
|
|
// Start server in a goroutine
|
|
go func() {
|
|
addr := cfg.GetAddress()
|
|
log.Printf("Server listening on %s", addr)
|
|
log.Printf("Health check available at: http://%s/health", addr)
|
|
log.Printf("API documentation: http://%s/api/v1/", addr)
|
|
|
|
if err := app.Listen(addr); err != nil {
|
|
log.Fatalf("Failed to start server: %v", err)
|
|
}
|
|
}()
|
|
|
|
// Wait for interrupt signal to gracefully shutdown the server
|
|
quit := make(chan os.Signal, 1)
|
|
signal.Notify(quit, os.Interrupt, syscall.SIGTERM)
|
|
<-quit
|
|
|
|
log.Println("Shutting down server...")
|
|
if err := app.Shutdown(); err != nil {
|
|
log.Fatalf("Server shutdown failed: %v", err)
|
|
}
|
|
|
|
log.Println("Server stopped gracefully")
|
|
}
|
|
|
|
// customErrorHandler handles errors globally
|
|
func customErrorHandler(c fiber.Ctx, err error) error {
|
|
// Default to 500 Internal Server Error
|
|
code := fiber.StatusInternalServerError
|
|
|
|
// Check if it's a Fiber error
|
|
if e, ok := err.(*fiber.Error); ok {
|
|
code = e.Code
|
|
}
|
|
|
|
// Log the error
|
|
log.Printf("Error: %v", err)
|
|
|
|
// Return JSON error response
|
|
return c.Status(code).JSON(fiber.Map{
|
|
"success": false,
|
|
"error": fiber.Map{
|
|
"code": fmt.Sprintf("ERROR_%d", code),
|
|
"message": err.Error(),
|
|
},
|
|
})
|
|
}
|