Merge changes from topic "change-messages-rest-api"
* changes: Add REST endpoint to get one change message Add REST endpoint for listing change messages
This commit is contained in:
commit
a72fbf418e
@ -2403,6 +2403,87 @@ As response the change's hashtags are returned as a list of strings.
|
||||
]
|
||||
----
|
||||
|
||||
[[list-change-messages]]
|
||||
=== List Change Messages
|
||||
--
|
||||
'GET /changes/link:#change-id[\{change-id\}]/messages'
|
||||
--
|
||||
|
||||
Lists all the messages of a change including link:#detailed-accounts[detailed account information].
|
||||
|
||||
.Request
|
||||
----
|
||||
GET /changes/myProject~master~I8473b95934b5732ac55d26311a706c9c2bde9940/messages
|
||||
----
|
||||
|
||||
As response a list of link:#change-message-info[ChangeMessageInfo] entities is returned.
|
||||
|
||||
.Response
|
||||
----
|
||||
HTTP/1.1 200 OK
|
||||
Content-Disposition: attachment
|
||||
Content-Type: application/json; charset=UTF-8
|
||||
|
||||
)]}'
|
||||
[
|
||||
{
|
||||
"id": "YH-egE",
|
||||
"author": {
|
||||
"_account_id": 1000096,
|
||||
"name": "John Doe",
|
||||
"email": "john.doe@example.com",
|
||||
"username": "jdoe"
|
||||
},
|
||||
"date": "2013-03-23 21:34:02.419000000",
|
||||
"message": "Patch Set 1:\n\nThis is the first message.",
|
||||
"_revision_number": 1
|
||||
},
|
||||
{
|
||||
"id": "WEEdhU",
|
||||
"author": {
|
||||
"_account_id": 1000097,
|
||||
"name": "Jane Roe",
|
||||
"email": "jane.roe@example.com",
|
||||
"username": "jroe"
|
||||
},
|
||||
"date": "2013-03-23 21:36:52.332000000",
|
||||
"message": "Patch Set 1:\n\nThis is the second message.\n\nWith a line break.",
|
||||
"_revision_number": 1
|
||||
}
|
||||
]
|
||||
----
|
||||
|
||||
[[get-change-message]]
|
||||
=== Get Change Message
|
||||
|
||||
Retrieves a change message including link:#detailed-accounts[detailed account information].
|
||||
|
||||
--
|
||||
'GET /changes/link:#change-id[\{change-id\}]/message/link:#change-message-id[\{change-message-id\}'
|
||||
--
|
||||
|
||||
As response a link:#change-message-info[ChangeMessageInfo] entity is returned.
|
||||
|
||||
.Response
|
||||
----
|
||||
HTTP/1.1 200 OK
|
||||
Content-Disposition: attachment
|
||||
Content-Type: application/json; charset=UTF-8
|
||||
|
||||
)]}'
|
||||
{
|
||||
"id": "aaee04dcb46bafc8be24d8aa70b3b1beb7df5780",
|
||||
"author": {
|
||||
"_account_id": 1000096,
|
||||
"name": "John Doe",
|
||||
"email": "john.doe@example.com",
|
||||
"username": "jdoe"
|
||||
},
|
||||
"date": "2013-03-23 21:34:02.419000000",
|
||||
"message": "Change message removed by: Administrator; Reason: spam",
|
||||
"_revision_number": 1
|
||||
}
|
||||
----
|
||||
|
||||
[[edit-endpoints]]
|
||||
== Change Edit Endpoints
|
||||
@ -5366,6 +5447,10 @@ If you need more time to migrate off of old change IDs, please see
|
||||
link:config-gerrit.html#change.api.allowedIdentifier[change.api.allowedIdentifier]
|
||||
for more information on how to enable the use of deprecated identifiers.
|
||||
|
||||
[[change-message-id]]
|
||||
=== \{change-message-id\}
|
||||
ID of a change message returned in a link:#change-message-info[ChangeMessageInfo].
|
||||
|
||||
[[comment-id]]
|
||||
=== \{comment-id\}
|
||||
UUID of a published comment.
|
||||
|
@ -19,6 +19,7 @@ import com.google.gerrit.common.Nullable;
|
||||
import com.google.gerrit.extensions.client.ListChangesOption;
|
||||
import com.google.gerrit.extensions.common.AccountInfo;
|
||||
import com.google.gerrit.extensions.common.ChangeInfo;
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.common.CommentInfo;
|
||||
import com.google.gerrit.extensions.common.CommitMessageInput;
|
||||
import com.google.gerrit.extensions.common.EditInfo;
|
||||
@ -283,6 +284,25 @@ public interface ChangeApi {
|
||||
/** Check if this change is a pure revert of claimedOriginal (SHA1 in 40 digit hex). */
|
||||
PureRevertInfo pureRevert(String claimedOriginal) throws RestApiException;
|
||||
|
||||
/**
|
||||
* Get all messages of a change with detailed account info.
|
||||
*
|
||||
* @return a list of messages sorted by their creation time.
|
||||
* @throws RestApiException
|
||||
*/
|
||||
List<ChangeMessageInfo> messages() throws RestApiException;
|
||||
|
||||
/**
|
||||
* Look up a change message of a change by its id.
|
||||
*
|
||||
* @param id the id of the change message. Note that in NoteDb, this id is the {@code ObjectId} of
|
||||
* a commit on the change meta branch. In ReviewDb, it's a UUID generated randomly. That means
|
||||
* a change message id could be different between NoteDb and ReviewDb.
|
||||
* @return API for accessing a change message.
|
||||
* @throws RestApiException if the id is invalid.
|
||||
*/
|
||||
ChangeMessageApi message(String id) throws RestApiException;
|
||||
|
||||
abstract class SuggestedReviewersRequest {
|
||||
private String query;
|
||||
private int limit;
|
||||
@ -590,5 +610,15 @@ public interface ChangeApi {
|
||||
public PureRevertInfo pureRevert(String claimedOriginal) throws RestApiException {
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<ChangeMessageInfo> messages() throws RestApiException {
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChangeMessageApi message(String id) throws RestApiException {
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,36 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.extensions.api.changes;
|
||||
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.restapi.NotImplementedException;
|
||||
import com.google.gerrit.extensions.restapi.RestApiException;
|
||||
|
||||
/** Interface for change message APIs. */
|
||||
public interface ChangeMessageApi {
|
||||
/** Gets one change message. */
|
||||
ChangeMessageInfo get() throws RestApiException;
|
||||
|
||||
/**
|
||||
* A default implementation which allows source compatibility when adding new methods to the
|
||||
* interface.
|
||||
*/
|
||||
class NotImplemented implements ChangeMessageApi {
|
||||
@Override
|
||||
public ChangeMessageInfo get() throws RestApiException {
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
@ -15,6 +15,7 @@
|
||||
package com.google.gerrit.extensions.common;
|
||||
|
||||
import java.sql.Timestamp;
|
||||
import java.util.Objects;
|
||||
|
||||
public class ChangeMessageInfo {
|
||||
public String id;
|
||||
@ -24,4 +25,24 @@ public class ChangeMessageInfo {
|
||||
public Timestamp date;
|
||||
public String message;
|
||||
public Integer _revisionNumber;
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof ChangeMessageInfo) {
|
||||
ChangeMessageInfo cmi = (ChangeMessageInfo) o;
|
||||
return Objects.equals(id, cmi.id)
|
||||
&& Objects.equals(tag, cmi.tag)
|
||||
&& Objects.equals(author, cmi.author)
|
||||
&& Objects.equals(realAuthor, cmi.realAuthor)
|
||||
&& Objects.equals(date, cmi.date)
|
||||
&& Objects.equals(message, cmi.message)
|
||||
&& Objects.equals(_revisionNumber, cmi._revisionNumber);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(id, tag, author, realAuthor, date, message, _revisionNumber);
|
||||
}
|
||||
}
|
||||
|
@ -19,10 +19,12 @@ import static com.google.common.base.Preconditions.checkState;
|
||||
|
||||
import com.google.common.annotations.VisibleForTesting;
|
||||
import com.google.gerrit.common.Nullable;
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.reviewdb.client.Account;
|
||||
import com.google.gerrit.reviewdb.client.ChangeMessage;
|
||||
import com.google.gerrit.reviewdb.client.PatchSet;
|
||||
import com.google.gerrit.reviewdb.server.ReviewDb;
|
||||
import com.google.gerrit.server.account.AccountLoader;
|
||||
import com.google.gerrit.server.notedb.ChangeNotes;
|
||||
import com.google.gerrit.server.notedb.ChangeUpdate;
|
||||
import com.google.gerrit.server.notedb.NotesMigration;
|
||||
@ -141,4 +143,21 @@ public class ChangeMessagesUtil {
|
||||
public static boolean isAutogenerated(@Nullable String tag) {
|
||||
return tag != null && tag.startsWith(AUTOGENERATED_TAG_PREFIX);
|
||||
}
|
||||
|
||||
public static ChangeMessageInfo createChangeMessageInfo(
|
||||
ChangeMessage message, AccountLoader accountLoader) {
|
||||
PatchSet.Id patchNum = message.getPatchSetId();
|
||||
ChangeMessageInfo cmi = new ChangeMessageInfo();
|
||||
cmi.id = message.getKey().get();
|
||||
cmi.author = accountLoader.get(message.getAuthor());
|
||||
cmi.date = message.getWrittenOn();
|
||||
cmi.message = message.getMessage();
|
||||
cmi.tag = message.getTag();
|
||||
cmi._revisionNumber = patchNum != null ? patchNum.get() : null;
|
||||
Account.Id realAuthor = message.getRealAuthor();
|
||||
if (realAuthor != null) {
|
||||
cmi.realAuthor = accountLoader.get(realAuthor);
|
||||
}
|
||||
return cmi;
|
||||
}
|
||||
}
|
||||
|
@ -23,6 +23,7 @@ import com.google.gerrit.extensions.api.changes.AddReviewerResult;
|
||||
import com.google.gerrit.extensions.api.changes.AssigneeInput;
|
||||
import com.google.gerrit.extensions.api.changes.ChangeApi;
|
||||
import com.google.gerrit.extensions.api.changes.ChangeEditApi;
|
||||
import com.google.gerrit.extensions.api.changes.ChangeMessageApi;
|
||||
import com.google.gerrit.extensions.api.changes.Changes;
|
||||
import com.google.gerrit.extensions.api.changes.FixInput;
|
||||
import com.google.gerrit.extensions.api.changes.HashtagsInput;
|
||||
@ -39,6 +40,7 @@ import com.google.gerrit.extensions.api.changes.TopicInput;
|
||||
import com.google.gerrit.extensions.client.ListChangesOption;
|
||||
import com.google.gerrit.extensions.common.AccountInfo;
|
||||
import com.google.gerrit.extensions.common.ChangeInfo;
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.common.CommentInfo;
|
||||
import com.google.gerrit.extensions.common.CommitMessageInput;
|
||||
import com.google.gerrit.extensions.common.EditInfo;
|
||||
@ -53,11 +55,13 @@ import com.google.gerrit.extensions.restapi.RestApiException;
|
||||
import com.google.gerrit.server.StarredChangesUtil;
|
||||
import com.google.gerrit.server.StarredChangesUtil.IllegalLabelException;
|
||||
import com.google.gerrit.server.change.ChangeJson;
|
||||
import com.google.gerrit.server.change.ChangeMessageResource;
|
||||
import com.google.gerrit.server.change.ChangeResource;
|
||||
import com.google.gerrit.server.change.PureRevert;
|
||||
import com.google.gerrit.server.change.WorkInProgressOp;
|
||||
import com.google.gerrit.server.restapi.change.Abandon;
|
||||
import com.google.gerrit.server.restapi.change.ChangeIncludedIn;
|
||||
import com.google.gerrit.server.restapi.change.ChangeMessages;
|
||||
import com.google.gerrit.server.restapi.change.Check;
|
||||
import com.google.gerrit.server.restapi.change.CreateMergePatchSet;
|
||||
import com.google.gerrit.server.restapi.change.DeleteAssignee;
|
||||
@ -111,6 +115,8 @@ class ChangeApiImpl implements ChangeApi {
|
||||
private final Revisions revisions;
|
||||
private final ReviewerApiImpl.Factory reviewerApi;
|
||||
private final RevisionApiImpl.Factory revisionApi;
|
||||
private final ChangeMessageApiImpl.Factory changeMessageApi;
|
||||
private final ChangeMessages changeMessages;
|
||||
private final SuggestChangeReviewers suggestReviewers;
|
||||
private final ChangeResource change;
|
||||
private final Abandon abandon;
|
||||
@ -157,6 +163,8 @@ class ChangeApiImpl implements ChangeApi {
|
||||
Revisions revisions,
|
||||
ReviewerApiImpl.Factory reviewerApi,
|
||||
RevisionApiImpl.Factory revisionApi,
|
||||
ChangeMessageApiImpl.Factory changeMessageApi,
|
||||
ChangeMessages changeMessages,
|
||||
SuggestChangeReviewers suggestReviewers,
|
||||
Abandon abandon,
|
||||
Revert revert,
|
||||
@ -201,6 +209,8 @@ class ChangeApiImpl implements ChangeApi {
|
||||
this.revisions = revisions;
|
||||
this.reviewerApi = reviewerApi;
|
||||
this.revisionApi = revisionApi;
|
||||
this.changeMessageApi = changeMessageApi;
|
||||
this.changeMessages = changeMessages;
|
||||
this.suggestReviewers = suggestReviewers;
|
||||
this.abandon = abandon;
|
||||
this.restore = restore;
|
||||
@ -709,4 +719,23 @@ class ChangeApiImpl implements ChangeApi {
|
||||
throw asRestApiException("Cannot compute pure revert", e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<ChangeMessageInfo> messages() throws RestApiException {
|
||||
try {
|
||||
return changeMessages.list().apply(change);
|
||||
} catch (Exception e) {
|
||||
throw asRestApiException("Cannot list change messages", e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChangeMessageApi message(String id) throws RestApiException {
|
||||
try {
|
||||
ChangeMessageResource resource = changeMessages.parse(change, IdString.fromDecoded(id));
|
||||
return changeMessageApi.create(resource);
|
||||
} catch (Exception e) {
|
||||
throw asRestApiException("Cannot parse change message " + id, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,50 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.server.api.changes;
|
||||
|
||||
import static com.google.gerrit.server.api.ApiUtil.asRestApiException;
|
||||
|
||||
import com.google.gerrit.extensions.api.changes.ChangeMessageApi;
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.restapi.RestApiException;
|
||||
import com.google.gerrit.server.change.ChangeMessageResource;
|
||||
import com.google.gerrit.server.restapi.change.GetChangeMessage;
|
||||
import com.google.inject.Inject;
|
||||
import com.google.inject.assistedinject.Assisted;
|
||||
|
||||
class ChangeMessageApiImpl implements ChangeMessageApi {
|
||||
interface Factory {
|
||||
ChangeMessageApiImpl create(ChangeMessageResource changeMessageResource);
|
||||
}
|
||||
|
||||
private final GetChangeMessage getChangeMessage;
|
||||
private final ChangeMessageResource changeMessageResource;
|
||||
|
||||
@Inject
|
||||
ChangeMessageApiImpl(
|
||||
GetChangeMessage getChangeMessage, @Assisted ChangeMessageResource changeMessageResource) {
|
||||
this.getChangeMessage = getChangeMessage;
|
||||
this.changeMessageResource = changeMessageResource;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChangeMessageInfo get() throws RestApiException {
|
||||
try {
|
||||
return getChangeMessage.apply(changeMessageResource);
|
||||
} catch (Exception e) {
|
||||
throw asRestApiException("Cannot retrieve change message", e);
|
||||
}
|
||||
}
|
||||
}
|
@ -31,5 +31,6 @@ public class Module extends FactoryModule {
|
||||
factory(ReviewerApiImpl.Factory.class);
|
||||
factory(RevisionReviewerApiImpl.Factory.class);
|
||||
factory(ChangeEditApiImpl.Factory.class);
|
||||
factory(ChangeMessageApiImpl.Factory.class);
|
||||
}
|
||||
}
|
||||
|
@ -37,6 +37,7 @@ import static com.google.gerrit.extensions.client.ListChangesOption.SKIP_MERGEAB
|
||||
import static com.google.gerrit.extensions.client.ListChangesOption.SUBMITTABLE;
|
||||
import static com.google.gerrit.extensions.client.ListChangesOption.TRACKING_IDS;
|
||||
import static com.google.gerrit.extensions.client.ListChangesOption.WEB_LINKS;
|
||||
import static com.google.gerrit.server.ChangeMessagesUtil.createChangeMessageInfo;
|
||||
import static com.google.gerrit.server.CommonConverters.toGitPerson;
|
||||
import static java.util.stream.Collectors.toList;
|
||||
|
||||
@ -1189,19 +1190,7 @@ public class ChangeJson {
|
||||
|
||||
List<ChangeMessageInfo> result = Lists.newArrayListWithCapacity(messages.size());
|
||||
for (ChangeMessage message : messages) {
|
||||
PatchSet.Id patchNum = message.getPatchSetId();
|
||||
ChangeMessageInfo cmi = new ChangeMessageInfo();
|
||||
cmi.id = message.getKey().get();
|
||||
cmi.author = accountLoader.get(message.getAuthor());
|
||||
cmi.date = message.getWrittenOn();
|
||||
cmi.message = message.getMessage();
|
||||
cmi.tag = message.getTag();
|
||||
cmi._revisionNumber = patchNum != null ? patchNum.get() : null;
|
||||
Account.Id realAuthor = message.getRealAuthor();
|
||||
if (realAuthor != null) {
|
||||
cmi.realAuthor = accountLoader.get(realAuthor);
|
||||
}
|
||||
result.add(cmi);
|
||||
result.add(createChangeMessageInfo(message, accountLoader));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
@ -0,0 +1,63 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.server.change;
|
||||
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.restapi.RestResource;
|
||||
import com.google.gerrit.extensions.restapi.RestView;
|
||||
import com.google.gerrit.reviewdb.client.Change;
|
||||
import com.google.inject.TypeLiteral;
|
||||
|
||||
/** A change message resource. */
|
||||
public class ChangeMessageResource implements RestResource {
|
||||
public static final TypeLiteral<RestView<ChangeMessageResource>> CHANGE_MESSAGE_KIND =
|
||||
new TypeLiteral<RestView<ChangeMessageResource>>() {};
|
||||
|
||||
private final ChangeResource changeResource;
|
||||
private final ChangeMessageInfo changeMessage;
|
||||
private final int changeMessageIndex;
|
||||
|
||||
public ChangeMessageResource(
|
||||
ChangeResource changeResource, ChangeMessageInfo changeMessage, int changeMessageIndex) {
|
||||
this.changeResource = changeResource;
|
||||
this.changeMessage = changeMessage;
|
||||
this.changeMessageIndex = changeMessageIndex;
|
||||
}
|
||||
|
||||
public ChangeResource getChangeResource() {
|
||||
return changeResource;
|
||||
}
|
||||
|
||||
public ChangeMessageInfo getChangeMessage() {
|
||||
return changeMessage;
|
||||
}
|
||||
|
||||
public Change.Id getChangeId() {
|
||||
return changeResource.getId();
|
||||
}
|
||||
|
||||
public String getChangeMessageId() {
|
||||
return changeMessage.id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the index of the change message among all messages of the change sorted by creation time.
|
||||
*
|
||||
* @return the index of the change message.
|
||||
*/
|
||||
public int getChangeMessageIndex() {
|
||||
return changeMessageIndex;
|
||||
}
|
||||
}
|
@ -0,0 +1,73 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.server.restapi.change;
|
||||
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.registration.DynamicMap;
|
||||
import com.google.gerrit.extensions.restapi.ChildCollection;
|
||||
import com.google.gerrit.extensions.restapi.IdString;
|
||||
import com.google.gerrit.extensions.restapi.ResourceNotFoundException;
|
||||
import com.google.gerrit.extensions.restapi.RestView;
|
||||
import com.google.gerrit.server.change.ChangeMessageResource;
|
||||
import com.google.gerrit.server.change.ChangeResource;
|
||||
import com.google.gwtorm.server.OrmException;
|
||||
import com.google.inject.Inject;
|
||||
import com.google.inject.Singleton;
|
||||
import java.util.List;
|
||||
|
||||
@Singleton
|
||||
public class ChangeMessages implements ChildCollection<ChangeResource, ChangeMessageResource> {
|
||||
private final DynamicMap<RestView<ChangeMessageResource>> views;
|
||||
private final ListChangeMessages listChangeMessages;
|
||||
|
||||
@Inject
|
||||
ChangeMessages(
|
||||
DynamicMap<RestView<ChangeMessageResource>> views, ListChangeMessages listChangeMessages) {
|
||||
this.views = views;
|
||||
this.listChangeMessages = listChangeMessages;
|
||||
}
|
||||
|
||||
@Override
|
||||
public DynamicMap<RestView<ChangeMessageResource>> views() {
|
||||
return views;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ListChangeMessages list() {
|
||||
return listChangeMessages;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ChangeMessageResource parse(ChangeResource parent, IdString id)
|
||||
throws OrmException, ResourceNotFoundException {
|
||||
String uuid = id.get();
|
||||
|
||||
List<ChangeMessageInfo> changeMessages = listChangeMessages.apply(parent);
|
||||
int index = -1;
|
||||
for (int i = 0; i < changeMessages.size(); ++i) {
|
||||
ChangeMessageInfo changeMessage = changeMessages.get(i);
|
||||
if (changeMessage.id.equals(uuid)) {
|
||||
index = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (index < 0) {
|
||||
throw new ResourceNotFoundException(String.format("change message %s not found", uuid));
|
||||
}
|
||||
|
||||
return new ChangeMessageResource(parent, changeMessages.get(index), index);
|
||||
}
|
||||
}
|
@ -0,0 +1,29 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.server.restapi.change;
|
||||
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.restapi.RestReadView;
|
||||
import com.google.gerrit.server.change.ChangeMessageResource;
|
||||
import com.google.inject.Singleton;
|
||||
|
||||
/** Gets one change message. */
|
||||
@Singleton
|
||||
public class GetChangeMessage implements RestReadView<ChangeMessageResource> {
|
||||
@Override
|
||||
public ChangeMessageInfo apply(ChangeMessageResource resource) {
|
||||
return resource.getChangeMessage();
|
||||
}
|
||||
}
|
@ -0,0 +1,61 @@
|
||||
// Copyright (C) 2018 The Android Open Source Project
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package com.google.gerrit.server.restapi.change;
|
||||
|
||||
import static com.google.gerrit.server.ChangeMessagesUtil.createChangeMessageInfo;
|
||||
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.extensions.restapi.RestReadView;
|
||||
import com.google.gerrit.reviewdb.client.ChangeMessage;
|
||||
import com.google.gerrit.reviewdb.server.ReviewDb;
|
||||
import com.google.gerrit.server.ChangeMessagesUtil;
|
||||
import com.google.gerrit.server.account.AccountLoader;
|
||||
import com.google.gerrit.server.change.ChangeResource;
|
||||
import com.google.gwtorm.server.OrmException;
|
||||
import com.google.inject.Inject;
|
||||
import com.google.inject.Provider;
|
||||
import com.google.inject.Singleton;
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Singleton
|
||||
public class ListChangeMessages implements RestReadView<ChangeResource> {
|
||||
private final Provider<ReviewDb> dbProvider;
|
||||
private final ChangeMessagesUtil changeMessagesUtil;
|
||||
private final AccountLoader accountLoader;
|
||||
|
||||
@Inject
|
||||
public ListChangeMessages(
|
||||
Provider<ReviewDb> dbProvider,
|
||||
ChangeMessagesUtil changeMessagesUtil,
|
||||
AccountLoader.Factory accountLoaderFactory) {
|
||||
this.dbProvider = dbProvider;
|
||||
this.changeMessagesUtil = changeMessagesUtil;
|
||||
this.accountLoader = accountLoaderFactory.create(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<ChangeMessageInfo> apply(ChangeResource resource) throws OrmException {
|
||||
List<ChangeMessage> messages =
|
||||
changeMessagesUtil.byChange(dbProvider.get(), resource.getNotes());
|
||||
List<ChangeMessageInfo> messageInfos =
|
||||
messages
|
||||
.stream()
|
||||
.map(m -> createChangeMessageInfo(m, accountLoader))
|
||||
.collect(Collectors.toList());
|
||||
accountLoader.fill();
|
||||
return messageInfos;
|
||||
}
|
||||
}
|
@ -15,6 +15,7 @@
|
||||
package com.google.gerrit.server.restapi.change;
|
||||
|
||||
import static com.google.gerrit.server.change.ChangeEditResource.CHANGE_EDIT_KIND;
|
||||
import static com.google.gerrit.server.change.ChangeMessageResource.CHANGE_MESSAGE_KIND;
|
||||
import static com.google.gerrit.server.change.ChangeResource.CHANGE_KIND;
|
||||
import static com.google.gerrit.server.change.CommentResource.COMMENT_KIND;
|
||||
import static com.google.gerrit.server.change.DraftCommentResource.DRAFT_COMMENT_KIND;
|
||||
@ -65,6 +66,7 @@ public class Module extends RestApiModule {
|
||||
DynamicMap.mapOf(binder(), REVISION_KIND);
|
||||
DynamicMap.mapOf(binder(), CHANGE_EDIT_KIND);
|
||||
DynamicMap.mapOf(binder(), VOTE_KIND);
|
||||
DynamicMap.mapOf(binder(), CHANGE_MESSAGE_KIND);
|
||||
|
||||
get(CHANGE_KIND).to(GetChange.class);
|
||||
post(CHANGE_KIND, "merge").to(CreateMergePatchSet.class);
|
||||
@ -174,6 +176,9 @@ public class Module extends RestApiModule {
|
||||
get(CHANGE_EDIT_KIND, "meta").to(ChangeEdits.GetMeta.class);
|
||||
post(COMMIT_KIND, "cherrypick").to(CherryPickCommit.class);
|
||||
|
||||
child(CHANGE_KIND, "messages").to(ChangeMessages.class);
|
||||
get(CHANGE_MESSAGE_KIND).to(GetChangeMessage.class);
|
||||
|
||||
factory(AccountLoader.Factory.class);
|
||||
factory(ChangeEdits.Create.Factory.class);
|
||||
factory(ChangeEdits.DeleteFile.Factory.class);
|
||||
|
@ -15,16 +15,22 @@
|
||||
package com.google.gerrit.acceptance.rest.change;
|
||||
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
import static com.google.gerrit.acceptance.PushOneCommit.FILE_NAME;
|
||||
import static com.google.gerrit.extensions.client.ListChangesOption.MESSAGES;
|
||||
import static java.util.concurrent.TimeUnit.SECONDS;
|
||||
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import com.google.common.collect.Lists;
|
||||
import com.google.gerrit.acceptance.AbstractDaemonTest;
|
||||
import com.google.gerrit.acceptance.PushOneCommit;
|
||||
import com.google.gerrit.extensions.api.changes.ReviewInput;
|
||||
import com.google.gerrit.extensions.common.ChangeInfo;
|
||||
import com.google.gerrit.extensions.common.ChangeMessageInfo;
|
||||
import com.google.gerrit.testing.ConfigSuite;
|
||||
import com.google.gerrit.testing.TestTimeUtil;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
@ -95,7 +101,64 @@ public class ChangeMessagesIT extends AbstractDaemonTest {
|
||||
assertThat(actual.tag).isEqualTo(tag);
|
||||
}
|
||||
|
||||
private void assertMessage(String expected, String actual) {
|
||||
@Test
|
||||
public void listChangeMessages() throws Exception {
|
||||
int changeNum = createOneChangeWithMultipleChangeMessagesInHistory();
|
||||
List<ChangeMessageInfo> messages1 = gApi.changes().id(changeNum).messages();
|
||||
List<ChangeMessageInfo> messages2 =
|
||||
new ArrayList<>(gApi.changes().id(changeNum).get().messages);
|
||||
assertThat(messages1).containsExactlyElementsIn(messages2).inOrder();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getOneChangeMessage() throws Exception {
|
||||
int changeNum = createOneChangeWithMultipleChangeMessagesInHistory();
|
||||
List<ChangeMessageInfo> messages = new ArrayList<>(gApi.changes().id(changeNum).get().messages);
|
||||
|
||||
for (ChangeMessageInfo messageInfo : messages) {
|
||||
String id = messageInfo.id;
|
||||
assertThat(gApi.changes().id(changeNum).message(id).get()).isEqualTo(messageInfo);
|
||||
}
|
||||
}
|
||||
|
||||
private int createOneChangeWithMultipleChangeMessagesInHistory() throws Exception {
|
||||
setApiUser(user);
|
||||
// Commit 1: create a change.
|
||||
PushOneCommit.Result result = createChange();
|
||||
String changeId = result.getChangeId();
|
||||
// Commit 2: post a review with message "message 1".
|
||||
setApiUser(admin);
|
||||
addOneReview(changeId, "message 1");
|
||||
// Commit 3: amend a new patch set.
|
||||
setApiUser(user);
|
||||
amendChange(changeId);
|
||||
// Commit 4: post a review with message "message 2".
|
||||
addOneReview(changeId, "message 2");
|
||||
// Commit 5: amend a new patch set.
|
||||
amendChange(changeId);
|
||||
// Commit 6: approve the change.
|
||||
setApiUser(admin);
|
||||
gApi.changes().id(changeId).current().review(ReviewInput.approve());
|
||||
// commit 7: submit the change.
|
||||
gApi.changes().id(changeId).current().submit();
|
||||
|
||||
return result.getChange().getId().get();
|
||||
}
|
||||
|
||||
private void addOneReview(String changeId, String changeMessage) throws Exception {
|
||||
ReviewInput.CommentInput c = new ReviewInput.CommentInput();
|
||||
c.line = 1;
|
||||
c.message = "comment 1";
|
||||
c.path = FILE_NAME;
|
||||
|
||||
ReviewInput reviewInput = new ReviewInput().label("Code-Review", 1);
|
||||
reviewInput.comments = ImmutableMap.of(c.path, Lists.newArrayList(c));
|
||||
reviewInput.message = changeMessage;
|
||||
|
||||
gApi.changes().id(changeId).current().review(reviewInput);
|
||||
}
|
||||
|
||||
private static void assertMessage(String expected, String actual) {
|
||||
assertThat(actual).isEqualTo("Patch Set 1:\n\n" + expected);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user