forked from TrueCloudLab/frostfs-s3-gw
[#713] Add check access control for system caches
Signed-off-by: Denis Kirillov <denis@nspcc.ru>
This commit is contained in:
parent
cb55d36063
commit
90eb4f0188
8 changed files with 94 additions and 59 deletions
|
@ -8,7 +8,6 @@ import (
|
|||
"github.com/nspcc-dev/neofs-s3-gw/api/data"
|
||||
"github.com/nspcc-dev/neofs-s3-gw/api/errors"
|
||||
"github.com/nspcc-dev/neofs-s3-gw/api/layer"
|
||||
"go.uber.org/zap"
|
||||
)
|
||||
|
||||
func (h *handler) PutBucketVersioningHandler(w http.ResponseWriter, r *http.Request) {
|
||||
|
@ -68,11 +67,8 @@ func (h *handler) GetBucketVersioningHandler(w http.ResponseWriter, r *http.Requ
|
|||
|
||||
settings, err := h.obj.GetBucketSettings(r.Context(), bktInfo)
|
||||
if err != nil {
|
||||
h.log.Warn("couldn't get version settings object: default version settings will be used",
|
||||
zap.String("request_id", reqInfo.RequestID),
|
||||
zap.String("method", reqInfo.API),
|
||||
zap.String("bucket_name", reqInfo.BucketName),
|
||||
zap.Error(err))
|
||||
h.logAndSendError(w, "couldn't get version settings", reqInfo, err)
|
||||
return
|
||||
}
|
||||
|
||||
if err = api.EncodeToResponse(w, formVersioningConfiguration(settings)); err != nil {
|
||||
|
|
|
@ -142,64 +142,110 @@ func (c *Cache) PutList(owner user.ID, key cache.ObjectsListKey, list []*data.No
|
|||
}
|
||||
}
|
||||
|
||||
func (c *Cache) GetTagging(key string) map[string]string {
|
||||
func (c *Cache) GetTagging(owner user.ID, key string) map[string]string {
|
||||
if !c.accessCache.Get(owner, key) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return c.systemCache.GetTagging(key)
|
||||
}
|
||||
|
||||
func (c *Cache) PutTagging(key string, tags map[string]string) {
|
||||
func (c *Cache) PutTagging(owner user.ID, key string, tags map[string]string) {
|
||||
if err := c.systemCache.PutTagging(key, tags); err != nil {
|
||||
c.logger.Error("couldn't cache tags", zap.Error(err))
|
||||
}
|
||||
|
||||
if err := c.accessCache.Put(owner, key); err != nil {
|
||||
c.logger.Warn("couldn't cache access control operation", zap.Error(err))
|
||||
}
|
||||
}
|
||||
|
||||
func (c *Cache) DeleteTagging(key string) {
|
||||
c.systemCache.Delete(key)
|
||||
}
|
||||
|
||||
func (c *Cache) GetLockInfo(key string) *data.LockInfo {
|
||||
func (c *Cache) GetLockInfo(owner user.ID, key string) *data.LockInfo {
|
||||
if !c.accessCache.Get(owner, key) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return c.systemCache.GetLockInfo(key)
|
||||
}
|
||||
|
||||
func (c *Cache) PutLockInfo(key string, lockInfo *data.LockInfo) {
|
||||
func (c *Cache) PutLockInfo(owner user.ID, key string, lockInfo *data.LockInfo) {
|
||||
if err := c.systemCache.PutLockInfo(key, lockInfo); err != nil {
|
||||
c.logger.Error("couldn't cache lock info", zap.Error(err))
|
||||
}
|
||||
|
||||
if err := c.accessCache.Put(owner, key); err != nil {
|
||||
c.logger.Warn("couldn't cache access control operation", zap.Error(err))
|
||||
}
|
||||
}
|
||||
|
||||
func (c *Cache) GetSettings(bktInfo *data.BucketInfo) *data.BucketSettings {
|
||||
func (c *Cache) GetSettings(owner user.ID, bktInfo *data.BucketInfo) *data.BucketSettings {
|
||||
key := bktInfo.Name + bktInfo.SettingsObjectName()
|
||||
|
||||
if !c.accessCache.Get(owner, key) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return c.systemCache.GetSettings(key)
|
||||
}
|
||||
|
||||
func (c *Cache) PutSettings(bktInfo *data.BucketInfo, settings *data.BucketSettings) {
|
||||
func (c *Cache) PutSettings(owner user.ID, bktInfo *data.BucketInfo, settings *data.BucketSettings) {
|
||||
key := bktInfo.Name + bktInfo.SettingsObjectName()
|
||||
if err := c.systemCache.PutSettings(key, settings); err != nil {
|
||||
c.logger.Warn("couldn't cache bucket settings", zap.String("bucket", bktInfo.Name), zap.Error(err))
|
||||
}
|
||||
|
||||
if err := c.accessCache.Put(owner, key); err != nil {
|
||||
c.logger.Warn("couldn't cache access control operation", zap.Error(err))
|
||||
}
|
||||
}
|
||||
|
||||
func (c *Cache) GetCORS(bkt *data.BucketInfo) *data.CORSConfiguration {
|
||||
return c.systemCache.GetCORS(bkt.Name + bkt.CORSObjectName())
|
||||
func (c *Cache) GetCORS(owner user.ID, bkt *data.BucketInfo) *data.CORSConfiguration {
|
||||
key := bkt.Name + bkt.CORSObjectName()
|
||||
|
||||
if !c.accessCache.Get(owner, key) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return c.systemCache.GetCORS(key)
|
||||
}
|
||||
|
||||
func (c *Cache) PutCORS(bkt *data.BucketInfo, settings *data.CORSConfiguration) {
|
||||
if err := c.systemCache.PutCORS(bkt.Name+bkt.CORSObjectName(), settings); err != nil {
|
||||
func (c *Cache) PutCORS(owner user.ID, bkt *data.BucketInfo, cors *data.CORSConfiguration) {
|
||||
key := bkt.Name + bkt.CORSObjectName()
|
||||
|
||||
if err := c.systemCache.PutCORS(key, cors); err != nil {
|
||||
c.logger.Warn("couldn't cache cors", zap.String("bucket", bkt.Name), zap.Error(err))
|
||||
}
|
||||
|
||||
if err := c.accessCache.Put(owner, key); err != nil {
|
||||
c.logger.Warn("couldn't cache access control operation", zap.Error(err))
|
||||
}
|
||||
}
|
||||
|
||||
func (c *Cache) DeleteCORS(bktInfo *data.BucketInfo) {
|
||||
c.systemCache.Delete(bktInfo.Name + bktInfo.CORSObjectName())
|
||||
}
|
||||
|
||||
func (c *Cache) GetNotificationConfiguration(bktInfo *data.BucketInfo) *data.NotificationConfiguration {
|
||||
func (c *Cache) GetNotificationConfiguration(owner user.ID, bktInfo *data.BucketInfo) *data.NotificationConfiguration {
|
||||
key := bktInfo.Name + bktInfo.NotificationConfigurationObjectName()
|
||||
|
||||
if !c.accessCache.Get(owner, key) {
|
||||
return nil
|
||||
}
|
||||
|
||||
return c.systemCache.GetNotificationConfiguration(key)
|
||||
}
|
||||
|
||||
func (c *Cache) PutNotificationConfiguration(bktInfo *data.BucketInfo, configuration *data.NotificationConfiguration) {
|
||||
func (c *Cache) PutNotificationConfiguration(owner user.ID, bktInfo *data.BucketInfo, configuration *data.NotificationConfiguration) {
|
||||
key := bktInfo.Name + bktInfo.NotificationConfigurationObjectName()
|
||||
if err := c.systemCache.PutNotificationConfiguration(key, configuration); err != nil {
|
||||
c.logger.Warn("couldn't cache notification configuration", zap.String("bucket", bktInfo.Name), zap.Error(err))
|
||||
}
|
||||
|
||||
if err := c.accessCache.Put(owner, key); err != nil {
|
||||
c.logger.Warn("couldn't cache access control operation", zap.Error(err))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -9,13 +9,11 @@ import (
|
|||
)
|
||||
|
||||
func (n *layer) GetObjectTaggingAndLock(ctx context.Context, objVersion *ObjectVersion, nodeVersion *data.NodeVersion) (map[string]string, *data.LockInfo, error) {
|
||||
var (
|
||||
err error
|
||||
tags map[string]string
|
||||
)
|
||||
var err error
|
||||
owner := n.Owner(ctx)
|
||||
|
||||
tags = n.cache.GetTagging(objectTaggingCacheKey(objVersion))
|
||||
lockInfo := n.cache.GetLockInfo(lockObjectKey(objVersion))
|
||||
tags := n.cache.GetTagging(owner, objectTaggingCacheKey(objVersion))
|
||||
lockInfo := n.cache.GetLockInfo(owner, lockObjectKey(objVersion))
|
||||
|
||||
if tags != nil && lockInfo != nil {
|
||||
return tags, lockInfo, nil
|
||||
|
@ -36,8 +34,8 @@ func (n *layer) GetObjectTaggingAndLock(ctx context.Context, objVersion *ObjectV
|
|||
return nil, nil, err
|
||||
}
|
||||
|
||||
n.cache.PutTagging(objectTaggingCacheKey(objVersion), tags)
|
||||
n.cache.PutLockInfo(lockObjectKey(objVersion), lockInfo)
|
||||
n.cache.PutTagging(owner, objectTaggingCacheKey(objVersion), tags)
|
||||
n.cache.PutLockInfo(owner, lockObjectKey(objVersion), lockInfo)
|
||||
|
||||
return tags, lockInfo, nil
|
||||
}
|
||||
|
|
|
@ -107,7 +107,6 @@ func (n *layer) containerList(ctx context.Context) ([]*data.BucketInfo, error) {
|
|||
}
|
||||
|
||||
func (n *layer) createContainer(ctx context.Context, p *CreateBucketParams) (*data.BucketInfo, error) {
|
||||
var err error
|
||||
ownerID := n.Owner(ctx)
|
||||
if p.LocationConstraint == "" {
|
||||
p.LocationConstraint = api.DefaultLocationConstraint // s3tests_boto3.functional.test_s3:test_bucket_get_location
|
||||
|
|
|
@ -64,7 +64,7 @@ func (n *layer) PutBucketCORS(ctx context.Context, p *PutCORSParams) error {
|
|||
}
|
||||
}
|
||||
|
||||
n.cache.PutCORS(p.BktInfo, cors)
|
||||
n.cache.PutCORS(n.Owner(ctx), p.BktInfo, cors)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -53,13 +53,14 @@ func (n *layer) PutBucketNotificationConfiguration(ctx context.Context, p *PutBu
|
|||
}
|
||||
}
|
||||
|
||||
n.cache.PutNotificationConfiguration(p.BktInfo, p.Configuration)
|
||||
n.cache.PutNotificationConfiguration(n.Owner(ctx), p.BktInfo, p.Configuration)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (n *layer) GetBucketNotificationConfiguration(ctx context.Context, bktInfo *data.BucketInfo) (*data.NotificationConfiguration, error) {
|
||||
if conf := n.cache.GetNotificationConfiguration(bktInfo); conf != nil {
|
||||
owner := n.Owner(ctx)
|
||||
if conf := n.cache.GetNotificationConfiguration(owner, bktInfo); conf != nil {
|
||||
return conf, nil
|
||||
}
|
||||
|
||||
|
@ -82,7 +83,7 @@ func (n *layer) GetBucketNotificationConfiguration(ctx context.Context, bktInfo
|
|||
}
|
||||
}
|
||||
|
||||
n.cache.PutNotificationConfiguration(bktInfo, conf)
|
||||
n.cache.PutNotificationConfiguration(owner, bktInfo, conf)
|
||||
|
||||
return conf, nil
|
||||
}
|
||||
|
|
|
@ -100,7 +100,7 @@ func (n *layer) PutLockInfo(ctx context.Context, p *PutLockInfoParams) (err erro
|
|||
return fmt.Errorf("couldn't put lock into tree: %w", err)
|
||||
}
|
||||
|
||||
n.cache.PutLockInfo(lockObjectKey(p.ObjVersion), lockInfo)
|
||||
n.cache.PutLockInfo(n.Owner(ctx), lockObjectKey(p.ObjVersion), lockInfo)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
@ -124,7 +124,8 @@ func (n *layer) putLockObject(ctx context.Context, bktInfo *data.BucketInfo, obj
|
|||
}
|
||||
|
||||
func (n *layer) GetLockInfo(ctx context.Context, objVersion *ObjectVersion) (*data.LockInfo, error) {
|
||||
if lockInfo := n.cache.GetLockInfo(lockObjectKey(objVersion)); lockInfo != nil {
|
||||
owner := n.Owner(ctx)
|
||||
if lockInfo := n.cache.GetLockInfo(owner, lockObjectKey(objVersion)); lockInfo != nil {
|
||||
return lockInfo, nil
|
||||
}
|
||||
|
||||
|
@ -141,13 +142,14 @@ func (n *layer) GetLockInfo(ctx context.Context, objVersion *ObjectVersion) (*da
|
|||
lockInfo = &data.LockInfo{}
|
||||
}
|
||||
|
||||
n.cache.PutLockInfo(lockObjectKey(objVersion), lockInfo)
|
||||
n.cache.PutLockInfo(owner, lockObjectKey(objVersion), lockInfo)
|
||||
|
||||
return lockInfo, nil
|
||||
}
|
||||
|
||||
func (n *layer) getCORS(ctx context.Context, bkt *data.BucketInfo) (*data.CORSConfiguration, error) {
|
||||
if cors := n.cache.GetCORS(bkt); cors != nil {
|
||||
owner := n.Owner(ctx)
|
||||
if cors := n.cache.GetCORS(owner, bkt); cors != nil {
|
||||
return cors, nil
|
||||
}
|
||||
|
||||
|
@ -172,7 +174,7 @@ func (n *layer) getCORS(ctx context.Context, bkt *data.BucketInfo) (*data.CORSCo
|
|||
return nil, fmt.Errorf("unmarshal cors: %w", err)
|
||||
}
|
||||
|
||||
n.cache.PutCORS(bkt, cors)
|
||||
n.cache.PutCORS(owner, bkt, cors)
|
||||
|
||||
return cors, nil
|
||||
}
|
||||
|
@ -183,7 +185,8 @@ func lockObjectKey(objVersion *ObjectVersion) string {
|
|||
}
|
||||
|
||||
func (n *layer) GetBucketSettings(ctx context.Context, bktInfo *data.BucketInfo) (*data.BucketSettings, error) {
|
||||
if settings := n.cache.GetSettings(bktInfo); settings != nil {
|
||||
owner := n.Owner(ctx)
|
||||
if settings := n.cache.GetSettings(owner, bktInfo); settings != nil {
|
||||
return settings, nil
|
||||
}
|
||||
|
||||
|
@ -195,7 +198,7 @@ func (n *layer) GetBucketSettings(ctx context.Context, bktInfo *data.BucketInfo)
|
|||
settings = &data.BucketSettings{Versioning: data.VersioningUnversioned}
|
||||
}
|
||||
|
||||
n.cache.PutSettings(bktInfo, settings)
|
||||
n.cache.PutSettings(owner, bktInfo, settings)
|
||||
|
||||
return settings, nil
|
||||
}
|
||||
|
@ -205,7 +208,7 @@ func (n *layer) PutBucketSettings(ctx context.Context, p *PutSettingsParams) err
|
|||
return fmt.Errorf("failed to get settings node: %w", err)
|
||||
}
|
||||
|
||||
n.cache.PutSettings(p.BktInfo, p.Settings)
|
||||
n.cache.PutSettings(n.Owner(ctx), p.BktInfo, p.Settings)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -12,14 +12,10 @@ import (
|
|||
)
|
||||
|
||||
func (n *layer) GetObjectTagging(ctx context.Context, p *ObjectVersion) (string, map[string]string, error) {
|
||||
var (
|
||||
err error
|
||||
tags map[string]string
|
||||
)
|
||||
owner := n.Owner(ctx)
|
||||
|
||||
if len(p.VersionID) != 0 && p.VersionID != data.UnversionedObjectVersionID {
|
||||
tags = n.cache.GetTagging(objectTaggingCacheKey(p))
|
||||
if tags != nil {
|
||||
if tags := n.cache.GetTagging(owner, objectTaggingCacheKey(p)); tags != nil {
|
||||
return p.VersionID, tags, nil
|
||||
}
|
||||
}
|
||||
|
@ -30,12 +26,11 @@ func (n *layer) GetObjectTagging(ctx context.Context, p *ObjectVersion) (string,
|
|||
}
|
||||
p.VersionID = version.OID.EncodeToString()
|
||||
|
||||
tags = n.cache.GetTagging(objectTaggingCacheKey(p))
|
||||
if tags != nil {
|
||||
if tags := n.cache.GetTagging(owner, objectTaggingCacheKey(p)); tags != nil {
|
||||
return p.VersionID, tags, nil
|
||||
}
|
||||
|
||||
tags, err = n.treeService.GetObjectTagging(ctx, p.BktInfo, version)
|
||||
tags, err := n.treeService.GetObjectTagging(ctx, p.BktInfo, version)
|
||||
if err != nil {
|
||||
if errorsStd.Is(err, ErrNodeNotFound) {
|
||||
return "", nil, errors.GetAPIError(errors.ErrNoSuchKey)
|
||||
|
@ -43,7 +38,7 @@ func (n *layer) GetObjectTagging(ctx context.Context, p *ObjectVersion) (string,
|
|||
return "", nil, err
|
||||
}
|
||||
|
||||
n.cache.PutTagging(objectTaggingCacheKey(p), tags)
|
||||
n.cache.PutTagging(owner, objectTaggingCacheKey(p), tags)
|
||||
|
||||
return p.VersionID, tags, nil
|
||||
}
|
||||
|
@ -63,7 +58,7 @@ func (n *layer) PutObjectTagging(ctx context.Context, p *ObjectVersion, tagSet m
|
|||
return nil, err
|
||||
}
|
||||
|
||||
n.cache.PutTagging(objectTaggingCacheKey(p), tagSet)
|
||||
n.cache.PutTagging(n.Owner(ctx), objectTaggingCacheKey(p), tagSet)
|
||||
|
||||
return version, nil
|
||||
}
|
||||
|
@ -90,21 +85,18 @@ func (n *layer) DeleteObjectTagging(ctx context.Context, p *ObjectVersion) (*dat
|
|||
}
|
||||
|
||||
func (n *layer) GetBucketTagging(ctx context.Context, bktInfo *data.BucketInfo) (map[string]string, error) {
|
||||
var (
|
||||
err error
|
||||
tags map[string]string
|
||||
)
|
||||
owner := n.Owner(ctx)
|
||||
|
||||
tags = n.cache.GetTagging(bucketTaggingCacheKey(bktInfo.CID))
|
||||
if tags != nil {
|
||||
if tags := n.cache.GetTagging(owner, bucketTaggingCacheKey(bktInfo.CID)); tags != nil {
|
||||
return tags, nil
|
||||
}
|
||||
|
||||
if tags, err = n.treeService.GetBucketTagging(ctx, bktInfo); err != nil && !errorsStd.Is(err, ErrNodeNotFound) {
|
||||
tags, err := n.treeService.GetBucketTagging(ctx, bktInfo)
|
||||
if err != nil && !errorsStd.Is(err, ErrNodeNotFound) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
n.cache.PutTagging(bucketTaggingCacheKey(bktInfo.CID), tags)
|
||||
n.cache.PutTagging(owner, bucketTaggingCacheKey(bktInfo.CID), tags)
|
||||
|
||||
return tags, nil
|
||||
}
|
||||
|
@ -114,7 +106,7 @@ func (n *layer) PutBucketTagging(ctx context.Context, bktInfo *data.BucketInfo,
|
|||
return err
|
||||
}
|
||||
|
||||
n.cache.PutTagging(bucketTaggingCacheKey(bktInfo.CID), tagSet)
|
||||
n.cache.PutTagging(n.Owner(ctx), bucketTaggingCacheKey(bktInfo.CID), tagSet)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue