Merge branch 'ai_0.3_dashboard' into test

This commit is contained in:
aichy126 2022-11-11 11:55:46 +08:00
commit 79ba518810
9 changed files with 168 additions and 9 deletions

View File

@ -152,7 +152,7 @@ func initApplication(debug bool, serverConf *conf.Server, dbConf *data.Database,
questionService := service.NewQuestionService(questionRepo, tagCommonService, questionCommon, userCommon, revisionService, metaService, collectionCommon, answerActivityService)
questionController := controller.NewQuestionController(questionService, rankService)
answerService := service.NewAnswerService(answerRepo, questionRepo, questionCommon, userCommon, collectionCommon, userRepo, revisionService, answerActivityService, answerCommon, voteRepo)
dashboardService := dashboard.NewDashboardService(questionRepo, answerRepo, commentCommonRepo, voteRepo, userRepo, reportRepo, configRepo, siteInfoCommonService)
dashboardService := dashboard.NewDashboardService(questionRepo, answerRepo, commentCommonRepo, voteRepo, userRepo, reportRepo, configRepo, siteInfoCommonService, serviceConf, dataData)
answerController := controller.NewAnswerController(answerService, rankService, dashboardService)
searchRepo := search_common.NewSearchRepo(dataData, uniqueIDRepo, userCommon)
searchService := service.NewSearchService(searchRepo, tagRepo, userCommon, followRepo)

View File

@ -5292,11 +5292,17 @@ const docTemplate = `{
"schema.SiteGeneralReq": {
"type": "object",
"required": [
"contact_email",
"description",
"name",
"short_description"
"short_description",
"site_url"
],
"properties": {
"contact_email": {
"type": "string",
"maxLength": 512
},
"description": {
"type": "string",
"maxLength": 2000
@ -5308,17 +5314,27 @@ const docTemplate = `{
"short_description": {
"type": "string",
"maxLength": 255
},
"site_url": {
"type": "string",
"maxLength": 512
}
}
},
"schema.SiteGeneralResp": {
"type": "object",
"required": [
"contact_email",
"description",
"name",
"short_description"
"short_description",
"site_url"
],
"properties": {
"contact_email": {
"type": "string",
"maxLength": 512
},
"description": {
"type": "string",
"maxLength": 2000
@ -5330,6 +5346,10 @@ const docTemplate = `{
"short_description": {
"type": "string",
"maxLength": 255
},
"site_url": {
"type": "string",
"maxLength": 512
}
}
},

View File

@ -5280,11 +5280,17 @@
"schema.SiteGeneralReq": {
"type": "object",
"required": [
"contact_email",
"description",
"name",
"short_description"
"short_description",
"site_url"
],
"properties": {
"contact_email": {
"type": "string",
"maxLength": 512
},
"description": {
"type": "string",
"maxLength": 2000
@ -5296,17 +5302,27 @@
"short_description": {
"type": "string",
"maxLength": 255
},
"site_url": {
"type": "string",
"maxLength": 512
}
}
},
"schema.SiteGeneralResp": {
"type": "object",
"required": [
"contact_email",
"description",
"name",
"short_description"
"short_description",
"site_url"
],
"properties": {
"contact_email": {
"type": "string",
"maxLength": 512
},
"description": {
"type": "string",
"maxLength": 2000
@ -5318,6 +5334,10 @@
"short_description": {
"type": "string",
"maxLength": 255
},
"site_url": {
"type": "string",
"maxLength": 512
}
}
},

View File

@ -983,6 +983,9 @@ definitions:
type: object
schema.SiteGeneralReq:
properties:
contact_email:
maxLength: 512
type: string
description:
maxLength: 2000
type: string
@ -992,13 +995,21 @@ definitions:
short_description:
maxLength: 255
type: string
site_url:
maxLength: 512
type: string
required:
- contact_email
- description
- name
- short_description
- site_url
type: object
schema.SiteGeneralResp:
properties:
contact_email:
maxLength: 512
type: string
description:
maxLength: 2000
type: string
@ -1008,10 +1019,15 @@ definitions:
short_description:
maxLength: 255
type: string
site_url:
maxLength: 512
type: string
required:
- contact_email
- description
- name
- short_description
- site_url
type: object
schema.SiteInterfaceReq:
properties:

View File

@ -0,0 +1 @@
package controller

View File

@ -29,7 +29,7 @@ func NewDashboardController(
// @Router /answer/admin/api/dashboard [get]
// @Success 200 {object} handler.RespBody
func (ac *DashboardController) DashboardInfo(ctx *gin.Context) {
info, err := ac.dashboardService.Statistical(ctx)
info, err := ac.dashboardService.StatisticalByCache(ctx)
handler.HandleResponse(ctx, err, gin.H{
"info": info,
})

View File

@ -4,6 +4,11 @@ import "time"
var AppStartTime time.Time
const (
DashBoardCachekey = "answer@dashboard"
DashBoardCacheTime = 60 * time.Minute
)
type DashboardInfo struct {
QuestionCount int64 `json:"question_count"`
AnswerCount int64 `json:"answer_count"`

View File

@ -6,9 +6,11 @@ import (
"fmt"
"io/ioutil"
"net/http"
"net/url"
"time"
"github.com/answerdev/answer/internal/base/constant"
"github.com/answerdev/answer/internal/base/data"
"github.com/answerdev/answer/internal/base/reason"
"github.com/answerdev/answer/internal/schema"
"github.com/answerdev/answer/internal/service/activity_common"
@ -18,8 +20,10 @@ import (
"github.com/answerdev/answer/internal/service/export"
questioncommon "github.com/answerdev/answer/internal/service/question_common"
"github.com/answerdev/answer/internal/service/report_common"
"github.com/answerdev/answer/internal/service/service_config"
"github.com/answerdev/answer/internal/service/siteinfo_common"
usercommon "github.com/answerdev/answer/internal/service/user_common"
"github.com/answerdev/answer/pkg/dir"
"github.com/segmentfault/pacman/errors"
"github.com/segmentfault/pacman/log"
)
@ -33,6 +37,9 @@ type DashboardService struct {
reportRepo report_common.ReportRepo
configRepo config.ConfigRepo
siteInfoService *siteinfo_common.SiteInfoCommonService
serviceConfig *service_config.ServiceConfig
data *data.Data
}
func NewDashboardService(
@ -44,6 +51,9 @@ func NewDashboardService(
reportRepo report_common.ReportRepo,
configRepo config.ConfigRepo,
siteInfoService *siteinfo_common.SiteInfoCommonService,
serviceConfig *service_config.ServiceConfig,
data *data.Data,
) *DashboardService {
return &DashboardService{
questionRepo: questionRepo,
@ -54,9 +64,47 @@ func NewDashboardService(
reportRepo: reportRepo,
configRepo: configRepo,
siteInfoService: siteInfoService,
serviceConfig: serviceConfig,
data: data,
}
}
func (ds *DashboardService) StatisticalByCache(ctx context.Context) (*schema.DashboardInfo, error) {
dashboardInfo := &schema.DashboardInfo{}
infoStr, err := ds.data.Cache.GetString(ctx, schema.DashBoardCachekey)
if err != nil {
info, statisticalErr := ds.Statistical(ctx)
if statisticalErr != nil {
return dashboardInfo, err
}
setCacheErr := ds.SetCache(ctx, info)
if setCacheErr != nil {
log.Error("ds.SetCache", setCacheErr)
}
return info, err
}
err = json.Unmarshal([]byte(infoStr), dashboardInfo)
if err != nil {
return dashboardInfo, err
}
startTime := time.Now().Unix() - schema.AppStartTime.Unix()
dashboardInfo.AppStartTime = fmt.Sprintf("%d", startTime)
return dashboardInfo, nil
}
func (ds *DashboardService) SetCache(ctx context.Context, info *schema.DashboardInfo) error {
infoStr, err := json.Marshal(info)
if err != nil {
return errors.InternalServer(reason.UnknownError).WithError(err).WithStack()
}
err = ds.data.Cache.SetString(ctx, schema.DashBoardCachekey, string(infoStr), schema.DashBoardCacheTime)
if err != nil {
return errors.InternalServer(reason.UnknownError).WithError(err).WithStack()
}
return nil
}
// Statistical
func (ds *DashboardService) Statistical(ctx context.Context) (*schema.DashboardInfo, error) {
dashboardInfo := &schema.DashboardInfo{}
@ -124,8 +172,24 @@ func (ds *DashboardService) Statistical(ctx context.Context) (*schema.DashboardI
if emailconfig.SMTPHost != "" {
dashboardInfo.SMTP = true
}
dashboardInfo.HTTPS = true
dashboardInfo.OccupyingStorageSpace = "1MB"
siteGeneral, err := ds.siteInfoService.GetSiteGeneral(ctx)
if err != nil {
return dashboardInfo, err
}
siteUrl, err := url.Parse(siteGeneral.SiteUrl)
if err != nil {
return dashboardInfo, err
}
if siteUrl.Scheme == "https" {
dashboardInfo.HTTPS = true
}
dirSize, err := dir.DirSize(ds.serviceConfig.UploadPath)
if err != nil {
return dashboardInfo, err
}
size := dir.FormatFileSize(dirSize)
dashboardInfo.OccupyingStorageSpace = size
startTime := time.Now().Unix() - schema.AppStartTime.Unix()
dashboardInfo.AppStartTime = fmt.Sprintf("%d", startTime)
dashboardInfo.TimeZone = siteInfoInterface.TimeZone

View File

@ -1,6 +1,10 @@
package dir
import "os"
import (
"fmt"
"os"
"path/filepath"
)
func CreateDirIfNotExist(path string) error {
return os.MkdirAll(path, os.ModePerm)
@ -15,3 +19,32 @@ func CheckFileExist(path string) bool {
f, err := os.Stat(path)
return err == nil && !f.IsDir()
}
func DirSize(path string) (int64, error) {
var size int64
err := filepath.Walk(path, func(_ string, info os.FileInfo, err error) error {
if !info.IsDir() {
size += info.Size()
}
return err
})
return size, err
}
func FormatFileSize(fileSize int64) (size string) {
if fileSize < 1024 {
//return strconv.FormatInt(fileSize, 10) + "B"
return fmt.Sprintf("%.2f B", float64(fileSize)/float64(1))
} else if fileSize < (1024 * 1024) {
return fmt.Sprintf("%.2f KB", float64(fileSize)/float64(1024))
} else if fileSize < (1024 * 1024 * 1024) {
return fmt.Sprintf("%.2f MB", float64(fileSize)/float64(1024*1024))
} else if fileSize < (1024 * 1024 * 1024 * 1024) {
return fmt.Sprintf("%.2f GB", float64(fileSize)/float64(1024*1024*1024))
} else if fileSize < (1024 * 1024 * 1024 * 1024 * 1024) {
return fmt.Sprintf("%.2f TB", float64(fileSize)/float64(1024*1024*1024*1024))
} else { //if fileSize < (1024 * 1024 * 1024 * 1024 * 1024 * 1024)
return fmt.Sprintf("%.2f EB", float64(fileSize)/float64(1024*1024*1024*1024*1024))
}
}