package ua.ansymo.hintco

import java.io.Closeable
import java.io.IOException
import java.util.List
import java.util.Map
import org.eclipse.core.runtime.Assert
import org.slf4j.Logger
import org.slf4j.LoggerFactory

class AdaptiveCosimRunner implements ICosimRunner, Closeable {
	
	protected Map<UnitInstance, IFmuInstance> fmuInstanceMap = newHashMap()
	
	protected IOutputProcessor outProcessor
	
	protected Logger logger = LoggerFactory.getLogger(typeof(AdaptiveCosimRunner))
	
	protected IFmuLoader fmuLoader
	
	protected ICosimRunner internalRunner
	
	boolean hardReset
	
	new (IOutputProcessor o, IFmuLoader l, boolean hR){
		outProcessor = o
		fmuLoader = l
		hardReset = hR
	}
	
	override run(RootCandidateScenario rootScenario, Map<Scenario, List<PrecedenceNode>> scenarioNodesMap, String variantID) {
		Assert.isTrue(scenarioNodesMap.values.forall[sortedNodes | sortedNodes.forall[n1 | rootScenario.eAllContents.exists[n2 | n1===n2]]])
		
		val nodes = scenarioNodesMap.get(rootScenario)
		
		if (nodes.filter(InputPortInstance).filter[it.isInput].exists[it.adaptation instanceof RollbackInterpolationAdaptation]){
			logger.debug("AdaptiveCosimRunner using strong coupling.")
			this.internalRunner = new StrongCouplingRunner(outProcessor, fmuLoader, hardReset)
		} else {
			logger.debug("AdaptiveCosimRunner using single runner.")
			this.internalRunner = new SingleCosimRunner(outProcessor, fmuLoader)
		}
		this.internalRunner.run(rootScenario, scenarioNodesMap, variantID)
	}
	
	override close() throws IOException {
		if (this.internalRunner !== null){
			this.internalRunner.close()
		}
	}
	
}