http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeInterruptedException.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeInterruptedException.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeInterruptedException.java deleted file mode 100644 index 5a02f46..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeInterruptedException.java +++ /dev/null @@ -1,29 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -/** - * This exception is raised when the probe loop detects that it has been requested to stop - * - */ -public class ProbeInterruptedException extends Exception { - - public ProbeInterruptedException() { - super("Probe Interrupted"); - } -}
http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbePhase.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbePhase.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbePhase.java deleted file mode 100644 index d87c81b..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbePhase.java +++ /dev/null @@ -1,56 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -/** - * Probe phases. The names are for strings; the index is the order in which things happen; - * -any state can got to terminating directly. - */ -public enum ProbePhase { - INIT("Initializing", 0), - DEPENDENCY_CHECKING("Dependencies", 1), - BOOTSTRAPPING("Bootstrapping", 2), - LIVE("Live", 3), - TERMINATING("Terminating", 4); - - private final String name; - private final int index; - - ProbePhase(String name, int index) { - this.name = name; - this.index = index; - } - - public String getName() { - return name; - } - - public int getIndex() { - return index; - } - - /** - * How many phases are there? - */ - public static final int PHASE_COUNT = TERMINATING.index + 1; - - @Override - public String toString() { - return name; - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeReportHandler.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeReportHandler.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeReportHandler.java deleted file mode 100644 index 36c20c8..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeReportHandler.java +++ /dev/null @@ -1,79 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -/** - * This interface is for use by the Poll Workers to send events to the reporters. - * - * It is up the reporters what to do with the specific events. - */ -public interface ProbeReportHandler { - - /** - * The probe process has changed state. - * @param probePhase the new process phrase - */ - void probeProcessStateChange(ProbePhase probePhase); - - /** - * Report a probe outcome - * @param phase the current phase of probing - * @param status the probe status - */ - void probeResult(ProbePhase phase, ProbeStatus status); - - /** - * A probe has failed - */ - void probeFailure(ProbeFailedException exception); - - /** - * A probe has just booted - * @param status probe status - */ - void probeBooted(ProbeStatus status); - - boolean commence(String name, String description); - - void unregister(); - - /** - * A heartbeat event should be raised - * @param status the probe status - */ - void heartbeat(ProbeStatus status); - - /** - * A probe has timed out - * @param currentPhase the current execution phase - * @param probe the probe that timed out - * @param lastStatus the last status that was successfully received -which is implicitly - * not the status of the timed out probe - * @param currentTime the current time - */ - void probeTimedOut(ProbePhase currentPhase, - Probe probe, - ProbeStatus lastStatus, - long currentTime); - - /** - * Event to say that the live probe cycle completed so the entire - * system can be considered functional. - */ - void liveProbeCycleCompleted(); -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeStatus.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeStatus.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeStatus.java deleted file mode 100644 index 653f479..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeStatus.java +++ /dev/null @@ -1,173 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -import java.io.Serializable; -import java.util.Date; - -/** - * Status message of a probe. This is designed to be sent over the wire, though the exception - * Had better be unserializable at the far end if that is to work. - */ -public final class ProbeStatus implements Serializable { - - private long timestamp; - private String timestampText; - private boolean success; - private boolean realOutcome; - private String message; - private Throwable thrown; - private transient Probe originator; - private ProbePhase probePhase; - - public ProbeStatus() { - } - - public ProbeStatus(long timestamp, String message, Throwable thrown) { - this.success = false; - this.message = message; - this.thrown = thrown; - setTimestamp(timestamp); - } - - public ProbeStatus(long timestamp, String message) { - this.success = true; - setTimestamp(timestamp); - this.message = message; - this.thrown = null; - } - - public long getTimestamp() { - return timestamp; - } - - public void setTimestamp(long timestamp) { - this.timestamp = timestamp; - timestampText = new Date(timestamp).toString(); - } - - public boolean isSuccess() { - return success; - } - - /** - * Set both the success and the real outcome bits to the same value - * @param success the new value - */ - public void setSuccess(boolean success) { - this.success = success; - realOutcome = success; - } - - public String getTimestampText() { - return timestampText; - } - - public boolean getRealOutcome() { - return realOutcome; - } - - public String getMessage() { - return message; - } - - public void setMessage(String message) { - this.message = message; - } - - public Throwable getThrown() { - return thrown; - } - - public void setThrown(Throwable thrown) { - this.thrown = thrown; - } - - public ProbePhase getProbePhase() { - return probePhase; - } - - public void setProbePhase(ProbePhase probePhase) { - this.probePhase = probePhase; - } - - /** - * Get the probe that generated this result. May be null - * @return a possibly null reference to a probe - */ - public Probe getOriginator() { - return originator; - } - - /** - * The probe has succeeded -capture the current timestamp, set - * success to true, and record any other data needed. - * @param probe probe - */ - public void succeed(Probe probe) { - finish(probe, true, probe.getName(), null); - } - - /** - * A probe has failed either because the test returned false, or an exception - * was thrown. The {@link #success} field is set to false, any exception - * thrown is recorded. - * @param probe probe that failed - * @param thrown an exception that was thrown. - */ - public void fail(Probe probe, Throwable thrown) { - finish(probe, false, "Failure in " + probe, thrown); - } - - public void finish(Probe probe, boolean succeeded, String text, Throwable thrown) { - setTimestamp(System.currentTimeMillis()); - setSuccess(succeeded); - originator = probe; - message = text; - this.thrown = thrown; - } - - @Override - public String toString() { - LogEntryBuilder builder = new LogEntryBuilder("Probe Status"); - builder.elt("time", timestampText) - .elt("phase", probePhase) - .elt("outcome", (success ? "success" : "failure")); - - if (success != realOutcome) { - builder.elt("originaloutcome", (realOutcome ? "success" : "failure")); - } - builder.elt("message", message); - if (thrown != null) { - builder.elt("exception", thrown); - } - - return builder.toString(); - } - - public boolean inPhase(ProbePhase phase) { - return getProbePhase().equals(phase); - } - - /** - * Flip the success bit on while the real outcome bit is kept false - */ - public void markAsSuccessful() { - success = true; - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeWorker.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeWorker.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeWorker.java deleted file mode 100644 index f64ec8d..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ProbeWorker.java +++ /dev/null @@ -1,446 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.IOException; -import java.util.ArrayList; -import java.util.List; - -/** - * This is the entry point to do work. A list of probes is taken in, in order of - * booting. Once live they go to the live probes list. - * - * The dependency probes are a set of probes for dependent services, all of which - * must be live before boot probes commence. - * - * The boot probes are executed and are allowed to fail; failure is interpreted as "not yet live" - * - * Once all boot probes are live, the live list is used for probes; these must not fail. - * - * There is no timeout on dependency probe bootstrap time, because of the notion that - * restarting this service will have no effect on the dependencies. - */ - -public class ProbeWorker implements Runnable { - protected static final Logger log = LoggerFactory.getLogger(ProbeWorker.class); - - public static final String FAILED_TO_BOOT = "Monitored service failed to bootstrap after "; - public static final String FAILURE_OF_A_LIVE_PROBE_DURING_BOOTSTRAPPING = "Failure of a live probe during bootstrapping"; - private final List<Probe> monitorProbes; - private final List<Probe> dependencyProbes; - public final int interval; - protected volatile ProbeStatus lastStatus; - protected volatile ProbeStatus lastFailingBootstrapProbe; - protected volatile Probe currentProbe; - private volatile boolean mustExit; - private final int bootstrapTimeout; - private long bootstrapEndtime; - - private ProbeReportHandler reportHandler; - private volatile ProbePhase probePhase = ProbePhase.INIT; - - /** - * Create a probe worker - * @param monitorProbes list of probes that must boot and then go live -after which - * they must stay live. - * @param dependencyProbes the list of dependency probes that must all succeed before - * any attempt to probe the direct probe list is performed. Once the - * dependency phase has completed, these probes are never checked again. - * @param interval probe interval in milliseconds. - * @param bootstrapTimeout timeout for bootstrap in milliseconds - */ - public ProbeWorker(List<Probe> monitorProbes, List<Probe> dependencyProbes, int interval, int bootstrapTimeout) { - this.monitorProbes = monitorProbes; - this.dependencyProbes = dependencyProbes != null ? dependencyProbes : new ArrayList<Probe>(0); - this.interval = interval; - lastStatus = new ProbeStatus(now(), - "Initial status"); - lastStatus.setProbePhase(ProbePhase.INIT); - this.bootstrapTimeout = bootstrapTimeout; - } - - public void init() throws IOException { - for (Probe probe : monitorProbes) { - probe.init(); - } - for (Probe probe : dependencyProbes) { - probe.init(); - } - } - - public void setReportHandler(ProbeReportHandler reportHandler) { - this.reportHandler = reportHandler; - } - - public void setMustExit() { - this.mustExit = true; - } - - public ProbeStatus getLastStatus() { - return lastStatus; - } - - public synchronized Probe getCurrentProbe() { - return currentProbe; - } - - public ProbePhase getProbePhase() { - return probePhase; - } - - /** - * Enter the new process state, and report it to the report handler. - * This is synchronized just to make sure there isn't more than one - * invocation at the same time. - * @param status the new process status - */ - private synchronized void enterProbePhase(ProbePhase status) { - this.probePhase = status; - if (reportHandler != null) { - reportHandler.probeProcessStateChange(status); - } - } - - /** - * Report the probe status to the listener -setting the probe phase field - * before doing so. - * The value is also stored in the {@link #lastStatus} field - * @param status the new status - */ - private void reportProbeStatus(ProbeStatus status) { - ProbePhase phase = getProbePhase(); - status.setProbePhase(phase); - lastStatus = status; - reportHandler.probeResult(phase, status); - } - - /** - * Ping one probe. Logs the operation at debug level; sets the field <code>currentProbe</code> - * to the probe for the duration of the operation -this is used when identifying the - * cause of a hung reporting loop - * @param probe probe to ping - * @param live flag to indicate whether or not the operation is live or bootstrapping - * @return the status of the ping - * @throws ProbeInterruptedException if the probe has been told to exit - */ - private ProbeStatus ping(Probe probe, boolean live) throws ProbeInterruptedException { - if (log.isDebugEnabled()) { - log.debug("Executing " + probe); - } - checkForExitRequest(); - currentProbe = probe; - try { - return probe.ping(live); - } finally { - currentProbe = null; - } - } - - /** - * Check for an exit request -and convert it to an exception if made - * @throws ProbeInterruptedException iff {@link #mustExit} is true - */ - private void checkForExitRequest() throws ProbeInterruptedException { - if (mustExit) { - throw new ProbeInterruptedException(); - } - } - - /** - * Check the dependencies. - * The moment a failing test is reached the call returns without - * any reporting. - * - * All successful probes are reported, so as to keep the heartbeats happy. - * - * @return the status of the last dependency check. If this is a success - * them every probe passed. - */ - private ProbeStatus checkDependencyProbes() throws ProbeInterruptedException { - ProbeStatus status = null; - for (Probe dependency : dependencyProbes) { - //ping them, making clear they are not to run any bootstrap logic - status = ping(dependency, true); - - if (!status.isSuccess()) { - //the first failure means the rest of the list can be skipped - break; - } - reportProbeStatus(status); - } - //return the last status - return status; - } - - /** - * Run through all the dependency probes and report their outcomes successes (even if they fail) - * @return true iff all the probes have succeeded. - * @throws ProbeInterruptedException if the process was interrupted. - */ - public boolean checkAndReportDependencyProbes() throws ProbeInterruptedException { - ProbeStatus status; - status = checkDependencyProbes(); - if (status != null && !status.isSuccess()) { - //during dependency checking, a failure is still reported as a success - status.markAsSuccessful(); - reportProbeStatus(status); - //then return without checking anything else - return false; - } - //all dependencies are done. - return true; - } - - /** - * Begin bootstrapping by telling each probe that they have started. - * This sets the timeouts up, as well as permits any other set-up actions - * to begin. - */ - private void beginBootstrapProbes() { - synchronized (this) { - bootstrapEndtime = now() + bootstrapTimeout; - } - for (Probe probe : monitorProbes) { - probe.beginBootstrap(); - } - } - - private long now() { - return System.currentTimeMillis(); - } - - - /** - * Check the bootstrap probe list. All successful probes get reported. - * The first unsuccessful probe will be returned and not reported (left for policy upstream). - * If the failing probe has timed out, that is turned into a {@link ProbeFailedException} - * @return the last (unsuccessful) probe, or null if they all succeeded - * @throws ProbeInterruptedException interrupts - * @throws ProbeFailedException on a boot timeout - */ - private boolean checkBootstrapProbes() throws ProbeInterruptedException, ProbeFailedException { - verifyBootstrapHasNotTimedOut(); - - boolean probeFailed = false; - //now run through all the bootstrap probes - for (Probe probe : monitorProbes) { - //ping them - ProbeStatus status = ping(probe, false); - if (!status.isSuccess()) { - probeFailed = true; - lastFailingBootstrapProbe = status; - probe.failureCount++; - if (log.isDebugEnabled()) { - log.debug("Booting probe failed: " + status); - } - //at this point check to see if the timeout has occurred -and if so, force in the last probe status. - - //this is a failure but not a timeout - //during boot, a failure of a probe that hasn't booted is still reported as a success - if (!probe.isBooted()) { - //so the success bit is flipped - status.markAsSuccessful(); - reportProbeStatus(status); - } else { - //the probe had booted but then it switched to failing - - //update the status unedited - reportProbeStatus(status); - //then fail - throw raiseProbeFailure(status, FAILURE_OF_A_LIVE_PROBE_DURING_BOOTSTRAPPING); - } - } else { - //this probe is working - if (!probe.isBooted()) { - //if it is new, mark it as live - if (log.isDebugEnabled()) { - log.debug("Booting probe is now live: " + probe); - } - probe.endBootstrap(); - //tell the report handler that another probe has booted - reportHandler.probeBooted(status); - } - //push out its status - reportProbeStatus(status); - probe.successCount++; - } - } - return !probeFailed; - } - - - public int getBootstrapTimeout() { - return bootstrapTimeout; - } - - /** - * This checks that bootstrap operations have not timed out - * @throws ProbeFailedException if the bootstrap has failed - */ - public void verifyBootstrapHasNotTimedOut() throws ProbeFailedException { - //first step -look for a timeout - if (isBootstrapTimeExceeded()) { - String text = FAILED_TO_BOOT - + MonitorUtils.millisToHumanTime(bootstrapTimeout); - - ProbeStatus status; - if (lastFailingBootstrapProbe != null) { - status = lastFailingBootstrapProbe; - status.setSuccess(false); - } else { - status = new ProbeStatus(); - status.finish(null, false, text, null); - } - - throw raiseProbeFailure(status, - text); - } - } - - /** - * predicate that gets current time and checks for its time being exceeded. - * @return true iff the current time is > the end time - */ - public synchronized boolean isBootstrapTimeExceeded() { - return now() > bootstrapEndtime; - } - - /** - * run through all the bootstrap probes and see if they are live. - * @return true iff all boot probes succeeded - * @throws ProbeInterruptedException the probe interruption flags - * @throws ProbeFailedException if a probe failed. - */ - public boolean checkAndReportBootstrapProbes() throws ProbeInterruptedException, - ProbeFailedException { - if (bootstrapTimeout <= 0) { - //there is no period of grace for bootstrapping probes, so return true saying - //this phase is complete - return true; - } - //now the bootstrapping probes - return checkBootstrapProbes(); - } - - - /** - * run through all the live probes, pinging and reporting them. - * A single probe failure is turned into an exception - * @throws ProbeFailedException a probe failed - * @throws ProbeInterruptedException the probe process was explicitly interrupted - */ - protected void checkAndReportLiveProbes() throws ProbeFailedException, ProbeInterruptedException { - ProbeStatus status = null; - //go through the live list - if (log.isDebugEnabled()) { - log.debug("Checking live probes"); - } - for (Probe probe : monitorProbes) { - status = ping(probe, true); - reportProbeStatus(status); - if (!status.isSuccess()) { - throw raiseProbeFailure(status, "Failure of probe in \"live\" monitor"); - } - probe.successCount++; - } - //here all is well, so notify the reporter - reportHandler.liveProbeCycleCompleted(); - } - - /** - * Run the set of probes relevant for this phase of the probe lifecycle. - * @throws ProbeFailedException a probe failed - * @throws ProbeInterruptedException the probe process was explicitly interrupted - */ - protected void executeProbePhases() throws ProbeFailedException, ProbeInterruptedException { - switch (probePhase) { - case INIT: - enterProbePhase(ProbePhase.DEPENDENCY_CHECKING); - //fall through straight into the dependency check - case DEPENDENCY_CHECKING: - if (checkAndReportDependencyProbes()) { - enterProbePhase(ProbePhase.BOOTSTRAPPING); - beginBootstrapProbes(); - } - break; - case BOOTSTRAPPING: - if (checkAndReportBootstrapProbes()) { - enterProbePhase(ProbePhase.LIVE); - } - break; - case LIVE: - checkAndReportLiveProbes(); - break; - - case TERMINATING: - default: - //do nothing. - break; - } - } - - - /** - * Raise a probe failure; injecting the phase into the status result first - * - * @param status ping result - * @param text optional text -null or "" means "none" - * @return an exception ready to throw - */ - private ProbeFailedException raiseProbeFailure(ProbeStatus status, String text) { - status.setProbePhase(probePhase); - log.info("Probe failed: " + status); - return new ProbeFailedException(text, status); - } - - @Override - public void run() { - int size = monitorProbes.size(); - log.info("Probe Worker Starting; " + size + " probe" + MonitorUtils.toPlural(size) + ":"); - enterProbePhase(ProbePhase.DEPENDENCY_CHECKING); - for (Probe probe : monitorProbes) { - log.info(probe.getName()); - } - while (!mustExit) { - try { - Thread.sleep(interval); - executeProbePhases(); - } catch (ProbeFailedException e) { - //relay to the inner loop handler - probeFailed(e); - } catch (InterruptedException interrupted) { - break; - } catch (ProbeInterruptedException e) { - //exit raised. - //this will be true, just making extra-sure - break; - } - } - log.info("Probe Worker Exiting"); - enterProbePhase(ProbePhase.TERMINATING); - } - - - protected void probeFailed(ProbeFailedException e) { - reportHandler.probeFailure(e); - } - -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ReportingLoop.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ReportingLoop.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ReportingLoop.java deleted file mode 100644 index 096838d..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/ReportingLoop.java +++ /dev/null @@ -1,265 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.Closeable; -import java.io.IOException; -import java.util.List; - -/** - * This is the monitor service - */ -public final class ReportingLoop implements Runnable, ProbeReportHandler, MonitorKeys, Closeable { - protected static final Logger log = LoggerFactory.getLogger(ReportingLoop.class); - private final ProbeWorker worker; - private final Thread workerThread; - private final int reportInterval; - private final int probeTimeout; - private final int bootstrapTimeout; - private ProbeReportHandler reporter; - private final String name; - private volatile boolean mustExit; - - public ReportingLoop(String name, - ProbeReportHandler reporter, - List<Probe> probes, - List<Probe> dependencyProbes, - int probeInterval, - int reportInterval, - int probeTimeout, - int bootstrapTimeout) throws IOException { - this(name, - reporter, - new ProbeWorker(probes, dependencyProbes, probeInterval, bootstrapTimeout), - reportInterval, - probeTimeout); - } - - /** - * Create a new reporting loop -and bond the worker's ProbeReportHandler - * to us - * @param name - * @param reporter - * @param worker - * @param reportInterval - * @param probeTimeout - */ - public ReportingLoop(String name, - ProbeReportHandler reporter, - ProbeWorker worker, - int reportInterval, - int probeTimeout) throws IOException { - this.name = name; - this.reporter = reporter; - this.reportInterval = reportInterval; - this.probeTimeout = probeTimeout; - this.worker = worker; - this.bootstrapTimeout = worker.getBootstrapTimeout(); - worker.setReportHandler(this); - workerThread = new Thread(worker, "probe thread - " + name); - worker.init(); - } - - public int getBootstrapTimeout() { - return bootstrapTimeout; - } - - public ReportingLoop withReporter(ProbeReportHandler reporter) { - assert this.reporter == null : "attempting to reassign reporter "; - assert reporter != null : "new reporter is null"; - this.reporter = reporter; - return this; - } - - /** - * Start the monitoring. - * - * @return false if the monitoring did not start and that the worker threads - * should be run up. - */ - public boolean startReporting() { - String description = "Service Monitor for " + name + ", probe-interval= " - + MonitorUtils.millisToHumanTime(worker.interval) - + ", report-interval=" + MonitorUtils.millisToHumanTime(reportInterval) - + ", probe-timeout=" + timeoutToStr(probeTimeout) - + ", bootstrap-timeout=" + timeoutToStr(bootstrapTimeout); - log.info("Starting reporting" - + " to " + reporter - + description); - return reporter.commence(name, description); - } - - private String timeoutToStr(int timeout) { - return timeout >= 0 ? MonitorUtils.millisToHumanTime(timeout) : "not set"; - } - - private void startWorker() { - log.info("Starting reporting worker thread "); - workerThread.setDaemon(true); - workerThread.start(); - } - - - /** - * This exits the process cleanly - */ - @Override - public void close() { - log.info("Stopping reporting"); - mustExit = true; - if (worker != null) { - worker.setMustExit(); - workerThread.interrupt(); - } - if (reporter != null) { - reporter.unregister(); - } - } - - @Override - public void probeFailure(ProbeFailedException exception) { - reporter.probeFailure(exception); - } - - @Override - public void probeProcessStateChange(ProbePhase probePhase) { - reporter.probeProcessStateChange(probePhase); - } - - @Override - public void probeBooted(ProbeStatus status) { - reporter.probeBooted(status); - } - - private long now() { - return System.currentTimeMillis(); - } - - @Override - public void probeResult(ProbePhase phase, ProbeStatus status) { - reporter.probeResult(phase, status); - } - - @Override - public boolean commence(String n, String description) { - return true; - } - - @Override - public void unregister() { - } - - @Override - public void heartbeat(ProbeStatus status) { - } - - @Override - public void probeTimedOut(ProbePhase currentPhase, Probe probe, ProbeStatus lastStatus, - long currentTime) { - } - - @Override - public void liveProbeCycleCompleted() { - //delegate to the reporter - reporter.liveProbeCycleCompleted(); - } - - /** - * The reporting loop - */ - void reportingLoop() { - - while (!mustExit) { - try { - ProbeStatus workerStatus = worker.getLastStatus(); - long now = now(); - long lastStatusIssued = workerStatus.getTimestamp(); - long timeSinceLastStatusIssued = now - lastStatusIssued; - //two actions can occur here: a heartbeat is issued or a timeout reported. - //this flag decides which - boolean heartbeat; - - //based on phase, decide whether to heartbeat or timeout - ProbePhase probePhase = worker.getProbePhase(); - switch (probePhase) { - case DEPENDENCY_CHECKING: - //no timeouts in dependency phase - heartbeat = true; - break; - - case BOOTSTRAPPING: - //the timeout here is fairly straightforward: heartbeats are - //raised while the worker hasn't timed out - heartbeat = bootstrapTimeout < 0 || timeSinceLastStatusIssued < bootstrapTimeout; - - break; - - case LIVE: - //use the probe timeout interval between the current time - //and the time the last status event was received. - heartbeat = timeSinceLastStatusIssued < probeTimeout; - break; - - case INIT: - case TERMINATING: - default: - //send a heartbeat, because this isn't the time to be failing - heartbeat = true; - } - if (heartbeat) { - //a heartbeat is sent to the reporter - reporter.heartbeat(workerStatus); - } else { - //no response from the worker -it is hung. - reporter.probeTimedOut(probePhase, - worker.getCurrentProbe(), - workerStatus, - now - ); - } - - //now sleep - Thread.sleep(reportInterval); - - } catch (InterruptedException e) { - //interrupted -always exit the loop. - break; - } - } - //this point is reached if and only if a clean exit was requested or something failed. - } - - /** - * This can be run in a separate thread, or it can be run directly from the caller. - * Test runs do the latter, HAM runs multiple reporting threads. - */ - @Override - public void run() { - try { - startWorker(); - reportingLoop(); - } catch (RuntimeException e) { - log.warn("Failure in the reporting loop: " + e, e); - //rethrow so that inline code can pick it up (e.g. test runs) - throw e; - } - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/servicemonitor/YarnApplicationProbe.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/YarnApplicationProbe.java b/slider-core/src/main/java/org/apache/slider/server/servicemonitor/YarnApplicationProbe.java deleted file mode 100644 index adf613c..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/servicemonitor/YarnApplicationProbe.java +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.servicemonitor; - -import org.apache.hadoop.conf.Configuration; -import org.apache.hadoop.yarn.api.records.ApplicationReport; -import org.apache.slider.client.SliderYarnClientImpl; -import org.apache.slider.core.exceptions.UnknownApplicationInstanceException; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.IOException; -import java.util.List; - -/** - * Probe for YARN application - */ -public class YarnApplicationProbe extends Probe { - protected static final Logger log = LoggerFactory.getLogger( - YarnApplicationProbe.class); - - /** - * Yarn client service - */ - private SliderYarnClientImpl yarnClient; - private final String clustername; - private final String username; - - public YarnApplicationProbe(String clustername, - SliderYarnClientImpl yarnClient, - String name, - Configuration conf, String username) - throws IOException { - super("Port probe " + name + " " + clustername, - conf); - this.clustername = clustername; - this.yarnClient = yarnClient; - this.username = username; - } - - - @Override - public void init() throws IOException { - - log.info("Checking " + clustername ); - } - - /** - * Try to connect to the (host,port); a failure to connect within - * the specified timeout is a failure - * @param livePing is the ping live: true for live; false for boot time - * @return the outcome - */ - @Override - public ProbeStatus ping(boolean livePing) { - - ProbeStatus status = new ProbeStatus(); - try { - - List<ApplicationReport> instances = - yarnClient.listDeployedInstances(username); - ApplicationReport instance = - yarnClient.findClusterInInstanceList(instances, clustername); - if (null == instance) { - throw UnknownApplicationInstanceException.unknownInstance(clustername); - } - - status.succeed(this); - } catch (Exception e) { - status.fail(this, e); - } - return status; - - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/AbstractSecurityStoreGenerator.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/AbstractSecurityStoreGenerator.java b/slider-core/src/main/java/org/apache/slider/server/services/security/AbstractSecurityStoreGenerator.java deleted file mode 100644 index 11d3aa1..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/AbstractSecurityStoreGenerator.java +++ /dev/null @@ -1,98 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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 org.apache.slider.server.services.security; - -import org.apache.hadoop.conf.Configuration; -import org.apache.hadoop.security.alias.CredentialProvider; -import org.apache.hadoop.security.alias.CredentialProviderFactory; -import org.apache.slider.common.SliderKeys; -import org.apache.slider.core.conf.MapOperations; -import org.apache.slider.core.exceptions.SliderException; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.IOException; -import java.util.List; -import java.util.Map; - -/** - * - */ -public abstract class AbstractSecurityStoreGenerator implements - SecurityStoreGenerator { - private static final Logger LOG = - LoggerFactory.getLogger(AbstractSecurityStoreGenerator.class); - - protected CertificateManager certificateMgr; - - public AbstractSecurityStoreGenerator(CertificateManager certificateMgr) { - this.certificateMgr = certificateMgr; - } - - protected String getStorePassword(Map<String, List<String>> credentials, - MapOperations compOps, String role) - throws SliderException, IOException { - String password = getPassword(compOps); - if (password == null) { - // need to leverage credential provider - String alias = getAlias(compOps); - LOG.debug("Alias {} found for role {}", alias, role); - if (alias == null) { - throw new SliderException("No store password or credential provider " - + "alias found"); - } - if (credentials.isEmpty()) { - LOG.info("Credentials can not be retrieved for store generation since " - + "no CP paths are configured"); - } - synchronized (this) { - for (Map.Entry<String, List<String>> cred : credentials.entrySet()) { - String provider = cred.getKey(); - Configuration c = new Configuration(); - c.set(CredentialProviderFactory.CREDENTIAL_PROVIDER_PATH, provider); - LOG.debug("Configured provider {}", provider); - CredentialProvider cp = - CredentialProviderFactory.getProviders(c).get(0); - LOG.debug("Aliases: {}", cp.getAliases()); - char[] credential = c.getPassword(alias); - if (credential != null) { - LOG.info("Credential found for role {}", role); - return String.valueOf(credential); - } - } - } - - if (password == null) { - LOG.info("No store credential found for alias {}. " - + "Generation of store for {} is not possible.", alias, role); - - } - } - - return password; - - } - - @Override - public boolean isStoreRequested(MapOperations compOps) { - return compOps.getOptionBool(SliderKeys.COMP_STORES_REQUIRED_KEY, false); - } - - abstract String getPassword(MapOperations compOps); - - abstract String getAlias(MapOperations compOps); -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/CertificateManager.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/CertificateManager.java b/slider-core/src/main/java/org/apache/slider/server/services/security/CertificateManager.java deleted file mode 100644 index e436ae9..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/CertificateManager.java +++ /dev/null @@ -1,495 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.services.security; - -import com.google.inject.Singleton; -import org.apache.commons.io.FileUtils; -import org.apache.slider.common.SliderKeys; -import org.apache.slider.core.conf.MapOperations; -import org.apache.slider.core.exceptions.SliderException; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.BufferedReader; -import java.io.File; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.net.InetAddress; -import java.net.UnknownHostException; -import java.nio.charset.Charset; -import java.text.MessageFormat; - -@Singleton -public class CertificateManager { - - private static final Logger LOG = - LoggerFactory.getLogger(CertificateManager.class); - - private static final String GEN_SRVR_KEY = "openssl genrsa -des3 " + - "-passout pass:{0} -out {1}" + File.separator + "{2} 4096 "; - private static final String GEN_SRVR_REQ = "openssl req -passin pass:{0} " + - "-new -key {1}" + File.separator + "{2} -out {1}" + File.separator + - "{5} -config {1}" + File.separator + "ca.config " + - "-subj {6} -batch"; - private static final String SIGN_SRVR_CRT = "openssl ca -create_serial " + - "-out {1}" + File.separator + "{3} -days 365 -keyfile {1}" + File.separator - + "{2} -key {0} -selfsign -extensions jdk7_ca -config {1}" + File.separator - + "ca.config -batch -infiles {1}" + File.separator + "{5}"; - private static final String EXPRT_KSTR = "openssl pkcs12 -export" + - " -in {2}" + File.separator + "{4} -inkey {2}" + File.separator + - "{3} -certfile {2}" + File.separator + "{4} -out {2}" + File.separator + - "{5} -password pass:{1} -passin pass:{0} \n"; - private static final String REVOKE_AGENT_CRT = "openssl ca " + - "-config {0}" + File.separator + "ca.config -keyfile {0}" + - File.separator + "{4} -revoke {0}" + File.separator + "{2} -batch " + - "-passin pass:{3} -cert {0}" + File.separator + "{5}"; - private static final String SIGN_AGENT_CRT = "openssl ca -config " + - "{0}" + File.separator + "ca.config -in {0}" + File.separator + - "{1} -out {0}" + File.separator + "{2} -batch -passin pass:{3} " + - "-keyfile {0}" + File.separator + "{4} -cert {0}" + File.separator + "{5}"; - private static final String GEN_AGENT_KEY="openssl req -new -newkey " + - "rsa:1024 -nodes -keyout {0}" + File.separator + - "{2}.key -subj {1} -out {0}" + File.separator + "{2}.csr " + - "-config {3}" + File.separator + "ca.config "; - private String passphrase; - private String applicationName; - - - public void initialize(MapOperations compOperations) throws SliderException { - String hostname = null; - try { - hostname = InetAddress.getLocalHost().getCanonicalHostName(); - } catch (UnknownHostException e) { - hostname = "localhost"; - } - this.initialize(compOperations, hostname, null, null); - } - - /** - * Verify that root certificate exists, generate it otherwise. - */ - public void initialize(MapOperations compOperations, - String hostname, String containerId, - String appName) throws SliderException { - SecurityUtils.initializeSecurityParameters(compOperations); - - LOG.info("Initialization of root certificate"); - boolean certExists = isCertExists(); - LOG.info("Certificate exists:" + certExists); - - this.applicationName = appName; - - if (!certExists) { - generateAMKeystore(hostname, containerId); - } - - } - - /** - * Checks root certificate state. - * @return "true" if certificate exists - */ - private boolean isCertExists() { - - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String srvrCrtName = SliderKeys.CRT_FILE_NAME; - File certFile = new File(srvrKstrDir + File.separator + srvrCrtName); - LOG.debug("srvrKstrDir = " + srvrKstrDir); - LOG.debug("srvrCrtName = " + srvrCrtName); - LOG.debug("certFile = " + certFile.getAbsolutePath()); - - return certFile.exists(); - } - - public void setPassphrase(String passphrase) { - this.passphrase = passphrase; - } - - class StreamConsumer extends Thread - { - InputStream is; - boolean logOutput; - - StreamConsumer(InputStream is, boolean logOutput) - { - this.is = is; - this.logOutput = logOutput; - } - - StreamConsumer(InputStream is) - { - this(is, false); - } - - public void run() - { - try - { - InputStreamReader isr = new InputStreamReader(is, - Charset.forName("UTF8")); - BufferedReader br = new BufferedReader(isr); - String line; - while ( (line = br.readLine()) != null) - if (logOutput) { - LOG.info(line); - } - } catch (IOException e) - { - LOG.error("Error during processing of process stream", e); - } - } - } - - - /** - * Runs os command - * - * @return command execution exit code - */ - private int runCommand(String command) throws SliderException { - int exitCode = -1; - String line = null; - Process process = null; - BufferedReader br= null; - try { - process = Runtime.getRuntime().exec(command); - StreamConsumer outputConsumer = - new StreamConsumer(process.getInputStream(), true); - StreamConsumer errorConsumer = - new StreamConsumer(process.getErrorStream(), true); - - outputConsumer.start(); - errorConsumer.start(); - - try { - process.waitFor(); - SecurityUtils.logOpenSslExitCode(command, process.exitValue()); - exitCode = process.exitValue(); - if (exitCode != 0) { - throw new SliderException(exitCode, "Error running command %s", command); - } - } catch (InterruptedException e) { - e.printStackTrace(); - } - } catch (IOException e) { - e.printStackTrace(); - } finally { - if (br != null) { - try { - br.close(); - } catch (IOException ioe) { - ioe.printStackTrace(); - } - } - } - - return exitCode;//some exception occurred - - } - - public synchronized void generateContainerCertificate(String hostname, - String identifier) { - LOG.info("Generation of certificate for {}", hostname); - - String srvrKstrDir = SecurityUtils.getSecurityDir(); - Object[] scriptArgs = {srvrKstrDir, getSubjectDN(hostname, identifier, - this.applicationName), identifier, SecurityUtils.getSecurityDir()}; - - try { - String command = MessageFormat.format(GEN_AGENT_KEY, scriptArgs); - runCommand(command); - - signAgentCertificate(identifier); - - } catch (SliderException e) { - LOG.error("Error generating the agent certificate", e); - } - } - - public synchronized SecurityStore generateContainerKeystore(String hostname, - String requesterId, - String role, - String keystorePass) - throws SliderException { - LOG.info("Generation of container keystore for container {} on {}", - requesterId, hostname); - - generateContainerCertificate(hostname, requesterId); - - // come up with correct args to invoke keystore command - String srvrCrtPass = SecurityUtils.getKeystorePass(); - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String containerCrtName = requesterId + ".crt"; - String containerKeyName = requesterId + ".key"; - String kstrName = getKeystoreFileName(requesterId, role); - - Object[] scriptArgs = {srvrCrtPass, keystorePass, srvrKstrDir, - containerKeyName, containerCrtName, kstrName}; - - String command = MessageFormat.format(EXPRT_KSTR, scriptArgs); - runCommand(command); - - return new SecurityStore(new File(srvrKstrDir, kstrName), - SecurityStore.StoreType.keystore); - } - - private static String getKeystoreFileName(String containerId, - String role) { - return String.format("keystore-%s-%s.p12", containerId, - role != null ? role : ""); - } - - private void generateAMKeystore(String hostname, String containerId) - throws SliderException { - LOG.info("Generation of server certificate"); - - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String srvrCrtName = SliderKeys.CRT_FILE_NAME; - String srvrCsrName = SliderKeys.CSR_FILE_NAME; - String srvrKeyName = SliderKeys.KEY_FILE_NAME; - String kstrName = SliderKeys.KEYSTORE_FILE_NAME; - String srvrCrtPass = SecurityUtils.getKeystorePass(); - - Object[] scriptArgs = {srvrCrtPass, srvrKstrDir, srvrKeyName, - srvrCrtName, kstrName, srvrCsrName, getSubjectDN(hostname, containerId, - this.applicationName)}; - - String command = MessageFormat.format(GEN_SRVR_KEY, scriptArgs); - runCommand(command); - - command = MessageFormat.format(GEN_SRVR_REQ, scriptArgs); - runCommand(command); - - command = MessageFormat.format(SIGN_SRVR_CRT, scriptArgs); - runCommand(command); - - Object[] keystoreArgs = {srvrCrtPass, srvrCrtPass, srvrKstrDir, srvrKeyName, - srvrCrtName, kstrName, srvrCsrName}; - command = MessageFormat.format(EXPRT_KSTR, keystoreArgs); - runCommand(command); - } - - public SecurityStore generateContainerTruststore(String containerId, - String role, - String truststorePass) - throws SliderException { - - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String srvrCrtName = SliderKeys.CRT_FILE_NAME; - String srvrCsrName = SliderKeys.CSR_FILE_NAME; - String srvrKeyName = SliderKeys.KEY_FILE_NAME; - String kstrName = getTruststoreFileName(role, containerId); - String srvrCrtPass = SecurityUtils.getKeystorePass(); - - Object[] scriptArgs = {srvrCrtPass, truststorePass, srvrKstrDir, srvrKeyName, - srvrCrtName, kstrName, srvrCsrName}; - - String command = MessageFormat.format(EXPRT_KSTR, scriptArgs); - runCommand(command); - - return new SecurityStore(new File(srvrKstrDir, kstrName), - SecurityStore.StoreType.truststore); - } - - private static String getTruststoreFileName(String role, String containerId) { - return String.format("truststore-%s-%s.p12", containerId, - role != null ? role : ""); - } - - /** - * Returns server certificate content - * @return string with server certificate content - */ - public String getServerCert() { - File certFile = getServerCertficateFilePath(); - String srvrCrtContent = null; - try { - srvrCrtContent = FileUtils.readFileToString(certFile); - } catch (IOException e) { - LOG.error(e.getMessage()); - } - return srvrCrtContent; - } - - public static File getServerCertficateFilePath() { - return new File(String.format("%s%s%s", - SecurityUtils.getSecurityDir(), - File.separator, - SliderKeys.CRT_FILE_NAME)); - } - - public static File getAgentCertficateFilePath(String containerId) { - return new File(String.format("%s%s%s.crt", - SecurityUtils.getSecurityDir(), - File.separator, - containerId)); - } - - public static File getContainerKeystoreFilePath(String containerId, - String role) { - return new File(SecurityUtils.getSecurityDir(), getKeystoreFileName( - containerId, - role - )); - } - - public static File getContainerTruststoreFilePath(String role, - String containerId) { - return new File(SecurityUtils.getSecurityDir(), - getTruststoreFileName(role, containerId)); - } - - public static File getAgentKeyFilePath(String containerId) { - return new File(String.format("%s%s%s.key", - SecurityUtils.getSecurityDir(), - File.separator, - containerId)); - } - - /** - * Signs agent certificate - * Adds agent certificate to server keystore - * @return string with agent signed certificate content - */ - public synchronized SignCertResponse signAgentCrt(String agentHostname, - String agentCrtReqContent, - String passphraseAgent) { - SignCertResponse response = new SignCertResponse(); - LOG.info("Signing of agent certificate"); - LOG.info("Verifying passphrase"); - - if (!this.passphrase.equals(passphraseAgent.trim())) { - LOG.warn("Incorrect passphrase from the agent"); - response.setResult(SignCertResponse.ERROR_STATUS); - response.setMessage("Incorrect passphrase from the agent"); - return response; - } - - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String srvrCrtPass = SecurityUtils.getKeystorePass(); - String srvrCrtName = SliderKeys.CRT_FILE_NAME; - String srvrKeyName = SliderKeys.KEY_FILE_NAME; - String agentCrtReqName = agentHostname + ".csr"; - String agentCrtName = agentHostname + ".crt"; - - Object[] scriptArgs = {srvrKstrDir, agentCrtReqName, agentCrtName, - srvrCrtPass, srvrKeyName, srvrCrtName}; - - //Revoke previous agent certificate if exists - File agentCrtFile = new File(srvrKstrDir + File.separator + agentCrtName); - - String command = null; - if (agentCrtFile.exists()) { - LOG.info("Revoking of " + agentHostname + " certificate."); - command = MessageFormat.format(REVOKE_AGENT_CRT, scriptArgs); - try { - runCommand(command); - } catch (SliderException e) { - int commandExitCode = e.getExitCode(); - response.setResult(SignCertResponse.ERROR_STATUS); - response.setMessage( - SecurityUtils.getOpenSslCommandResult(command, commandExitCode)); - return response; - } - } - - File agentCrtReqFile = new File(srvrKstrDir + File.separator + - agentCrtReqName); - try { - FileUtils.writeStringToFile(agentCrtReqFile, agentCrtReqContent); - } catch (IOException e1) { - // TODO Auto-generated catch block - e1.printStackTrace(); - } - - command = MessageFormat.format(SIGN_AGENT_CRT, scriptArgs); - - LOG.debug(SecurityUtils.hideOpenSslPassword(command)); - try { - runCommand(command); - } catch (SliderException e) { - int commandExitCode = e.getExitCode(); - response.setResult(SignCertResponse.ERROR_STATUS); - response.setMessage( - SecurityUtils.getOpenSslCommandResult(command, commandExitCode)); - return response; - } - - String agentCrtContent = ""; - try { - agentCrtContent = FileUtils.readFileToString(agentCrtFile); - } catch (IOException e) { - e.printStackTrace(); - LOG.error("Error reading signed agent certificate"); - response.setResult(SignCertResponse.ERROR_STATUS); - response.setMessage("Error reading signed agent certificate"); - return response; - } - response.setResult(SignCertResponse.OK_STATUS); - response.setSignedCa(agentCrtContent); - //LOG.info(ShellCommandUtil.getOpenSslCommandResult(command, commandExitCode)); - return response; - } - - private String signAgentCertificate (String containerId) - throws SliderException { - String srvrKstrDir = SecurityUtils.getSecurityDir(); - String srvrCrtPass = SecurityUtils.getKeystorePass(); - String srvrCrtName = SliderKeys.CRT_FILE_NAME; - String srvrKeyName = SliderKeys.KEY_FILE_NAME; - String agentCrtReqName = containerId + ".csr"; - String agentCrtName = containerId + ".crt"; - - // server certificate must exist already - if (!(new File(srvrKstrDir, srvrCrtName).exists())) { - throw new SliderException("CA certificate not generated"); - } - - Object[] scriptArgs = {srvrKstrDir, agentCrtReqName, agentCrtName, - srvrCrtPass, srvrKeyName, srvrCrtName}; - - //Revoke previous agent certificate if exists - File agentCrtFile = new File(srvrKstrDir + File.separator + agentCrtName); - - String command; - if (agentCrtFile.exists()) { - LOG.info("Revoking of " + containerId + " certificate."); - command = MessageFormat.format(REVOKE_AGENT_CRT, scriptArgs); - runCommand(command); - } - - command = MessageFormat.format(SIGN_AGENT_CRT, scriptArgs); - - LOG.debug(SecurityUtils.hideOpenSslPassword(command)); - runCommand(command); - - return agentCrtName; - - } - - private String getSubjectDN(String hostname, String containerId, - String appName) { - return String.format("/CN=%s%s%s", - hostname, - containerId != null ? "/OU=" + containerId : "", - appName != null ? "/OU=" + appName : ""); - - - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/KeystoreGenerator.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/KeystoreGenerator.java b/slider-core/src/main/java/org/apache/slider/server/services/security/KeystoreGenerator.java deleted file mode 100644 index e2339d5..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/KeystoreGenerator.java +++ /dev/null @@ -1,64 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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 org.apache.slider.server.services.security; - -import org.apache.slider.common.SliderKeys; -import org.apache.slider.core.conf.AggregateConf; -import org.apache.slider.core.conf.MapOperations; -import org.apache.slider.core.exceptions.SliderException; - -import java.io.File; -import java.io.IOException; - -/** - * - */ -public class KeystoreGenerator extends AbstractSecurityStoreGenerator { - - - public KeystoreGenerator(CertificateManager certificateMgr) { - super(certificateMgr); - } - - @Override - public SecurityStore generate(String hostname, String containerId, - AggregateConf instanceDefinition, - MapOperations compOps, String role) - throws SliderException, IOException { - SecurityStore keystore = null; - String password = getStorePassword( - instanceDefinition.getAppConf().credentials, compOps, role); - if (password != null) { - keystore = - certificateMgr.generateContainerKeystore(hostname, containerId, role, - password); - } - return keystore; - } - - @Override - String getPassword(MapOperations compOps) { - return compOps.get( - compOps.get(SliderKeys.COMP_KEYSTORE_PASSWORD_PROPERTY_KEY)); - } - - @Override - String getAlias(MapOperations compOps) { - return compOps.getOption(SliderKeys.COMP_KEYSTORE_PASSWORD_ALIAS_KEY, - SliderKeys.COMP_KEYSTORE_PASSWORD_ALIAS_DEFAULT); - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStore.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStore.java b/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStore.java deleted file mode 100644 index fc54267..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStore.java +++ /dev/null @@ -1,66 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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 org.apache.slider.server.services.security; - -import java.io.File; - -/** - * - */ -public class SecurityStore { - private File file; - - public enum StoreType {truststore, keystore} - - private StoreType type; - - public String getType() { - return type.name(); - } - - public File getFile() { - return file; - } - - public SecurityStore(File file, - StoreType type) { - - this.file = file; - this.type = type; - } - - @Override - public boolean equals(Object o) { - if (this == o) return true; - if (o == null || getClass() != o.getClass()) return false; - - SecurityStore that = (SecurityStore) o; - - if (file != null ? !file.equals(that.file) : that.file != null) - return false; - if (type != that.type) return false; - - return true; - } - - @Override - public int hashCode() { - int result = file != null ? file.hashCode() : 0; - result = 31 * result + (type != null ? type.hashCode() : 0); - return result; - } -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStoreGenerator.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStoreGenerator.java b/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStoreGenerator.java deleted file mode 100644 index a814988..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityStoreGenerator.java +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.services.security; - -import org.apache.slider.core.conf.AggregateConf; -import org.apache.slider.core.conf.MapOperations; -import org.apache.slider.core.exceptions.SliderException; - -import java.io.File; -import java.io.IOException; - -/** - * - */ -public interface SecurityStoreGenerator { - - SecurityStore generate(String hostname, - String containerId, - AggregateConf instanceDefinition, - MapOperations compOps, - String role) - throws SliderException, IOException; - - boolean isStoreRequested(MapOperations compOps); -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityUtils.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityUtils.java b/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityUtils.java deleted file mode 100644 index e82ad84..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/SecurityUtils.java +++ /dev/null @@ -1,256 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You 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 org.apache.slider.server.services.security; - -import org.apache.commons.io.FileUtils; -import org.apache.commons.lang.RandomStringUtils; -import org.apache.hadoop.fs.Path; -import org.apache.hadoop.fs.RawLocalFileSystem; -import org.apache.hadoop.fs.permission.FsAction; -import org.apache.hadoop.fs.permission.FsPermission; -import org.apache.slider.common.SliderKeys; -import org.apache.slider.common.SliderXmlConfKeys; -import org.apache.slider.core.conf.MapOperations; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - -import java.io.File; -import java.io.IOException; -//import java.nio.file.Files; -//import java.nio.file.Path; -//import java.nio.file.Paths; -//import java.nio.file.attribute.PosixFilePermission; -//import java.nio.file.attribute.PosixFilePermissions; - - -/** - * - */ -public class SecurityUtils { - private static final Logger LOG = - LoggerFactory.getLogger(SecurityUtils.class); - - private static String CA_CONFIG_CONTENTS = "HOME = .\n" - + "RANDFILE = $ENV::HOME/.rnd\n\n" - + "[ ca ]\n" - + "default_ca = CA_CLIENT\n" - + "[ CA_CLIENT ]\n" - + "dir = ${SEC_DIR}/db\n" - + "certs = $dir/certs\n" - + "new_certs_dir = $dir/newcerts\n" - + "\n" - + "database = $dir/index.txt\n" - + "serial = $dir/serial\n" - + "default_days = 365 \n" - + "\n" - + "default_crl_days = 7 \n" - + "default_md = sha256 \n" - + "\n" - + "policy = policy_anything \n" - + "\n" - + "[ policy_anything ]\n" - + "countryName = optional\n" - + "stateOrProvinceName = optional\n" - + "localityName = optional\n" - + "organizationName = optional\n" - + "organizationalUnitName = optional\n" - + "commonName = optional\n" - + "emailAddress = optional\n" - + "\n" - + "[req]\n" - + "distinguished_name = req_distinguished_name\n" - + "\n" - + "[ req_distinguished_name ]\n" - + "\n" - + "[ jdk7_ca ]\n" - + "subjectKeyIdentifier = hash\n" - + "authorityKeyIdentifier = keyid:always,issuer:always\n" - + "basicConstraints = CA:true\n"; - - private static final String PASS_TOKEN = "pass:"; - private static String keystorePass; - private static String securityDir; - - public static void logOpenSslExitCode(String command, int exitCode) { - if (exitCode == 0) { - LOG.info(getOpenSslCommandResult(command, exitCode)); - } else { - LOG.warn(getOpenSslCommandResult(command, exitCode)); - } - - } - - public static String hideOpenSslPassword(String command){ - int start = command.indexOf(PASS_TOKEN); - while (start >= 0) { - start += PASS_TOKEN.length(); - CharSequence cs = command.subSequence(start, command.indexOf(" ", start)); - command = command.replace(cs, "****"); - start = command.indexOf(PASS_TOKEN, start + 1); - } - return command; - } - - public static String getOpenSslCommandResult(String command, int exitCode) { - return new StringBuilder().append("Command ") - .append(hideOpenSslPassword(command)) - .append(" was finished with exit code: ") - .append(exitCode).append(" - ") - .append(getOpenSslExitCodeDescription(exitCode)).toString(); - } - - private static String getOpenSslExitCodeDescription(int exitCode) { - switch (exitCode) { - case 0: { - return "the operation was completed successfully."; - } - case 1: { - return "an error occurred parsing the command options."; - } - case 2: { - return "one of the input files could not be read."; - } - case 3: { - return "an error occurred creating the PKCS#7 file or when reading the MIME message."; - } - case 4: { - return "an error occurred decrypting or verifying the message."; - } - case 5: { - return "the message was verified correctly but an error occurred writing out the signers certificates."; - } - default: - return "unsupported code"; - } - } - - public static void writeCaConfigFile(String path) throws IOException { - String contents = CA_CONFIG_CONTENTS.replace("${SEC_DIR}", path); - FileUtils.writeStringToFile(new File(path, "ca.config"), contents); - } - - public static String getKeystorePass() { - return keystorePass; - } - - public static String getSecurityDir() { - return securityDir; - } - - public static void initializeSecurityParameters(MapOperations configMap) { - initializeSecurityParameters(configMap, false); - } - - public static void initializeSecurityParameters(MapOperations configMap, - boolean persistPassword) { - String keyStoreLocation = configMap.getOption( - SliderXmlConfKeys.KEY_KEYSTORE_LOCATION, getDefaultKeystoreLocation()); - if (keyStoreLocation == null) { - LOG.error(SliderXmlConfKeys.KEY_KEYSTORE_LOCATION - + " is not specified. Unable to initialize security params."); - return; - } - File secDirFile = new File(keyStoreLocation).getParentFile(); - if (!secDirFile.exists()) { - // create entire required directory structure - File dbDir = new File(secDirFile, "db"); - File newCertsDir = new File(dbDir, "newcerts"); - newCertsDir.mkdirs(); - RawLocalFileSystem fileSystem = null; - try { - fileSystem = new RawLocalFileSystem(); - FsPermission permissions = new FsPermission(FsAction.ALL, FsAction.NONE, - FsAction.NONE); - fileSystem.setPermission(new Path(dbDir.getAbsolutePath()), - permissions); - fileSystem.setPermission(new Path(dbDir.getAbsolutePath()), permissions); - fileSystem.setPermission(new Path(newCertsDir.getAbsolutePath()), - permissions); - File indexFile = new File(dbDir, "index.txt"); - indexFile.createNewFile(); - SecurityUtils.writeCaConfigFile(secDirFile.getAbsolutePath().replace('\\', '/')); - - } catch (IOException e) { - LOG.error("Unable to create SSL configuration directories/files", e); - } finally { - if (fileSystem != null) { - try { - fileSystem.close(); - } catch (IOException e) { - LOG.warn("Unable to close fileSystem", e); - } - } - } - // need to create the password - } - keystorePass = getKeystorePassword(secDirFile, persistPassword); - securityDir = secDirFile.getAbsolutePath(); - } - - private static String getKeystorePassword(File secDirFile, - boolean persistPassword) { - File passFile = new File(secDirFile, SliderKeys.CRT_PASS_FILE_NAME); - String password = null; - if (!passFile.exists()) { - LOG.info("Generating keystore password"); - password = RandomStringUtils.randomAlphanumeric( - Integer.valueOf(SliderKeys.PASS_LEN)); - if (persistPassword) { - try { - FileUtils.writeStringToFile(passFile, password); - passFile.setWritable(true); - passFile.setReadable(true); - } catch (IOException e) { - e.printStackTrace(); - throw new RuntimeException( - "Error creating certificate password file"); - } - } - } else { - LOG.info("Reading password from existing file"); - try { - password = FileUtils.readFileToString(passFile); - password = password.replaceAll("\\p{Cntrl}", ""); - } catch (IOException e) { - e.printStackTrace(); - } - } - - return password; - } - - private static String getDefaultKeystoreLocation() { - File workDir = null; - try { - workDir = new File(FileUtils.getTempDirectory().getAbsolutePath() - + "/sec" + System.currentTimeMillis()); - if (!workDir.mkdirs()) { - throw new IOException("Unable to create temporary security directory"); - } - } catch (IOException e) { - LOG.warn("Unable to create security directory"); - return null; - } - - return new StringBuilder().append(workDir.getAbsolutePath()) - .append(File.separator) - .append(SliderKeys.SECURITY_DIR) - .append(File.separator) - .append(SliderKeys.KEYSTORE_FILE_NAME).toString(); - } - -} http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/SignCertResponse.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/SignCertResponse.java b/slider-core/src/main/java/org/apache/slider/server/services/security/SignCertResponse.java deleted file mode 100644 index 8437d88..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/SignCertResponse.java +++ /dev/null @@ -1,67 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.services.security; - -import javax.xml.bind.annotation.XmlAccessType; -import javax.xml.bind.annotation.XmlAccessorType; -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; -import javax.xml.bind.annotation.XmlType; - -/** - * - * Sign certificate response data model. - * - */ -@XmlRootElement -@XmlAccessorType(XmlAccessType.FIELD) -@XmlType(name = "", propOrder = {}) -public class SignCertResponse { - - public static final String ERROR_STATUS = "ERROR"; - public static final String OK_STATUS = "OK"; - - @XmlElement - private String result; - @XmlElement - private String signedCa; - @XmlElement - private String message; - - public String getResult() { - return result; - } - public void setResult(String result) { - this.result = result; - } - public String getSignedCa() { - return signedCa; - } - public void setSignedCa(String signedCa) { - this.signedCa = signedCa; - } - - public String getMessage() { - return message; - } - public void setMessage(String message) { - this.message = message; - } -} - http://git-wip-us.apache.org/repos/asf/incubator-slider/blob/51c2b92c/slider-core/src/main/java/org/apache/slider/server/services/security/SignMessage.java ---------------------------------------------------------------------- diff --git a/slider-core/src/main/java/org/apache/slider/server/services/security/SignMessage.java b/slider-core/src/main/java/org/apache/slider/server/services/security/SignMessage.java deleted file mode 100644 index 4bccb87..0000000 --- a/slider-core/src/main/java/org/apache/slider/server/services/security/SignMessage.java +++ /dev/null @@ -1,54 +0,0 @@ -/** - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you 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 org.apache.slider.server.services.security; - -import javax.xml.bind.annotation.XmlAccessType; -import javax.xml.bind.annotation.XmlAccessorType; -import javax.xml.bind.annotation.XmlElement; -import javax.xml.bind.annotation.XmlRootElement; -import javax.xml.bind.annotation.XmlType; - -/** - * - * Sign certificate request data model. - * - */ -@XmlRootElement -@XmlAccessorType(XmlAccessType.FIELD) -@XmlType(name = "", propOrder = {}) -public class SignMessage { - - @XmlElement - private String csr; - @XmlElement - private String passphrase; - public String getCsr() { - return csr; - } - public void setCsr(String csr) { - this.csr = csr; - } - public String getPassphrase() { - return passphrase; - } - public void setPassphrase(String passphrase) { - this.passphrase = passphrase; - } -} -