blob: 7256497fd023cf151aa72546d47c332c4a04afd0 [file] [log] [blame]
// Copyright (C) 2016 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.client.change;
import com.google.gerrit.client.FormatUtil;
import com.google.gerrit.client.Gerrit;
import com.google.gerrit.client.NotSignedInDialog;
import com.google.gerrit.client.changes.ChangeApi;
import com.google.gerrit.client.changes.Util;
import com.google.gerrit.client.info.AccountInfo;
import com.google.gerrit.client.info.ChangeInfo;
import com.google.gerrit.client.rpc.GerritCallback;
import com.google.gerrit.client.ui.InlineHyperlink;
import com.google.gerrit.client.ui.RemoteSuggestBox;
import com.google.gerrit.common.PageLinks;
import com.google.gerrit.reviewdb.client.Change;
import com.google.gwt.core.client.GWT;
import com.google.gwt.dom.client.Element;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.event.logical.shared.CloseEvent;
import com.google.gwt.event.logical.shared.CloseHandler;
import com.google.gwt.event.logical.shared.SelectionEvent;
import com.google.gwt.event.logical.shared.SelectionHandler;
import com.google.gwt.uibinder.client.UiBinder;
import com.google.gwt.uibinder.client.UiField;
import com.google.gwt.uibinder.client.UiHandler;
import com.google.gwt.user.client.DOM;
import com.google.gwt.user.client.EventListener;
import com.google.gwt.user.client.rpc.StatusCodeException;
import com.google.gwt.user.client.ui.Composite;
import com.google.gwt.user.client.ui.HTMLPanel;
import com.google.gwt.user.client.ui.Image;
import com.google.gwt.user.client.ui.UIObject;
/** Edit assignee using auto-completion. */
public class Assignee extends Composite {
interface Binder extends UiBinder<HTMLPanel, Assignee> {}
private static final Binder uiBinder = GWT.create(Binder.class);
@UiField Element show;
@UiField InlineHyperlink assigneeLink;
@UiField Image editAssigneeIcon;
@UiField Element form;
@UiField Element error;
@UiField(provided = true)
RemoteSuggestBox suggestBox;
private AssigneeSuggestOracle assigneeSuggestOracle;
private Change.Id changeId;
private boolean canEdit;
private AccountInfo currentAssignee;
Assignee() {
assigneeSuggestOracle = new AssigneeSuggestOracle();
suggestBox = new RemoteSuggestBox(assigneeSuggestOracle);
suggestBox.setVisibleLength(55);
suggestBox.setHintText(Util.C.approvalTableEditAssigneeHint());
suggestBox.addCloseHandler(
new CloseHandler<RemoteSuggestBox>() {
@Override
public void onClose(CloseEvent<RemoteSuggestBox> event) {
Assignee.this.onCancel(null);
}
});
suggestBox.addSelectionHandler(
new SelectionHandler<String>() {
@Override
public void onSelection(SelectionEvent<String> event) {
editAssignee(event.getSelectedItem());
}
});
initWidget(uiBinder.createAndBindUi(this));
editAssigneeIcon.addDomHandler(
new ClickHandler() {
@Override
public void onClick(ClickEvent event) {
onOpenForm();
}
},
ClickEvent.getType());
}
void set(ChangeInfo info) {
this.changeId = info.legacyId();
this.canEdit = info.hasActions() && info.actions().containsKey("assignee");
assigneeSuggestOracle.setChange(info);
setAssignee(info.assignee());
editAssigneeIcon.setVisible(canEdit);
if (!canEdit) {
show.setTitle(null);
}
}
void onOpenForm() {
UIObject.setVisible(form, true);
UIObject.setVisible(show, false);
UIObject.setVisible(error, false);
editAssigneeIcon.setVisible(false);
suggestBox.setFocus(true);
if (currentAssignee != null) {
suggestBox.setText(FormatUtil.nameEmail(currentAssignee));
suggestBox.selectAll();
} else {
suggestBox.setText("");
}
}
void onCloseForm() {
UIObject.setVisible(form, false);
UIObject.setVisible(show, true);
UIObject.setVisible(error, false);
editAssigneeIcon.setVisible(true);
suggestBox.setFocus(false);
}
@UiHandler("assign")
void onEditAssignee(@SuppressWarnings("unused") ClickEvent e) {
if (canEdit) {
editAssignee(suggestBox.getText());
}
}
@UiHandler("cancel")
void onCancel(@SuppressWarnings("unused") ClickEvent e) {
onCloseForm();
}
private void editAssignee(final String assignee) {
if (assignee.trim().isEmpty()) {
ChangeApi.deleteAssignee(
changeId.get(),
new GerritCallback<AccountInfo>() {
@Override
public void onSuccess(AccountInfo result) {
onCloseForm();
setAssignee(null);
}
@Override
public void onFailure(Throwable err) {
if (isSigninFailure(err)) {
new NotSignedInDialog().center();
} else {
UIObject.setVisible(error, true);
error.setInnerText(
err instanceof StatusCodeException
? ((StatusCodeException) err).getEncodedResponse()
: err.getMessage());
}
}
});
} else {
ChangeApi.setAssignee(
changeId.get(),
assignee,
new GerritCallback<AccountInfo>() {
@Override
public void onSuccess(AccountInfo result) {
onCloseForm();
setAssignee(result);
Reviewers reviewers = getReviewers();
if (reviewers != null) {
reviewers.updateReviewerList();
}
}
@Override
public void onFailure(Throwable err) {
if (isSigninFailure(err)) {
new NotSignedInDialog().center();
} else {
UIObject.setVisible(error, true);
error.setInnerText(
err instanceof StatusCodeException
? ((StatusCodeException) err).getEncodedResponse()
: err.getMessage());
}
}
});
}
}
private void setAssignee(AccountInfo assignee) {
currentAssignee = assignee;
assigneeLink.setText(assignee != null ? getName(assignee) : null);
assigneeLink.setTargetHistoryToken(
assignee != null
? PageLinks.toAssigneeQuery(
assignee.name() != null
? assignee.name()
: assignee.email() != null
? assignee.email()
: String.valueOf(assignee._accountId()))
: "");
}
private Reviewers getReviewers() {
Element e = DOM.getParent(getElement());
for (e = DOM.getParent(e); e != null; e = DOM.getParent(e)) {
EventListener l = DOM.getEventListener(e);
if (l instanceof ChangeScreen) {
ChangeScreen screen = (ChangeScreen) l;
return screen.reviewers;
}
}
return null;
}
private String getName(AccountInfo info) {
if (info.name() != null) {
return info.name();
}
if (info.email() != null) {
return info.email();
}
return Gerrit.info().user().anonymousCowardName();
}
}