mirror of
https://github.com/goharbor/harbor.git
synced 2024-11-23 18:55:18 +01:00
Merge branch 'new-ui-with-sync-image' of https://github.com/vmware/harbor into new-ui-with-sync-image
This commit is contained in:
commit
d5dc67a166
@ -18,7 +18,7 @@ package api
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
"strings"
|
||||
"regexp"
|
||||
|
||||
"github.com/vmware/harbor/dao"
|
||||
"github.com/vmware/harbor/models"
|
||||
@ -285,19 +285,13 @@ func isProjectAdmin(userID int, pid int64) bool {
|
||||
|
||||
func validateProjectReq(req projectReq) error {
|
||||
pn := req.ProjectName
|
||||
if len(pn) == 0 {
|
||||
return fmt.Errorf("Project name can not be empty")
|
||||
}
|
||||
if isIllegalLength(req.ProjectName, projectNameMinLen, projectNameMaxLen) {
|
||||
return fmt.Errorf("project name is illegal in length. (greater than 4 or less than 30)")
|
||||
return fmt.Errorf("Project name is illegal in length. (greater than 4 or less than 30)")
|
||||
}
|
||||
if isContainIllegalChar(req.ProjectName, []string{"~", "-", "$", "\\", "[", "]", "{", "}", "(", ")", "&", "^", "%", "*", "<", ">", "\"", "'", "/", "?", "@"}) {
|
||||
return fmt.Errorf("project name contains illegal characters")
|
||||
validProjectName := regexp.MustCompile(`^[a-z0-9](?:-*[a-z0-9])*(?:[._][a-z0-9](?:-*[a-z0-9])*)*$`)
|
||||
legal := validProjectName.MatchString(pn)
|
||||
if !legal {
|
||||
return fmt.Errorf("Project name is not in lower case or contains illegal characters!")
|
||||
}
|
||||
|
||||
if pn != strings.ToLower(pn) {
|
||||
return fmt.Errorf("project name must be in lower case")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
@ -59,7 +59,7 @@ func (cc *CommonController) SendEmail() {
|
||||
cc.CustomAbort(http.StatusInternalServerError, "Internal error.")
|
||||
}
|
||||
err = messageTemplate.Execute(message, messageDetail{
|
||||
Hint: cc.Tr("reset_email_hint"),
|
||||
Hint: cc.Tr("Warning: You're receiving this because you're requesting for changing password in Harbor, if it is not your operation, please ignore; otherwise, please click the link below"),
|
||||
URL: harborURL,
|
||||
UUID: uuid,
|
||||
})
|
||||
|
@ -150,14 +150,44 @@ func GetRecentLogs(userID, linesNum int, startTime, endTime string) ([]models.Ac
|
||||
func GetTopRepos(countNum int) ([]models.TopRepo, error) {
|
||||
|
||||
o := GetOrmer()
|
||||
|
||||
sql := "select repo_name, COUNT(repo_name) as access_count from access_log left join project on access_log.project_id=project.project_id where project.public = 1 and access_log.operation = 'pull' group by repo_name order by access_count desc limit ? "
|
||||
queryParam := make([]interface{}, 1)
|
||||
// hide the where condition: project.public = 1, Can add to the sql when necessary.
|
||||
sql := "select repo_name, COUNT(repo_name) as access_count from access_log left join project on access_log.project_id=project.project_id where access_log.operation = 'pull' group by repo_name order by access_count desc limit ? "
|
||||
queryParam := []interface{}{}
|
||||
queryParam = append(queryParam, countNum)
|
||||
var lists []models.TopRepo
|
||||
_, err := o.Raw(sql, queryParam).QueryRows(&lists)
|
||||
var list []models.TopRepo
|
||||
_, err := o.Raw(sql, queryParam).QueryRows(&list)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return lists, nil
|
||||
if len(list) == 0 {
|
||||
return list, nil
|
||||
}
|
||||
placeHolder := make([]string, len(list))
|
||||
repos := make([]string, len(list))
|
||||
for i, v := range list {
|
||||
repos[i] = v.RepoName
|
||||
placeHolder[i] = "?"
|
||||
}
|
||||
placeHolderStr := strings.Join(placeHolder, ",")
|
||||
queryParam = nil
|
||||
queryParam = append(queryParam, repos)
|
||||
var usrnameList []models.TopRepo
|
||||
sql = `select a.username as creator, a.repo_name from (select access_log.repo_name, user.username,
|
||||
access_log.op_time from user left join access_log on user.user_id = access_log.user_id where
|
||||
access_log.operation = 'push' and access_log.repo_name in (######) order by access_log.repo_name,
|
||||
access_log.op_time ASC) a group by a.repo_name`
|
||||
sql = strings.Replace(sql, "######", placeHolderStr, 1)
|
||||
_, err = o.Raw(sql, queryParam).QueryRows(&usrnameList)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
for i := 0; i < len(list); i++ {
|
||||
for _, v := range usrnameList {
|
||||
if v.RepoName == list[i].RepoName {
|
||||
list[i].Creator = v.Creator
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
return list, nil
|
||||
}
|
||||
|
@ -19,4 +19,5 @@ package models
|
||||
type TopRepo struct {
|
||||
RepoName string `json:"name"`
|
||||
AccessCount int64 `json:"count"`
|
||||
Creator string `json:"creator"`
|
||||
}
|
||||
|
@ -81,8 +81,7 @@ func initRouters() {
|
||||
beego.Router("/api/targets/ping", &api.TargetAPI{}, "post:Ping")
|
||||
beego.Router("/api/users/:id/sysadmin", &api.UserAPI{}, "put:ToggleUserAdminRole")
|
||||
beego.Router("/api/repositories/top", &api.RepositoryAPI{}, "get:GetTopRepos")
|
||||
beego.Router("api/logs", &api.LogAPI{})
|
||||
|
||||
beego.Router("/api/logs", &api.LogAPI{})
|
||||
//external service that hosted on harbor process:
|
||||
beego.Router("/service/notifications", &service.NotificationHandler{})
|
||||
beego.Router("/service/token", &token.Handler{})
|
||||
|
Loading…
Reference in New Issue
Block a user