001/* 002 * (C) Copyright 2011 Nuxeo SA (http://nuxeo.com/) and others. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 * 016 * Contributors: 017 * Julien Carsique 018 * 019 */ 020 021package org.nuxeo.ecm.core.management.statuses; 022 023import java.io.IOException; 024import java.io.OutputStream; 025 026import javax.servlet.ServletException; 027import javax.servlet.http.HttpServlet; 028import javax.servlet.http.HttpServletRequest; 029import javax.servlet.http.HttpServletResponse; 030 031import org.apache.commons.lang3.StringUtils; 032import org.apache.commons.logging.Log; 033import org.apache.commons.logging.LogFactory; 034import org.nuxeo.common.Environment; 035import org.nuxeo.ecm.core.management.api.ProbeManager; 036import org.nuxeo.runtime.RuntimeService; 037import org.nuxeo.runtime.api.Framework; 038 039/** 040 * Servlet for retrieving Nuxeo services running status. 041 * 042 * @since 9.3 this servlet returns a status based of all the probes registered for the healthCheck. 043 */ 044public class StatusServlet extends HttpServlet { 045 046 private static final long serialVersionUID = 1L; 047 048 private static final Log log = LogFactory.getLog(StatusServlet.class); 049 050 public static final String PARAM = "info"; 051 052 public static final String PARAM_STARTED = "started"; 053 054 public static final String PARAM_SUMMARY = "summary"; 055 056 public static final String PARAM_SUMMARY_KEY = "key"; 057 058 public static final String PARAM_RELOAD = "reload"; 059 060 public static final String PROBE_PARAM = "probe"; 061 062 @Override 063 protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 064 String param = req.getParameter(PARAM); 065 if (param != null) { 066 doPost(req, resp); 067 } else { 068 HealthCheckResult result = getOrRunHealthCheck(null); 069 sendHealthCheckResponse(resp, result); 070 } 071 } 072 073 protected void sendHealthCheckResponse(HttpServletResponse resp, HealthCheckResult result) throws IOException { 074 if (result.isHealthy()) { 075 resp.setStatus(HttpServletResponse.SC_OK); 076 } else { 077 resp.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR); 078 } 079 sendResponse(resp, result.toJson()); 080 } 081 082 @Override 083 protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 084 StringBuilder response = new StringBuilder(); 085 String requestedInfo = req.getParameter(PARAM); 086 if (requestedInfo.equals(PARAM_STARTED)) { 087 getStartedInfo(response); 088 } else if (requestedInfo.equals(PARAM_SUMMARY)) { 089 String givenKey = req.getParameter(PARAM_SUMMARY_KEY); 090 if (Framework.getRuntime().getProperty(Environment.SERVER_STATUS_KEY).equals(givenKey)) { 091 getSummaryInfo(response); 092 } else { 093 resp.setStatus(HttpServletResponse.SC_FORBIDDEN); 094 } 095 } else if (requestedInfo.equals(PARAM_RELOAD)) { 096 if (isStarted()) { 097 response.append("reload();"); 098 } else { 099 resp.setStatus(HttpServletResponse.SC_SERVICE_UNAVAILABLE); 100 } 101 } else if (requestedInfo.equals(PROBE_PARAM)) { 102 String probetoEval = req.getParameter(PARAM_SUMMARY_KEY); 103 try { 104 HealthCheckResult result = getOrRunHealthCheck(probetoEval); 105 sendHealthCheckResponse(resp, result); 106 } catch (IllegalArgumentException e) { 107 resp.setStatus(HttpServletResponse.SC_NOT_FOUND); 108 } 109 } 110 sendResponse(resp, response.toString()); 111 } 112 113 protected void sendResponse(HttpServletResponse resp, String response) throws IOException { 114 resp.setContentType("application/json"); 115 resp.setContentLength(response.getBytes().length); 116 OutputStream out = resp.getOutputStream(); 117 out.write(response.getBytes()); 118 out.close(); 119 } 120 121 protected void getSummaryInfo(StringBuilder response) { 122 if (isStarted()) { 123 StringBuilder msg = new StringBuilder(); 124 boolean isFine = Framework.getRuntime().getStatusMessage(msg); 125 response.append(isFine).append("\n"); 126 response.append(msg); 127 } else { 128 response.append(false).append("\n"); 129 response.append("Runtime failed to start"); 130 } 131 } 132 133 protected void getStartedInfo(StringBuilder response) { 134 response.append(isStarted()).toString(); 135 } 136 137 private boolean isStarted() { 138 RuntimeService runtimeService = Framework.getRuntime(); 139 return runtimeService != null && runtimeService.isStarted(); 140 } 141 142 @Override 143 public void init() throws ServletException { 144 log.debug("Ready."); 145 } 146 147 protected HealthCheckResult getOrRunHealthCheck(String probe) { 148 ProbeManager pm = Framework.getService(ProbeManager.class); 149 if (StringUtils.isEmpty(probe)) { // run all healthCheck probes 150 return pm.getOrRunHealthChecks(); 151 } else { 152 return pm.getOrRunHealthCheck(probe); 153 } 154 } 155}