From 9268dd7ba76df972e6b2d6958d27706d9a1b100c Mon Sep 17 00:00:00 2001 From: zouap Date: Thu, 30 Sep 2021 16:49:40 +0800 Subject: [PATCH] =?UTF-8?q?=E6=8F=90=E4=BA=A4=E4=BB=A3=E7=A0=81=EF=BC=8C?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E7=94=A8=E6=88=B7=E7=BB=9F=E8=AE=A1=E6=95=B0?= =?UTF-8?q?=E6=8D=AE?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: zouap --- models/attachment.go | 1 - models/repo_watch.go | 9 +- models/star.go | 7 +- models/user_business_analysis.go | 194 ++++++++++++++++++++++++++++++++++++- models/user_follow.go | 7 +- routers/repo/attachment.go | 2 + routers/repo/user_data_analysis.go | 66 +++++++++++++ routers/repo/wiki.go | 15 +++ 8 files changed, 288 insertions(+), 13 deletions(-) create mode 100644 routers/repo/user_data_analysis.go diff --git a/models/attachment.go b/models/attachment.go index 35292b0bd..418d7c881 100755 --- a/models/attachment.go +++ b/models/attachment.go @@ -284,7 +284,6 @@ func DeleteAttachments(attachments []*Attachment, remove bool) (int, error) { */ } } - countData() return int(cnt), nil } diff --git a/models/repo_watch.go b/models/repo_watch.go index 11cfa8891..6bdef9c7f 100644 --- a/models/repo_watch.go +++ b/models/repo_watch.go @@ -26,10 +26,11 @@ const ( // Watch is connection request for receiving repository notification. type Watch struct { - ID int64 `xorm:"pk autoincr"` - UserID int64 `xorm:"UNIQUE(watch)"` - RepoID int64 `xorm:"UNIQUE(watch)"` - Mode RepoWatchMode `xorm:"SMALLINT NOT NULL DEFAULT 1"` + ID int64 `xorm:"pk autoincr"` + UserID int64 `xorm:"UNIQUE(watch)"` + RepoID int64 `xorm:"UNIQUE(watch)"` + Mode RepoWatchMode `xorm:"SMALLINT NOT NULL DEFAULT 1"` + CreatedUnix int64 `xorm:"created"` } // getWatch gets what kind of subscription a user has on a given repository; returns dummy record if none found diff --git a/models/star.go b/models/star.go index 4e84a6e4d..bb3c4329b 100644 --- a/models/star.go +++ b/models/star.go @@ -6,9 +6,10 @@ package models // Star represents a starred repo by an user. type Star struct { - ID int64 `xorm:"pk autoincr"` - UID int64 `xorm:"UNIQUE(s)"` - RepoID int64 `xorm:"UNIQUE(s)"` + ID int64 `xorm:"pk autoincr"` + UID int64 `xorm:"UNIQUE(s)"` + RepoID int64 `xorm:"UNIQUE(s)"` + CreatedUnix int64 `xorm:"created"` } // StarRepo or unstar repository. diff --git a/models/user_business_analysis.go b/models/user_business_analysis.go index 0bbb05c55..bbb409d00 100644 --- a/models/user_business_analysis.go +++ b/models/user_business_analysis.go @@ -62,7 +62,7 @@ type UserBusinessAnalysis struct { Name string `xorm:"NOT NULL"` } -func countData() { +func CountData(wikiCountMap map[int64]int) { log.Info("start to count data") sess := x.NewSession() defer sess.Close() @@ -88,6 +88,12 @@ func countData() { CommitCountMap := queryAction(start_unix, end_unix, 5) IssueCountMap := queryAction(start_unix, end_unix, 10) + CommentCountMap := queryComment(start_unix, end_unix) + FocusRepoCountMap := queryWatch(start_unix, end_unix) + StarRepoCountMap := queryStar(start_unix, end_unix) + WatchedCountMap := queryFollow(start_unix, end_unix) + CommitDatasetSizeMap := queryDatasetSize(start_unix, end_unix) + for i, userRecord := range userList { var dateRecord UserBusinessAnalysis dateRecord.ID = userRecord.ID @@ -96,7 +102,7 @@ func countData() { dateRecord.Email = userRecord.Email dateRecord.RegistDate = userRecord.CreatedUnix dateRecord.Name = userRecord.Name - + dateRecord.GiteaAgeMonth = subMonth(currentTimeNow, userRecord.CreatedUnix.AsTime()) if _, ok := CodeMergeCountMap[dateRecord.ID]; !ok { dateRecord.CodeMergeCount = 0 } else { @@ -115,11 +121,65 @@ func countData() { dateRecord.IssueCount = IssueCountMap[dateRecord.ID] } + if _, ok := CommentCountMap[dateRecord.ID]; !ok { + dateRecord.CommentCount = 0 + } else { + dateRecord.CommentCount = CommentCountMap[dateRecord.ID] + } + + if _, ok := FocusRepoCountMap[dateRecord.ID]; !ok { + dateRecord.FocusRepoCount = 0 + } else { + dateRecord.FocusRepoCount = FocusRepoCountMap[dateRecord.ID] + } + + if _, ok := StarRepoCountMap[dateRecord.ID]; !ok { + dateRecord.StarRepoCount = 0 + } else { + dateRecord.StarRepoCount = StarRepoCountMap[dateRecord.ID] + } + + if _, ok := WatchedCountMap[dateRecord.ID]; !ok { + dateRecord.WatchedCount = 0 + } else { + dateRecord.WatchedCount = WatchedCountMap[dateRecord.ID] + } + + if _, ok := CommitDatasetSizeMap[dateRecord.ID]; !ok { + dateRecord.CommitDatasetSize = 0 + } else { + dateRecord.CommitDatasetSize = CommitDatasetSizeMap[dateRecord.ID] + } + + dateRecord.CommitModelCount = 0 + sess.Insert(&dateRecord) } } +func querySolveIssue(start_unix int64, end_unix int64) map[int64]int { + //select issue_assignees.* from issue_assignees,issue where issue.is_closed=true and issue.id=issue_assignees.issue_id + sess := x.NewSession() + defer sess.Close() + sess.Select("issue_assignees.*").Table("issue_assignees"). + Join("inner", "issue", "issue.id=issue_assignees.issue_id"). + Where("issue.is_closed=true and issue.closed_unix>=" + fmt.Sprint(start_unix) + " and issue.closed_unix<=" + fmt.Sprint(end_unix)) + issueAssigneesList := make([]*IssueAssignees, 0) + sess.Find(&issueAssigneesList) + resultMap := make(map[int64]int) + log.Info("query IssueAssignees size=" + fmt.Sprint(len(issueAssigneesList))) + for _, issueAssigneesRecord := range issueAssigneesList { + if _, ok := resultMap[issueAssigneesRecord.AssigneeID]; !ok { + resultMap[issueAssigneesRecord.AssigneeID] = 1 + } else { + resultMap[issueAssigneesRecord.AssigneeID] += 1 + } + } + return resultMap + +} + func queryAction(start_unix int64, end_unix int64, actionType int64) map[int64]int { sess := x.NewSession() defer sess.Close() @@ -137,3 +197,133 @@ func queryAction(start_unix int64, end_unix int64, actionType int64) map[int64]i } return resultMap } + +func queryComment(start_unix int64, end_unix int64) map[int64]int { + + sess := x.NewSession() + defer sess.Close() + sess.Select("id,type,poster_id").Table("comment").Where(" created_unix>=" + fmt.Sprint(start_unix) + " and created_unix<=" + fmt.Sprint(end_unix)) + commentList := make([]*Comment, 0) + sess.Find(&commentList) + resultMap := make(map[int64]int) + log.Info("query Comment size=" + fmt.Sprint(len(commentList))) + for _, commentRecord := range commentList { + if _, ok := resultMap[commentRecord.PosterID]; !ok { + resultMap[commentRecord.PosterID] = 1 + } else { + resultMap[commentRecord.PosterID] += 1 + } + } + return resultMap +} + +func queryWatch(start_unix int64, end_unix int64) map[int64]int { + + sess := x.NewSession() + defer sess.Close() + sess.Select("id,user_id,repo_id").Table("watch").Where(" created_unix>=" + fmt.Sprint(start_unix) + " and created_unix<=" + fmt.Sprint(end_unix)) + watchList := make([]*Watch, 0) + sess.Find(&watchList) + resultMap := make(map[int64]int) + log.Info("query Watch size=" + fmt.Sprint(len(watchList))) + for _, watchRecord := range watchList { + if _, ok := resultMap[watchRecord.UserID]; !ok { + resultMap[watchRecord.UserID] = 1 + } else { + resultMap[watchRecord.UserID] += 1 + } + } + return resultMap + +} + +func queryStar(start_unix int64, end_unix int64) map[int64]int { + + sess := x.NewSession() + defer sess.Close() + sess.Select("id,uid,repo_id").Table("star").Where(" created_unix>=" + fmt.Sprint(start_unix) + " and created_unix<=" + fmt.Sprint(end_unix)) + starList := make([]*Star, 0) + sess.Find(&starList) + resultMap := make(map[int64]int) + log.Info("query Star size=" + fmt.Sprint(len(starList))) + for _, starRecord := range starList { + if _, ok := resultMap[starRecord.UID]; !ok { + resultMap[starRecord.UID] = 1 + } else { + resultMap[starRecord.UID] += 1 + } + } + return resultMap + +} + +func queryFollow(start_unix int64, end_unix int64) map[int64]int { + + sess := x.NewSession() + defer sess.Close() + sess.Select("id,user_id,follow_id").Table("follow").Where(" created_unix>=" + fmt.Sprint(start_unix) + " and created_unix<=" + fmt.Sprint(end_unix)) + followList := make([]*Follow, 0) + sess.Find(&followList) + resultMap := make(map[int64]int) + log.Info("query Follow size=" + fmt.Sprint(len(followList))) + for _, followRecord := range followList { + if _, ok := resultMap[followRecord.UserID]; !ok { + resultMap[followRecord.UserID] = 1 + } else { + resultMap[followRecord.UserID] += 1 + } + } + return resultMap +} + +func queryDatasetSize(start_unix int64, end_unix int64) map[int64]int { + sess := x.NewSession() + defer sess.Close() + sess.Select("id,uploader_id,size").Table("attachment").Where(" created_unix>=" + fmt.Sprint(start_unix) + " and created_unix<=" + fmt.Sprint(end_unix)) + attachmentList := make([]*Attachment, 0) + sess.Find(&attachmentList) + resultMap := make(map[int64]int) + log.Info("query Attachment size=" + fmt.Sprint(len(attachmentList))) + for _, attachRecord := range attachmentList { + if _, ok := resultMap[attachRecord.UploaderID]; !ok { + resultMap[attachRecord.UploaderID] = int(attachRecord.Size / (1024 * 1024)) //MB + } else { + resultMap[attachRecord.UploaderID] += int(attachRecord.Size / (1024 * 1024)) //MB + } + } + return resultMap + +} + +func subMonth(t1, t2 time.Time) (month int) { + y1 := t1.Year() + y2 := t2.Year() + m1 := int(t1.Month()) + m2 := int(t2.Month()) + d1 := t1.Day() + d2 := t2.Day() + + yearInterval := y1 - y2 + // 如果 d1的 月-日 小于 d2的 月-日 那么 yearInterval-- 这样就得到了相差的年数 + if m1 < m2 || m1 == m2 && d1 < d2 { + yearInterval-- + } + // 获取月数差值 + monthInterval := (m1 + 12) - m2 + if d1 < d2 { + monthInterval-- + } + monthInterval %= 12 + month = yearInterval*12 + monthInterval + return month +} + +func QueryAllRepo() []*Repository { + sess := x.NewSession() + defer sess.Close() + sess.Select("*").Table("repository") + repositoryList := make([]*Repository, 0) + sess.Find(&repositoryList) + + return repositoryList +} diff --git a/models/user_follow.go b/models/user_follow.go index 4bde71cb9..51997f681 100644 --- a/models/user_follow.go +++ b/models/user_follow.go @@ -6,9 +6,10 @@ package models // Follow represents relations of user and his/her followers. type Follow struct { - ID int64 `xorm:"pk autoincr"` - UserID int64 `xorm:"UNIQUE(follow)"` - FollowID int64 `xorm:"UNIQUE(follow)"` + ID int64 `xorm:"pk autoincr"` + UserID int64 `xorm:"UNIQUE(follow)"` + FollowID int64 `xorm:"UNIQUE(follow)"` + CreatedUnix int64 `xorm:"created"` } // IsFollowing returns true if user is following followID. diff --git a/routers/repo/attachment.go b/routers/repo/attachment.go index a8b2c8fbe..f71e3520e 100755 --- a/routers/repo/attachment.go +++ b/routers/repo/attachment.go @@ -146,6 +146,8 @@ func DeleteAttachment(ctx *context.Context) { DeleteAllUnzipFile(attach, "") + TimeingCountData() + _, err = models.DeleteFileChunkById(attach.UUID) if err != nil { ctx.Error(500, fmt.Sprintf("DeleteFileChunkById: %v", err)) diff --git a/routers/repo/user_data_analysis.go b/routers/repo/user_data_analysis.go new file mode 100644 index 000000000..de7e07d0d --- /dev/null +++ b/routers/repo/user_data_analysis.go @@ -0,0 +1,66 @@ +package repo + +import ( + "encoding/json" + + "code.gitea.io/gitea/models" + "code.gitea.io/gitea/modules/log" + wiki_service "code.gitea.io/gitea/services/wiki" +) + +func TimeingCountData() { + //query wiki data + log.Info("start to time count data") + wikiMap := make(map[int64]int) + + repoList := models.QueryAllRepo() + + for _, repoRecord := range repoList { + wikiPath := models.WikiPath(repoRecord.OwnerName, repoRecord.Name) + wikiRepo, commit, err := FindWikiRepoCommitByWikiPath(wikiPath) + if err != nil { + log.Error("query error.") + } else { + entries, err := commit.ListEntries() + if err != nil { + if wikiRepo != nil { + wikiRepo.Close() + } + } else { + pages := make([]PageMeta, 0, len(entries)) + for _, entry := range entries { + if !entry.IsRegular() { + continue + } + wikiName, err := wiki_service.FilenameToName(entry.Name()) + if err != nil { + if models.IsErrWikiInvalidFileName(err) { + continue + } + if wikiRepo != nil { + wikiRepo.Close() + } + } else if wikiName == "_Sidebar" || wikiName == "_Footer" { + continue + } + + jsonObj, err := json.Marshal(entry) + if err != nil { + log.Error("convert to json error.") + } else { + log.Info("json=" + string(jsonObj)) + } + + pages = append(pages, PageMeta{ + Name: wikiName, + SubURL: wiki_service.NameToSubURL(wikiName), + }) + } + + } + + } + } + + models.CountData(wikiMap) +} diff --git a/routers/repo/wiki.go b/routers/repo/wiki.go index 5da01f21a..03ab42036 100644 --- a/routers/repo/wiki.go +++ b/routers/repo/wiki.go @@ -82,6 +82,20 @@ func findEntryForFile(commit *git.Commit, target string) (*git.TreeEntry, error) return commit.GetTreeEntryByPath(unescapedTarget) } +func FindWikiRepoCommitByWikiPath(wikiPath string) (*git.Repository, *git.Commit, error) { + wikiRepo, err := git.OpenRepository(wikiPath) + if err != nil { + log.Info("get wiki error.") + return nil, nil, err + } + + commit, err := wikiRepo.GetBranchCommit("master") + if err != nil { + return wikiRepo, nil, err + } + return wikiRepo, commit, nil +} + func findWikiRepoCommit(ctx *context.Context) (*git.Repository, *git.Commit, error) { wikiRepo, err := git.OpenRepository(ctx.Repo.Repository.WikiPath()) if err != nil { @@ -150,6 +164,7 @@ func renderViewPage(ctx *context.Context) (*git.Repository, *git.TreeEntry) { if !entry.IsRegular() { continue } + wikiName, err := wiki_service.FilenameToName(entry.Name()) if err != nil { if models.IsErrWikiInvalidFileName(err) {