132 lines
3.2 KiB
Go
132 lines
3.2 KiB
Go
package server
|
|
|
|
import (
|
|
"fmt"
|
|
"strings"
|
|
|
|
"github.com/gofiber/fiber/v2"
|
|
"github.com/gofiber/fiber/v2/middleware/cors"
|
|
"github.com/gofiber/fiber/v2/middleware/logger"
|
|
"github.com/gofiber/fiber/v2/middleware/recover"
|
|
"github.com/gofiber/template/html/v2"
|
|
|
|
"gitee.ltd/lxh/wechat-robot/internal/config"
|
|
"gitee.ltd/lxh/wechat-robot/internal/handler"
|
|
"gitee.ltd/lxh/wechat-robot/internal/middleware"
|
|
)
|
|
|
|
// Server 表示HTTP服务器
|
|
type Server struct {
|
|
app *fiber.App
|
|
config *config.Config
|
|
}
|
|
|
|
// New 创建新的服务器实例
|
|
func New(cfg *config.Config) *Server {
|
|
// 初始化模板引擎
|
|
engine := html.New("./internal/view", ".html")
|
|
engine.Reload(cfg.Server.Env == "development") // 开发环境下启用热重载
|
|
|
|
// 添加自定义模板函数
|
|
engine.AddFunc("sub", func(a, b int) int {
|
|
return a - b
|
|
})
|
|
|
|
// 创建Fiber应用
|
|
app := fiber.New(fiber.Config{
|
|
Views: engine,
|
|
ViewsLayout: "layouts/main",
|
|
ErrorHandler: customErrorHandler,
|
|
EnablePrintRoutes: cfg.Server.Env == "development",
|
|
})
|
|
|
|
// 注册中间件
|
|
app.Use(recover.New())
|
|
app.Use(logger.New(logger.Config{
|
|
Format: "[${time}] ${status} - ${latency} ${method} ${path}\n",
|
|
}))
|
|
app.Use(cors.New())
|
|
|
|
// 静态文件服务
|
|
app.Static("/public", "./public")
|
|
|
|
return &Server{
|
|
app: app,
|
|
config: cfg,
|
|
}
|
|
}
|
|
|
|
// SetupRoutes 设置路由
|
|
func (s *Server) SetupRoutes() {
|
|
// 公共路由
|
|
s.app.Get("/", handler.Home)
|
|
s.app.Get("/login", handler.LoginPage)
|
|
s.app.Post("/login", handler.LoginSubmit)
|
|
s.app.Get("/logout", handler.Logout)
|
|
|
|
// 受保护的路由
|
|
auth := s.app.Group("/admin", middleware.Authenticate())
|
|
|
|
// 机器人管理
|
|
auth.Get("/robots", handler.ListRobots)
|
|
auth.Get("/robots/new", handler.NewRobotForm)
|
|
auth.Post("/robots", handler.CreateRobot)
|
|
auth.Get("/robots/:id", handler.ShowRobot)
|
|
auth.Delete("/robots/:id", handler.DeleteRobot)
|
|
auth.Get("/robots/:id/login", handler.RobotLogin)
|
|
auth.Post("/robots/:id/logout", handler.RobotLogout)
|
|
|
|
// 联系人管理
|
|
auth.Get("/robots/:id/contacts", handler.ListContacts)
|
|
auth.Get("/robots/:id/contacts/:contactId", handler.ShowContact)
|
|
auth.Get("/robots/:id/contacts/:contactId/members", handler.ListGroupMembers)
|
|
|
|
// 消息管理
|
|
auth.Get("/robots/:id/contacts/:contactId/messages", handler.ListMessages)
|
|
|
|
// API路由
|
|
api := s.app.Group("/api")
|
|
api.Get("/robots", handler.APIListRobots)
|
|
api.Get("/robots/:id/status", handler.APIGetRobotStatus)
|
|
// 更多API路由...
|
|
}
|
|
|
|
// Start 启动HTTP服务器
|
|
func (s *Server) Start() error {
|
|
addr := s.config.Server.Address()
|
|
fmt.Printf("Server starting on %s\n", addr)
|
|
return s.app.Listen(addr)
|
|
}
|
|
|
|
// Shutdown 优雅地关闭服务器
|
|
func (s *Server) Shutdown() error {
|
|
if s.app != nil {
|
|
return s.app.Shutdown()
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// 自定义错误处理器
|
|
func customErrorHandler(c *fiber.Ctx, err error) error {
|
|
code := fiber.StatusInternalServerError
|
|
|
|
if e, ok := err.(*fiber.Error); ok {
|
|
code = e.Code
|
|
}
|
|
|
|
// 检查是否请求API
|
|
if strings.HasPrefix(c.Path(), "/api") {
|
|
return c.Status(code).JSON(fiber.Map{
|
|
"error": true,
|
|
"message": err.Error(),
|
|
})
|
|
}
|
|
|
|
// 网页错误
|
|
return c.Status(code).Render("error", fiber.Map{
|
|
"Title": fmt.Sprintf("Error %d", code),
|
|
"StatusCode": code,
|
|
"ErrorMessage": err.Error(),
|
|
})
|
|
}
|