1
0
mirror of https://github.com/nitezs/sub2clash.git synced 2024-12-26 01:10:53 -05:00
sub2clash/api/controller/short_link.go

109 lines
2.8 KiB
Go
Raw Normal View History

2023-09-17 03:52:37 -04:00
package controller
import (
"errors"
2023-09-17 03:52:37 -04:00
"github.com/gin-gonic/gin"
2023-09-22 20:48:45 -04:00
"go.uber.org/zap"
"gorm.io/gorm"
2023-09-22 20:48:45 -04:00
"io"
2023-09-17 04:59:02 -04:00
"net/http"
2023-09-22 20:48:45 -04:00
"strconv"
"strings"
2023-09-17 04:59:02 -04:00
"sub2clash/config"
2023-09-22 20:48:45 -04:00
"sub2clash/logger"
2023-09-17 03:52:37 -04:00
"sub2clash/model"
"sub2clash/utils"
2023-09-17 03:52:37 -04:00
"sub2clash/utils/database"
"sub2clash/validator"
"time"
)
func ShortLinkGenHandler(c *gin.Context) {
// 从请求中获取参数
var params validator.ShortLinkGenValidator
if err := c.ShouldBind(&params); err != nil {
c.String(400, "参数错误: "+err.Error())
}
if strings.TrimSpace(params.Url) == "" {
c.String(400, "参数错误")
return
}
// 生成hash
hash := utils.RandomString(config.Default.ShortLinkLength)
var item model.ShortLink
result := database.FindShortLinkByUrl(params.Url, &item)
if result.Error == nil {
2023-09-22 20:48:45 -04:00
if item.Password != params.Password {
2023-09-22 13:55:43 -04:00
item.Password = params.Password
database.SaveShortLink(&item)
c.String(200, item.Hash+"?password="+params.Password)
} else {
c.String(200, item.Hash)
}
return
} else {
if !errors.Is(result.Error, gorm.ErrRecordNotFound) {
c.String(500, "数据库错误: "+result.Error.Error())
return
}
}
// 如果记录存在则重新生成hash直到记录不存在
result = database.FindShortLinkByHash(hash, &item)
for result.Error == nil {
hash = utils.RandomString(config.Default.ShortLinkLength)
result = database.FindShortLinkByHash(hash, &item)
}
// 创建记录
database.FirstOrCreateShortLink(
2023-09-17 03:52:37 -04:00
&model.ShortLink{
Hash: hash,
Url: params.Url,
LastRequestTime: -1,
Password: params.Password,
2023-09-17 03:52:37 -04:00
},
)
// 返回短链接
if params.Password != "" {
2023-09-22 13:55:43 -04:00
hash += "?password=" + params.Password
}
2023-09-17 03:52:37 -04:00
c.String(200, hash)
}
func ShortLinkGetHandler(c *gin.Context) {
// 获取动态路由
hash := c.Param("hash")
password := c.Query("password")
if strings.TrimSpace(hash) == "" {
c.String(400, "参数错误")
return
}
2023-09-17 03:52:37 -04:00
// 查询数据库
var shortLink model.ShortLink
result := database.FindShortLinkByHash(hash, &shortLink)
2023-09-17 03:52:37 -04:00
// 重定向
if result.Error != nil {
2023-09-22 13:55:43 -04:00
c.String(404, "未找到短链接或密码错误")
2023-09-17 03:52:37 -04:00
return
}
if shortLink.Password != "" && shortLink.Password != password {
2023-09-22 13:55:43 -04:00
c.String(404, "未找到短链接或密码错误")
return
}
// 更新最后访问时间
shortLink.LastRequestTime = time.Now().Unix()
database.SaveShortLink(&shortLink)
2023-09-22 20:48:45 -04:00
get, err := utils.Get("http://localhost:" + strconv.Itoa(config.Default.Port) + "/" + shortLink.Url)
if err != nil {
logger.Logger.Debug("get short link data failed", zap.Error(err))
c.String(500, "请求错误: "+err.Error())
return
}
all, err := io.ReadAll(get.Body)
if err != nil {
logger.Logger.Debug("read short link data failed", zap.Error(err))
c.String(500, "读取错误: "+err.Error())
return
}
c.String(http.StatusOK, string(all))
2023-09-17 03:52:37 -04:00
}