2023-12-20 16:50:05 +08:00
|
|
|
package main
|
|
|
|
|
|
2024-01-10 16:05:15 +08:00
|
|
|
import (
|
2024-11-07 10:09:53 +08:00
|
|
|
"fmt"
|
2025-04-01 17:59:10 +08:00
|
|
|
conf "go_blog/config"
|
2024-07-04 19:15:44 +08:00
|
|
|
"go_blog/controllers"
|
2024-01-10 16:05:15 +08:00
|
|
|
"go_blog/models"
|
2025-04-09 16:56:05 +08:00
|
|
|
"go_blog/routers"
|
2024-11-11 19:35:24 +08:00
|
|
|
"go_blog/serializers"
|
2024-11-07 10:09:53 +08:00
|
|
|
"log"
|
2024-01-22 17:55:16 +08:00
|
|
|
"net/http"
|
2024-08-05 17:19:23 +08:00
|
|
|
"strconv"
|
2024-01-10 16:05:15 +08:00
|
|
|
|
2025-04-09 16:56:05 +08:00
|
|
|
"go_blog/themes"
|
|
|
|
|
|
|
|
|
|
"gorm.io/driver/mysql"
|
|
|
|
|
"gorm.io/gorm"
|
|
|
|
|
"gorm.io/gorm/schema"
|
|
|
|
|
"honnef.co/go/tools/config"
|
|
|
|
|
|
2024-01-10 16:05:15 +08:00
|
|
|
"github.com/gin-gonic/gin"
|
|
|
|
|
)
|
|
|
|
|
|
2024-07-04 19:15:44 +08:00
|
|
|
const templatePath = "./templates/*"
|
|
|
|
|
|
2024-01-10 16:05:15 +08:00
|
|
|
func init() {
|
|
|
|
|
conf.SetUp()
|
2024-12-16 18:15:15 +08:00
|
|
|
models.SetUp()
|
2024-01-10 16:05:15 +08:00
|
|
|
}
|
2023-12-20 16:50:05 +08:00
|
|
|
|
|
|
|
|
func main() {
|
|
|
|
|
|
2025-04-09 16:56:05 +08:00
|
|
|
// 4. 初始化主题管理器
|
|
|
|
|
themeManager := themes.NewManager()
|
|
|
|
|
if err := themeManager.LoadTheme(conf.GetCurrentTheme()); err != nil {
|
|
|
|
|
panic("主题加载失败: " + err.Error())
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 5. 创建Gin实例
|
|
|
|
|
router := gin.Default()
|
|
|
|
|
router.LoadHTMLGlob(templatePath)
|
2024-07-04 19:15:44 +08:00
|
|
|
// 注册WebSocket路由
|
2025-04-09 16:56:05 +08:00
|
|
|
registerRoutes(router)
|
|
|
|
|
router.GET("/events", esSSE)
|
|
|
|
|
|
|
|
|
|
// 6. 注册中间件
|
|
|
|
|
router.Use(
|
|
|
|
|
gin.Logger(),
|
|
|
|
|
gin.Recovery(),
|
|
|
|
|
databaseMiddleware(models.DB),
|
|
|
|
|
//configMiddleware(cfg),
|
|
|
|
|
themeMiddleware(themeManager),
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
// 7. 设置模板路径
|
|
|
|
|
//router.HTMLRender = createTemplateRenderer(cfg.Theme.Current)
|
|
|
|
|
|
|
|
|
|
// 8. 注册路由
|
|
|
|
|
routers.RegisterRoutes(router)
|
|
|
|
|
// 9. 启动服务
|
|
|
|
|
router.Run(":8910") //router.Run(":" + cfg.Server.Port)
|
2024-07-04 19:15:44 +08:00
|
|
|
}
|
2024-11-07 10:09:53 +08:00
|
|
|
func esSSE(c *gin.Context) {
|
|
|
|
|
w := c.Writer
|
|
|
|
|
|
|
|
|
|
w.Header().Set("Content-Type", "text/event-stream")
|
|
|
|
|
w.Header().Set("Cache-Control", "no-cache")
|
|
|
|
|
w.Header().Set("Connection", "keep-alive")
|
|
|
|
|
w.Header().Set("Access-Control-Allow-Origin", "*")
|
|
|
|
|
|
|
|
|
|
_, ok := w.(http.Flusher)
|
|
|
|
|
|
|
|
|
|
if !ok {
|
|
|
|
|
log.Panic("server not support") //浏览器不兼容
|
|
|
|
|
}
|
|
|
|
|
|
2024-11-07 17:44:14 +08:00
|
|
|
_, err := fmt.Fprintf(w, "id: aaa\ndata: %s\n\n", "dsdf")
|
|
|
|
|
_, er1r := fmt.Fprintf(w, "event: connecttime\ndata: %s\n\n", "connecttime")
|
|
|
|
|
if err != nil || er1r != nil {
|
|
|
|
|
print("error", err)
|
2024-11-07 10:09:53 +08:00
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
}
|
2024-07-04 19:15:44 +08:00
|
|
|
|
|
|
|
|
func registerRoutes(r *gin.Engine) {
|
|
|
|
|
|
2023-12-20 16:50:05 +08:00
|
|
|
r.GET("/", func(c *gin.Context) {
|
2024-11-11 19:35:24 +08:00
|
|
|
var items []models.Content
|
|
|
|
|
models.DB.Select("*").Limit(5).Find(&items, "type = ?", "post")
|
|
|
|
|
c.HTML(http.StatusOK, "index.tmpl", gin.H{
|
|
|
|
|
"Items": items,
|
|
|
|
|
})
|
|
|
|
|
})
|
|
|
|
|
|
|
|
|
|
r.GET("/page", func(c *gin.Context) {
|
|
|
|
|
var items []models.Content
|
|
|
|
|
var pager serializers.Pager
|
|
|
|
|
pager.InitPager(c)
|
2024-11-11 19:38:40 +08:00
|
|
|
offset := (pager.Page - 1) * pager.PageSize
|
|
|
|
|
models.DB.Select("*").Offset(offset).Limit(pager.PageSize).Find(&items, "type = ?", "post")
|
2024-08-01 02:44:06 +08:00
|
|
|
c.HTML(http.StatusOK, "index.tmpl", gin.H{
|
|
|
|
|
"Items": items,
|
2024-11-26 18:41:24 +08:00
|
|
|
"Pager": pager,
|
|
|
|
|
"Title": "文章列表",
|
2024-08-01 02:44:06 +08:00
|
|
|
})
|
|
|
|
|
})
|
|
|
|
|
r.GET("/createcontent", func(c *gin.Context) {
|
|
|
|
|
c.HTML(http.StatusOK, "content.tmpl", nil)
|
2023-12-20 16:50:05 +08:00
|
|
|
})
|
2024-01-10 16:05:15 +08:00
|
|
|
|
2024-08-05 17:19:23 +08:00
|
|
|
r.GET("/post/:id", func(c *gin.Context) {
|
|
|
|
|
id, err := strconv.ParseInt(c.Param("id"), 10, 32)
|
|
|
|
|
if err != nil {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
var content = models.Content{Cid: int32(id)}
|
|
|
|
|
models.DB.First(&content)
|
|
|
|
|
c.HTML(http.StatusOK, "post.tmpl", content)
|
|
|
|
|
})
|
|
|
|
|
user := getUserInfo()
|
2024-01-10 16:05:15 +08:00
|
|
|
r.GET("/login", func(c *gin.Context) {
|
|
|
|
|
c.HTML(200, "login.tmpl", map[string]interface{}{
|
|
|
|
|
"title": "这个是titile,传入templates中的",
|
|
|
|
|
"user": user,
|
|
|
|
|
})
|
|
|
|
|
})
|
2024-12-19 10:29:31 +08:00
|
|
|
r.GET("/register", func(c *gin.Context) {
|
|
|
|
|
c.HTML(200, "register.tmpl", map[string]interface{}{
|
|
|
|
|
"title": "这个是titile,传入templates中的",
|
|
|
|
|
"user": user,
|
|
|
|
|
})
|
|
|
|
|
})
|
2024-01-10 16:05:15 +08:00
|
|
|
|
2024-07-04 19:15:44 +08:00
|
|
|
r.GET("/ws", controllers.WebSocketHandler)
|
2024-08-01 02:44:06 +08:00
|
|
|
r.POST("/content", controllers.CreateContentHandler)
|
2024-07-04 19:15:44 +08:00
|
|
|
r.POST("/login", controllers.UsersLoginHandler)
|
2024-12-19 09:56:01 +08:00
|
|
|
r.POST("/register", controllers.UsersRegisterHandler)
|
|
|
|
|
r.POST("/setinfo", controllers.UsersSetInfoHandler)
|
|
|
|
|
r.POST("/setpwd", controllers.UsersSetPwdHandler)
|
|
|
|
|
|
2023-12-20 16:50:05 +08:00
|
|
|
}
|
2024-01-22 17:55:16 +08:00
|
|
|
|
2025-04-09 16:56:05 +08:00
|
|
|
func getUserInfo() models.User {
|
|
|
|
|
user := models.User{
|
2024-07-04 19:15:44 +08:00
|
|
|
Name: "user",
|
|
|
|
|
Gender: "male",
|
|
|
|
|
Age: 18,
|
|
|
|
|
Password: "nothings",
|
|
|
|
|
PasswordHash: []byte("nothings"),
|
2024-01-22 17:55:16 +08:00
|
|
|
}
|
2024-07-04 19:15:44 +08:00
|
|
|
return user
|
2024-01-22 17:55:16 +08:00
|
|
|
}
|
2025-04-09 16:56:05 +08:00
|
|
|
|
|
|
|
|
func initDatabase() {
|
|
|
|
|
// 1. 初始化配置
|
|
|
|
|
cfg, err := config.Load("config.yaml")
|
|
|
|
|
if err != nil {
|
|
|
|
|
panic("加载配置失败: " + err.Error())
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 2. 初始化数据库
|
|
|
|
|
db, err := gorm.Open(mysql.Open(cfg.String()), &gorm.Config{
|
|
|
|
|
NamingStrategy: schema.NamingStrategy{
|
|
|
|
|
TablePrefix: conf.DataBase.Prefix,
|
|
|
|
|
},
|
|
|
|
|
})
|
|
|
|
|
if err != nil {
|
|
|
|
|
panic("数据库连接失败: " + err.Error())
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 3. 自动迁移数据模型
|
|
|
|
|
if err := db.AutoMigrate(&models.Article{}, &models.User{}); err != nil {
|
|
|
|
|
panic("数据库迁移失败: " + err.Error())
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 自定义模板渲染器
|
|
|
|
|
// func createTemplateRenderer(currentTheme string) gin.HTMLRender {
|
|
|
|
|
// return gin.HTMLTemplates{
|
|
|
|
|
// Root: "web/templates",
|
|
|
|
|
// Extension: ".html",
|
|
|
|
|
// FuncMap: template.FuncMap{
|
|
|
|
|
// "safe": func(s string) template.HTML { return template.HTML(s) },
|
|
|
|
|
// },
|
|
|
|
|
// Directory: "web/themes/" + currentTheme,
|
|
|
|
|
// }
|
|
|
|
|
// }
|
|
|
|
|
|
|
|
|
|
// 数据库中间件
|
|
|
|
|
func databaseMiddleware(db *gorm.DB) gin.HandlerFunc {
|
|
|
|
|
return func(c *gin.Context) {
|
|
|
|
|
c.Set("DB", db)
|
|
|
|
|
c.Next()
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 配置上下文中间件
|
|
|
|
|
func configMiddleware(cfg *config.Config) gin.HandlerFunc {
|
|
|
|
|
return func(c *gin.Context) {
|
|
|
|
|
c.Set("Config", cfg)
|
|
|
|
|
c.Next()
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 主题管理器中间件
|
|
|
|
|
func themeMiddleware(manager *themes.ThemeManager) gin.HandlerFunc {
|
|
|
|
|
return func(c *gin.Context) {
|
|
|
|
|
c.Set("ThemeManager", manager)
|
|
|
|
|
c.Next()
|
|
|
|
|
}
|
|
|
|
|
}
|