Skip to content

Commit

Permalink
first implementation of shareByMe endpoint
Browse files Browse the repository at this point in the history
  • Loading branch information
gmgigi96 committed Aug 1, 2024
1 parent a15f8d3 commit 1e9046e
Show file tree
Hide file tree
Showing 2 changed files with 155 additions and 1 deletion.
5 changes: 4 additions & 1 deletion internal/http/services/owncloud/ocgraph/ocgraph.go
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,10 @@ func (s *svc) initRouter() {
})
})
s.router.Route("/v1beta1", func(r chi.Router) {
r.Get("/me/drive/sharedWithMe", s.getSharedWithMe)
r.Route("/me/drive", func(r chi.Router) {
r.Get("/sharedWithMe", s.getSharedWithMe)
r.Get("/sharedByMe", s.getSharedByMe)
})
r.Get("/roleManagement/permissions/roleDefinitions", s.getRoleDefinitions)
})
}
Expand Down
151 changes: 151 additions & 0 deletions internal/http/services/owncloud/ocgraph/shares.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,10 +25,13 @@ import (
"encoding/json"
"fmt"
"net/http"
"path"

"github.com/alitto/pond"
gateway "github.com/cs3org/go-cs3apis/cs3/gateway/v1beta1"
groupv1beta1 "github.com/cs3org/go-cs3apis/cs3/identity/group/v1beta1"
userv1beta1 "github.com/cs3org/go-cs3apis/cs3/identity/user/v1beta1"
rpcv1beta1 "github.com/cs3org/go-cs3apis/cs3/rpc/v1beta1"

collaborationv1beta1 "github.com/cs3org/go-cs3apis/cs3/sharing/collaboration/v1beta1"
provider "github.com/cs3org/go-cs3apis/cs3/storage/provider/v1beta1"
Expand Down Expand Up @@ -228,5 +231,153 @@ func (s *svc) cs3GranteeToSharePointIdentitySet(ctx context.Context, grantee *pr
}

func (s *svc) getSharedByMe(w http.ResponseWriter, r *http.Request) {
ctx := r.Context()
log := appctx.GetLogger(ctx)

list, err := s.listExistingShares(ctx)
if err != nil {
log.Error().Err(err).Msg("error getting shares")
w.WriteHeader(http.StatusInternalServerError)
return
}

shares := make([]*libregraph.DriveItem, 0, len(list))
for _, share := range list {
drive, err := s.cs3ShareToDriveItem(ctx, share)
if err != nil {
log.Error().Err(err).Msg("error getting shares")
w.WriteHeader(http.StatusInternalServerError)
return
}
shares = append(shares, drive)
}

if err := json.NewEncoder(w).Encode(map[string]any{
"value": shares,
}); err != nil {
log.Error().Err(err).Msg("error marshalling shares as json")
w.WriteHeader(http.StatusInternalServerError)
return
}

}

func (s *svc) cs3ShareToDriveItem(ctx context.Context, p *Pair[*collaborationv1beta1.Share, *provider.ResourceInfo]) (*libregraph.DriveItem, error) {
createdTime := utils.TSToTime(p.First.Ctime)

creator, err := s.getUserByID(ctx, p.First.Creator)
if err != nil {
return nil, err
}

grantee, err := s.cs3GranteeToSharePointIdentitySet(ctx, p.First.Grantee)
if err != nil {
return nil, err
}

roles := make([]string, 0, 1)
role := CS3ResourcePermissionsToUnifiedRole(p.Second.PermissionSet)
if role != nil {
roles = append(roles, *role.Id)
}

parentRelativePath := path.Dir(relativePathToSpaceID(p.Second))

d := &libregraph.DriveItem{
ETag: libregraph.PtrString(p.Second.Etag),
Id: libregraph.PtrString(spaces.EncodeResourceID(p.Second.Id)),
LastModifiedDateTime: libregraph.PtrTime(utils.TSToTime(p.First.Mtime)),
Name: libregraph.PtrString(p.Second.Name),
ParentReference: &libregraph.ItemReference{
DriveId: libregraph.PtrString(spaces.EncodeSpaceID(p.Second.Id.StorageId, p.Second.Id.SpaceId)),
// DriveType: libregraph.PtrString(p.Second.Space.SpaceType),
Id: libregraph.PtrString(spaces.EncodeResourceID(p.Second.ParentId)),
Name: libregraph.PtrString(path.Base(parentRelativePath)),
Path: libregraph.PtrString(parentRelativePath),
},
Permissions: []libregraph.Permission{
{
CreatedDateTime: *libregraph.NewNullableTime(&createdTime),
GrantedToV2: grantee,
Id: nil, // TODO: what is this??
Invitation: &libregraph.SharingInvitation{
InvitedBy: &libregraph.IdentitySet{
User: &libregraph.Identity{
DisplayName: creator.DisplayName,
Id: libregraph.PtrString(creator.Id.OpaqueId),
},
},
},
Roles: roles,
},
},
Size: libregraph.PtrInt64(int64(p.Second.Size)),
}

if p.Second.Type == provider.ResourceType_RESOURCE_TYPE_CONTAINER {
d.Folder = libregraph.NewFolder()
} else {
d.File = &libregraph.OpenGraphFile{
MimeType: &p.Second.MimeType,
}
}

return d, nil
}

type Pair[T, V any] struct {
First T
Second V
}

func (s *svc) listExistingShares(ctx context.Context) ([]*Pair[*collaborationv1beta1.Share, *provider.ResourceInfo], error) {
gw, err := s.getClient()
if err != nil {
return nil, err
}

rshares, err := gw.ListShares(ctx, &collaborationv1beta1.ListSharesRequest{})
if err != nil {
return nil, err
}

sharesCh := make(chan *Pair[*collaborationv1beta1.Share, *provider.ResourceInfo], len(rshares.Shares))
pool := pond.New(50, len(rshares.Shares))
for _, share := range rshares.Shares {
share := share
// TODO (gdelmont): we should report any eventual error raised by the goroutines
pool.Submit(func() {
stat, err := gw.Stat(ctx, &provider.StatRequest{
Ref: &provider.Reference{
ResourceId: share.ResourceId,
},
})
if err != nil {
return
}
if stat.Status.Code != rpcv1beta1.Code_CODE_OK {
return
}

sharesCh <- &Pair[*collaborationv1beta1.Share, *provider.ResourceInfo]{
First: share,
Second: stat.Info,
}
})
}

sris := make([]*Pair[*collaborationv1beta1.Share, *provider.ResourceInfo], 0, len(rshares.Shares))
done := make(chan struct{})
go func() {
for s := range sharesCh {
sris = append(sris, s)
}
done <- struct{}{}
}()
pool.StopAndWait()
close(sharesCh)
<-done
close(done)

return sris, nil
}

0 comments on commit 1e9046e

Please sign in to comment.