package productapp

import (
	"context"
	"fmt"
	"git.gocasts.ir/ebhomengo/niki/productapp/service/product"
	"log"

	httpserver "git.gocasts.ir/ebhomengo/niki/delivery/http_server"
	producthttp "git.gocasts.ir/ebhomengo/niki/productapp/delivery/http"
	productdb "git.gocasts.ir/ebhomengo/niki/productapp/repository/database"
	"git.gocasts.ir/ebhomengo/niki/repository/mysql"
	"github.com/labstack/echo/v4"
	"github.com/labstack/echo/v4/middleware"
)

type HTTPServerConfig struct {
	Port int
}

type Config struct {
	HTTPServer HTTPServerConfig
	Database   mysql.Config
}

type Application struct {
	Config     Config
	HTTPServer *producthttp.Server
	productSvc product.Service
	DB         *productdb.DB
	Echo       *echo.Echo
}

func Setup(cfg Config) *Application {
	db := mysql.New(cfg.Database)
	productDB := productdb.New(db)

	e := echo.New()
	e.Use(middleware.Recover())

	hsrv := &httpserver.Server{
		Router: e,
	}

	productSvc := product.New(productDB)

	srv := producthttp.NewServer(hsrv, productSvc)
	srv.RegisterRoutes()

	return &Application{
		Config:     cfg,
		productSvc: productSvc,
		HTTPServer: srv,
		DB:         productDB,
		Echo:       e,
	}
}

func (app *Application) Start() {
	address := fmt.Sprintf(":%d", app.Config.HTTPServer.Port)
	log.Printf("Product Service listening on %s", address)
	if err := app.Echo.Start(address); err != nil {
		log.Fatalf("Failed to start server: %v", err)
	}
}

func (app *Application) Stop(ctx context.Context) error {
	return app.Echo.Shutdown(ctx)
}
