mirror of
https://github.com/goharbor/harbor
synced 2025-04-21 01:18:02 +00:00
Update creating project API to support proxy cache project
Update creating project API to support proxy cache project Signed-off-by: Wenkai Yin <yinw@vmware.com>
This commit is contained in:
parent
d5cce98d56
commit
a79bb127b3
|
@ -3766,6 +3766,10 @@ definitions:
|
||||||
type: integer
|
type: integer
|
||||||
format: int64
|
format: int64
|
||||||
description: The storage quota of the project.
|
description: The storage quota of the project.
|
||||||
|
registry_id:
|
||||||
|
type: integer
|
||||||
|
format: int64
|
||||||
|
description: The ID of referenced registry when creating the proxy cache project
|
||||||
Project:
|
Project:
|
||||||
type: object
|
type: object
|
||||||
properties:
|
properties:
|
||||||
|
@ -3780,6 +3784,10 @@ definitions:
|
||||||
name:
|
name:
|
||||||
type: string
|
type: string
|
||||||
description: The name of the project.
|
description: The name of the project.
|
||||||
|
registry_id:
|
||||||
|
type: integer
|
||||||
|
format: int64
|
||||||
|
description: The ID of referenced registry when the project is a proxy cache project.
|
||||||
creation_time:
|
creation_time:
|
||||||
type: string
|
type: string
|
||||||
description: The creation time of the project.
|
description: The creation time of the project.
|
||||||
|
|
1
make/migrations/postgresql/0040_2.1.0_schema.up.sql
Normal file
1
make/migrations/postgresql/0040_2.1.0_schema.up.sql
Normal file
|
@ -0,0 +1 @@
|
||||||
|
ALTER TABLE project ADD COLUMN IF NOT EXISTS registry_id int;
|
|
@ -27,11 +27,11 @@ import (
|
||||||
func AddProject(project models.Project) (int64, error) {
|
func AddProject(project models.Project) (int64, error) {
|
||||||
o := GetOrmer()
|
o := GetOrmer()
|
||||||
|
|
||||||
sql := "insert into project (owner_id, name, creation_time, update_time, deleted) values (?, ?, ?, ?, ?) RETURNING project_id"
|
sql := "insert into project (owner_id, name, registry_id, creation_time, update_time, deleted) values (?, ?, ?, ?, ?, ?) RETURNING project_id"
|
||||||
var projectID int64
|
var projectID int64
|
||||||
now := time.Now()
|
now := time.Now()
|
||||||
|
|
||||||
err := o.Raw(sql, project.OwnerID, project.Name, now, now, project.Deleted).QueryRow(&projectID)
|
err := o.Raw(sql, project.OwnerID, project.Name, project.RegistryID, now, now, project.Deleted).QueryRow(&projectID)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return 0, err
|
return 0, err
|
||||||
}
|
}
|
||||||
|
@ -78,7 +78,7 @@ func addProjectMember(member models.Member) (int, error) {
|
||||||
func GetProjectByID(id int64) (*models.Project, error) {
|
func GetProjectByID(id int64) (*models.Project, error) {
|
||||||
o := GetOrmer()
|
o := GetOrmer()
|
||||||
|
|
||||||
sql := `select p.project_id, p.name, u.username as owner_name, p.owner_id, p.creation_time, p.update_time
|
sql := `select p.project_id, p.name, p.registry_id, u.username as owner_name, p.owner_id, p.creation_time, p.update_time
|
||||||
from project p left join harbor_user u on p.owner_id = u.user_id where p.deleted = false and p.project_id = ?`
|
from project p left join harbor_user u on p.owner_id = u.user_id where p.deleted = false and p.project_id = ?`
|
||||||
queryParam := make([]interface{}, 1)
|
queryParam := make([]interface{}, 1)
|
||||||
queryParam = append(queryParam, id)
|
queryParam = append(queryParam, id)
|
||||||
|
@ -142,7 +142,7 @@ func GetTotalOfProjects(query *models.ProjectQueryParam) (int64, error) {
|
||||||
// GetProjects returns a project list according to the query conditions
|
// GetProjects returns a project list according to the query conditions
|
||||||
func GetProjects(query *models.ProjectQueryParam) ([]*models.Project, error) {
|
func GetProjects(query *models.ProjectQueryParam) ([]*models.Project, error) {
|
||||||
sqlStr, queryParam := projectQueryConditions(query)
|
sqlStr, queryParam := projectQueryConditions(query)
|
||||||
sqlStr = `select distinct p.project_id, p.name, p.owner_id,
|
sqlStr = `select distinct p.project_id, p.name, p.registry_id, p.owner_id,
|
||||||
p.creation_time, p.update_time ` + sqlStr + ` order by p.name`
|
p.creation_time, p.update_time ` + sqlStr + ` order by p.name`
|
||||||
sqlStr, queryParam = CreatePagination(query, sqlStr, queryParam)
|
sqlStr, queryParam = CreatePagination(query, sqlStr, queryParam)
|
||||||
|
|
||||||
|
@ -157,12 +157,12 @@ func GetProjects(query *models.ProjectQueryParam) ([]*models.Project, error) {
|
||||||
// and the user is in the group which is a group member of this project.
|
// and the user is in the group which is a group member of this project.
|
||||||
func GetGroupProjects(groupIDs []int, query *models.ProjectQueryParam) ([]*models.Project, error) {
|
func GetGroupProjects(groupIDs []int, query *models.ProjectQueryParam) ([]*models.Project, error) {
|
||||||
sql, params := projectQueryConditions(query)
|
sql, params := projectQueryConditions(query)
|
||||||
sql = `select distinct p.project_id, p.name, p.owner_id,
|
sql = `select distinct p.project_id, p.name, p.registry_id, p.owner_id,
|
||||||
p.creation_time, p.update_time ` + sql
|
p.creation_time, p.update_time ` + sql
|
||||||
groupIDCondition := JoinNumberConditions(groupIDs)
|
groupIDCondition := JoinNumberConditions(groupIDs)
|
||||||
if len(groupIDs) > 0 {
|
if len(groupIDs) > 0 {
|
||||||
sql = fmt.Sprintf(
|
sql = fmt.Sprintf(
|
||||||
`%s union select distinct p.project_id, p.name, p.owner_id, p.creation_time, p.update_time
|
`%s union select distinct p.project_id, p.name, p.registry_id, p.owner_id, p.creation_time, p.update_time
|
||||||
from project p
|
from project p
|
||||||
left join project_member pm on p.project_id = pm.project_id
|
left join project_member pm on p.project_id = pm.project_id
|
||||||
left join user_group ug on ug.id = pm.entity_id and pm.entity_type = 'g'
|
left join user_group ug on ug.id = pm.entity_id and pm.entity_type = 'g'
|
||||||
|
@ -237,6 +237,11 @@ func projectQueryConditions(query *models.ProjectQueryParam) (string, []interfac
|
||||||
params = append(params, "%"+Escape(query.Name)+"%")
|
params = append(params, "%"+Escape(query.Name)+"%")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if query.RegistryID > 0 {
|
||||||
|
sql += ` and p.registry_id = ?`
|
||||||
|
params = append(params, query.RegistryID)
|
||||||
|
}
|
||||||
|
|
||||||
if query.Member != nil && len(query.Member.Name) != 0 {
|
if query.Member != nil && len(query.Member.Name) != 0 {
|
||||||
sql += ` and u2.username=?`
|
sql += ` and u2.username=?`
|
||||||
params = append(params, query.Member.Name)
|
params = append(params, query.Member.Name)
|
||||||
|
|
|
@ -45,6 +45,7 @@ type Project struct {
|
||||||
ChartCount uint64 `orm:"-" json:"chart_count"`
|
ChartCount uint64 `orm:"-" json:"chart_count"`
|
||||||
Metadata map[string]string `orm:"-" json:"metadata"`
|
Metadata map[string]string `orm:"-" json:"metadata"`
|
||||||
CVEWhitelist CVEWhitelist `orm:"-" json:"cve_whitelist"`
|
CVEWhitelist CVEWhitelist `orm:"-" json:"cve_whitelist"`
|
||||||
|
RegistryID int64 `orm:"column(registry_id)" json:"registry_id"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// GetMetadata ...
|
// GetMetadata ...
|
||||||
|
@ -136,9 +137,10 @@ func isTrue(value string) bool {
|
||||||
// List projects which user1 is member of: query := &QueryParam{Member:&Member{Name:"user1"}}
|
// List projects which user1 is member of: query := &QueryParam{Member:&Member{Name:"user1"}}
|
||||||
// List projects which user1 is the project admin : query := &QueryParam{Member:&Member{Name:"user1",Role:1}}
|
// List projects which user1 is the project admin : query := &QueryParam{Member:&Member{Name:"user1",Role:1}}
|
||||||
type ProjectQueryParam struct {
|
type ProjectQueryParam struct {
|
||||||
Name string // the name of project
|
Name string // the name of project
|
||||||
Owner string // the username of project owner
|
Owner string // the username of project owner
|
||||||
Public *bool // the project is public or not, can be ture, false and nil
|
Public *bool // the project is public or not, can be ture, false and nil
|
||||||
|
RegistryID int64
|
||||||
Member *MemberQuery // the member of project
|
Member *MemberQuery // the member of project
|
||||||
Pagination *Pagination // pagination information
|
Pagination *Pagination // pagination information
|
||||||
ProjectIDs []int64 // project ID list
|
ProjectIDs []int64 // project ID list
|
||||||
|
@ -178,6 +180,7 @@ type ProjectRequest struct {
|
||||||
CVEWhitelist CVEWhitelist `json:"cve_whitelist"`
|
CVEWhitelist CVEWhitelist `json:"cve_whitelist"`
|
||||||
|
|
||||||
StorageLimit *int64 `json:"storage_limit,omitempty"`
|
StorageLimit *int64 `json:"storage_limit,omitempty"`
|
||||||
|
RegistryID int64 `json:"registry_id"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// ProjectQueryResult ...
|
// ProjectQueryResult ...
|
||||||
|
|
|
@ -17,6 +17,7 @@ package api
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"github.com/goharbor/harbor/src/replication"
|
||||||
"net/http"
|
"net/http"
|
||||||
"regexp"
|
"regexp"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
@ -126,6 +127,24 @@ func (p *ProjectAPI) Post() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// trying to create a proxy cache project
|
||||||
|
if pro.RegistryID > 0 {
|
||||||
|
// only system admin can create the proxy cache project
|
||||||
|
if !p.SecurityCtx.IsSysAdmin() {
|
||||||
|
p.SendForbiddenError(errors.New("Only system admin can create proxy cache project"))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
registry, err := replication.RegistryMgr.Get(pro.RegistryID)
|
||||||
|
if err != nil {
|
||||||
|
p.SendInternalServerError(fmt.Errorf("failed to get the registry %d: %v", pro.RegistryID, err))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if registry == nil {
|
||||||
|
p.SendNotFoundError(fmt.Errorf("registry %d not found", pro.RegistryID))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
var hardLimits types.ResourceList
|
var hardLimits types.ResourceList
|
||||||
if config.QuotaPerProjectEnable() {
|
if config.QuotaPerProjectEnable() {
|
||||||
setting, err := config.QuotaSetting()
|
setting, err := config.QuotaSetting()
|
||||||
|
@ -187,9 +206,10 @@ func (p *ProjectAPI) Post() {
|
||||||
owner = user.Username
|
owner = user.Username
|
||||||
}
|
}
|
||||||
projectID, err := p.ProjectMgr.Create(&models.Project{
|
projectID, err := p.ProjectMgr.Create(&models.Project{
|
||||||
Name: pro.Name,
|
Name: pro.Name,
|
||||||
OwnerName: owner,
|
OwnerName: owner,
|
||||||
Metadata: pro.Metadata,
|
Metadata: pro.Metadata,
|
||||||
|
RegistryID: pro.RegistryID,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
if err == errutil.ErrDupProject {
|
if err == errutil.ErrDupProject {
|
||||||
|
|
|
@ -7,6 +7,7 @@ import (
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
common_http "github.com/goharbor/harbor/src/common/http"
|
common_http "github.com/goharbor/harbor/src/common/http"
|
||||||
|
common_models "github.com/goharbor/harbor/src/common/models"
|
||||||
"github.com/goharbor/harbor/src/common/utils"
|
"github.com/goharbor/harbor/src/common/utils"
|
||||||
"github.com/goharbor/harbor/src/core/api/models"
|
"github.com/goharbor/harbor/src/core/api/models"
|
||||||
"github.com/goharbor/harbor/src/lib/log"
|
"github.com/goharbor/harbor/src/lib/log"
|
||||||
|
@ -375,6 +376,17 @@ func (t *RegistryAPI) Delete() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check whether the registry is referenced by any proxy cache projects
|
||||||
|
result, err := t.ProjectMgr.List(&common_models.ProjectQueryParam{RegistryID: id})
|
||||||
|
if err != nil {
|
||||||
|
t.SendInternalServerError(fmt.Errorf("failed to list projects: %v", err))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if result != nil && result.Total > 0 {
|
||||||
|
t.SendPreconditionFailedError(fmt.Errorf("Can't delete registry %d, %d proxy cache projects referennce it", id, result.Total))
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
if err := t.manager.Remove(id); err != nil {
|
if err := t.manager.Remove(id); err != nil {
|
||||||
msg := fmt.Sprintf("Delete registry %d error: %v", id, err)
|
msg := fmt.Sprintf("Delete registry %d error: %v", id, err)
|
||||||
log.Error(msg)
|
log.Error(msg)
|
||||||
|
|
|
@ -83,6 +83,7 @@ func (d *driver) Create(project *models.Project) (int64, error) {
|
||||||
pro := &models.Project{
|
pro := &models.Project{
|
||||||
Name: project.Name,
|
Name: project.Name,
|
||||||
OwnerID: project.OwnerID,
|
OwnerID: project.OwnerID,
|
||||||
|
RegistryID: project.RegistryID,
|
||||||
CreationTime: t,
|
CreationTime: t,
|
||||||
UpdateTime: t,
|
UpdateTime: t,
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user