Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix the permissions response for shared files in the cbox sql driver #2244

Merged
merged 2 commits into from
Nov 9, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions changelog/unreleased/sql-share-file-perm.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
Bugfix: Fix the permissions response for shared files in the cbox sql driver

https://github.com/cs3org/reva/pull/2244
16 changes: 8 additions & 8 deletions pkg/cbox/publicshare/sql/sql.go
Original file line number Diff line number Diff line change
Expand Up @@ -252,8 +252,8 @@ func (m *manager) UpdatePublicShare(ctx context.Context, u *user.User, req *link

func (m *manager) getByToken(ctx context.Context, token string, u *user.User) (*link.PublicShare, string, error) {
s := conversions.DBShare{Token: token}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND share_type=? AND token=?"
if err := m.db.QueryRow(query, publicShareType, token).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND share_type=? AND token=?"
if err := m.db.QueryRow(query, publicShareType, token).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
if err == sql.ErrNoRows {
return nil, "", errtypes.NotFound(token)
}
Expand All @@ -265,8 +265,8 @@ func (m *manager) getByToken(ctx context.Context, token string, u *user.User) (*
func (m *manager) getByID(ctx context.Context, id *link.PublicShareId, u *user.User) (*link.PublicShare, string, error) {
uid := conversions.FormatUserID(u.Id)
s := conversions.DBShare{ID: id.OpaqueId}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(token,'') as token, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND share_type=? AND id=? AND (uid_owner=? OR uid_initiator=?)"
if err := m.db.QueryRow(query, publicShareType, id.OpaqueId, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.Token, &s.Expiration, &s.ShareName, &s.STime, &s.Permissions); err != nil {
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, coalesce(token,'') as token, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND share_type=? AND id=? AND (uid_owner=? OR uid_initiator=?)"
if err := m.db.QueryRow(query, publicShareType, id.OpaqueId, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.Token, &s.Expiration, &s.ShareName, &s.STime, &s.Permissions); err != nil {
if err == sql.ErrNoRows {
return nil, "", errtypes.NotFound(id.OpaqueId)
}
Expand Down Expand Up @@ -310,7 +310,7 @@ func (m *manager) GetPublicShare(ctx context.Context, u *user.User, ref *link.Pu

func (m *manager) ListPublicShares(ctx context.Context, u *user.User, filters []*link.ListPublicSharesRequest_Filter, md *provider.ResourceInfo, sign bool) ([]*link.PublicShare, error) {
uid := conversions.FormatUserID(u.Id)
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(token,'') as token, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND (uid_owner=? or uid_initiator=?) AND (share_type=?)"
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, coalesce(token,'') as token, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND (uid_owner=? or uid_initiator=?) AND (share_type=?)"
var filterQuery string
params := []interface{}{uid, uid, publicShareType}

Expand Down Expand Up @@ -349,7 +349,7 @@ func (m *manager) ListPublicShares(ctx context.Context, u *user.User, filters []
var s conversions.DBShare
shares := []*link.PublicShare{}
for rows.Next() {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.Token, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.Token, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
continue
}
cs3Share := conversions.ConvertToCS3PublicShare(s)
Expand Down Expand Up @@ -408,8 +408,8 @@ func (m *manager) RevokePublicShare(ctx context.Context, u *user.User, ref *link

func (m *manager) GetPublicShareByToken(ctx context.Context, token string, auth *link.PublicShareAuthentication, sign bool) (*link.PublicShare, error) {
s := conversions.DBShare{Token: token}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE share_type=? AND token=?"
if err := m.db.QueryRow(query, publicShareType, token).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, coalesce(expiration, '') as expiration, coalesce(share_name, '') as share_name, id, stime, permissions FROM oc_share WHERE share_type=? AND token=?"
if err := m.db.QueryRow(query, publicShareType, token).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.Expiration, &s.ShareName, &s.ID, &s.STime, &s.Permissions); err != nil {
if err == sql.ErrNoRows {
return nil, errtypes.NotFound(token)
}
Expand Down
24 changes: 12 additions & 12 deletions pkg/cbox/share/sql/sql.go
Original file line number Diff line number Diff line change
Expand Up @@ -167,8 +167,8 @@ func (m *mgr) Share(ctx context.Context, md *provider.ResourceInfo, g *collabora
func (m *mgr) getByID(ctx context.Context, id *collaboration.ShareId) (*collaboration.Share, error) {
uid := conversions.FormatUserID(ctxpkg.ContextMustGetUser(ctx).Id)
s := conversions.DBShare{ID: id.OpaqueId}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, stime, permissions, share_type FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND id=? AND (uid_owner=? or uid_initiator=?)"
if err := m.db.QueryRow(query, id.OpaqueId, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.STime, &s.Permissions, &s.ShareType); err != nil {
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, stime, permissions, share_type FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND id=? AND (uid_owner=? or uid_initiator=?)"
if err := m.db.QueryRow(query, id.OpaqueId, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.STime, &s.Permissions, &s.ShareType); err != nil {
if err == sql.ErrNoRows {
return nil, errtypes.NotFound(id.OpaqueId)
}
Expand All @@ -183,8 +183,8 @@ func (m *mgr) getByKey(ctx context.Context, key *collaboration.ShareKey) (*colla

s := conversions.DBShare{}
shareType, shareWith := conversions.FormatGrantee(key.Grantee)
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, id, stime, permissions, share_type FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND uid_owner=? AND fileid_prefix=? AND item_source=? AND share_type=? AND share_with=? AND (uid_owner=? or uid_initiator=?)"
if err := m.db.QueryRow(query, owner, key.ResourceId.StorageId, key.ResourceId.OpaqueId, shareType, shareWith, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ID, &s.STime, &s.Permissions, &s.ShareType); err != nil {
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, id, stime, permissions, share_type FROM oc_share WHERE (orphan = 0 or orphan IS NULL) AND uid_owner=? AND fileid_prefix=? AND item_source=? AND share_type=? AND share_with=? AND (uid_owner=? or uid_initiator=?)"
if err := m.db.QueryRow(query, owner, key.ResourceId.StorageId, key.ResourceId.OpaqueId, shareType, shareWith, uid, uid).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.ID, &s.STime, &s.Permissions, &s.ShareType); err != nil {
if err == sql.ErrNoRows {
return nil, errtypes.NotFound(key.String())
}
Expand Down Expand Up @@ -283,7 +283,7 @@ func (m *mgr) UpdateShare(ctx context.Context, ref *collaboration.ShareReference
func (m *mgr) ListShares(ctx context.Context, filters []*collaboration.Filter) ([]*collaboration.Share, error) {
uid := conversions.FormatUserID(ctxpkg.ContextMustGetUser(ctx).Id)
query := `select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with,
coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, id, stime, permissions, share_type
coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, id, stime, permissions, share_type
FROM oc_share
WHERE (orphan = 0 or orphan IS NULL) AND (uid_owner=? or uid_initiator=?)`
params := []interface{}{uid, uid}
Expand Down Expand Up @@ -317,7 +317,7 @@ func (m *mgr) ListShares(ctx context.Context, filters []*collaboration.Filter) (
var s conversions.DBShare
shares := []*collaboration.Share{}
for rows.Next() {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ID, &s.STime, &s.Permissions, &s.ShareType); err != nil {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.ID, &s.STime, &s.Permissions, &s.ShareType); err != nil {
continue
}
shares = append(shares, conversions.ConvertToCS3Share(s))
Expand All @@ -340,7 +340,7 @@ func (m *mgr) ListReceivedShares(ctx context.Context, filters []*collaboration.F
}

query := `SELECT coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with,
coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, ts.id, stime,
coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, ts.id, stime,
permissions, share_type, accepted, coalesce(tr.rejected_by, '') as rejected_by
FROM oc_share ts LEFT JOIN oc_share_acl tr ON (ts.id = tr.id AND tr.rejected_by = ?)
WHERE (orphan = 0 or orphan IS NULL) AND (uid_owner != ? AND uid_initiator != ?)`
Expand Down Expand Up @@ -369,7 +369,7 @@ func (m *mgr) ListReceivedShares(ctx context.Context, filters []*collaboration.F
var s conversions.DBShare
shares := []*collaboration.ReceivedShare{}
for rows.Next() {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ID, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
if err := rows.Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.ID, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
continue
}
shares = append(shares, conversions.ConvertToCS3ReceivedShare(s))
Expand All @@ -391,13 +391,13 @@ func (m *mgr) getReceivedByID(ctx context.Context, id *collaboration.ShareId) (*
}

s := conversions.DBShare{ID: id.OpaqueId}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, stime, permissions, share_type, accepted, coalesce(tr.rejected_by, '') as rejected_by FROM oc_share ts LEFT JOIN oc_share_acl tr ON (ts.id = tr.id AND tr.rejected_by = ?) WHERE (orphan = 0 or orphan IS NULL) AND ts.id=? "
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, stime, permissions, share_type, accepted, coalesce(tr.rejected_by, '') as rejected_by FROM oc_share ts LEFT JOIN oc_share_acl tr ON (ts.id = tr.id AND tr.rejected_by = ?) WHERE (orphan = 0 or orphan IS NULL) AND ts.id=? "
if len(user.Groups) > 0 {
query += "AND ((share_with=? AND share_type = 0) OR (share_type = 1 AND share_with in (?" + strings.Repeat(",?", len(user.Groups)-1) + ")))"
} else {
query += "AND (share_with=? AND share_type = 0)"
}
if err := m.db.QueryRow(query, params...).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
if err := m.db.QueryRow(query, params...).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
if err == sql.ErrNoRows {
return nil, errtypes.NotFound(id.OpaqueId)
}
Expand All @@ -417,14 +417,14 @@ func (m *mgr) getReceivedByKey(ctx context.Context, key *collaboration.ShareKey)
}

s := conversions.DBShare{}
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, ts.id, stime, permissions, share_type, accepted, coalesce(tr.rejected_by, '') as rejected_by FROM oc_share ts LEFT JOIN oc_share_acl tr ON (ts.id = tr.id AND tr.rejected_by = ?) WHERE (orphan = 0 or orphan IS NULL) AND uid_owner=? AND fileid_prefix=? AND item_source=? AND share_type=? AND share_with=? "
query := "select coalesce(uid_owner, '') as uid_owner, coalesce(uid_initiator, '') as uid_initiator, coalesce(share_with, '') as share_with, coalesce(fileid_prefix, '') as fileid_prefix, coalesce(item_source, '') as item_source, coalesce(item_type, '') as item_type, ts.id, stime, permissions, share_type, accepted, coalesce(tr.rejected_by, '') as rejected_by FROM oc_share ts LEFT JOIN oc_share_acl tr ON (ts.id = tr.id AND tr.rejected_by = ?) WHERE (orphan = 0 or orphan IS NULL) AND uid_owner=? AND fileid_prefix=? AND item_source=? AND share_type=? AND share_with=? "
if len(user.Groups) > 0 {
query += "AND ((share_with=? AND share_type = 0) OR (share_type = 1 AND share_with in (?" + strings.Repeat(",?", len(user.Groups)-1) + ")))"
} else {
query += "AND (share_with=? AND share_type = 0)"
}

if err := m.db.QueryRow(query, params...).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ID, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
if err := m.db.QueryRow(query, params...).Scan(&s.UIDOwner, &s.UIDInitiator, &s.ShareWith, &s.Prefix, &s.ItemSource, &s.ItemType, &s.ID, &s.STime, &s.Permissions, &s.ShareType, &s.State, &s.RejectedBy); err != nil {
if err == sql.ErrNoRows {
return nil, errtypes.NotFound(key.String())
}
Expand Down
20 changes: 12 additions & 8 deletions pkg/cbox/utils/conversions.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ type DBShare struct {
UIDInitiator string
Prefix string
ItemSource string
ItemType string
ShareWith string
Token string
Expiration string
Expand Down Expand Up @@ -111,7 +112,7 @@ func SharePermToInt(p *provider.ResourcePermissions) int {
}

// IntTosharePerm retrieves read/write permissions from an integer
func IntTosharePerm(p int) *provider.ResourcePermissions {
func IntTosharePerm(p int, itemType string) *provider.ResourcePermissions {
switch p {
case 1:
return &provider.ResourcePermissions{
Expand All @@ -125,7 +126,7 @@ func IntTosharePerm(p int) *provider.ResourcePermissions {
InitiateFileDownload: true,
}
case 15:
return &provider.ResourcePermissions{
perm := &provider.ResourcePermissions{
ListContainer: true,
ListGrants: true,
ListFileVersions: true,
Expand All @@ -135,14 +136,17 @@ func IntTosharePerm(p int) *provider.ResourcePermissions {
GetQuota: true,
InitiateFileDownload: true,

Move: true,
InitiateFileUpload: true,
RestoreFileVersion: true,
RestoreRecycleItem: true,
CreateContainer: true,
Delete: true,
PurgeRecycle: true,
}
if itemType == "folder" {
perm.CreateContainer = true
perm.Delete = true
perm.Move = true
perm.PurgeRecycle = true
}
return perm
default:
// TODO we may have other options, for now this is a denial
return &provider.ResourcePermissions{}
Expand Down Expand Up @@ -199,7 +203,7 @@ func ConvertToCS3Share(s DBShare) *collaboration.Share {
StorageId: s.Prefix,
OpaqueId: s.ItemSource,
},
Permissions: &collaboration.SharePermissions{Permissions: IntTosharePerm(s.Permissions)},
Permissions: &collaboration.SharePermissions{Permissions: IntTosharePerm(s.Permissions, s.ItemType)},
Grantee: ExtractGrantee(s.ShareType, s.ShareWith),
Owner: ExtractUserID(s.UIDOwner),
Creator: ExtractUserID(s.UIDInitiator),
Expand Down Expand Up @@ -249,7 +253,7 @@ func ConvertToCS3PublicShare(s DBShare) *link.PublicShare {
StorageId: s.Prefix,
OpaqueId: s.ItemSource,
},
Permissions: &link.PublicSharePermissions{Permissions: IntTosharePerm(s.Permissions)},
Permissions: &link.PublicSharePermissions{Permissions: IntTosharePerm(s.Permissions, s.ItemType)},
Owner: ExtractUserID(s.UIDOwner),
Creator: ExtractUserID(s.UIDInitiator),
Token: s.Token,
Expand Down