summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorEdwin Kempin <ekempin@google.com>2023-08-16 08:13:43 +0000
committerEdwin Kempin <ekempin@google.com>2023-08-16 08:14:47 +0000
commit6d861b5eaab02374236bf856e1465039b7def819 (patch)
tree97f72b814fc2c0e363c48cfad5c5f99bebbfb251
parente9edc9fceff535b406e511ac413e90caf4c1b888 (diff)
ListProjectImpl: Delegate to QueryProjects if prefix is used
QueryProjects supports matching by prefix now (see change Ibfb3b354f), hence enable delegation to QueryProjects if this option is used. The delegation only happens when 'gerrit.listProjectsFromIndex' is set to 'true'. Searching projects by prefix is only supported from project index version V8 that added PREFIX_NAME_SPEC. Hence we can only delegate to QueryProjects if that field is present in the currently used index schema. Release-Notes: skip Change-Id: I140d095a63956c5b04ad911ead12fb6189a480e9 Signed-off-by: Edwin Kempin <ekempin@google.com>
-rw-r--r--java/com/google/gerrit/server/restapi/project/ListProjectsImpl.java30
-rw-r--r--javatests/com/google/gerrit/acceptance/rest/project/ListProjectsIT.java13
2 files changed, 38 insertions, 5 deletions
diff --git a/java/com/google/gerrit/server/restapi/project/ListProjectsImpl.java b/java/com/google/gerrit/server/restapi/project/ListProjectsImpl.java
index 055648d2f7..09f6d71478 100644
--- a/java/com/google/gerrit/server/restapi/project/ListProjectsImpl.java
+++ b/java/com/google/gerrit/server/restapi/project/ListProjectsImpl.java
@@ -41,6 +41,8 @@ import com.google.gerrit.extensions.restapi.MethodNotAllowedException;
import com.google.gerrit.extensions.restapi.Response;
import com.google.gerrit.extensions.restapi.TopLevelResource;
import com.google.gerrit.extensions.restapi.Url;
+import com.google.gerrit.index.project.ProjectField;
+import com.google.gerrit.index.project.ProjectIndexCollection;
import com.google.gerrit.json.OutputFormat;
import com.google.gerrit.server.CurrentUser;
import com.google.gerrit.server.WebLinks;
@@ -184,6 +186,7 @@ public class ListProjectsImpl extends AbstractListProjects {
private AccountGroup.UUID groupUuid;
private final Provider<QueryProjects> queryProjectsProvider;
private final boolean listProjectsFromIndex;
+ private final ProjectIndexCollection projectIndexes;
@Inject
protected ListProjectsImpl(
@@ -196,7 +199,8 @@ public class ListProjectsImpl extends AbstractListProjects {
ProjectNode.Factory projectNodeFactory,
WebLinks webLinks,
Provider<QueryProjects> queryProjectsProvider,
- @GerritServerConfig Config config) {
+ @GerritServerConfig Config config,
+ ProjectIndexCollection projectIndexes) {
this.currentUser = currentUser;
this.projectCache = projectCache;
this.groupResolver = groupResolver;
@@ -207,6 +211,7 @@ public class ListProjectsImpl extends AbstractListProjects {
this.webLinks = webLinks;
this.queryProjectsProvider = queryProjectsProvider;
this.listProjectsFromIndex = config.getBoolean("gerrit", "listProjectsFromIndex", false);
+ this.projectIndexes = projectIndexes;
}
public List<String> getShowBranch() {
@@ -251,11 +256,15 @@ public class ListProjectsImpl extends AbstractListProjects {
return display(null);
}
- private Optional<String> expressAsProjectsQuery() {
+ private Optional<String> expressAsProjectsQuery() throws BadRequestException {
return listProjectsFromIndex
&& !all
&& state != HIDDEN
- && isNullOrEmpty(matchPrefix)
+ && (isNullOrEmpty(matchPrefix)
+ || projectIndexes
+ .getSearchIndex()
+ .getSchema()
+ .hasField(ProjectField.PREFIX_NAME_SPEC))
&& isNullOrEmpty(matchRegex)
&& type == FilterType.ALL
&& showBranch.isEmpty()
@@ -264,12 +273,25 @@ public class ListProjectsImpl extends AbstractListProjects {
: Optional.empty();
}
- private String toQuery() {
+ private String toQuery() throws BadRequestException {
+ // QueryProjects supports specifying matchPrefix and matchSubstring at the same time, but to
+ // keep the behavior consistent regardless of whether 'gerrit.listProjectsFromIndex' is true or
+ // false, disallow specifying both at the same time here. This way
+ // 'gerrit.listProjectsFromIndex' can be troggled without breaking any caller.
+ if (matchPrefix != null) {
+ checkMatchOptions(matchSubstring == null);
+ } else if (matchSubstring != null) {
+ checkMatchOptions(matchPrefix == null);
+ }
+
List<String> queries = new ArrayList<>();
if (state != null) {
queries.add(String.format("(state:%s)", state.name()));
}
+ if (!isNullOrEmpty(matchPrefix)) {
+ queries.add(String.format("prefix:%s", matchPrefix));
+ }
if (!isNullOrEmpty(matchSubstring)) {
queries.add(String.format("substring:%s", matchSubstring));
}
diff --git a/javatests/com/google/gerrit/acceptance/rest/project/ListProjectsIT.java b/javatests/com/google/gerrit/acceptance/rest/project/ListProjectsIT.java
index 5a7d7b3271..1b3ff0d5b4 100644
--- a/javatests/com/google/gerrit/acceptance/rest/project/ListProjectsIT.java
+++ b/javatests/com/google/gerrit/acceptance/rest/project/ListProjectsIT.java
@@ -199,7 +199,18 @@ public class ListProjectsIT extends AbstractDaemonTest {
}
@Test
- public void listProjectsWithPrefix() throws Exception {
+ @GerritConfig(name = "gerrit.listProjectsFromIndex", value = "true")
+ public void listProjectsWithPrefix_indexEnabled() throws Exception {
+ testListProjectsWithPrefix();
+ }
+
+ @Test
+ @GerritConfig(name = "gerrit.listProjectsFromIndex", value = "false")
+ public void listProjectsWithPrefix_indexDisabled() throws Exception {
+ testListProjectsWithPrefix();
+ }
+
+ private void testListProjectsWithPrefix() throws Exception {
Project.NameKey someProject = projectOperations.newProject().name("listtest-p1").create();
Project.NameKey someOtherProject = projectOperations.newProject().name("listtest-p2").create();
projectOperations.newProject().name("other-prefix-project").create();