diff options
author | Jesse Morgan <jesse@jesterpm.net> | 2018-01-29 20:23:59 -0800 |
---|---|---|
committer | Jesse Morgan <jesse@jesterpm.net> | 2018-01-29 20:23:59 -0800 |
commit | b4b71b902493cac1e5b57c70ab53961c26ceb323 (patch) | |
tree | d529a306c3203b9a942464b15225511b7b3fc12e /src | |
parent | 8e7a0c2442674ee95b4ed2453436b6e20c153118 (diff) |
Adding /ping resource for deep health checks
Diffstat (limited to 'src')
8 files changed, 178 insertions, 1 deletions
diff --git a/src/main/java/com/p4square/f1oauth/FellowshipOneIntegrationDriver.java b/src/main/java/com/p4square/f1oauth/FellowshipOneIntegrationDriver.java index 865f5d6..d3690af 100644 --- a/src/main/java/com/p4square/f1oauth/FellowshipOneIntegrationDriver.java +++ b/src/main/java/com/p4square/f1oauth/FellowshipOneIntegrationDriver.java @@ -52,4 +52,11 @@ public class FellowshipOneIntegrationDriver implements IntegrationDriver { public ProgressReporter getProgressReporter() { return mProgressReporter; } + + @Override + public boolean doHealthCheck() { + // Since I no longer have access to an F1 account, + // this will remain unimplemented until it's needed. + throw new UnsupportedOperationException("Health check is not yet implemented for the F1 driver."); + } } diff --git a/src/main/java/com/p4square/grow/backend/GrowBackend.java b/src/main/java/com/p4square/grow/backend/GrowBackend.java index c7b9f42..a51c04a 100644 --- a/src/main/java/com/p4square/grow/backend/GrowBackend.java +++ b/src/main/java/com/p4square/grow/backend/GrowBackend.java @@ -30,12 +30,12 @@ import com.p4square.grow.model.UserRecord; import com.p4square.grow.backend.resources.AccountResource; import com.p4square.grow.backend.resources.BannerResource; +import com.p4square.grow.backend.resources.HealthCheckResource; import com.p4square.grow.backend.resources.SurveyResource; import com.p4square.grow.backend.resources.SurveyResultsResource; import com.p4square.grow.backend.resources.TrainingRecordResource; import com.p4square.grow.backend.resources.TrainingResource; -import com.p4square.grow.backend.feed.FeedDataProvider; import com.p4square.grow.backend.feed.ThreadResource; import com.p4square.grow.backend.feed.TopicResource; @@ -98,6 +98,7 @@ public class GrowBackend extends Application implements GrowData, ProvidesNotifi // Misc. router.attach("/banner", BannerResource.class); + router.attach("/ping", HealthCheckResource.class); // Feed router.attach("/feed/{topic}", TopicResource.class); diff --git a/src/main/java/com/p4square/grow/backend/resources/HealthCheckResource.java b/src/main/java/com/p4square/grow/backend/resources/HealthCheckResource.java new file mode 100644 index 0000000..7d43af4 --- /dev/null +++ b/src/main/java/com/p4square/grow/backend/resources/HealthCheckResource.java @@ -0,0 +1,55 @@ +/* + * Copyright 2013 Jesse Morgan + */ + +package com.p4square.grow.backend.resources; + +import java.io.IOException; + +import org.restlet.data.Status; +import org.restlet.representation.Representation; +import org.restlet.representation.StringRepresentation; +import org.restlet.resource.ServerResource; + +import org.apache.log4j.Logger; + +import com.p4square.grow.backend.GrowBackend; +import com.p4square.grow.provider.Provider; + +/** + * Check if dependencies are healthy. + * + * @author Jesse Morgan <jesse@jesterpm.net> + */ +public class HealthCheckResource extends ServerResource { + private static final Logger LOG = Logger.getLogger(HealthCheckResource.class); + + private Provider<String, String> mStringProvider; + + @Override + public void doInit() { + super.doInit(); + + final GrowBackend backend = (GrowBackend) getApplication(); + mStringProvider = backend.getStringProvider(); + } + + /** + * Handle GET Requests. + */ + @Override + protected Representation get() { + try { + // Try loading the banner string + mStringProvider.get("banner"); + + // If nothing exploded, we'll say it works. + return new StringRepresentation("SUCCESS"); + + } catch (IOException e) { + LOG.warn("Health Check Failed: " + e); + setStatus(Status.SERVER_ERROR_INTERNAL); + return new StringRepresentation("FAIL"); + } + } +} diff --git a/src/main/java/com/p4square/grow/ccb/ChurchCommunityBuilderIntegrationDriver.java b/src/main/java/com/p4square/grow/ccb/ChurchCommunityBuilderIntegrationDriver.java index 3704fdc..dd62401 100644 --- a/src/main/java/com/p4square/grow/ccb/ChurchCommunityBuilderIntegrationDriver.java +++ b/src/main/java/com/p4square/grow/ccb/ChurchCommunityBuilderIntegrationDriver.java @@ -6,9 +6,11 @@ import com.p4square.ccbapi.CCBAPIClient; import com.p4square.grow.config.Config; import com.p4square.grow.frontend.IntegrationDriver; import com.p4square.grow.frontend.ProgressReporter; +import org.apache.log4j.Logger; import org.restlet.Context; import org.restlet.security.Verifier; +import java.io.IOException; import java.net.URI; import java.net.URISyntaxException; @@ -17,6 +19,8 @@ import java.net.URISyntaxException; */ public class ChurchCommunityBuilderIntegrationDriver implements IntegrationDriver { + private static final Logger LOG = Logger.getLogger(ChurchCommunityBuilderIntegrationDriver.class); + private final Context mContext; private final MetricRegistry mMetricRegistry; private final Config mConfig; @@ -65,4 +69,18 @@ public class ChurchCommunityBuilderIntegrationDriver implements IntegrationDrive public ProgressReporter getProgressReporter() { return mProgressReporter; } + + @Override + public boolean doHealthCheck() { + try { + // Try something benign, like getting the custom field labels, + // to verify that we can talk to CCB. + mAPI.getCustomFieldLabels(); + return true; + + } catch (IOException e) { + LOG.warn("CCB Health Check Failed: " + e.getMessage(), e); + return false; + } + } } diff --git a/src/main/java/com/p4square/grow/frontend/GrowFrontend.java b/src/main/java/com/p4square/grow/frontend/GrowFrontend.java index ebaa8df..29f7e14 100644 --- a/src/main/java/com/p4square/grow/frontend/GrowFrontend.java +++ b/src/main/java/com/p4square/grow/frontend/GrowFrontend.java @@ -118,6 +118,7 @@ public class GrowFrontend extends FMFacade { router.attach("/login.html", LoginPageResource.class); router.attach("/newaccount.html", NewAccountResource.class); router.attach("/newbeliever", NewBelieverResource.class); + router.attach("/ping", HealthCheckPage.class); final Router accountRouter = new MetricRouter(getContext(), mMetricRegistry); accountRouter.attach("/authenticate", AuthenticatedResource.class); diff --git a/src/main/java/com/p4square/grow/frontend/HealthCheckPage.java b/src/main/java/com/p4square/grow/frontend/HealthCheckPage.java new file mode 100644 index 0000000..7469b09 --- /dev/null +++ b/src/main/java/com/p4square/grow/frontend/HealthCheckPage.java @@ -0,0 +1,82 @@ +/* + * Copyright 2018 Jesse Morgan + */ + +package com.p4square.grow.frontend; + +import org.restlet.Request; +import org.restlet.Response; +import org.restlet.data.Method; +import org.restlet.data.Status; +import org.restlet.representation.Representation; +import org.restlet.representation.StringRepresentation; + +import org.apache.log4j.Logger; + +import com.p4square.grow.config.Config; +import org.restlet.resource.ServerResource; + +/** + * This page verifies all of the dependencies are working. + * If so, it returns a 200, otherwise a 500. + * + * @author Jesse Morgan <jesse@jesterpm.net> + */ +public class HealthCheckPage extends ServerResource { + private static final Logger LOG = Logger.getLogger(HealthCheckPage.class); + + private GrowFrontend mGrowFrontend; + private Config mConfig; + + @Override + public void doInit() { + super.doInit(); + + mGrowFrontend = (GrowFrontend) getApplication(); + mConfig = mGrowFrontend.getConfig(); + } + + /** + * Health check + */ + @Override + protected Representation get() { + try { + // Check the backend + boolean backendOk = checkBackend(); + + // Check the Third-Party Integration driver + boolean integrationOk = mGrowFrontend.getThirdPartyIntegrationFactory().doHealthCheck(); + + if (backendOk && integrationOk) { + return new StringRepresentation("SUCCESS"); + } + + } catch (Exception e) { + LOG.fatal("Health check exception: " + e.getMessage(), e); + } + + // Something went wrong... + setStatus(Status.SERVER_ERROR_INTERNAL); + return new StringRepresentation("FAIL"); + } + + private boolean checkBackend() { + final Request request = new Request(Method.GET, getBackendEndpoint() + "/ping"); + final Response response = getContext().getClientDispatcher().handle(request); + + if (response.getStatus().isSuccess()) { + return true; + } else { + LOG.warn("Backend health check failed. Got " + response.getStatus().toString()); + return false; + } + } + + /** + * @return The backend endpoint URI + */ + private String getBackendEndpoint() { + return mConfig.getString("backendUri", "riap://component/backend"); + } +} diff --git a/src/main/java/com/p4square/grow/frontend/IntegrationDriver.java b/src/main/java/com/p4square/grow/frontend/IntegrationDriver.java index b9c3508..8ea2600 100644 --- a/src/main/java/com/p4square/grow/frontend/IntegrationDriver.java +++ b/src/main/java/com/p4square/grow/frontend/IntegrationDriver.java @@ -23,4 +23,14 @@ public interface IntegrationDriver { * @return The ProgressReporter. */ ProgressReporter getProgressReporter(); + + /** + * Check if the IntegrationDriver is configured correctly and working. + * + * This method should try to contact the CMS to ensure endpoints, + * credentials, etc. are working correctly. + * + * @return true for success. + */ + boolean doHealthCheck(); } diff --git a/src/main/resources/com/p4square/grow/backend/apiinfo.html b/src/main/resources/com/p4square/grow/backend/apiinfo.html index a3637c9..1e44348 100644 --- a/src/main/resources/com/p4square/grow/backend/apiinfo.html +++ b/src/main/resources/com/p4square/grow/backend/apiinfo.html @@ -31,6 +31,9 @@ <dt>/backend/banner</dt> <dd>GET the info banner or PUT new banner info.</dd> +<dt>/backend/ping</dt> +<dd>GET the current status of the backend dependencies.</dd> + <dt>/backend/feed/{topic}</dt> <dd>Get all threads for forum <em>topic</em>.</dd> |