Skip to content

Commit

Permalink
Added status information servlet "/smp-status/"; #73
Browse files Browse the repository at this point in the history
  • Loading branch information
phax committed Jun 1, 2018
1 parent 4c5a5ea commit 7e472d9
Show file tree
Hide file tree
Showing 4 changed files with 181 additions and 2 deletions.
13 changes: 12 additions & 1 deletion peppol-smp-server-webapp-sql/src/main/webapp/WEB-INF/web.xml
Original file line number Diff line number Diff line change
Expand Up @@ -42,14 +42,25 @@
</init-param>
<init-param>
<param-name>jersey.config.servlet.filter.staticContentRegex</param-name>
<param-value>/(stream|public|secure|ajax|resbundle)/.*|/favicon.ico|/logout</param-value>
<param-value>/(stream|public|secure|ajax|resbundle|smp-status)/.*|/favicon.ico|/logout</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>RestFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

<!-- Misc stuff -->

<servlet>
<servlet-name>SMPStatusServlet</servlet-name>
<servlet-class>com.helger.peppol.smpserver.servlet.SMPStatusServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>SMPStatusServlet</servlet-name>
<url-pattern>/smp-status/*</url-pattern>
</servlet-mapping>

<!-- UI stuff -->

<filter>
Expand Down
13 changes: 12 additions & 1 deletion peppol-smp-server-webapp-xml/src/main/webapp/WEB-INF/web.xml
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@
</init-param>
<init-param>
<param-name>jersey.config.servlet.filter.staticContentRegex</param-name>
<param-value>/(stream|public|secure|ajax|resbundle)/.*|/favicon.ico|/logout</param-value>
<param-value>/(stream|public|secure|ajax|resbundle|smp-status)/.*|/favicon.ico|/logout</param-value>
</init-param>
<init-param>
<param-name>jersey.config.server.tracing.type</param-name>
Expand All @@ -60,6 +60,17 @@
<url-pattern>/*</url-pattern>
</filter-mapping>

<!-- Misc stuff -->

<servlet>
<servlet-name>SMPStatusServlet</servlet-name>
<servlet-class>com.helger.peppol.smpserver.servlet.SMPStatusServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>SMPStatusServlet</servlet-name>
<url-pattern>/smp-status/*</url-pattern>
</servlet-mapping>

<!-- UI stuff -->

<filter>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
/**
* Copyright (C) 2014-2018 Philip Helger (www.helger.com)
* philip[at]helger[dot]com
*
* 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.helger.peppol.smpserver.servlet;

import com.helger.commons.http.EHttpMethod;
import com.helger.xservlet.AbstractXServlet;

/**
* The servlet to show the application status.<br>
* Source: https://github.com/phax/peppol-smp-server/issues/73
*
* @author Philip Helger
*/
public class SMPStatusServlet extends AbstractXServlet
{
public static final String SERVLET_DEFAULT_NAME = "smp-status";
public static final String SERVLET_DEFAULT_PATH = '/' + SERVLET_DEFAULT_NAME;

public SMPStatusServlet ()
{
handlerRegistry ().registerHandler (EHttpMethod.GET, new SMPStatusXServletHandler ());
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
package com.helger.peppol.smpserver.servlet;

import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import java.security.KeyStore.PrivateKeyEntry;
import java.security.cert.Certificate;
import java.security.cert.X509Certificate;
import java.time.LocalDateTime;

import javax.annotation.Nonnull;
import javax.annotation.Nullable;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.helger.commons.annotation.ReturnsMutableCopy;
import com.helger.commons.datetime.PDTFactory;
import com.helger.commons.datetime.PDTWebDateHelper;
import com.helger.commons.debug.GlobalDebug;
import com.helger.commons.mime.CMimeType;
import com.helger.commons.mime.MimeType;
import com.helger.commons.system.SystemProperties;
import com.helger.json.IJsonObject;
import com.helger.json.JsonObject;
import com.helger.peppol.smpserver.CSMPServer;
import com.helger.peppol.smpserver.SMPServerConfiguration;
import com.helger.peppol.smpserver.app.AppConfiguration;
import com.helger.peppol.smpserver.domain.SMPMetaManager;
import com.helger.peppol.smpserver.security.SMPKeyManager;
import com.helger.peppol.smpserver.settings.ISMPSettings;
import com.helger.servlet.response.UnifiedResponse;
import com.helger.web.scope.IRequestWebScopeWithoutResponse;
import com.helger.xservlet.handler.simple.IXServletSimpleHandler;

public class SMPStatusXServletHandler implements IXServletSimpleHandler
{
private static final Logger s_aLogger = LoggerFactory.getLogger (SMPStatusXServletHandler.class);
private static final Charset CHARSET = StandardCharsets.UTF_8;

@Nullable
private static String _toString (@Nullable final Object o)
{
return o == null ? null : o.toString ();
}

@Nonnull
@ReturnsMutableCopy
public static IJsonObject getDefaultStatusData ()
{
final ISMPSettings aSettings = SMPMetaManager.getSettings ();
final LocalDateTime aNow = PDTFactory.getCurrentLocalDateTime ();

final IJsonObject aStatusData = new JsonObject ();
aStatusData.add ("status.datetime", PDTWebDateHelper.getAsStringXSD (PDTFactory.getCurrentZonedDateTimeUTC ()));
aStatusData.add ("version.smp", CSMPServer.getVersionNumber ());
aStatusData.add ("version.java", SystemProperties.getJavaVersion ());
aStatusData.add ("global.debug", GlobalDebug.isDebugMode ());
aStatusData.add ("global.production", GlobalDebug.isProductionMode ());
aStatusData.add ("smp.backend", SMPServerConfiguration.getBackend ());
aStatusData.add ("smp.mode", AppConfiguration.isTestVersion () ? "test" : "production");
aStatusData.add ("smp.resttype", SMPServerConfiguration.getRESTType ().getID ());
aStatusData.add ("smp.identifiertype", SMPServerConfiguration.getIdentifierType ().getID ());
aStatusData.add ("smp.id", SMPServerConfiguration.getSMLSMPID ());
aStatusData.add ("smp.writable-rest-api.enabled", !aSettings.isRESTWritableAPIDisabled ());

// SML information
aStatusData.add ("smp.sml.enabled", aSettings.isSMLActive ());
aStatusData.add ("smp.sml.needed", aSettings.isSMLNeeded ());
aStatusData.add ("smp.sml.url", aSettings.getSMLURL ());
aStatusData.addIfNotNull ("smp.sml.connection-timeout-ms",
_toString (SMPServerConfiguration.getSMLConnectionTimeoutMS ()));
aStatusData.addIfNotNull ("smp.sml.request-timeout-ms",
_toString (SMPServerConfiguration.getSMLRequestTimeoutMS ()));

// Directory information
aStatusData.add ("smp.pd.enabled", aSettings.isPEPPOLDirectoryIntegrationEnabled ());
aStatusData.add ("smp.pd.auto-update", aSettings.isPEPPOLDirectoryIntegrationAutoUpdate ());
aStatusData.add ("smp.pd.hostname", aSettings.getPEPPOLDirectoryHostName ());

// Certificate information
final boolean bCertConfigOk = SMPKeyManager.isCertificateValid ();
aStatusData.add ("smp.certificate.configuration-valid", bCertConfigOk);
if (bCertConfigOk)
{
final SMPKeyManager aKeyMgr = SMPKeyManager.getInstance ();
final PrivateKeyEntry aKeyEntry = aKeyMgr.getPrivateKeyEntry ();
if (aKeyEntry != null)
{
final Certificate [] aChain = aKeyEntry.getCertificateChain ();
if (aChain.length > 0 && aChain[0] instanceof X509Certificate)
{
final X509Certificate aX509Cert = (X509Certificate) aChain[0];
aStatusData.add ("smp.certificate.issuer", aX509Cert.getIssuerX500Principal ().getName ());
aStatusData.add ("smp.certificate.subject", aX509Cert.getSubjectX500Principal ().getName ());

final LocalDateTime aNotAfter = PDTFactory.createLocalDateTime (aX509Cert.getNotAfter ());
final boolean bIsExpired = aNow.isAfter (aNotAfter);
aStatusData.add ("smp.certificate.expired", bIsExpired);
}
}
}
return aStatusData;
}

public void handleRequest (@Nonnull final IRequestWebScopeWithoutResponse aRequestScope,
@Nonnull final UnifiedResponse aUnifiedResponse) throws Exception
{
if (s_aLogger.isDebugEnabled ())
s_aLogger.debug ("Status information requested");

// Build data to provide
final IJsonObject aStatusData = getDefaultStatusData ();

// Put JSON on response
aUnifiedResponse.disableCaching ();
aUnifiedResponse.setMimeType (new MimeType (CMimeType.APPLICATION_JSON).addParameter (CMimeType.PARAMETER_NAME_CHARSET,
CHARSET.name ()));
aUnifiedResponse.setContentAndCharset (aStatusData.getAsJsonString (), CHARSET);
}
}

0 comments on commit 7e472d9

Please sign in to comment.