LCOV - code coverage report
Current view: top level - server/restapi/change - DeleteComment.java (source / functions) Hit Total Coverage
Test: _coverage_report.dat Lines: 38 39 97.4 %
Date: 2022-11-19 15:00:39 Functions: 6 6 100.0 %

          Line data    Source code
       1             : // Copyright (C) 2017 The Android Open Source Project
       2             : //
       3             : // Licensed under the Apache License, Version 2.0 (the "License");
       4             : // you may not use this file except in compliance with the License.
       5             : // You may obtain a copy of the License at
       6             : //
       7             : // http://www.apache.org/licenses/LICENSE-2.0
       8             : //
       9             : // Unless required by applicable law or agreed to in writing, software
      10             : // distributed under the License is distributed on an "AS IS" BASIS,
      11             : // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
      12             : // See the License for the specific language governing permissions and
      13             : // limitations under the License.
      14             : 
      15             : package com.google.gerrit.server.restapi.change;
      16             : 
      17             : import com.google.common.base.Strings;
      18             : import com.google.gerrit.entities.HumanComment;
      19             : import com.google.gerrit.entities.PatchSet;
      20             : import com.google.gerrit.extensions.api.changes.DeleteCommentInput;
      21             : import com.google.gerrit.extensions.common.CommentInfo;
      22             : import com.google.gerrit.extensions.restapi.ResourceConflictException;
      23             : import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
      24             : import com.google.gerrit.extensions.restapi.Response;
      25             : import com.google.gerrit.extensions.restapi.RestApiException;
      26             : import com.google.gerrit.extensions.restapi.RestModifyView;
      27             : import com.google.gerrit.server.CommentsUtil;
      28             : import com.google.gerrit.server.CurrentUser;
      29             : import com.google.gerrit.server.change.HumanCommentResource;
      30             : import com.google.gerrit.server.notedb.ChangeNotes;
      31             : import com.google.gerrit.server.permissions.GlobalPermission;
      32             : import com.google.gerrit.server.permissions.PermissionBackend;
      33             : import com.google.gerrit.server.permissions.PermissionBackendException;
      34             : import com.google.gerrit.server.update.BatchUpdate;
      35             : import com.google.gerrit.server.update.BatchUpdateOp;
      36             : import com.google.gerrit.server.update.ChangeContext;
      37             : import com.google.gerrit.server.update.UpdateException;
      38             : import com.google.gerrit.server.util.time.TimeUtil;
      39             : import com.google.inject.Inject;
      40             : import com.google.inject.Provider;
      41             : import com.google.inject.Singleton;
      42             : import java.io.IOException;
      43             : import java.util.List;
      44             : import java.util.Optional;
      45             : import org.eclipse.jgit.errors.ConfigInvalidException;
      46             : 
      47             : @Singleton
      48             : public class DeleteComment implements RestModifyView<HumanCommentResource, DeleteCommentInput> {
      49             : 
      50             :   private final Provider<CurrentUser> userProvider;
      51             :   private final PermissionBackend permissionBackend;
      52             :   private final BatchUpdate.Factory updateFactory;
      53             :   private final CommentsUtil commentsUtil;
      54             :   private final Provider<CommentJson> commentJson;
      55             :   private final ChangeNotes.Factory notesFactory;
      56             : 
      57             :   @Inject
      58             :   public DeleteComment(
      59             :       Provider<CurrentUser> userProvider,
      60             :       PermissionBackend permissionBackend,
      61             :       BatchUpdate.Factory updateFactory,
      62             :       CommentsUtil commentsUtil,
      63             :       Provider<CommentJson> commentJson,
      64         138 :       ChangeNotes.Factory notesFactory) {
      65         138 :     this.userProvider = userProvider;
      66         138 :     this.permissionBackend = permissionBackend;
      67         138 :     this.updateFactory = updateFactory;
      68         138 :     this.commentsUtil = commentsUtil;
      69         138 :     this.commentJson = commentJson;
      70         138 :     this.notesFactory = notesFactory;
      71         138 :   }
      72             : 
      73             :   @Override
      74             :   public Response<CommentInfo> apply(HumanCommentResource rsrc, DeleteCommentInput input)
      75             :       throws RestApiException, IOException, ConfigInvalidException, PermissionBackendException,
      76             :           UpdateException {
      77           3 :     CurrentUser user = userProvider.get();
      78           3 :     permissionBackend.user(user).check(GlobalPermission.ADMINISTRATE_SERVER);
      79             : 
      80           3 :     if (input == null) {
      81           1 :       input = new DeleteCommentInput();
      82             :     }
      83             : 
      84           3 :     String newMessage = getCommentNewMessage(user.asIdentifiedUser().getName(), input.reason);
      85           3 :     DeleteCommentOp deleteCommentOp = new DeleteCommentOp(rsrc, newMessage);
      86           3 :     try (BatchUpdate batchUpdate =
      87           3 :         updateFactory.create(rsrc.getRevisionResource().getProject(), user, TimeUtil.now())) {
      88           3 :       batchUpdate.addOp(rsrc.getRevisionResource().getChange().getId(), deleteCommentOp).execute();
      89             :     }
      90             : 
      91           3 :     ChangeNotes updatedNotes =
      92           3 :         notesFactory.createChecked(
      93           3 :             rsrc.getRevisionResource().getProject(),
      94           3 :             rsrc.getRevisionResource().getChangeResource().getId());
      95           3 :     List<HumanComment> changeComments = commentsUtil.publishedHumanCommentsByChange(updatedNotes);
      96           3 :     Optional<HumanComment> updatedComment =
      97           3 :         changeComments.stream().filter(c -> c.key.equals(rsrc.getComment().key)).findFirst();
      98           3 :     if (!updatedComment.isPresent()) {
      99             :       // This should not happen as this endpoint should not remove the whole comment.
     100           0 :       throw new ResourceNotFoundException("comment not found: " + rsrc.getComment().key);
     101             :     }
     102             : 
     103           3 :     return Response.ok(commentJson.get().newHumanCommentFormatter().format(updatedComment.get()));
     104             :   }
     105             : 
     106             :   private static String getCommentNewMessage(String name, String reason) {
     107           3 :     StringBuilder stringBuilder = new StringBuilder("Comment removed by: ").append(name);
     108           3 :     if (!Strings.isNullOrEmpty(reason)) {
     109           1 :       stringBuilder.append("; Reason: ").append(reason);
     110             :     }
     111           3 :     return stringBuilder.toString();
     112             :   }
     113             : 
     114             :   private class DeleteCommentOp implements BatchUpdateOp {
     115             :     private final HumanCommentResource rsrc;
     116             :     private final String newMessage;
     117             : 
     118           3 :     DeleteCommentOp(HumanCommentResource rsrc, String newMessage) {
     119           3 :       this.rsrc = rsrc;
     120           3 :       this.newMessage = newMessage;
     121           3 :     }
     122             : 
     123             :     @Override
     124             :     public boolean updateChange(ChangeContext ctx)
     125             :         throws ResourceConflictException, ResourceNotFoundException {
     126           3 :       PatchSet.Id psId = ctx.getChange().currentPatchSetId();
     127           3 :       commentsUtil.deleteCommentByRewritingHistory(
     128           3 :           ctx.getUpdate(psId), rsrc.getComment().key, newMessage);
     129           3 :       return true;
     130             :     }
     131             :   }
     132             : }

Generated by: LCOV version 1.16+git.20220603.dfeb750