/**
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * <p>
 * http://www.apache.org/licenses/LICENSE-2.0
 * <p>
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.winegrower.extension.build.maven;

import static java.util.Collections.singletonList;
import static java.util.Optional.ofNullable;
import static java.util.stream.Collectors.toList;
import static org.apache.maven.plugins.annotations.ResolutionScope.RUNTIME_PLUS_SYSTEM;

import java.io.File;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
import java.util.function.Predicate;
import java.util.stream.Stream;

import org.apache.maven.artifact.Artifact;
import org.apache.maven.plugin.AbstractMojo;
import org.apache.maven.plugins.annotations.Mojo;
import org.apache.maven.plugins.annotations.Parameter;
import org.apache.maven.project.MavenProject;
import org.apache.winegrower.Ripener;
import org.apache.winegrower.extension.build.common.Run;
import org.apache.winegrower.scanner.manifest.ManifestContributor;

@Mojo(name = "pour", requiresDependencyResolution = RUNTIME_PLUS_SYSTEM)
public class PourMojo extends AbstractMojo {

    @Parameter(property = "winegrower.workDir", defaultValue = "${project.build.directory}/winegrower/workdir")
    private File workDir;

    @Parameter(property = "winegrower.jarFilter")
    private String jarFilter;

    @Parameter(property = "winegrower.scanningIncludes")
    private Collection<String> scanningIncludes;

    @Parameter(property = "winegrower.scanningExcludes")
    private Collection<String> scanningExcludes;

    @Parameter(property = "winegrower.manifestContributors")
    private Collection<String> manifestContributors;

    @Parameter(property = "winegrower.dependencyScopes", defaultValue = "provided,compile,system,runtime")
    private Collection<String> dependencyScopes;

    @Parameter(property = "winegrower.prioritizedBundles", defaultValue = "org.apache.aries.blueprint.core")
    private Collection<String> prioritizedBundles;

    @Parameter(property = "winegrower.systemVariables")
    private Map<String, String> systemVariables;

    @Parameter(property = "winegrower.waitOnSystemIn", defaultValue = "true")
    private boolean waitOnSystemIn; // if you use the shell this breaks it if set to true

    @Parameter(defaultValue = "${project}", readonly = true, required = true)
    private MavenProject project;

    @Override
    public void execute() {
        final Thread thread = Thread.currentThread();
        final ClassLoader loader = thread.getContextClassLoader();
        final ClassLoader appLoader = createClassLoader(loader);
        thread.setContextClassLoader(appLoader);
        try {
            new Run(createConfiguration(), systemVariables) {

                @Override
                protected void waitForExit() {
                    if (waitOnSystemIn) {
                        super.waitForExit();
                    } else { // just block
                        try {
                            new CountDownLatch(1).await();
                        } catch (final InterruptedException e) {
                            Thread.currentThread().interrupt();
                        }
                    }
                }
            }.run();
        } finally {
            if (appLoader != loader) {
                try {
                    URLClassLoader.class.cast(appLoader).close();
                } catch (final IOException e) {
                    getLog().warn(e.getMessage(), e);
                }
            }
            thread.setContextClassLoader(loader);
        }
    }

    private ClassLoader createClassLoader(final ClassLoader parent) {
        final List<URL> urls = Stream.concat(
                project.getArtifacts().stream()
                        .filter(a -> !((dependencyScopes == null
                                && !(Artifact.SCOPE_COMPILE.equals(a.getScope()) || Artifact.SCOPE_RUNTIME.equals(a.getScope())))
                                || (dependencyScopes != null && !dependencyScopes.contains(a.getScope()))))
                        .map(Artifact::getFile),
                Stream.of(project.getBuild().getOutputDirectory()).map(File::new).filter(File::exists)).map(file -> {
                    try {
                        return file.toURI().toURL();
                    } catch (final MalformedURLException e) {
                        throw new IllegalArgumentException(e);
                    }
                }).collect(toList());
        return urls.isEmpty() ? parent : new URLClassLoader(urls.toArray(new URL[0]), parent) {

            @Override
            public boolean equals(final Object obj) {
                return super.equals(obj) || parent.equals(obj);
            }
        };
    }

    private Ripener.Configuration createConfiguration() {
        final Ripener.Configuration configuration = new Ripener.Configuration();
        ofNullable(workDir).ifPresent(configuration::setWorkDir);
        ofNullable(prioritizedBundles).filter(it -> !it.isEmpty()).ifPresent(configuration::setPrioritizedBundles);
        ofNullable(scanningIncludes).filter(it -> !it.isEmpty()).ifPresent(configuration::setScanningIncludes);
        ofNullable(scanningExcludes).filter(it -> !it.isEmpty()).ifPresent(configuration::setScanningIncludes);
        ofNullable(manifestContributors).filter(it -> !it.isEmpty()).ifPresent(contributors -> {
            configuration.setManifestContributors(manifestContributors.stream().map(clazz -> {
                try {
                    return Thread.currentThread().getContextClassLoader().loadClass(clazz).getConstructor().newInstance();
                } catch (final InstantiationException | NoSuchMethodException | IllegalAccessException
                        | ClassNotFoundException e) {
                    throw new IllegalArgumentException(e);
                } catch (final InvocationTargetException e) {
                    throw new IllegalArgumentException(e.getTargetException());
                }
            }).map(ManifestContributor.class::cast).collect(toList()));
        });
        ofNullable(jarFilter).ifPresent(filter -> {
            try {
                configuration.setJarFilter((Predicate<String>) Thread.currentThread().getContextClassLoader().loadClass(filter)
                        .getConstructor().newInstance());
            } catch (final InstantiationException | NoSuchMethodException | IllegalAccessException | ClassNotFoundException e) {
                throw new IllegalArgumentException(e);
            } catch (final InvocationTargetException e) {
                throw new IllegalArgumentException(e.getTargetException());
            }
        });
        return configuration;
    }
}
