package org.apache.maven.plugin.war.packaging;

/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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
 *
 *  http://www.apache.org/licenses/LICENSE-2.0
 *
 * 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.
 */

import org.apache.maven.artifact.Artifact;
import org.apache.maven.model.Dependency;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.plugin.MojoFailureException;
import org.apache.maven.plugin.war.util.WebappStructure;

import java.io.File;

/**
 * Analyzes the dependencies of the project with its previous state and update the target directory accordingly.
 *
 * @author Stephane Nicoll
 * @version $Id$
 */
public class DependenciesAnalysisPackagingTask
    extends AbstractWarPackagingTask
{

    public void performPackaging( final WarPackagingContext context )
        throws MojoExecutionException, MojoFailureException
    {

        context.getWebappStructure().analyseDependencies( new DependenciesAnalysisCallbackImpl( context ) );

    }

    protected void handleDependency( WarPackagingContext context, Dependency dependency, String notBundledMessage,
                                     String warOrZipMessage, String standardMessage, boolean removeFile )
    {
        if ( Artifact.SCOPE_PROVIDED.equals( dependency.getScope() )
            || Artifact.SCOPE_TEST.equals( dependency.getScope() ) || dependency.isOptional() )
        {
            context.getLog().debug( notBundledMessage );
        }
        else
        {
            handleDependencyScope( context, dependency, warOrZipMessage, standardMessage, removeFile );
        }
    }

    protected void handleDependencyScope( WarPackagingContext context, Dependency dependency, String warOrZipMessage,
                                          String standardMessage, boolean removeFile )
    {
        if ( "war".equals( dependency.getType() ) || "zip".equals( dependency.getType() ) )
        {
            context.getLog().warn( warOrZipMessage );
        }
        else if ( "tld".equals( dependency.getType() ) || "aar".equals( dependency.getType() )
            || "mar".equals( dependency.getType() ) || "xar".equals( dependency.getType() )
            || "jar".equals( dependency.getType() ) || "ejb".equals( dependency.getType() )
            || "ejb-client".equals( dependency.getType() ) || "test-jar".equals( dependency.getType() )
            || "par".equals( dependency.getType() ) )
        {
            context.getLog().info( standardMessage );
            if ( removeFile )
            {
                removeDependency( context, dependency );
            }
        }
    }

    private void removeDependency( WarPackagingContext context, Dependency dependency )
    {
        final String targetFileName = context.getWebappStructure().getCachedTargetFileName( dependency );
        if ( targetFileName != null )
        {
            final String type = dependency.getType();
            File targetFile = null;
            if ( "tld".equals( type ) )
            {
                targetFile = new File( context.getWebappDirectory(), ArtifactsPackagingTask.TLD_PATH + targetFileName );
            }
            else if ( "aar".equals( type ) )
            {
                targetFile =
                    new File( context.getWebappDirectory(), ArtifactsPackagingTask.SERVICES_PATH + targetFileName );
            }
            else if ( "mar".equals( type ) )
            {
                targetFile =
                    new File( context.getWebappDirectory(), ArtifactsPackagingTask.MODULES_PATH + targetFileName );
            }
            else if ( "xar".equals( type ) )
            {
                targetFile =
                    new File( context.getWebappDirectory(), ArtifactsPackagingTask.EXTENSIONS_PATH + targetFileName );
            }
            else if ( "jar".equals( type ) || "ejb".equals( type ) || "ejb-client".equals( type )
                || "test-jar".equals( type ) )
            {
                targetFile = new File( context.getWebappDirectory(), LIB_PATH + targetFileName );
            }
            else if ( "par".equals( type ) )
            {
                String targetFileName2 = targetFileName.substring( 0, targetFileName.lastIndexOf( '.' ) ) + ".jar";
                targetFile = new File( context.getWebappDirectory(), LIB_PATH + targetFileName2 );
            }

            // now remove
            if ( targetFile == null )
            {
                context.getLog().error( "Could not get file from dependency [" + dependency + "]" );
            }
            else if ( targetFile.exists() )
            {
                context.getLog().debug( "Removing file [" + targetFile.getAbsolutePath() + "]" );
                targetFile.delete();
            }
            else
            {
                context.getLog().warn( "File to remove [" + targetFile.getAbsolutePath() + "] has not been found" );
            }
        }
        else
        {
            context.getLog().warn( "Could not retrieve the target file name of dependency [" + dependency + "]" );
        }
    }

    class DependenciesAnalysisCallbackImpl
        implements WebappStructure.DependenciesAnalysisCallback
    {
        private final WarPackagingContext context;

        DependenciesAnalysisCallbackImpl( WarPackagingContext context )
        {
            this.context = context;
        }

        public void unchangedDependency( Dependency dependency )
        {
            context.getLog().debug( "Dependency [" + dependency + "] has not changed since last build." );
        }

        public void newDependency( Dependency dependency )
        {
            context.getLog().debug( "New dependency [" + dependency + "]." );
        }

        public void removedDependency( Dependency dependency )
        {
            handleDependency( context, dependency, "Dependency [" + dependency
                + "] has been removed from the project but it was not bundled anyway.", "Dependency [" + dependency
                + "] has been removed from the project. If it was included in the build as an overlay, "
                + "consider cleaning the target directory of the project (mvn clean)", "Dependency [" + dependency
                + "] has been removed from the project.", true );
        }

        public void updatedVersion( Dependency dependency, String previousVersion )
        {
            handleDependency( context, dependency, "Version of dependency [" + dependency + "] has changed ("
                                  + previousVersion + " -> " + dependency.getVersion()
                                  + ") but it was not bundled anyway.",
                              "Version of dependency [" + dependency + "] has changed (" + previousVersion + " -> "
                                  + dependency.getVersion() + "). If it was included in the build as an overlay, "
                                  + "consider " + "cleaning the target directory of the project (mvn clean)",
                              "Version of dependency [" + dependency + "] has changed (" + previousVersion + " -> "
                                  + dependency.getVersion() + ").", true );
        }

        public void updatedScope( Dependency dependency, String previousScope )
        {
            if ( Artifact.SCOPE_PROVIDED.equals( dependency.getScope() )
                || Artifact.SCOPE_TEST.equals( dependency.getScope() )
                && ( !Artifact.SCOPE_PROVIDED.equals( previousScope ) && !Artifact.SCOPE_TEST.equals( previousScope ) ) )
            {
                // It's now provided or test so it should be removed
                handleDependencyScope( context, dependency, "Scope of dependency [" + dependency + "] has changed ("
                    + previousScope + " -> " + dependency.getScope()
                    + "). If it was included in the build as an overlay, "
                    + "consider cleaning the target directory of the project (mvn clean)", "Scope of dependency ["
                    + dependency + "] has changed (" + previousScope + " -> " + dependency.getScope() + ").", true );
            }

        }

        public void updatedOptionalFlag( Dependency dependency, boolean previousOptional )
        {
            if ( !previousOptional && dependency.isOptional() )
            {
                // It wasn't optional but now it is anymore
                handleDependency( context, dependency, "Dependency [" + dependency
                    + "] is now optional but it was not bundled anyway.", "Dependency [" + dependency
                    + "] is now optional. If it was included in the build as an overlay, "
                    + "consider cleaning the target directory of the project (mvn clean)", "Dependency [" + dependency
                    + "] is now optional", true );

            }
        }

        public void updatedUnknown( Dependency dependency, Dependency previousDep )
        {
            handleDependency( context, dependency, "Dependency [" + dependency + "] has changed (was " + previousDep
                + ") but it was not bundled anyway.", "Dependency [" + dependency + "] has changed (was " + previousDep
                + "). If it was included in the build as an overlay, " + "consider "
                + "cleaning the target directory of the project (mvn clean)", "Dependency [" + dependency
                + "] has changed (was " + previousDep + ").", true );
        }

    }

}
