/**
* Copyright (C) 2013 - present by OpenGamma Inc. and the OpenGamma group of companies
*
* Please see distribution for license.
*/
package com.opengamma.engine.view.worker;
import java.util.EnumSet;
import com.opengamma.engine.view.ViewDefinition;
import com.opengamma.engine.view.execution.ExecutionOptions;
import com.opengamma.engine.view.execution.ViewExecutionFlags;
import com.opengamma.engine.view.execution.ViewExecutionOptions;
import com.opengamma.util.ArgumentChecker;
/**
* When the "parallel recompilation" flags are set, work is distributed between two delegate workers. The primary worker executes cycles without considering recompilation changes. When a change is
* detected, a secondary worker begins the recompilation. When compilation is complete, the primary worker is terminated and the secondary worker promoted to a primary role.
* <p>
* For example in the case of presenting live market data, this can be used to avoid the interface stalling during configuration changes.
*/
public class ParallelRecompilationViewProcessWorkerFactory implements ViewProcessWorkerFactory {
private final ViewProcessWorkerFactory _passThrough;
private ViewProcessWorkerFactory _delegate;
public ParallelRecompilationViewProcessWorkerFactory(final ViewProcessWorkerFactory passThrough) {
ArgumentChecker.notNull(passThrough, "passThrough");
_passThrough = passThrough;
_delegate = passThrough;
}
public ViewProcessWorkerFactory getPassThrough() {
return _passThrough;
}
public ViewProcessWorkerFactory getDelegate() {
return _delegate;
}
public void setDelegate(final ViewProcessWorkerFactory delegate) {
ArgumentChecker.notNull(delegate, "delegate");
_delegate = delegate;
}
protected ViewExecutionOptions getPrimaryExecutionOptions(final ViewExecutionOptions executionOptions) {
final EnumSet<ViewExecutionFlags> flags = EnumSet.copyOf(executionOptions.getFlags());
flags.remove(ViewExecutionFlags.PARALLEL_RECOMPILATION_AND_EXECUTION);
flags.remove(ViewExecutionFlags.PARALLEL_RECOMPILATION_DEFERRED_EXECUTION);
flags.remove(ViewExecutionFlags.PARALLEL_RECOMPILATION_IMMEDIATE_EXECUTION);
flags.add(ViewExecutionFlags.IGNORE_COMPILATION_VALIDITY);
return new ExecutionOptions(executionOptions.getExecutionSequence(), flags, executionOptions.getMaxSuccessiveDeltaCycles(), executionOptions.getDefaultExecutionOptions());
}
protected ViewExecutionOptions getSecondaryExecutionOptions(final ViewExecutionOptions executionOptions) {
final EnumSet<ViewExecutionFlags> flags = EnumSet.copyOf(executionOptions.getFlags());
if (!flags.remove(ViewExecutionFlags.WAIT_FOR_INITIAL_TRIGGER)) {
return executionOptions;
}
return new ExecutionOptions(executionOptions.getExecutionSequence(), flags, executionOptions.getMaxSuccessiveDeltaCycles(), executionOptions.getDefaultExecutionOptions());
}
protected ParallelRecompilationViewProcessWorker createWorkerImpl(final ViewProcessWorkerContext context, final ViewExecutionOptions executionOptions, final ViewDefinition viewDefinition) {
return new ParallelRecompilationViewProcessWorker(getDelegate(), context, getSecondaryExecutionOptions(executionOptions), viewDefinition);
}
protected ViewProcessWorker parallelExecution(final ViewProcessWorkerContext context, final ViewExecutionOptions executionOptions, final ViewDefinition viewDefinition) {
final ViewExecutionOptions primaryOptions = getPrimaryExecutionOptions(executionOptions);
final ParallelRecompilationViewProcessWorker worker = createWorkerImpl(context, primaryOptions, viewDefinition);
worker.startParallel(primaryOptions);
return worker;
}
protected ViewProcessWorker deferredExecution(final ViewProcessWorkerContext context, final ViewExecutionOptions executionOptions, final ViewDefinition viewDefinition) {
final ViewExecutionOptions primaryOptions = getPrimaryExecutionOptions(executionOptions);
final ParallelRecompilationViewProcessWorker worker = createWorkerImpl(context, primaryOptions, viewDefinition);
worker.startDeferred(primaryOptions);
return worker;
}
protected ViewProcessWorker immediateExecution(final ViewProcessWorkerContext context, final ViewExecutionOptions executionOptions, final ViewDefinition viewDefinition) {
final ViewExecutionOptions primaryOptions = getPrimaryExecutionOptions(executionOptions);
final ParallelRecompilationViewProcessWorker worker = createWorkerImpl(context, primaryOptions, viewDefinition);
worker.startImmediate(primaryOptions);
return worker;
}
// ViewProcessWorkerFactory
@Override
public ViewProcessWorker createWorker(final ViewProcessWorkerContext context, final ViewExecutionOptions executionOptions, final ViewDefinition viewDefinition) {
if (!executionOptions.getFlags().contains(ViewExecutionFlags.IGNORE_COMPILATION_VALIDITY)) {
if (executionOptions.getFlags().contains(ViewExecutionFlags.PARALLEL_RECOMPILATION_AND_EXECUTION)) {
return parallelExecution(context, executionOptions, viewDefinition);
}
if (executionOptions.getFlags().contains(ViewExecutionFlags.PARALLEL_RECOMPILATION_DEFERRED_EXECUTION)) {
return deferredExecution(context, executionOptions, viewDefinition);
}
if (executionOptions.getFlags().contains(ViewExecutionFlags.PARALLEL_RECOMPILATION_IMMEDIATE_EXECUTION)) {
return immediateExecution(context, executionOptions, viewDefinition);
}
}
return getPassThrough().createWorker(context, executionOptions, viewDefinition);
}
}