Merge "Add dependencies to query."

This commit is contained in:
Martin Fick
2012-03-15 10:24:53 -07:00
committed by gerrit code review
6 changed files with 125 additions and 1 deletions

View File

@@ -15,6 +15,7 @@ SYNOPSIS
[--files]
[--comments]
[--commit-message]
[--dependencies]
[--]
<query>
[limit:<n>]
@@ -75,6 +76,10 @@ OPTIONS
--commit-message::
Include the full commit message in the change description.
--dependencies::
Show information about patch sets which depend on, or are needed by,
each patch set.
limit:<n>::
Maximum number of results to return. This is actually a
query operator, and not a command line option. If more

View File

@@ -39,4 +39,7 @@ public class ChangeAttribute {
public List<TrackingIdAttribute> trackingIds;
public PatchSetAttribute currentPatchSet;
public List<PatchSetAttribute> patchSets;
public List<DependencyAttribute> dependsOn;
public List<DependencyAttribute> neededBy;
}

View File

@@ -0,0 +1,23 @@
// Copyright (C) 2012 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.events;
public class DependencyAttribute {
public String id;
public String number;
public String revision;
public String ref;
public Boolean isCurrentPatchSet;
}

View File

@@ -22,13 +22,18 @@ import com.google.gerrit.reviewdb.client.Change;
import com.google.gerrit.reviewdb.client.ChangeMessage;
import com.google.gerrit.reviewdb.client.PatchLineComment;
import com.google.gerrit.reviewdb.client.PatchSet;
import com.google.gerrit.reviewdb.client.PatchSetAncestor;
import com.google.gerrit.reviewdb.client.PatchSetApproval;
import com.google.gerrit.reviewdb.client.RevId;
import com.google.gerrit.reviewdb.client.TrackingId;
import com.google.gerrit.reviewdb.server.ReviewDb;
import com.google.gerrit.server.account.AccountCache;
import com.google.gerrit.server.config.CanonicalWebUrl;
import com.google.gerrit.server.patch.PatchList;
import com.google.gerrit.server.patch.PatchListCache;
import com.google.gerrit.server.patch.PatchListEntry;
import com.google.gwtorm.server.OrmException;
import com.google.gwtorm.server.SchemaFactory;
import com.google.inject.Inject;
import com.google.inject.Provider;
import com.google.inject.Singleton;
@@ -47,16 +52,18 @@ public class EventFactory {
private final Provider<String> urlProvider;
private final ApprovalTypes approvalTypes;
private final PatchListCache patchListCache;
private final SchemaFactory<ReviewDb> schema;
@Inject
EventFactory(AccountCache accountCache,
@CanonicalWebUrl @Nullable Provider<String> urlProvider,
ApprovalTypes approvalTypes,
PatchListCache patchListCache) {
PatchListCache patchListCache, SchemaFactory<ReviewDb> schema) {
this.accountCache = accountCache;
this.urlProvider = urlProvider;
this.approvalTypes = approvalTypes;
this.patchListCache = patchListCache;
this.schema = schema;
}
/**
@@ -110,6 +117,61 @@ public class EventFactory {
a.status = change.getStatus();
}
public void addDependencies(ChangeAttribute ca, Change change) {
ca.dependsOn = new ArrayList<DependencyAttribute>();
ca.neededBy = new ArrayList<DependencyAttribute>();
try {
final ReviewDb db = schema.open();
try {
final PatchSet.Id psId = change.currentPatchSetId();
for (PatchSetAncestor a : db.patchSetAncestors().ancestorsOf(psId)) {
for (PatchSet p :
db.patchSets().byRevision(a.getAncestorRevision())) {
Change c = db.changes().get(p.getId().getParentKey());
ca.dependsOn.add(newDependsOn(c, p));
}
}
final RevId revId = db.patchSets().get(psId).getRevision();
for (PatchSetAncestor a : db.patchSetAncestors().descendantsOf(revId)) {
final PatchSet p = db.patchSets().get(a.getPatchSet());
final Change c = db.changes().get(p.getId().getParentKey());
ca.neededBy.add(newNeededBy(c, p));
}
} finally {
db.close();
}
} catch (OrmException e) {
// Squash DB exceptions and leave dependency lists partially filled.
}
// Remove empty lists so a confusing label won't be displayed in the output.
if (ca.dependsOn.isEmpty()) {
ca.dependsOn = null;
}
if (ca.neededBy.isEmpty()) {
ca.neededBy = null;
}
}
private DependencyAttribute newDependsOn(Change c, PatchSet ps) {
DependencyAttribute d = newDependencyAttribute(c, ps);
d.isCurrentPatchSet = c.currPatchSetId().equals(ps.getId());
return d;
}
private DependencyAttribute newNeededBy(Change c, PatchSet ps) {
return newDependencyAttribute(c, ps);
}
private DependencyAttribute newDependencyAttribute(Change c, PatchSet ps) {
DependencyAttribute d = new DependencyAttribute();
d.number = c.getId().toString();
d.id = c.getKey().toString();
d.revision = ps.getRevision().get();
d.ref = ps.getRefName();
return d;
}
public void addTrackingIds(ChangeAttribute a, Collection<TrackingId> ids) {
if (!ids.isEmpty()) {
a.trackingIds = new ArrayList<TrackingIdAttribute>(ids.size());

View File

@@ -77,6 +77,7 @@ public class QueryProcessor {
private boolean includeComments;
private boolean includeFiles;
private boolean includeCommitMessage;
private boolean includeDependencies;
private OutputStream outputStream = DisabledOutputStream.INSTANCE;
private PrintWriter out;
@@ -128,6 +129,14 @@ public class QueryProcessor {
return includeFiles;
}
public void setIncludeDependencies(boolean on) {
includeDependencies = on;
}
public boolean getIncludeDependencies() {
return includeDependencies;
}
public void setIncludeCommitMessage(boolean on) {
includeCommitMessage = on;
}
@@ -242,6 +251,10 @@ public class QueryProcessor {
}
}
if (includeDependencies) {
eventFactory.addDependencies(c, d.getChange());
}
show(c);
}
@@ -367,7 +380,20 @@ public class QueryProcessor {
out.print('\n');
} else if (value instanceof Collection) {
out.print('\n');
boolean firstElement = true;
for (Object thing : ((Collection<?>) value)) {
// The name of the collection was initially printed at the beginning
// of this routine. Beginning at the second sub-element, reprint
// the collection name so humans can separate individual elements
// with less strain and error.
//
if (firstElement) {
firstElement = false;
} else {
out.print(indent);
out.print(field);
out.print(":\n");
}
if (isPrimitive(thing)) {
out.print(' ');
out.print(value);

View File

@@ -66,6 +66,11 @@ class Query extends BaseCommand {
processor.setIncludeCommitMessage(on);
}
@Option(name = "--dependencies", usage = "Include depends-on and needed-by information")
void setDependencies(boolean on) {
processor.setIncludeDependencies(on);
}
@Argument(index = 0, required = true, multiValued = true, metaVar = "QUERY", usage = "Query to execute")
private List<String> query;