Merge branch 'stable-3.2' into master

* stable-3.2:
  Honour container.replica option
  Disable querychanges for gerrit replicas
  Normalize response payload returned by replicas
  Expose authenticated healthcheck for replicas
  Remove the terms slave and master
  Respect container.replica option for Gerrit replica
  Format with google-java-format 1.7

Change-Id: Ife9efe0f34983c566fd4047b2d5418a5f0bdfe11
diff --git a/README.md b/README.md
index e5ad599..8be0b33 100644
--- a/README.md
+++ b/README.md
@@ -25,9 +25,9 @@
 ## How to install
 
 Copy the healthcheck.jar into the Gerrit's /plugins directory and wait for the plugin to be automatically loaded.
-The healthcheck plugin is compatible with both Gerrit master and slave setups. The only difference to bear in mind
-is that some checks may not be successful on slaves (e.g. query changes) because the associated subsystem is switched
-off.
+The healthcheck plugin is compatible with both primary Gerrit setups and Gerrit replicas. The only difference to bear
+in mind is that some checks will be automatically disabled on replicas (e.g. query changes) because the associated
+subsystem is switched off.
 
 ## How to use
 
diff --git a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckConfig.java b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckConfig.java
index fc6acc7..3e5306c 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckConfig.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckConfig.java
@@ -15,6 +15,7 @@
 package com.googlesource.gerrit.plugins.healthcheck;
 
 import static com.google.common.base.Preconditions.checkNotNull;
+import static com.googlesource.gerrit.plugins.healthcheck.check.HealthCheckNames.QUERYCHANGES;
 
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.base.MoreObjects;
@@ -23,9 +24,11 @@
 import com.google.gerrit.extensions.annotations.PluginName;
 import com.google.gerrit.server.config.AllProjectsName;
 import com.google.gerrit.server.config.AllUsersName;
+import com.google.gerrit.server.config.GerritIsReplica;
 import com.google.gerrit.server.config.PluginConfigFactory;
 import com.google.inject.Inject;
 import com.google.inject.Singleton;
+import java.util.Collections;
 import java.util.Set;
 import java.util.concurrent.TimeUnit;
 import java.util.stream.Collectors;
@@ -48,16 +51,22 @@
   private final AllUsersName allUsersName;
 
   private final Config config;
+  private final boolean isReplica;
+
+  private static final Set<String> HEALTH_CHECK_DISABLED_FOR_REPLICAS =
+      Collections.singleton(QUERYCHANGES);
 
   @Inject
   public HealthCheckConfig(
       PluginConfigFactory configFactory,
       @PluginName String pluginName,
       AllProjectsName allProjectsName,
-      AllUsersName allUsersName) {
+      AllUsersName allUsersName,
+      @GerritIsReplica boolean isReplica) {
     config = configFactory.getGlobalPluginConfig(pluginName);
     this.allProjectsName = allProjectsName;
     this.allUsersName = allUsersName;
+    this.isReplica = isReplica;
   }
 
   @VisibleForTesting
@@ -72,6 +81,7 @@
     }
     allProjectsName = new AllProjectsName("All-Projects");
     allUsersName = new AllUsersName("All-Users");
+    isReplica = false;
   }
 
   @VisibleForTesting
@@ -125,6 +135,9 @@
   }
 
   public boolean healthCheckEnabled(String healthCheckName) {
+    if (isReplica && HEALTH_CHECK_DISABLED_FOR_REPLICAS.contains(healthCheckName)) {
+      return false;
+    }
     return config.getBoolean(
         HEALTHCHECK, checkNotNull(healthCheckName), "enabled", HEALTH_CHECK_ENABLED_DEFAULT);
   }
diff --git a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HttpModule.java b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HttpModule.java
index c62a261..5217dff 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HttpModule.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/HttpModule.java
@@ -16,24 +16,23 @@
 
 import com.google.gerrit.extensions.registration.DynamicSet;
 import com.google.gerrit.httpd.AllRequestFilter;
-import com.google.gerrit.server.config.GerritServerConfig;
+import com.google.gerrit.server.config.GerritIsReplica;
 import com.google.inject.Inject;
 import com.google.inject.Scopes;
 import com.google.inject.servlet.ServletModule;
 import com.googlesource.gerrit.plugins.healthcheck.filter.HealthCheckStatusFilter;
-import org.eclipse.jgit.lib.Config;
 
 public class HttpModule extends ServletModule {
-  private boolean isSlave;
+  private boolean isReplica;
 
   @Inject
-  public HttpModule(@GerritServerConfig Config gerritConfig) {
-    isSlave = gerritConfig.getBoolean("container", "slave", false);
+  public HttpModule(@GerritIsReplica boolean isReplica) {
+    this.isReplica = isReplica;
   }
 
   @Override
   protected void configureServlets() {
-    if (isSlave) {
+    if (isReplica) {
       DynamicSet.bind(binder(), AllRequestFilter.class)
           .to(HealthCheckStatusFilter.class)
           .in(Scopes.SINGLETON);
diff --git a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/filter/HealthCheckStatusFilter.java b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/filter/HealthCheckStatusFilter.java
index e19f18a..b2e91b1 100644
--- a/src/main/java/com/googlesource/gerrit/plugins/healthcheck/filter/HealthCheckStatusFilter.java
+++ b/src/main/java/com/googlesource/gerrit/plugins/healthcheck/filter/HealthCheckStatusFilter.java
@@ -61,14 +61,14 @@
   }
 
   private boolean isStatusCheck(HttpServletRequest httpServletRequest) {
-    return httpServletRequest.getRequestURI().equals("/config/server/healthcheck~status");
+    return httpServletRequest.getRequestURI().matches("(?:/a)?/config/server/healthcheck~status");
   }
 
   private void doStatusCheck(HttpServletResponse httpResponse) throws ServletException {
     try {
       Response<Map<String, Object>> healthStatus =
           (Response<Map<String, Object>>) statusEndpoint.apply(new ConfigResource());
-      String healthStatusJson = gson.toJson(healthStatus);
+      String healthStatusJson = gson.toJson(healthStatus.value());
       if (healthStatus.statusCode() == HttpServletResponse.SC_OK) {
         PrintWriter writer = httpResponse.getWriter();
         writer.print(new String(RestApiServlet.JSON_MAGIC));
diff --git a/src/test/java/com/googlesource/gerrit/plugins/healthcheck/DeadlockCheckTest.java b/src/test/java/com/googlesource/gerrit/plugins/healthcheck/DeadlockCheckTest.java
index 01a1147..d53a1d8 100644
--- a/src/test/java/com/googlesource/gerrit/plugins/healthcheck/DeadlockCheckTest.java
+++ b/src/test/java/com/googlesource/gerrit/plugins/healthcheck/DeadlockCheckTest.java
@@ -16,7 +16,6 @@
 
 import static com.google.common.truth.Truth.assertThat;
 import static com.googlesource.gerrit.plugins.healthcheck.HealthCheckConfig.DEFAULT_CONFIG;
-import static com.googlesource.gerrit.plugins.healthcheck.check.HealthCheckNames.DEADLOCK;
 
 import com.codahale.metrics.Gauge;
 import com.codahale.metrics.MetricRegistry;
@@ -71,7 +70,6 @@
     assertThat(check.run().result).isEqualTo(Result.FAILED);
   }
 
-
   private Injector testInjector(AbstractModule testModule) {
     return Guice.createInjector(new HealthCheckModule(), testModule);
   }
diff --git a/src/test/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckIT.java b/src/test/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckIT.java
index 199543b..e409917 100644
--- a/src/test/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckIT.java
+++ b/src/test/java/com/googlesource/gerrit/plugins/healthcheck/HealthCheckIT.java
@@ -25,6 +25,7 @@
 import com.google.gerrit.acceptance.RestResponse;
 import com.google.gerrit.acceptance.Sandboxed;
 import com.google.gerrit.acceptance.TestPlugin;
+import com.google.gerrit.acceptance.config.GerritConfig;
 import com.google.gson.Gson;
 import com.google.gson.JsonObject;
 import com.googlesource.gerrit.plugins.healthcheck.check.HealthCheckNames;
@@ -33,7 +34,10 @@
 import org.junit.Before;
 import org.junit.Test;
 
-@TestPlugin(name = "healthcheck", sysModule = "com.googlesource.gerrit.plugins.healthcheck.Module")
+@TestPlugin(
+    name = "healthcheck",
+    sysModule = "com.googlesource.gerrit.plugins.healthcheck.Module",
+    httpModule = "com.googlesource.gerrit.plugins.healthcheck.HttpModule")
 @Sandboxed
 public class HealthCheckIT extends LightweightPluginDaemonTest {
   Gson gson = new Gson();
@@ -80,6 +84,22 @@
   }
 
   @Test
+  @GerritConfig(name = "container.replica", value = "true")
+  public void shouldReturnJGitCheckForReplicaWhenAuthenticated() throws Exception {
+    RestResponse resp = getHealthCheckStatus();
+    resp.assertOK();
+    assertCheckResult(getResponseJson(resp), JGIT, "passed");
+  }
+
+  @Test
+  @GerritConfig(name = "container.replica", value = "true")
+  public void shouldReturnJGitCheckForReplicaAnonymously() throws Exception {
+    RestResponse resp = getHealthCheckStatusAnonymously();
+    resp.assertOK();
+    assertCheckResult(getResponseJson(resp), JGIT, "passed");
+  }
+
+  @Test
   public void shouldReturnAuthCheck() throws Exception {
     RestResponse resp = getHealthCheckStatus();
 
@@ -115,6 +135,15 @@
   }
 
   @Test
+  @GerritConfig(name = "container.replica", value = "true")
+  public void shouldReturnQueryChangesAsDisabledForReplica() throws Exception {
+    RestResponse resp = getHealthCheckStatus();
+    resp.assertOK();
+
+    assertCheckResult(getResponseJson(resp), QUERYCHANGES, "disabled");
+  }
+
+  @Test
   public void shouldReturnQueryChangesMultipleTimesCheck() throws Exception {
     createChange("refs/for/master");
     getHealthCheckStatus();
@@ -156,6 +185,10 @@
     return adminRestSession.get("/config/server/healthcheck~status");
   }
 
+  private RestResponse getHealthCheckStatusAnonymously() throws IOException {
+    return anonymousRestSession.get("/config/server/healthcheck~status");
+  }
+
   private void assertCheckResult(JsonObject respPayload, String checkName, String result) {
     assertThat(respPayload.has(checkName)).isTrue();
     JsonObject reviewDbStatus = respPayload.get(checkName).getAsJsonObject();