视频连线

This commit is contained in:
duoaohui
2026-05-26 22:41:53 +08:00
parent 331941f9ce
commit 24e3a37c96
19 changed files with 860 additions and 4 deletions

View File

@@ -2,9 +2,16 @@
package controller
import (
"encoding/base64"
"encoding/json"
"net/http"
"net/url"
"strings"
"github.com/echochat/backend/app/auth/service"
"github.com/echochat/backend/app/constants"
"github.com/echochat/backend/app/dto"
"github.com/echochat/backend/config"
"github.com/echochat/backend/pkg/logs"
"github.com/echochat/backend/pkg/middleware"
"github.com/echochat/backend/pkg/utils"
@@ -16,11 +23,13 @@ import (
// 处理用户注册、登录、Token 刷新、个人信息管理等接口
type AuthController struct {
authService *service.AuthService
oauthService *service.OAuthService
oauthCfg *config.OAuthConfig
}
// NewAuthController 创建前台认证控制器实例
func NewAuthController(authService *service.AuthService) *AuthController {
return &AuthController{authService: authService}
func NewAuthController(authService *service.AuthService, oauthService *service.OAuthService, oauthCfg *config.OAuthConfig) *AuthController {
return &AuthController{authService: authService, oauthService: oauthService, oauthCfg: oauthCfg}
}
// Register 用户注册
@@ -77,6 +86,53 @@ func (ctrl *AuthController) Login(c *gin.Context) {
utils.ResponseOK(c, resp)
}
func (ctrl *AuthController) OAuthAuthorize(c *gin.Context) {
provider := strings.ToLower(strings.TrimSpace(c.Param("provider")))
authURL, err := ctrl.oauthService.BuildAuthorizeURL(c.Request.Context(), provider)
if err != nil {
handleAuthError(c, err, "第三方登录初始化失败")
return
}
utils.ResponseOK(c, gin.H{"url": authURL})
}
func (ctrl *AuthController) OAuthCallback(c *gin.Context) {
provider := strings.ToLower(strings.TrimSpace(c.Param("provider")))
code := strings.TrimSpace(c.Query("code"))
state := strings.TrimSpace(c.Query("state"))
if code == "" {
ctrl.redirectOAuthFailure(c, "第三方登录授权失败")
return
}
resp, err := ctrl.oauthService.Callback(c.Request.Context(), provider, code, state, c.ClientIP())
if err != nil {
ctrl.redirectOAuthFailure(c, err.Error())
return
}
payload, err := json.Marshal(resp)
if err != nil {
ctrl.redirectOAuthFailure(c, "登录结果生成失败")
return
}
ctrl.redirectOAuthResult(c, "success", base64.RawURLEncoding.EncodeToString(payload))
}
func (ctrl *AuthController) redirectOAuthFailure(c *gin.Context, message string) {
ctrl.redirectOAuthResult(c, "error", base64.RawURLEncoding.EncodeToString([]byte(message)))
}
func (ctrl *AuthController) redirectOAuthResult(c *gin.Context, status, payload string) {
callbackURL := "/echoChat-frontend/#/pages/auth/oauth-callback"
if ctrl.oauthCfg != nil && strings.TrimSpace(ctrl.oauthCfg.FrontendCallbackURL) != "" {
callbackURL = strings.TrimSpace(ctrl.oauthCfg.FrontendCallbackURL)
}
sep := "?"
if strings.Contains(callbackURL, "?") {
sep = "&"
}
c.Redirect(http.StatusFound, callbackURL+sep+"status="+url.QueryEscape(status)+"&payload="+url.QueryEscape(payload))
}
// Logout 用户登出
// POST /api/v1/auth/logout需认证
func (ctrl *AuthController) Logout(c *gin.Context) {
@@ -226,6 +282,12 @@ func handleAuthError(c *gin.Context, err error, fallbackMsg ...string) {
utils.ResponseForbidden(c, err.Error())
case service.ErrRefreshTokenType:
utils.ResponseBadRequest(c, err.Error())
case service.ErrOAuthProviderUnsupported:
utils.ResponseBadRequest(c, err.Error())
case service.ErrOAuthProviderDisabled:
utils.ResponseBadRequest(c, err.Error())
case service.ErrOAuthStateInvalid:
utils.ResponseBadRequest(c, err.Error())
default:
msg := "服务器内部错误"
if len(fallbackMsg) > 0 && fallbackMsg[0] != "" {