package eu.dnetlib.enabling.nodeManager;

import java.util.Map;
import java.util.concurrent.Executor;
import java.util.concurrent.Executors;

import javax.annotation.Resource;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.google.common.base.Joiner;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;

import eu.dnetlib.common.services.AbstractBaseService;
import eu.dnetlib.enabling.blackboard.BlackboardDispatcher;
import eu.dnetlib.enabling.blackboard.BlackboardRegistry;
import eu.dnetlib.rmi.objects.is.BlackboardActionStatus;
import eu.dnetlib.rmi.objects.is.BlackboardMessageContainer;
import eu.dnetlib.rmi.objects.is.Operation;
import eu.dnetlib.rmi.soap.NodeManagerService;

public class NodeManagerServiceImpl extends AbstractBaseService implements NodeManagerService {

	private static final Log log = LogFactory.getLog(NodeManagerServiceImpl.class);

	private static final Executor executor = Executors.newCachedThreadPool();

	@Resource
	private BlackboardRegistry blackboardRegistry;

	@Resource
	private BlackboardDispatcher blackboardDispatcher;

	@Override
	public String echo(final String message) {
		return Joiner.on(", ").join(message, message, message);
	}

	@Override
	public void notify(final String subscriptionId, final Operation operation, final String message) {
		executor.execute(new Runnable() {

			@Override
			public void run() {
				if (blackboardRegistry.requiresBlackboardAction(subscriptionId)) {
					final BlackboardMessageContainer bbMessage = toBlackboardMessage(message);
					log.debug("got blackboard request - subscrId: " + subscriptionId + ", operation: " + operation + ", message: " + bbMessage.getJsonMessage());
					blackboardRegistry.activateAction(subscriptionId, bbMessage);
				} else if (blackboardDispatcher.isRegisteredSubscription(subscriptionId)) {
					final BlackboardMessageContainer bbMessage = toBlackboardMessage(message);
					log.debug("got blackboard response - subscrId: " + subscriptionId + ", operation: " + operation + ", message: "
							+ bbMessage.getJsonMessage());
					blackboardDispatcher.activateResponseAction(subscriptionId, bbMessage);
				} else {
					log.warn("got unmanaged notification - subscrId: " + subscriptionId + ", operation: " + operation + ", message: " + message);
				}
			}
		});
	}

	private BlackboardMessageContainer toBlackboardMessage(final String message) {
		final Map<String, String> map = new Gson().fromJson(message, new TypeToken<Map<String, String>>() {}.getType());

		final BlackboardMessageContainer bbMessage = new BlackboardMessageContainer();
		bbMessage.setAction(map.get("action"));
		bbMessage.setId(map.get("id"));
		bbMessage.setJsonMessage(map.get("message"));
		bbMessage.setStatus(BlackboardActionStatus.valueOf(map.get("status")));
		return bbMessage;
	}

}
