package be.iminds.ilabt.jfed.highlevel.tasks;

import be.iminds.ilabt.jfed.highlevel.controller.JFedHighLevelException;
import be.iminds.ilabt.jfed.highlevel.controller.Task;
import be.iminds.ilabt.jfed.highlevel.controller.TaskExecution;
import be.iminds.ilabt.jfed.highlevel.model.Slice;
import be.iminds.ilabt.jfed.highlevel.util.AggregateManagerWrapperFactory;
import be.iminds.ilabt.jfed.lowlevel.ApiInfo;
import be.iminds.ilabt.jfed.lowlevel.JFedException;
import be.iminds.ilabt.jfed.lowlevel.api_wrapper.AggregateManagerWrapper;
import be.iminds.ilabt.jfed.fedmon.webapi.service.json.*;
import be.iminds.ilabt.jfed.rspec.model.StringRspec;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.annotation.Nonnull;
import java.util.Collections;
import java.util.List;

/**
 * User: twalcari
 * Date: 6/16/2015
 * Time: 16:56
 */
public class SliceManifestForAuthorityTask extends Task {
    private static final Logger LOG = LoggerFactory.getLogger(SliceManifestForAuthorityTask.class);

    private final Server auth;
    private final Slice slice;
    private String manifestRspec = null;

    private final AggregateManagerWrapperFactory aggregateManagerWrapperFactory;
    private final HighLevelTaskFactory highLevelTaskFactory;

    public SliceManifestForAuthorityTask(@Nonnull Slice slice, @Nonnull Server auth,
                                         AggregateManagerWrapperFactory aggregateManagerWrapperFactory,
                                         HighLevelTaskFactory highLevelTaskFactory) {
        super("get Manifest of Slice @ " + auth.getName());
        this.auth = auth;
        this.slice = slice;
        this.aggregateManagerWrapperFactory = aggregateManagerWrapperFactory;
        this.highLevelTaskFactory = highLevelTaskFactory;
    }

    @Override
    public void doTask(TaskExecution taskExecution) throws JFedException, InterruptedException {
        AggregateManagerWrapper amWrapper =
                aggregateManagerWrapperFactory.getAggregateManagerWrapper(taskExecution, auth);

        if (!ApiInfo.hasService(auth, ApiInfo.ApiName.GENI_AM)) {
            LOG.error("Tried to get manifest for slice '{}', at authority '{}', " +
                            "but that authority has no AM URL: cannot continue.",
                    slice.getUrnString(), auth.getName());

            throw new JFedHighLevelException("Tried to get manifest for slice \"" + slice.getUrnString() + "\"," +
                    " at authority \"" + auth.getDefaultComponentManagerUrn() + "\", but that authority has no AM URL: cannot continue.");
        }

        manifestRspec = amWrapper.describe(slice.getUrn(), slice.getCredentials());
    }

    @Override
    public List<Task> initDependsOn() {
        return Collections.singletonList(highLevelTaskFactory.getSliceCredential(slice));
    }

    public String getManifestRspec() {
        return manifestRspec;
    }

    public StringRspec getManifestStringRspec() {
        if (manifestRspec != null) {
            return new StringRspec(manifestRspec);
        } else {
            return null;
        }
    }
}
