From 4a67b571032c8aeee95d60f3284eb7cf5e9703ce Mon Sep 17 00:00:00 2001 From: Wilfred Asomani Date: Mon, 13 Feb 2023 18:19:20 +0000 Subject: [PATCH] satellite/{console,web}: make bucket endpoints support publicID This change adds support for project public id to the bucket-names and usage-report endpoints. Issue: https://github.com/storj/storj/issues/5578 Change-Id: I2429ebebe52dfc8217fc40f4691e7bc473b805fb --- .../console/consoleweb/consoleapi/buckets.go | 19 +++++- .../consoleweb/consoleapi/buckets_test.go | 61 +++++++++++-------- satellite/console/consoleweb/server.go | 21 ++++++- satellite/console/service.go | 10 +-- satellite/console/service_test.go | 5 ++ web/satellite/src/api/buckets.ts | 2 +- 6 files changed, 82 insertions(+), 36 deletions(-) diff --git a/satellite/console/consoleweb/consoleapi/buckets.go b/satellite/console/consoleweb/consoleapi/buckets.go index 367c1771b..485e8c78d 100644 --- a/satellite/console/consoleweb/consoleapi/buckets.go +++ b/satellite/console/consoleweb/consoleapi/buckets.go @@ -43,10 +43,23 @@ func (b *Buckets) AllBucketNames(w http.ResponseWriter, r *http.Request) { w.Header().Set("Content-Type", "application/json") projectIDString := r.URL.Query().Get("projectID") + publicIDString := r.URL.Query().Get("publicID") - projectID, err := uuid.FromString(projectIDString) - if err != nil { - b.serveJSONError(w, http.StatusInternalServerError, err) + var projectID uuid.UUID + if projectIDString != "" { + projectID, err = uuid.FromString(projectIDString) + if err != nil { + b.serveJSONError(w, http.StatusBadRequest, err) + return + } + } else if publicIDString != "" { + projectID, err = uuid.FromString(publicIDString) + if err != nil { + b.serveJSONError(w, http.StatusBadRequest, err) + return + } + } else { + b.serveJSONError(w, http.StatusBadRequest, errs.New("Project ID was not provided.")) return } diff --git a/satellite/console/consoleweb/consoleapi/buckets_test.go b/satellite/console/consoleweb/consoleapi/buckets_test.go index 4f02684fb..123c7edad 100644 --- a/satellite/console/consoleweb/consoleapi/buckets_test.go +++ b/satellite/console/consoleweb/consoleapi/buckets_test.go @@ -69,37 +69,46 @@ func Test_AllBucketNames(t *testing.T) { client := http.Client{} - req, err := http.NewRequestWithContext(ctx, "GET", "http://"+planet.Satellites[0].API.Console.Listener.Addr().String()+"/api/v0/buckets/bucket-names?projectID="+project.ID.String(), nil) - require.NoError(t, err) + testRequest := func(req *http.Request) { + expire := time.Now().AddDate(0, 0, 1) + cookie := http.Cookie{ + Name: "_tokenKey", + Path: "/", + Value: tokenInfo.Token.String(), + Expires: expire, + } - expire := time.Now().AddDate(0, 0, 1) - cookie := http.Cookie{ - Name: "_tokenKey", - Path: "/", - Value: tokenInfo.Token.String(), - Expires: expire, + req.AddCookie(&cookie) + + result, err := client.Do(req) + require.NoError(t, err) + require.Equal(t, http.StatusOK, result.StatusCode) + + body, err := io.ReadAll(result.Body) + require.NoError(t, err) + + var output []string + + err = json.Unmarshal(body, &output) + require.NoError(t, err) + + require.Equal(t, bucket1.Name, output[0]) + require.Equal(t, bucket2.Name, output[1]) + + defer func() { + err = result.Body.Close() + require.NoError(t, err) + }() } - req.AddCookie(&cookie) - - result, err := client.Do(req) + // test using Project.ID + req, err := http.NewRequestWithContext(ctx, "GET", "http://"+planet.Satellites[0].API.Console.Listener.Addr().String()+"/api/v0/buckets/bucket-names?projectID="+project.ID.String(), nil) require.NoError(t, err) - require.Equal(t, http.StatusOK, result.StatusCode) + testRequest(req) - body, err := io.ReadAll(result.Body) + // test using Project.PublicID + req, err = http.NewRequestWithContext(ctx, "GET", "http://"+planet.Satellites[0].API.Console.Listener.Addr().String()+"/api/v0/buckets/bucket-names?publicID="+project.PublicID.String(), nil) require.NoError(t, err) - - var output []string - - err = json.Unmarshal(body, &output) - require.NoError(t, err) - - require.Equal(t, bucket1.Name, output[0]) - require.Equal(t, bucket2.Name, output[1]) - - defer func() { - err = result.Body.Close() - require.NoError(t, err) - }() + testRequest(req) }) } diff --git a/satellite/console/consoleweb/server.go b/satellite/console/consoleweb/server.go index f6290a4b0..38bf9cd9a 100644 --- a/satellite/console/consoleweb/server.go +++ b/satellite/console/consoleweb/server.go @@ -580,11 +580,28 @@ func (server *Server) bucketUsageReportHandler(w http.ResponseWriter, r *http.Re } // parse query params - projectID, err := uuid.FromString(r.URL.Query().Get("projectID")) - if err != nil { + projectIDString := r.URL.Query().Get("projectID") + publicIDString := r.URL.Query().Get("publicID") + + var projectID uuid.UUID + if projectIDString != "" { + projectID, err = uuid.FromString(projectIDString) + if err != nil { + server.serveError(w, http.StatusBadRequest) + return + } + } else if publicIDString != "" { + projectID, err = uuid.FromString(publicIDString) + if err != nil { + server.serveError(w, http.StatusBadRequest) + return + } + } else { + server.log.Error("bucket usage report error", zap.Error(errs.New("Project ID was not provided."))) server.serveError(w, http.StatusBadRequest) return } + sinceStamp, err := strconv.ParseInt(r.URL.Query().Get("since"), 10, 64) if err != nil { server.serveError(w, http.StatusBadRequest) diff --git a/satellite/console/service.go b/satellite/console/service.go index c7d2abb54..2e7aea99e 100644 --- a/satellite/console/service.go +++ b/satellite/console/service.go @@ -2416,6 +2416,7 @@ func (s *Service) GetBucketTotals(ctx context.Context, projectID uuid.UUID, curs } // GetAllBucketNames retrieves all bucket names of a specific project. +// projectID here may be Project.ID or Project.PublicID. func (s *Service) GetAllBucketNames(ctx context.Context, projectID uuid.UUID) (_ []string, err error) { defer mon.Task()(&ctx)(&err) @@ -2424,7 +2425,7 @@ func (s *Service) GetAllBucketNames(ctx context.Context, projectID uuid.UUID) (_ return nil, Error.Wrap(err) } - _, err = s.isProjectMember(ctx, user.ID, projectID) + isMember, err := s.isProjectMember(ctx, user.ID, projectID) if err != nil { return nil, Error.Wrap(err) } @@ -2437,7 +2438,7 @@ func (s *Service) GetAllBucketNames(ctx context.Context, projectID uuid.UUID) (_ All: true, } - bucketsList, err := s.buckets.ListBuckets(ctx, projectID, listOptions, allowedBuckets) + bucketsList, err := s.buckets.ListBuckets(ctx, isMember.project.ID, listOptions, allowedBuckets) if err != nil { return nil, Error.Wrap(err) } @@ -2451,6 +2452,7 @@ func (s *Service) GetAllBucketNames(ctx context.Context, projectID uuid.UUID) (_ } // GetBucketUsageRollups retrieves summed usage rollups for every bucket of particular project for a given period. +// projectID here may be Project.ID or Project.PublicID. func (s *Service) GetBucketUsageRollups(ctx context.Context, projectID uuid.UUID, since, before time.Time) (_ []accounting.BucketUsageRollup, err error) { defer mon.Task()(&ctx)(&err) @@ -2459,12 +2461,12 @@ func (s *Service) GetBucketUsageRollups(ctx context.Context, projectID uuid.UUID return nil, Error.Wrap(err) } - _, err = s.isProjectMember(ctx, user.ID, projectID) + isMember, err := s.isProjectMember(ctx, user.ID, projectID) if err != nil { return nil, Error.Wrap(err) } - result, err := s.projectAccounting.GetBucketUsageRollups(ctx, projectID, since, before) + result, err := s.projectAccounting.GetBucketUsageRollups(ctx, isMember.project.ID, since, before) if err != nil { return nil, Error.Wrap(err) } diff --git a/satellite/console/service_test.go b/satellite/console/service_test.go index 11d05eaaa..381a07fa4 100644 --- a/satellite/console/service_test.go +++ b/satellite/console/service_test.go @@ -358,6 +358,11 @@ func TestService(t *testing.T) { require.Equal(t, bucket1.Name, bucketNames[0]) require.Equal(t, bucket2.Name, bucketNames[1]) + bucketNames, err = service.GetAllBucketNames(userCtx2, up2Pro1.PublicID) + require.NoError(t, err) + require.Equal(t, bucket1.Name, bucketNames[0]) + require.Equal(t, bucket2.Name, bucketNames[1]) + // Getting someone else buckets should not work bucketsForUnauthorizedUser, err := service.GetAllBucketNames(userCtx1, up2Pro1.ID) require.Error(t, err) diff --git a/web/satellite/src/api/buckets.ts b/web/satellite/src/api/buckets.ts index faf058abb..a2e36b0de 100644 --- a/web/satellite/src/api/buckets.ts +++ b/web/satellite/src/api/buckets.ts @@ -65,7 +65,7 @@ export class BucketsApiGql extends BaseGql implements BucketsApi { * @throws Error */ public async getAllBucketNames(projectId: string): Promise { - const path = `${this.ROOT_PATH}/bucket-names?projectID=${projectId}`; + const path = `${this.ROOT_PATH}/bucket-names?publicID=${projectId}`; const response = await this.client.get(path); if (!response.ok) {