Browse Source

提交代码。

Signed-off-by: zouap <zouap@pcl.ac.cn>
tags/v1.22.5.2
zouap 3 years ago
parent
commit
3efb1697f1
8 changed files with 225 additions and 66 deletions
  1. +1
    -0
      models/models.go
  2. +126
    -52
      models/user_business_analysis.go
  3. +66
    -0
      models/user_business_struct.go
  4. +1
    -0
      options/locale/locale_en-US.ini
  5. +1
    -0
      options/locale/locale_zh-CN.ini
  6. +1
    -0
      routers/api/v1/api.go
  7. +23
    -14
      routers/repo/user_data_analysis.go
  8. +6
    -0
      web_src/js/components/UserAnalysis.vue

+ 1
- 0
models/models.go View File

@@ -157,6 +157,7 @@ func init() {
new(UserBusinessAnalysisCurrentMonth),
new(UserBusinessAnalysisCurrentWeek),
new(UserBusinessAnalysisYesterday),
new(UserBusinessAnalysisLastWeek),
new(UserLoginLog),
new(UserMetrics),
new(UserAnalysisPara),


+ 126
- 52
models/user_business_analysis.go View File

@@ -407,63 +407,132 @@ func QueryUserStaticDataAll(opts *UserBusinessAnalysisQueryOptions) ([]*UserBusi
return userBusinessAnalysisReturnList, allCount
}

func QueryUserStaticDataForUserDefine(opts *UserBusinessAnalysisQueryOptions) ([]*UserBusinessAnalysis, int64) {
log.Info("query startTime =" + fmt.Sprint(opts.StartTime) + " endTime=" + fmt.Sprint(opts.EndTime) + " isAll=" + fmt.Sprint(opts.IsAll))
statictisSess := xStatistic.NewSession()
defer statictisSess.Close()
var cond = builder.NewCond()
cond = cond.And(
builder.Gte{"count_date": opts.StartTime},
)
cond = cond.And(
builder.Lte{"count_date": opts.EndTime},
)
count, err := statictisSess.Where(cond).Count(new(UserBusinessAnalysis))
func QueryUserStaticDataForUserDefine(opts *UserBusinessAnalysisQueryOptions, wikiCountMap map[string]int) ([]*UserBusinessAnalysis, int64) {
log.Info("start to count other user info data")
sess := x.NewSession()
defer sess.Close()

currentTimeNow := time.Now()
log.Info("current time:" + currentTimeNow.Format("2006-01-02 15:04:05"))

start_unix := opts.StartTime

end_unix := opts.EndTime
CountDate := time.Date(currentTimeNow.Year(), currentTimeNow.Month(), currentTimeNow.Day(), 0, 1, 0, 0, currentTimeNow.Location())

CodeMergeCountMap := queryPullRequest(start_unix, end_unix)
CommitCountMap := queryCommitAction(start_unix, end_unix, 5)
IssueCountMap := queryCreateIssue(start_unix, end_unix)

CommentCountMap := queryComment(start_unix, end_unix)
FocusRepoCountMap := queryWatch(start_unix, end_unix)
StarRepoCountMap := queryStar(start_unix, end_unix)
WatchedCountMap, WatchOtherMap := queryFollow(start_unix, end_unix)

CommitCodeSizeMap, err := GetAllUserKPIStats()
if err != nil {
log.Info("query error." + err.Error())
return nil, 0
log.Info("query commit code errr.")
} else {
log.Info("query commit code size, len=" + fmt.Sprint(len(CommitCodeSizeMap)))
CommitCodeSizeMapJson, _ := json.Marshal(CommitCodeSizeMap)
log.Info("CommitCodeSizeMapJson=" + string(CommitCodeSizeMapJson))
}
resultMap := make(map[int64]*UserBusinessAnalysis)
if count > 0 {
pageSize := 1000
totalPage := int(count) / pageSize
for i := 0; i <= int(totalPage); i++ {
userBusinessAnalysisList := make([]*UserBusinessAnalysis, 0)
if err := statictisSess.Table("user_business_analysis").Where(cond).OrderBy("count_date desc").Limit(pageSize, i*pageSize).
Find(&userBusinessAnalysisList); err != nil {
return nil, 0
CommitDatasetSizeMap, CommitDatasetNumMap := queryDatasetSize(start_unix, end_unix)
SolveIssueCountMap := querySolveIssue(start_unix, end_unix)
CreateRepoCountMap := queryUserCreateRepo(start_unix, end_unix)
LoginCountMap := queryLoginCount(start_unix, end_unix)
OpenIIndexMap := queryUserRepoOpenIIndex(start_unix, end_unix)
CloudBrainTaskMap, CloudBrainTaskItemMap := queryCloudBrainTask(start_unix, end_unix)
AiModelManageMap := queryUserModel(start_unix, end_unix)

CollectDataset, CollectedDataset := queryDatasetStars(start_unix, end_unix)
RecommendDataset := queryRecommedDataSet(start_unix, end_unix)
CollectImage, CollectedImage := queryImageStars(start_unix, end_unix)
RecommendImage := queryRecommedImage(start_unix, end_unix)

statictisSess := xStatistic.NewSession()
defer statictisSess.Close()

cond := "type != 1 and and is_active=true"
count, err := sess.Where(cond).Count(new(User))

ParaWeight := getParaWeight()
ResultList := make([]*UserBusinessAnalysis, 0)
var indexTotal int64
indexTotal = 0
for {
sess.Select("`user`.*").Table("user").Where(cond).OrderBy("id asc").Limit(PAGE_SIZE, int(indexTotal))
userList := make([]*User, 0)
sess.Find(&userList)

for i, userRecord := range userList {
var dateRecord UserBusinessAnalysis
dateRecord.ID = userRecord.ID
log.Info("i=" + fmt.Sprint(i) + " userName=" + userRecord.Name)
dateRecord.CountDate = CountDate.Unix()

dateRecord.Email = userRecord.Email
dateRecord.RegistDate = userRecord.CreatedUnix
dateRecord.Name = userRecord.Name
dateRecord.GiteaAgeMonth = subMonth(currentTimeNow, userRecord.CreatedUnix.AsTime())

dateRecord.CodeMergeCount = getMapValue(dateRecord.ID, CodeMergeCountMap)
dateRecord.CommitCount = getMapValue(dateRecord.ID, CommitCountMap)
dateRecord.IssueCount = getMapValue(dateRecord.ID, IssueCountMap)
dateRecord.CommentCount = getMapValue(dateRecord.ID, CommentCountMap)
dateRecord.FocusRepoCount = getMapValue(dateRecord.ID, FocusRepoCountMap)
dateRecord.StarRepoCount = getMapValue(dateRecord.ID, StarRepoCountMap)
dateRecord.WatchedCount = getMapValue(dateRecord.ID, WatchedCountMap)
dateRecord.FocusOtherUser = getMapValue(dateRecord.ID, WatchOtherMap)
if _, ok := CommitCodeSizeMap[dateRecord.Email]; !ok {
dateRecord.CommitCodeSize = 0
} else {
dateRecord.CommitCodeSize = int(CommitCodeSizeMap[dateRecord.Email].CommitLines)
}
log.Info("query result size=" + fmt.Sprint(len(userBusinessAnalysisList)))
for _, userRecord := range userBusinessAnalysisList {
if _, ok := resultMap[userRecord.ID]; !ok {
resultMap[userRecord.ID] = userRecord
} else {
resultMap[userRecord.ID].CodeMergeCount += userRecord.CodeMergeCount
resultMap[userRecord.ID].CommitCount += userRecord.CommitCount
resultMap[userRecord.ID].IssueCount += userRecord.IssueCount
resultMap[userRecord.ID].CommentCount += userRecord.CommentCount
resultMap[userRecord.ID].FocusRepoCount += userRecord.FocusRepoCount
resultMap[userRecord.ID].StarRepoCount += userRecord.StarRepoCount
resultMap[userRecord.ID].WatchedCount += userRecord.WatchedCount
resultMap[userRecord.ID].CommitCodeSize += userRecord.CommitCodeSize
resultMap[userRecord.ID].CommitDatasetSize += userRecord.CommitDatasetSize
resultMap[userRecord.ID].CommitDatasetNum += userRecord.CommitDatasetNum
resultMap[userRecord.ID].CommitModelCount += userRecord.CommitModelCount
resultMap[userRecord.ID].SolveIssueCount += userRecord.SolveIssueCount
resultMap[userRecord.ID].EncyclopediasCount += userRecord.EncyclopediasCount
resultMap[userRecord.ID].CreateRepoCount += userRecord.CreateRepoCount
resultMap[userRecord.ID].LoginCount += userRecord.LoginCount
}
dateRecord.CommitDatasetSize = getMapValue(dateRecord.ID, CommitDatasetSizeMap)
dateRecord.CommitDatasetNum = getMapValue(dateRecord.ID, CommitDatasetNumMap)
dateRecord.SolveIssueCount = getMapValue(dateRecord.ID, SolveIssueCountMap)

dateRecord.EncyclopediasCount = getMapKeyStringValue(dateRecord.Name, wikiCountMap)

dateRecord.CreateRepoCount = getMapValue(dateRecord.ID, CreateRepoCountMap)

dateRecord.LoginCount = getMapValue(dateRecord.ID, LoginCountMap)

if _, ok := OpenIIndexMap[dateRecord.ID]; !ok {
dateRecord.OpenIIndex = 0
} else {
dateRecord.OpenIIndex = OpenIIndexMap[dateRecord.ID]
}

dateRecord.CloudBrainTaskNum = getMapValue(dateRecord.ID, CloudBrainTaskMap)
dateRecord.GpuDebugJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_GpuDebugJob", CloudBrainTaskItemMap)
dateRecord.NpuDebugJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_NpuDebugJob", CloudBrainTaskItemMap)
dateRecord.GpuTrainJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_GpuTrainJob", CloudBrainTaskItemMap)
dateRecord.NpuTrainJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_NpuTrainJob", CloudBrainTaskItemMap)
dateRecord.NpuInferenceJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_NpuInferenceJob", CloudBrainTaskItemMap)
dateRecord.GpuBenchMarkJob = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_GpuBenchMarkJob", CloudBrainTaskItemMap)
dateRecord.CloudBrainRunTime = getMapKeyStringValue(fmt.Sprint(dateRecord.ID)+"_CloudBrainRunTime", CloudBrainTaskItemMap)
dateRecord.CommitModelCount = getMapValue(dateRecord.ID, AiModelManageMap)

dateRecord.CollectDataset = getMapValue(dateRecord.ID, CollectDataset)
dateRecord.CollectedDataset = getMapValue(dateRecord.ID, CollectedDataset)
dateRecord.RecommendDataset = getMapValue(dateRecord.ID, RecommendDataset)
dateRecord.CollectImage = getMapValue(dateRecord.ID, CollectImage)
dateRecord.CollectedImage = getMapValue(dateRecord.ID, CollectedImage)
dateRecord.RecommendImage = getMapValue(dateRecord.ID, RecommendImage)

dateRecord.UserIndexPrimitive = getUserIndex(dateRecord, ParaWeight)
ResultList = append(ResultList, &dateRecord)
}

indexTotal += PAGE_SIZE
if indexTotal >= count {
break
}
}
userBusinessAnalysisReturnList := UserBusinessAnalysisList{}
for _, v := range resultMap {
userBusinessAnalysisReturnList = append(userBusinessAnalysisReturnList, v)
}
sort.Sort(userBusinessAnalysisReturnList)
log.Info("return size=" + fmt.Sprint(len(userBusinessAnalysisReturnList)))
return userBusinessAnalysisReturnList, count

return ResultList, int64(len(ResultList))
}

func QueryUserStaticDataPage(opts *UserBusinessAnalysisQueryOptions) ([]*UserBusinessAnalysis, int64) {
@@ -792,7 +861,12 @@ func RefreshUserStaticAllTabel(wikiCountMap map[string]int, userMetrics map[stri
pageStartTime = time.Date(currentTimeNow.Year(), currentTimeNow.Month(), currentTimeNow.Day(), 0, 0, 0, 0, time.Local).AddDate(0, 0, offset)
refreshUserStaticTable(wikiCountMap, "user_business_analysis_current_week", pageStartTime, pageEndTime, userMetrics)

pageEndTime = pageStartTime
pageStartTime = pageStartTime.AddDate(0, 0, -7)
refreshUserStaticTable(wikiCountMap, "user_business_analysis_last_week", pageStartTime, pageEndTime, userMetrics)

pageStartTime = time.Date(currentTimeNow.Year(), currentTimeNow.Month(), currentTimeNow.Day(), 0, 0, 0, 0, time.Local).AddDate(0, 0, -30)
pageEndTime = time.Date(currentTimeNow.Year(), currentTimeNow.Month(), currentTimeNow.Day(), 23, 59, 59, 0, currentTimeNow.Location())
refreshUserStaticTable(wikiCountMap, "user_business_analysis_last30_day", pageStartTime, pageEndTime, userMetrics)

pageStartTime = time.Date(currentTimeNow.Year(), currentTimeNow.Month(), currentTimeNow.Day(), 0, 0, 0, 0, time.Local).AddDate(0, 0, -1)
@@ -937,7 +1011,7 @@ func CounDataByDateAndReCount(wikiCountMap map[string]int, startTime time.Time,
log.Info("has activity." + userRecord.Name)
addUserToMap(userNewAddActivity, userRecord.CreatedUnix, dateRecord.ID)
}
if userRecord.IsActive {
if !userRecord.IsActive {
continue
}
statictisSess.Delete(&dateRecord)


+ 66
- 0
models/user_business_struct.go View File

@@ -394,6 +394,72 @@ type UserBusinessAnalysisYesterday struct {
RecommendImage int `xorm:"NOT NULL DEFAULT 0"`
}

type UserBusinessAnalysisLastWeek struct {
ID int64 `xorm:"pk"`
CountDate int64 `xorm:"pk"`
//action :ActionMergePullRequest // 11
CodeMergeCount int `xorm:"NOT NULL DEFAULT 0"`
//action :ActionCommitRepo
CommitCount int `xorm:"NOT NULL DEFAULT 0"`
//issue // 10
IssueCount int `xorm:"NOT NULL DEFAULT 0"`
//comment table current date
CommentCount int `xorm:"NOT NULL DEFAULT 0"`
//watch table current date
FocusRepoCount int `xorm:"NOT NULL DEFAULT 0"`
//star table current date
StarRepoCount int `xorm:"NOT NULL DEFAULT 0"`
//follow table
WatchedCount int `xorm:"NOT NULL DEFAULT 0"`
// user table
GiteaAgeMonth int `xorm:"NOT NULL DEFAULT 0"`
//
CommitCodeSize int `xorm:"NOT NULL DEFAULT 0"`
//attachement table
CommitDatasetSize int `xorm:"NOT NULL DEFAULT 0"`
//0
CommitModelCount int `xorm:"NOT NULL DEFAULT 0"`
//issue, issueassignees
SolveIssueCount int `xorm:"NOT NULL DEFAULT 0"`
//baike
EncyclopediasCount int `xorm:"NOT NULL DEFAULT 0"`
//user
RegistDate timeutil.TimeStamp `xorm:"NOT NULL"`
//repo
CreateRepoCount int `xorm:"NOT NULL DEFAULT 0"`
//login count, from elk
LoginCount int `xorm:"NOT NULL DEFAULT 0"`
//openi index
OpenIIndex float64 `xorm:"NOT NULL DEFAULT 0"`
//user
Email string `xorm:"NOT NULL"`
//user
Name string `xorm:"NOT NULL"`
DataDate string `xorm:"NULL"`

CloudBrainTaskNum int `xorm:"NOT NULL DEFAULT 0"`
GpuDebugJob int `xorm:"NOT NULL DEFAULT 0"`
NpuDebugJob int `xorm:"NOT NULL DEFAULT 0"`
GpuTrainJob int `xorm:"NOT NULL DEFAULT 0"`
NpuTrainJob int `xorm:"NOT NULL DEFAULT 0"`
NpuInferenceJob int `xorm:"NOT NULL DEFAULT 0"`
GpuBenchMarkJob int `xorm:"NOT NULL DEFAULT 0"`
CloudBrainRunTime int `xorm:"NOT NULL DEFAULT 0"`
CommitDatasetNum int `xorm:"NOT NULL DEFAULT 0"`
UserIndex float64 `xorm:"NOT NULL DEFAULT 0"`
UserIndexPrimitive float64 `xorm:"NOT NULL DEFAULT 0"`

UserLocation string `xorm:"NULL"`

FocusOtherUser int `xorm:"NOT NULL DEFAULT 0"`
CollectDataset int `xorm:"NOT NULL DEFAULT 0"`
CollectedDataset int `xorm:"NOT NULL DEFAULT 0"`
RecommendDataset int `xorm:"NOT NULL DEFAULT 0"`
CollectImage int `xorm:"NOT NULL DEFAULT 0"`
CollectedImage int `xorm:"NOT NULL DEFAULT 0"`
RecommendImage int `xorm:"NOT NULL DEFAULT 0"`
}

type UserAnalysisPara struct {
Key string `xorm:"NOT NULL"`
Value float64 `xorm:"NOT NULL DEFAULT 0"`


+ 1
- 0
options/locale/locale_en-US.ini View File

@@ -522,6 +522,7 @@ static.RecommendImage=Recommended Image Count
static.all=All
static.public.user_business_analysis_current_month=Current_Month
static.public.user_business_analysis_current_week=Current_Week
static.public.user_business_analysis_last_week=Last_Week
static.public.user_business_analysis_current_year=Current_Year
static.public.user_business_analysis_last30_day=Last_30_day
static.public.user_business_analysis_last_month=Last_Month


+ 1
- 0
options/locale/locale_zh-CN.ini View File

@@ -527,6 +527,7 @@ static.RecommendImage=被推荐镜像数
static.all=所有
static.public.user_business_analysis_current_month=本月
static.public.user_business_analysis_current_week=本周
static.public.user_business_analysis_last_week=上周
static.public.user_business_analysis_current_year=今年
static.public.user_business_analysis_last30_day=近30天
static.public.user_business_analysis_last_month=上月


+ 1
- 0
routers/api/v1/api.go View File

@@ -564,6 +564,7 @@ func RegisterRoutes(m *macaron.Macaron) {
m.Get("/query_user_static_page", operationReq, repo_ext.QueryUserStaticDataPage)
m.Get("/query_user_current_month", operationReq, repo_ext.QueryUserStaticCurrentMonth)
m.Get("/query_user_current_week", operationReq, repo_ext.QueryUserStaticCurrentWeek)
m.Get("/query_user_last_week", operationReq, repo_ext.QueryUserStaticCurrentWeek)
m.Get("/query_user_current_year", operationReq, repo_ext.QueryUserStaticCurrentYear)
m.Get("/query_user_last30_day", operationReq, repo_ext.QueryUserStaticLast30Day)
m.Get("/query_user_last_month", operationReq, repo_ext.QueryUserStaticLastMonth)


+ 23
- 14
routers/repo/user_data_analysis.go View File

@@ -455,6 +455,10 @@ func QueryUserMetricsCurrentWeek(ctx *context.Context) {
func QueryUserStaticCurrentWeek(ctx *context.Context) {
queryUserDataPage(ctx, "public.user_business_analysis_current_week", new(models.UserBusinessAnalysisCurrentWeek))
}
func QueryUserStaticLastWeek(ctx *context.Context) {
queryUserDataPage(ctx, "public.user_business_analysis_last_week", new(models.UserBusinessAnalysisLastWeek))
}

func QueryUserMetricsCurrentYear(ctx *context.Context) {
currentTimeNow := time.Now()
pageStartTime := time.Date(currentTimeNow.Year(), 1, 1, 0, 0, 0, 0, currentTimeNow.Location())
@@ -572,7 +576,8 @@ func QueryUserStaticDataPage(ctx *context.Context) {

if IsReturnFile {
//re, count := models.QueryUserStaticDataAll(pageOpts)
re, count := models.QueryUserStaticDataForUserDefine(pageOpts)
wikiMap, _ := queryWikiCountMap(startTime, endTime)
re, count := models.QueryUserStaticDataForUserDefine(pageOpts, wikiMap)
sheetName := ctx.Tr("user.static.sheetname")
filename := sheetName + "_" + startDate + "_" + endDate + ".xlsx"
os.Remove(setting.AppDataPath + Excel_File_Path + filename)
@@ -620,22 +625,14 @@ func writeFileToDisk(ctx *context.Context, count int64, re []*models.UserBusines
}
}

func TimingCountDataByDateAndReCount(date string, isReCount bool) {

t, _ := time.Parse("2006-01-02", date)
startTime := time.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, t.Location())

endTime := time.Date(t.Year(), t.Month(), t.Day(), 23, 59, 59, 0, t.Location())

//query wiki data
log.Info("start to time count data")
func queryWikiCountMap(startTime time.Time, endTime time.Time) (map[string]int, error) {
wikiMap := make(map[string]int)
warnEmailMessage := "用户统计信息入库失败,请尽快定位。"
repoList, err := models.GetAllRepositories()
if err != nil {
log.Error("query repo error." + err.Error())
mailer.SendWarnNotifyMail(setting.Warn_Notify_Mails, warnEmailMessage)
return
return nil, err
}
log.Info("start to query wiki data")
for _, repoRecord := range repoList {
@@ -643,7 +640,7 @@ func TimingCountDataByDateAndReCount(date string, isReCount bool) {
time, err := git.GetLatestCommitTime(wikiPath)
if err == nil {
log.Info("last commit time:" + time.Format("2006-01-02 15:04:05") + " wikiPath=" + wikiPath)
if time.After(startTime) {
if time.After(startTime) && time.Before(endTime) {
wikiRepo, _, err := FindWikiRepoCommitByWikiPath(wikiPath)
if err != nil {
log.Error("wiki not exist. wikiPath=" + wikiPath)
@@ -668,14 +665,26 @@ func TimingCountDataByDateAndReCount(date string, isReCount bool) {
}
}
}
return wikiMap, nil
}

func TimingCountDataByDateAndReCount(date string, isReCount bool) {

t, _ := time.Parse("2006-01-02", date)
startTime := time.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, t.Location())

endTime := time.Date(t.Year(), t.Month(), t.Day(), 23, 59, 59, 0, t.Location())
warnEmailMessage := "用户统计信息入库失败,请尽快定位。"
//query wiki data
log.Info("start to time count data")
wikiMap, err := queryWikiCountMap(startTime, endTime)
//other user info data
err = models.CounDataByDateAndReCount(wikiMap, startTime, endTime, isReCount)
if err != nil {
log.Error("count user info error." + err.Error())
mailer.SendWarnNotifyMail(setting.Warn_Notify_Mails, warnEmailMessage)
}
log.Info("start to count all user info data")
//models.RefreshUserStaticAllTabel(wikiMap)

log.Info("end to count all user info data")
}



+ 6
- 0
web_src/js/components/UserAnalysis.vue View File

@@ -7,6 +7,7 @@
<span class="sta_iterm">统计周期:</span>
<button type="button" class='btnFirst' id ="yesterday_usr" v-bind:class="{colorChange:1==dynamic}" @click="resetPage(),getUserList('yesterday_usr',1)">昨天</button>
<button type="button" class='btn' id = "current_week_usr" v-bind:class="{colorChange:2==dynamic}" @click="resetPage(),getUserList('current_week_usr',2)">本周</button>
<button type="button" class='btn' id = "last_week_usr" v-bind:class="{colorChange:2==dynamic}" @click="resetPage(),getUserList('current_week_usr',8)">上周</button>
<button type="button" class='btn' id = "current_month_usr" v-bind:class="{colorChange:3==dynamic}" @click="resetPage(),getUserList('current_month_usr',3)">本月</button>
<button type="button" class='btn' id = "last_month_usr" v-bind:class="{colorChange:4==dynamic}" @click="resetPage(),getUserList('last_month_usr',4)">上月</button>
<button type="button" class='btn' id = "monthly_usr" v-bind:class="{colorChange:5==dynamic}" @click="resetPage(),getUserList('monthly_usr',5)">近30天</button>
@@ -375,6 +376,11 @@
this.dataUrl = '../../api/v1/query_user_current_week';
break
}
case "last_week_usr":{
this.value_time=[]
this.dataUrl = '../../api/v1/query_user_last_week';
break
}
case "current_month_usr":{
this.value_time=[]
this.dataUrl = '../../api/v1/query_user_current_month';


Loading…
Cancel
Save