mirror of
https://github.com/goharbor/harbor
synced 2025-04-20 16:16:00 +00:00
create different security context according to the rquest
This commit is contained in:
parent
b4c172b754
commit
f8615e4746
|
@ -29,6 +29,9 @@ const (
|
||||||
RoleDeveloper = 3
|
RoleDeveloper = 3
|
||||||
RoleGuest = 4
|
RoleGuest = 4
|
||||||
|
|
||||||
|
DeployModeStandAlone = "standalone"
|
||||||
|
DeployModeIntegration = "integration"
|
||||||
|
|
||||||
ExtEndpoint = "ext_endpoint"
|
ExtEndpoint = "ext_endpoint"
|
||||||
AUTHMode = "auth_mode"
|
AUTHMode = "auth_mode"
|
||||||
DatabaseType = "database_type"
|
DatabaseType = "database_type"
|
||||||
|
|
|
@ -17,17 +17,17 @@ package rbac
|
||||||
import (
|
import (
|
||||||
"github.com/vmware/harbor/src/common"
|
"github.com/vmware/harbor/src/common"
|
||||||
"github.com/vmware/harbor/src/common/models"
|
"github.com/vmware/harbor/src/common/models"
|
||||||
"github.com/vmware/harbor/src/ui/pm"
|
"github.com/vmware/harbor/src/ui/projectmanager"
|
||||||
)
|
)
|
||||||
|
|
||||||
// SecurityContext implements security.Context interface based on database
|
// SecurityContext implements security.Context interface based on database
|
||||||
type SecurityContext struct {
|
type SecurityContext struct {
|
||||||
user *models.User
|
user *models.User
|
||||||
pm pm.PM
|
pm projectmanager.ProjectManager
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewSecurityContext ...
|
// NewSecurityContext ...
|
||||||
func NewSecurityContext(user *models.User, pm pm.PM) *SecurityContext {
|
func NewSecurityContext(user *models.User, pm projectmanager.ProjectManager) *SecurityContext {
|
||||||
return &SecurityContext{
|
return &SecurityContext{
|
||||||
user: user,
|
user: user,
|
||||||
pm: pm,
|
pm: pm,
|
||||||
|
|
|
@ -24,7 +24,10 @@ import (
|
||||||
"github.com/vmware/harbor/src/common"
|
"github.com/vmware/harbor/src/common"
|
||||||
comcfg "github.com/vmware/harbor/src/common/config"
|
comcfg "github.com/vmware/harbor/src/common/config"
|
||||||
"github.com/vmware/harbor/src/common/models"
|
"github.com/vmware/harbor/src/common/models"
|
||||||
|
"github.com/vmware/harbor/src/common/secret"
|
||||||
"github.com/vmware/harbor/src/common/utils/log"
|
"github.com/vmware/harbor/src/common/utils/log"
|
||||||
|
"github.com/vmware/harbor/src/ui/projectmanager"
|
||||||
|
"github.com/vmware/harbor/src/ui/projectmanager/db"
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
@ -33,10 +36,15 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
var (
|
var (
|
||||||
|
// SecretStore manages secrets
|
||||||
|
SecretStore *secret.Store
|
||||||
// AdminserverClient is a client for adminserver
|
// AdminserverClient is a client for adminserver
|
||||||
AdminserverClient client.Client
|
AdminserverClient client.Client
|
||||||
mg *comcfg.Manager
|
// DBProjectManager is the project manager based on database,
|
||||||
keyProvider comcfg.KeyProvider
|
// it is initialized only the deploy mode is standalone
|
||||||
|
DBProjectManager projectmanager.ProjectManager
|
||||||
|
mg *comcfg.Manager
|
||||||
|
keyProvider comcfg.KeyProvider
|
||||||
)
|
)
|
||||||
|
|
||||||
// Init configurations
|
// Init configurations
|
||||||
|
@ -62,6 +70,12 @@ func Init() error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// init secret store
|
||||||
|
initSecretStore()
|
||||||
|
|
||||||
|
// init project manager based on database
|
||||||
|
initDBProjectManager()
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -75,6 +89,20 @@ func initKeyProvider() {
|
||||||
keyProvider = comcfg.NewFileKeyProvider(path)
|
keyProvider = comcfg.NewFileKeyProvider(path)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func initSecretStore() {
|
||||||
|
m := map[string]string{}
|
||||||
|
m[secret.JobserviceUser] = JobserviceSecret()
|
||||||
|
SecretStore = secret.NewStore(m)
|
||||||
|
}
|
||||||
|
|
||||||
|
func initDBProjectManager() {
|
||||||
|
if len(DeployMode()) == 0 ||
|
||||||
|
DeployMode() == common.DeployModeStandAlone {
|
||||||
|
log.Info("initializing the project manager based on database...")
|
||||||
|
DBProjectManager = &db.ProjectManager{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Load configurations
|
// Load configurations
|
||||||
func Load() error {
|
func Load() error {
|
||||||
_, err := mg.Load()
|
_, err := mg.Load()
|
||||||
|
@ -271,6 +299,7 @@ func UISecret() string {
|
||||||
|
|
||||||
// JobserviceSecret returns a secret to mark Jobservice when communicate with
|
// JobserviceSecret returns a secret to mark Jobservice when communicate with
|
||||||
// other component
|
// other component
|
||||||
|
// TODO replace it with method of SecretStore
|
||||||
func JobserviceSecret() string {
|
func JobserviceSecret() string {
|
||||||
return os.Getenv("JOBSERVICE_SECRET")
|
return os.Getenv("JOBSERVICE_SECRET")
|
||||||
}
|
}
|
||||||
|
@ -303,3 +332,9 @@ func AdmiralEndpoint() string {
|
||||||
func WithAdmiral() bool {
|
func WithAdmiral() bool {
|
||||||
return len(AdmiralEndpoint()) > 0
|
return len(AdmiralEndpoint()) > 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeployMode returns the deploy mode
|
||||||
|
// TODO read from adminserver
|
||||||
|
func DeployMode() string {
|
||||||
|
return common.DeployModeStandAlone
|
||||||
|
}
|
||||||
|
|
|
@ -71,6 +71,7 @@ func (cc *CommonController) Login() {
|
||||||
|
|
||||||
cc.SetSession("userId", user.UserID)
|
cc.SetSession("userId", user.UserID)
|
||||||
cc.SetSession("username", user.Username)
|
cc.SetSession("username", user.Username)
|
||||||
|
cc.SetSession("isSysAdmin", user.HasAdminRole == 1)
|
||||||
}
|
}
|
||||||
|
|
||||||
// LogOut Habor UI
|
// LogOut Habor UI
|
||||||
|
|
|
@ -15,22 +15,29 @@
|
||||||
package filter
|
package filter
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"net/http"
|
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/astaxie/beego/context"
|
beegoctx "github.com/astaxie/beego/context"
|
||||||
"github.com/vmware/harbor/src/common/security"
|
"github.com/vmware/harbor/src/common"
|
||||||
|
"github.com/vmware/harbor/src/common/models"
|
||||||
|
"github.com/vmware/harbor/src/common/security/rbac"
|
||||||
|
"github.com/vmware/harbor/src/common/security/secret"
|
||||||
"github.com/vmware/harbor/src/common/utils/log"
|
"github.com/vmware/harbor/src/common/utils/log"
|
||||||
|
"github.com/vmware/harbor/src/ui/auth"
|
||||||
|
"github.com/vmware/harbor/src/ui/config"
|
||||||
|
"github.com/vmware/harbor/src/ui/projectmanager"
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
// HarborSecurityContext is the name of security context passed to handlers
|
// HarborSecurityContext is the name of security context passed to handlers
|
||||||
HarborSecurityContext = "harbor_security_context"
|
HarborSecurityContext = "harbor_security_context"
|
||||||
|
// HarborProjectManager is the name of project manager passed to handlers
|
||||||
|
HarborProjectManager = "harbor_project_manager"
|
||||||
)
|
)
|
||||||
|
|
||||||
// SecurityFilter authenticates the request and passes a security context with it
|
// SecurityFilter authenticates the request and passes a security context with it
|
||||||
// which can be used to do some authorization
|
// which can be used to do some authorization
|
||||||
func SecurityFilter(ctx *context.Context) {
|
func SecurityFilter(ctx *beegoctx.Context) {
|
||||||
if ctx == nil {
|
if ctx == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
@ -40,20 +47,89 @@ func SecurityFilter(ctx *context.Context) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if !strings.HasPrefix(req.RequestURI, "/api/") &&
|
if !strings.HasPrefix(req.URL.RequestURI(), "/api/") &&
|
||||||
!strings.HasPrefix(req.RequestURI, "/service/") {
|
!strings.HasPrefix(req.URL.RequestURI(), "/service/") {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
securityCtx, err := createSecurityContext(req)
|
// fill ctx with security context and project manager
|
||||||
if err != nil {
|
fillContext(ctx)
|
||||||
log.Warningf("failed to create security context: %v", err)
|
}
|
||||||
|
|
||||||
|
func fillContext(ctx *beegoctx.Context) {
|
||||||
|
// secret
|
||||||
|
scrt := ctx.GetCookie("secret")
|
||||||
|
if len(scrt) != 0 {
|
||||||
|
ctx.Input.SetData(HarborProjectManager,
|
||||||
|
getProjectManager(ctx))
|
||||||
|
|
||||||
|
log.Info("creating a secret security context...")
|
||||||
|
ctx.Input.SetData(HarborSecurityContext,
|
||||||
|
secret.NewSecurityContext(scrt, config.SecretStore))
|
||||||
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx.Input.SetData(HarborSecurityContext, securityCtx)
|
var user *models.User
|
||||||
|
var err error
|
||||||
|
|
||||||
|
// basic auth
|
||||||
|
username, password, ok := ctx.Request.BasicAuth()
|
||||||
|
if ok {
|
||||||
|
// TODO the return data contains other params when integrated
|
||||||
|
// with vic
|
||||||
|
user, err = auth.Login(models.AuthModel{
|
||||||
|
Principal: username,
|
||||||
|
Password: password,
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
log.Errorf("failed to authenticate %s: %v", username, err)
|
||||||
|
}
|
||||||
|
if user != nil {
|
||||||
|
log.Info("got user information via basic auth")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// session
|
||||||
|
if user == nil {
|
||||||
|
username := ctx.Input.Session("username")
|
||||||
|
isSysAdmin := ctx.Input.Session("isSysAdmin")
|
||||||
|
if username != nil {
|
||||||
|
user = &models.User{
|
||||||
|
Username: username.(string),
|
||||||
|
}
|
||||||
|
|
||||||
|
if isSysAdmin != nil && isSysAdmin.(bool) {
|
||||||
|
user.HasAdminRole = 1
|
||||||
|
}
|
||||||
|
log.Info("got user information from session")
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO maybe need to get token from session
|
||||||
|
}
|
||||||
|
|
||||||
|
if user == nil {
|
||||||
|
log.Info("user information is nil")
|
||||||
|
}
|
||||||
|
|
||||||
|
pm := getProjectManager(ctx)
|
||||||
|
ctx.Input.SetData(HarborProjectManager, pm)
|
||||||
|
|
||||||
|
log.Info("creating a rbac security context...")
|
||||||
|
ctx.Input.SetData(HarborSecurityContext,
|
||||||
|
rbac.NewSecurityContext(user, pm))
|
||||||
|
|
||||||
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func createSecurityContext(req *http.Request) (security.Context, error) {
|
func getProjectManager(ctx *beegoctx.Context) projectmanager.ProjectManager {
|
||||||
return nil, nil
|
if len(config.DeployMode()) == 0 ||
|
||||||
|
config.DeployMode() == common.DeployModeStandAlone {
|
||||||
|
log.Info("filling a project manager based on database...")
|
||||||
|
return config.DBProjectManager
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO create project manager based on pms
|
||||||
|
log.Info("filling a project manager based on pms...")
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,22 +15,73 @@
|
||||||
package filter
|
package filter
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/json"
|
||||||
|
"log"
|
||||||
"net/http"
|
"net/http"
|
||||||
|
"net/http/httptest"
|
||||||
|
"net/url"
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
"testing"
|
"testing"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/astaxie/beego"
|
||||||
"github.com/astaxie/beego/context"
|
"github.com/astaxie/beego/context"
|
||||||
|
"github.com/astaxie/beego/session"
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
|
"github.com/vmware/harbor/src/common/dao"
|
||||||
|
"github.com/vmware/harbor/src/common/security"
|
||||||
|
"github.com/vmware/harbor/src/common/security/rbac"
|
||||||
|
"github.com/vmware/harbor/src/common/security/secret"
|
||||||
|
_ "github.com/vmware/harbor/src/ui/auth/db"
|
||||||
|
_ "github.com/vmware/harbor/src/ui/auth/ldap"
|
||||||
|
"github.com/vmware/harbor/src/ui/config"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func TestMain(m *testing.M) {
|
||||||
|
// initialize beego session manager
|
||||||
|
conf := map[string]interface{}{
|
||||||
|
"cookieName": beego.BConfig.WebConfig.Session.SessionName,
|
||||||
|
"gclifetime": beego.BConfig.WebConfig.Session.SessionGCMaxLifetime,
|
||||||
|
"providerConfig": filepath.ToSlash(beego.BConfig.WebConfig.Session.SessionProviderConfig),
|
||||||
|
"secure": beego.BConfig.Listen.EnableHTTPS,
|
||||||
|
"enableSetCookie": beego.BConfig.WebConfig.Session.SessionAutoSetCookie,
|
||||||
|
"domain": beego.BConfig.WebConfig.Session.SessionDomain,
|
||||||
|
"cookieLifeTime": beego.BConfig.WebConfig.Session.SessionCookieLifeTime,
|
||||||
|
}
|
||||||
|
confBytes, err := json.Marshal(conf)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("failed to marshal session conf: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
beego.GlobalSessions, err = session.NewManager("memory", string(confBytes))
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("failed to create session manager: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := config.Init(); err != nil {
|
||||||
|
log.Fatalf("failed to initialize configurations: %v", err)
|
||||||
|
}
|
||||||
|
database, err := config.Database()
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("failed to get database configurations: %v", err)
|
||||||
|
}
|
||||||
|
if err = dao.InitDatabase(database); err != nil {
|
||||||
|
log.Fatalf("failed to initialize database: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
os.Exit(m.Run())
|
||||||
|
}
|
||||||
|
|
||||||
func TestSecurityFilter(t *testing.T) {
|
func TestSecurityFilter(t *testing.T) {
|
||||||
// nil request
|
// nil request
|
||||||
ctx := &context.Context{
|
ctx, err := newContext(nil)
|
||||||
Request: nil,
|
if err != nil {
|
||||||
Input: context.NewInput(),
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
}
|
}
|
||||||
SecurityFilter(ctx)
|
SecurityFilter(ctx)
|
||||||
securityContext := ctx.Input.GetData(HarborSecurityContext)
|
assert.Nil(t, securityContext(ctx))
|
||||||
assert.Nil(t, securityContext)
|
assert.Nil(t, projectManager(ctx))
|
||||||
|
|
||||||
// the pattern of request does not need security check
|
// the pattern of request does not need security check
|
||||||
req, err := http.NewRequest(http.MethodGet, "http://127.0.0.1/static/index.html", nil)
|
req, err := http.NewRequest(http.MethodGet, "http://127.0.0.1/static/index.html", nil)
|
||||||
|
@ -38,13 +89,156 @@ func TestSecurityFilter(t *testing.T) {
|
||||||
t.Fatalf("failed to create request: %v", req)
|
t.Fatalf("failed to create request: %v", req)
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx = &context.Context{
|
ctx, err = newContext(req)
|
||||||
Request: req,
|
if err != nil {
|
||||||
Input: context.NewInput(),
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
}
|
}
|
||||||
SecurityFilter(ctx)
|
SecurityFilter(ctx)
|
||||||
securityContext = ctx.Input.GetData(HarborSecurityContext)
|
assert.Nil(t, securityContext(ctx))
|
||||||
assert.Nil(t, securityContext)
|
assert.Nil(t, projectManager(ctx))
|
||||||
|
|
||||||
//TODO add a case to test normal process
|
// the pattern of request needs security check
|
||||||
|
req, err = http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx, err = newContext(req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
|
}
|
||||||
|
SecurityFilter(ctx)
|
||||||
|
assert.NotNil(t, securityContext(ctx))
|
||||||
|
assert.NotNil(t, projectManager(ctx))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFillContext(t *testing.T) {
|
||||||
|
// secret
|
||||||
|
req, err := http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
req.AddCookie(&http.Cookie{
|
||||||
|
Name: "secret",
|
||||||
|
Value: "secret",
|
||||||
|
})
|
||||||
|
|
||||||
|
ctx, err := newContext(req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
fillContext(ctx)
|
||||||
|
assert.IsType(t, &secret.SecurityContext{},
|
||||||
|
securityContext(ctx))
|
||||||
|
assert.NotNil(t, projectManager(ctx))
|
||||||
|
|
||||||
|
// session
|
||||||
|
req, err = http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
store, err := beego.GlobalSessions.SessionStart(httptest.NewRecorder(), req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create session store: %v", err)
|
||||||
|
}
|
||||||
|
if err = store.Set("username", "admin"); err != nil {
|
||||||
|
t.Fatalf("failed to set session: %v", err)
|
||||||
|
}
|
||||||
|
if err = store.Set("isSysAdmin", true); err != nil {
|
||||||
|
t.Fatalf("failed to set session: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
req, err = http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
addSessionIDToCookie(req, store.SessionID())
|
||||||
|
|
||||||
|
ctx, err = newContext(req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
|
}
|
||||||
|
fillContext(ctx)
|
||||||
|
sc := securityContext(ctx)
|
||||||
|
assert.IsType(t, &rbac.SecurityContext{}, sc)
|
||||||
|
s := sc.(security.Context)
|
||||||
|
assert.Equal(t, "admin", s.GetUsername())
|
||||||
|
assert.True(t, s.IsSysAdmin())
|
||||||
|
assert.NotNil(t, projectManager(ctx))
|
||||||
|
|
||||||
|
// basic auth
|
||||||
|
req, err = http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
req.SetBasicAuth("admin", "Harbor12345")
|
||||||
|
|
||||||
|
ctx, err = newContext(req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
|
}
|
||||||
|
fillContext(ctx)
|
||||||
|
sc = securityContext(ctx)
|
||||||
|
assert.IsType(t, &rbac.SecurityContext{}, sc)
|
||||||
|
s = sc.(security.Context)
|
||||||
|
assert.Equal(t, "admin", s.GetUsername())
|
||||||
|
assert.NotNil(t, projectManager(ctx))
|
||||||
|
|
||||||
|
// no credential
|
||||||
|
req, err = http.NewRequest(http.MethodGet,
|
||||||
|
"http://127.0.0.1/api/projects/", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to create request: %v", req)
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx, err = newContext(req)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("failed to crate context: %v", err)
|
||||||
|
}
|
||||||
|
fillContext(ctx)
|
||||||
|
sc = securityContext(ctx)
|
||||||
|
assert.IsType(t, &rbac.SecurityContext{}, sc)
|
||||||
|
s = sc.(security.Context)
|
||||||
|
assert.False(t, s.IsAuthenticated())
|
||||||
|
assert.NotNil(t, projectManager(ctx))
|
||||||
|
}
|
||||||
|
|
||||||
|
func newContext(req *http.Request) (*context.Context, error) {
|
||||||
|
var err error
|
||||||
|
ctx := context.NewContext()
|
||||||
|
ctx.Reset(httptest.NewRecorder(), req)
|
||||||
|
if req != nil {
|
||||||
|
ctx.Input.CruSession, err = beego.GlobalSessions.SessionStart(ctx.ResponseWriter, req)
|
||||||
|
}
|
||||||
|
return ctx, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func addSessionIDToCookie(req *http.Request, sessionID string) {
|
||||||
|
cookie := &http.Cookie{
|
||||||
|
Name: beego.BConfig.WebConfig.Session.SessionName,
|
||||||
|
Value: url.QueryEscape(sessionID),
|
||||||
|
Path: "/",
|
||||||
|
HttpOnly: true,
|
||||||
|
Secure: beego.BConfig.Listen.EnableHTTPS,
|
||||||
|
Domain: beego.BConfig.WebConfig.Session.SessionDomain,
|
||||||
|
}
|
||||||
|
cookie.MaxAge = beego.BConfig.WebConfig.Session.SessionCookieLifeTime
|
||||||
|
cookie.Expires = time.Now().Add(
|
||||||
|
time.Duration(
|
||||||
|
beego.BConfig.WebConfig.Session.SessionCookieLifeTime) * time.Second)
|
||||||
|
req.AddCookie(cookie)
|
||||||
|
}
|
||||||
|
|
||||||
|
func securityContext(ctx *context.Context) interface{} {
|
||||||
|
return ctx.Input.Data()[HarborSecurityContext]
|
||||||
|
}
|
||||||
|
|
||||||
|
func projectManager(ctx *context.Context) interface{} {
|
||||||
|
return ctx.Input.Data()[HarborProjectManager]
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,11 +21,11 @@ import (
|
||||||
"github.com/vmware/harbor/src/common/utils/log"
|
"github.com/vmware/harbor/src/common/utils/log"
|
||||||
)
|
)
|
||||||
|
|
||||||
// PM implements pm.PM interface based on database
|
// ProjectManager implements pm.PM interface based on database
|
||||||
type PM struct{}
|
type ProjectManager struct{}
|
||||||
|
|
||||||
// IsPublic returns whether the project is public or not
|
// IsPublic returns whether the project is public or not
|
||||||
func (p *PM) IsPublic(projectIDOrName interface{}) bool {
|
func (p *ProjectManager) IsPublic(projectIDOrName interface{}) bool {
|
||||||
var project *models.Project
|
var project *models.Project
|
||||||
var err error
|
var err error
|
||||||
switch projectIDOrName.(type) {
|
switch projectIDOrName.(type) {
|
||||||
|
@ -53,7 +53,7 @@ func (p *PM) IsPublic(projectIDOrName interface{}) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
// GetRoles return a role list which contains the user's roles to the project
|
// GetRoles return a role list which contains the user's roles to the project
|
||||||
func (p *PM) GetRoles(username string, projectIDOrName interface{}) []int {
|
func (p *ProjectManager) GetRoles(username string, projectIDOrName interface{}) []int {
|
||||||
roles := []int{}
|
roles := []int{}
|
||||||
|
|
||||||
user, err := dao.GetUser(models.User{
|
user, err := dao.GetUser(models.User{
|
|
@ -71,7 +71,7 @@ func TestMain(m *testing.M) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestIsPublic(t *testing.T) {
|
func TestIsPublic(t *testing.T) {
|
||||||
pms := &PM{}
|
pms := &ProjectManager{}
|
||||||
// project name
|
// project name
|
||||||
assert.True(t, pms.IsPublic("library"))
|
assert.True(t, pms.IsPublic("library"))
|
||||||
// project ID
|
// project ID
|
||||||
|
@ -83,7 +83,7 @@ func TestIsPublic(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestGetRoles(t *testing.T) {
|
func TestGetRoles(t *testing.T) {
|
||||||
pm := &PM{}
|
pm := &ProjectManager{}
|
||||||
|
|
||||||
// non exist user
|
// non exist user
|
||||||
assert.Equal(t, []int{},
|
assert.Equal(t, []int{},
|
|
@ -12,11 +12,11 @@
|
||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
package pm
|
package projectmanager
|
||||||
|
|
||||||
// PM is the project mamager which abstracts the operations related
|
// ProjectManager is the project mamager which abstracts the operations related
|
||||||
// to projects
|
// to projects
|
||||||
type PM interface {
|
type ProjectManager interface {
|
||||||
IsPublic(projectIDOrName interface{}) bool
|
IsPublic(projectIDOrName interface{}) bool
|
||||||
GetRoles(username string, projectIDOrName interface{}) []int
|
GetRoles(username string, projectIDOrName interface{}) []int
|
||||||
}
|
}
|
|
@ -22,6 +22,7 @@ import (
|
||||||
)
|
)
|
||||||
|
|
||||||
// VerifySecret verifies the UI_SECRET cookie in a http request.
|
// VerifySecret verifies the UI_SECRET cookie in a http request.
|
||||||
|
// TODO remove
|
||||||
func VerifySecret(r *http.Request, expectedSecret string) bool {
|
func VerifySecret(r *http.Request, expectedSecret string) bool {
|
||||||
c, err := r.Cookie("secret")
|
c, err := r.Cookie("secret")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user