* @return File which stores validation result.
*/
@SuppressWarnings("SynchronizationOnLocalVariableOrMethodParameter")
public File doValidate(File base, File script, Condition eventSynchronisation, boolean securityEnabled,
String hostString, final int timeout) {
FanOutStreamSender fanOutStreamSender = null;
ErrorStreamRedirectWorkerLauncher workerLauncher = null;
boolean stopByTooMuchExecution = false;
ByteArrayOutputStream byteArrayErrorStream = new ByteArrayOutputStream();
File file = new File(base, "validation-0.log");
try {
fanOutStreamSender = new FanOutStreamSender(1);
deleteLogs(base);
AbstractLanguageHandler handler = Lang.getByFileName(script).getHandler();
AbstractGrinderClassPathProcessor classPathProcessor = handler.getClassPathProcessor();
GrinderProperties properties = new GrinderProperties();
PropertyBuilder builder = new PropertyBuilder(properties, new Directory(base), securityEnabled, hostString,
NetworkUtils.getLocalHostName());
properties.setInt("grinder.agents", 1);
properties.setInt("grinder.processes", 1);
properties.setInt("grinder.threads", 1);
properties.setBoolean("grinder.script.validation", true);
String grinderJVMClassPath = classPathProcessor.buildForemostClasspathBasedOnCurrentClassLoader(LOGGER)
+ File.pathSeparator + classPathProcessor.buildPatchClasspathBasedOnCurrentClassLoader(LOGGER)
+ File.pathSeparator + builder.buildCustomClassPath(true);
properties.setProperty("grinder.jvm.classpath", grinderJVMClassPath);
LOGGER.info("grinder.jvm.classpath : {} ", grinderJVMClassPath);
AgentIdentityImplementation agentIdentity = new AgentIdentityImplementation("validation");
agentIdentity.setNumber(0);
String newClassPath = classPathProcessor.buildClasspathBasedOnCurrentClassLoader(LOGGER);
LOGGER.debug("validation class path " + newClassPath);
Properties systemProperties = new Properties();
systemProperties.put("java.class.path", base.getAbsolutePath() + File.pathSeparator + newClassPath);
Directory workingDirectory = new Directory(base);
String buildJVMArgumentWithoutMemory = builder.buildJVMArgumentWithoutMemory();
LOGGER.info("jvm args : {} ", buildJVMArgumentWithoutMemory);
final WorkerProcessCommandLine workerCommandLine = new WorkerProcessCommandLine(properties,
systemProperties, buildJVMArgumentWithoutMemory, workingDirectory);
ScriptLocation scriptLocation = new ScriptLocation(workingDirectory, script);
ProcessWorkerFactory workerFactory = new ProcessWorkerFactory(workerCommandLine, agentIdentity,
fanOutStreamSender, false, scriptLocation, properties);
workerLauncher = new ErrorStreamRedirectWorkerLauncher(1, workerFactory, eventSynchronisation, LOGGER,
byteArrayErrorStream);
// Start
workerLauncher.startAllWorkers();
// Wait for a termination event.
synchronized (eventSynchronisation) {
final long sleep = 1000;
int waitingCount = 0;
while (true) {
if (workerLauncher.allFinished()) {
break;
}
if (waitingCount++ > timeout) {
LOGGER.error("Validation should be performed within {} sec. Stop it by force", timeout);
workerLauncher.destroyAllWorkers();
stopByTooMuchExecution = true;
break;
}
eventSynchronisation.waitNoInterrruptException(sleep);
}
}
} catch (Exception e) {
LOGGER.error("Error while executing {} because {}", script, e.getMessage());
LOGGER.info("The error detail is ", e);
appendingMessageOn(file, ExceptionUtils.getFullStackTrace(e));
} finally {
if (workerLauncher != null) {
workerLauncher.shutdown();
}
if (fanOutStreamSender != null) {
fanOutStreamSender.shutdown();
}
// To be safe, wait again..
int waitingCount = 0;
while (workerLauncher != null) {
final int maximumWaitingCount = 10;