Skip to content

Commit

Permalink
Merge remote-tracking branch 'refs/remotes/origin/main'
Browse files Browse the repository at this point in the history
  • Loading branch information
Soulter committed Apr 26, 2024
2 parents 48f84f3 + 865a72f commit 9c63d09
Show file tree
Hide file tree
Showing 9 changed files with 233 additions and 8 deletions.
7 changes: 7 additions & 0 deletions backend/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,13 @@ func SetDefault() {
viper.SetDefault("oss.minio.secret_key", "minio123")
viper.SetDefault("oss.minio.bucket", "campux")
viper.SetDefault("oss.minio.use_ssl", false)

// redis
viper.SetDefault("mq.redis.addr", "localhost:6379")
viper.SetDefault("mq.redis.password", "")
viper.SetDefault("mq.redis.db", 0)
viper.SetDefault("mq.redis.stream.publish_post", "campux_publish_post")

}

// 创建配置文件对象
Expand Down
16 changes: 16 additions & 0 deletions backend/controller/accapi.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,14 @@ func NewAccountRouter(rg *gin.RouterGroup, as service.AccountService) *AccountRo

// 创建账户
func (ar *AccountRouter) CreateAccount(c *gin.Context) {

_, err := ar.Auth(c, ServiceOnly)

if err != nil {
ar.StatusCode(c, 401, err.Error())
return
}

// 取body的json里的uin
var body AccountCreateBody

Expand Down Expand Up @@ -105,6 +113,14 @@ func (ar *AccountRouter) LoginAccount(c *gin.Context) {

// 重置密码
func (ar *AccountRouter) ResetPassword(c *gin.Context) {

_, err := ar.Auth(c, ServiceOnly)

if err != nil {
ar.StatusCode(c, 401, err.Error())
return
}

// 取body的json里的uin
var body AccountCreateBody

Expand Down
43 changes: 43 additions & 0 deletions backend/controller/api.go
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package controller

import (
"errors"
"net/http"
"strings"
"time"
Expand All @@ -9,6 +10,7 @@ import (
"github.com/RockChinQ/Campux/backend/util"
"github.com/gin-contrib/cors"
"github.com/gin-gonic/gin"
"github.com/spf13/viper"
)

type APIController struct {
Expand Down Expand Up @@ -40,6 +42,8 @@ func NewApiController(
)
}

// 鉴权中间件

r.Use(func(c *gin.Context) {
if strings.HasPrefix(c.Request.URL.Path, "/v1") {
c.Next()
Expand Down Expand Up @@ -68,6 +72,45 @@ func NewApiController(
type APIRouter struct {
}

type AuthenticationType int

const (
UserOnly AuthenticationType = 1
ServiceOnly AuthenticationType = 2
Both AuthenticationType = 3
)

// 鉴权
// 如果是服务鉴权,则拿Authorization头对比service.token
// 其他的都是用户鉴权,直接尝试从GetUin取uin
func (ar *APIRouter) Auth(c *gin.Context, authType AuthenticationType) (int64, error) {
serviceToken := viper.GetString("service.token")

uin, err := int64(-1), errors.New("authentication failed")

if authType&ServiceOnly == ServiceOnly {
bearer := c.GetHeader("Authorization")
if bearer != "" {
bearer = bearer[7:]

if bearer == serviceToken {
uin = 0
err = nil
}
}
}

if err == nil {
return uin, err
}

if authType&UserOnly == UserOnly {
uin, err = ar.GetUin(c)
}

return uin, err
}

// 从jwt取uin
func (ar *APIRouter) GetUin(c *gin.Context) (int64, error) {

Expand Down
19 changes: 17 additions & 2 deletions backend/controller/postapi.go
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,8 @@ func (pr *PostRouter) PostNew(c *gin.Context) {

// 下载图片
func (pr *PostRouter) DownloadImage(c *gin.Context) {
_, err := pr.GetUin(c)

_, err := pr.Auth(c, Both)

if err != nil {
pr.StatusCode(c, 401, err.Error())
Expand Down Expand Up @@ -162,6 +163,16 @@ func (pr *PostRouter) GetSelfPosts(c *gin.Context) {

// 获取稿件列表
func (pr *PostRouter) GetPosts(c *gin.Context) {

_, err := pr.Auth(c, Both)

if err != nil {
pr.StatusCode(c, 401, err.Error())
return
}

// TODO 检查用户权限

var body GetPostsBody

if err := c.ShouldBindJSON(&body); err != nil {
Expand Down Expand Up @@ -189,13 +200,15 @@ func (pr *PostRouter) GetPosts(c *gin.Context) {
}

func (pr *PostRouter) GetPostInfo(c *gin.Context) {
_, err := pr.GetUin(c)
_, err := pr.Auth(c, Both)

if err != nil {
pr.StatusCode(c, 401, err.Error())
return
}

// TODO 检查用户权限

id := c.Param("id")

idInt, err := strconv.Atoi(id)
Expand Down Expand Up @@ -256,6 +269,8 @@ func (pr *PostRouter) ReviewPost(c *gin.Context) {
return
}

// TODO 检查用户权限

// 取body的json里的id, status, comment
var body PostReviewBody

Expand Down
44 changes: 41 additions & 3 deletions backend/core/app.go
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
package core

import (
"time"

"github.com/RockChinQ/Campux/backend/controller"
"github.com/RockChinQ/Campux/backend/database"
"github.com/RockChinQ/Campux/backend/mq"
"github.com/RockChinQ/Campux/backend/oss"
"github.com/RockChinQ/Campux/backend/service"
"github.com/RockChinQ/Campux/backend/service/routine"
gocron "github.com/go-co-op/gocron/v2"
)

type Application struct {
Expand All @@ -14,18 +19,51 @@ type Application struct {
func NewApplication() *Application {

db := database.NewMongoDBManager()
as := service.NewAccountService(*db)

fs := oss.NewMinioClient()
ps := service.NewPostService(*db, *fs)
msq := mq.NewRedisStreamMQ()

as := service.NewAccountService(*db)
ps := service.NewPostService(*db, *fs)
ms := service.NewMiscService(*db)

err := ScheduleRoutines(*db, *msq)
if err != nil {
panic(err)
}

return &Application{
API: controller.NewApiController(*as, *ps, *ms),
}
}

func ScheduleRoutines(
db database.MongoDBManager,
msq mq.RedisStreamMQ,
) error {
s, err := gocron.NewScheduler()
if err != nil {
return err
}

_, err = s.NewJob(
gocron.DurationJob(
20*time.Second,
),
gocron.NewTask(
routine.SchedulePublishing,
db,
msq,
),
)
if err != nil {
return err
}

s.Start()

return nil
}

func (a *Application) Run() {
a.API.R.Run()
}
35 changes: 35 additions & 0 deletions backend/mq/redis.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
package mq

import (
"context"

"github.com/redis/go-redis/v9"
"github.com/spf13/viper"
)

type RedisStreamMQ struct {
Client *redis.Client
PublishPostStream string
}

func NewRedisStreamMQ() *RedisStreamMQ {
client := redis.NewClient(&redis.Options{
Addr: viper.GetString("mq.redis.addr"),
Password: viper.GetString("mq.redis.password"),
DB: viper.GetInt("mq.redis.db"),
})
return &RedisStreamMQ{
Client: client,
PublishPostStream: viper.GetString("mq.redis.stream.publish_post"),
}
}

func (r *RedisStreamMQ) PublishPost(postID int) error {
_, err := r.Client.XAdd(context.Background(), &redis.XAddArgs{
Stream: r.PublishPostStream,
Values: map[string]interface{}{
"post_id": postID,
},
}).Result()
return err
}
47 changes: 47 additions & 0 deletions backend/service/routine/schedule_publishing.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
package routine

import (
"fmt"

"github.com/RockChinQ/Campux/backend/database"
"github.com/RockChinQ/Campux/backend/mq"
"github.com/RockChinQ/Campux/backend/util"
)

func SchedulePublishing(db database.MongoDBManager, msq mq.RedisStreamMQ) {
// 从数据库中查询出所有待发布的稿件
// 遍历稿件, 发布到消息队列
// 更新稿件状态
approvedPosts, err := db.GetPosts(-1, database.POST_STATUS_APPROVED, 1, 1, 10)
if err != nil {
return
}

for _, post := range approvedPosts {
err = msq.PublishPost(post.ID)
if err != nil {
fmt.Println(err)
continue
}

// 加日志
err = db.AddPostLog(&database.PostLogPO{
PostID: post.ID,
Op: -1,
OldStat: database.POST_STATUS_APPROVED,
NewStat: database.POST_STATUS_IN_QUEUE,
Comment: "发布到消息队列",
CreatedAt: util.GetCSTTime(),
})
if err != nil {
fmt.Println(err)
continue
}

err = db.UpdatePostStatus(post.ID, database.POST_STATUS_IN_QUEUE)
if err != nil {
fmt.Println(err)
continue
}
}
}
8 changes: 7 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,21 @@ go 1.22.1
require (
github.com/gin-contrib/cors v1.7.1
github.com/gin-gonic/gin v1.9.1
github.com/go-co-op/gocron/v2 v2.2.9
github.com/golang-jwt/jwt/v5 v5.2.1
github.com/google/uuid v1.6.0
github.com/minio/minio-go/v7 v7.0.69
github.com/redis/go-redis/v9 v9.5.1
github.com/spf13/viper v1.18.2
go.mongodb.org/mongo-driver v1.14.0
)

require (
github.com/bytedance/sonic v1.11.3 // indirect
github.com/cespare/xxhash/v2 v2.2.0 // indirect
github.com/chenzhuoyu/base64x v0.0.0-20230717121745-296ad89f973d // indirect
github.com/chenzhuoyu/iasm v0.9.1 // indirect
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect
github.com/dustin/go-humanize v1.0.1 // indirect
github.com/fsnotify/fsnotify v1.7.0 // indirect
github.com/gabriel-vasile/mimetype v1.4.3 // indirect
Expand All @@ -26,6 +30,7 @@ require (
github.com/goccy/go-json v0.10.2 // indirect
github.com/golang/snappy v0.0.1 // indirect
github.com/hashicorp/hcl v1.0.0 // indirect
github.com/jonboulle/clockwork v0.4.0 // indirect
github.com/json-iterator/go v1.1.12 // indirect
github.com/klauspost/compress v1.17.6 // indirect
github.com/klauspost/cpuid/v2 v2.2.7 // indirect
Expand All @@ -39,6 +44,7 @@ require (
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/montanaflynn/stats v0.0.0-20171201202039-1bf9dbcd8cbe // indirect
github.com/pelletier/go-toml/v2 v2.2.0 // indirect
github.com/robfig/cron/v3 v3.0.1 // indirect
github.com/rs/xid v1.5.0 // indirect
github.com/sagikazarmark/locafero v0.4.0 // indirect
github.com/sagikazarmark/slog-shim v0.1.0 // indirect
Expand All @@ -57,7 +63,7 @@ require (
go.uber.org/multierr v1.9.0 // indirect
golang.org/x/arch v0.7.0 // indirect
golang.org/x/crypto v0.21.0 // indirect
golang.org/x/exp v0.0.0-20230905200255-921286631fa9 // indirect
golang.org/x/exp v0.0.0-20231219180239-dc181d75b848 // indirect
golang.org/x/net v0.22.0 // indirect
golang.org/x/sync v0.5.0 // indirect
golang.org/x/sys v0.18.0 // indirect
Expand Down
Loading

0 comments on commit 9c63d09

Please sign in to comment.