/**
   * Unpacks the specified file to the specified directory.
   *
   * @param context the packaging context
   * @param file the file to unpack
   * @param unpackDirectory the directory to use for th unpacked file
   * @throws MojoExecutionException if an error occured while unpacking the file
   */
  protected void doUnpack(AmpPackagingContext context, File file, File unpackDirectory)
      throws MojoExecutionException {
    String archiveExt = FileUtils.getExtension(file.getAbsolutePath()).toLowerCase();

    // Uncompressing an AMP into another AMP does not require any
    // special treatment so we just use a zip unarchiver
    if ("amp".equals(archiveExt)) {
      archiveExt = "zip";
    }

    try {
      UnArchiver unArchiver = context.getArchiverManager().getUnArchiver(archiveExt);
      unArchiver.setSourceFile(file);
      unArchiver.setDestDirectory(unpackDirectory);
      unArchiver.setOverwrite(true);
      unArchiver.extract();
    } catch (IOException e) {
      throw new MojoExecutionException(
          "Error unpacking file["
              + file.getAbsolutePath()
              + "]"
              + "to["
              + unpackDirectory.getAbsolutePath()
              + "]",
          e);
    } catch (ArchiverException e) {
      throw new MojoExecutionException(
          "Error unpacking file["
              + file.getAbsolutePath()
              + "]"
              + "to["
              + unpackDirectory.getAbsolutePath()
              + "]",
          e);
    } catch (NoSuchArchiverException e) {
      context
          .getLog()
          .warn(
              "Skip unpacking dependency file["
                  + file.getAbsolutePath()
                  + " with unknown extension["
                  + archiveExt
                  + "]");
    }
  }
  private void addFilteredUnpackedArtifact(
      final DependencySet dependencySet,
      final Artifact depArtifact,
      final MavenProject depProject,
      final Archiver archiver,
      final AssemblerConfigurationSource configSource)
      throws ArchiveCreationException, AssemblyFormattingException {
    logger.debug(
        "Adding dependency artifact "
            + depArtifact.getId()
            + " after filtering the unpacked contents.");

    final StringBuilder sb =
        new StringBuilder()
            .append(depArtifact.getGroupId())
            .append("_")
            .append(depArtifact.getArtifactId())
            .append("_")
            .append(depArtifact.getVersion());

    final String classifier = depArtifact.getClassifier();
    if (classifier != null) {
      sb.append("_").append(classifier);
    }

    sb.append(".").append(depArtifact.getType());

    final File dir = new File(configSource.getWorkingDirectory(), sb.toString());
    if (dir.exists()) {
      logger.debug(
          "NOT unpacking: "
              + depArtifact.getId()
              + ". Directory already exists in workdir:\n\t"
              + dir.getAbsolutePath());
    } else {
      dir.mkdirs();

      UnArchiver unarchiver;
      try {
        unarchiver = archiverManager.getUnArchiver(depArtifact.getFile());
      } catch (final NoSuchArchiverException e) {
        throw new ArchiveCreationException(
            "Failed to retrieve un-archiver for: "
                + depArtifact.getId()
                + ". Dependency filtering cannot proceed.",
            e);
      }

      unarchiver.setDestDirectory(dir);
      unarchiver.setOverwrite(true);
      unarchiver.setSourceFile(depArtifact.getFile());
      unarchiver.setIgnorePermissions(configSource.isIgnorePermissions());

      try {
        unarchiver.extract();
      } catch (final ArchiverException e) {
        throw new ArchiveCreationException(
            "Failed to unpack dependency archive: "
                + depArtifact.getId()
                + ". Dependency filtering cannot proceed.",
            e);
      }
    }

    final UnpackOptions opts = dependencySet.getUnpackOptions();

    final FileSet fs = new FileSet();
    fs.setDirectory(dir.getAbsolutePath());
    fs.setDirectoryMode(dependencySet.getDirectoryMode());
    fs.setExcludes(opts.getExcludes());
    fs.setFileMode(dependencySet.getFileMode());
    fs.setFiltered(opts.isFiltered());
    fs.setIncludes(opts.getIncludes());

    String outDir = dependencySet.getOutputDirectory();
    if (outDir == null) {
      outDir = defaultOutputDirectory;
    }

    String filenameMapping = dependencySet.getOutputFileNameMapping();
    if (filenameMapping == null) {
      filenameMapping = defaultOutputFileNameMapping;
    }

    filenameMapping =
        AssemblyFormatUtils.evaluateFileNameMapping(
            filenameMapping,
            depArtifact,
            configSource.getProject(),
            moduleProject,
            moduleArtifact,
            depProject,
            configSource);

    final String outputLocation = new File(outDir, filenameMapping).getPath();

    fs.setOutputDirectory(outputLocation);

    fs.setLineEnding(opts.getLineEnding());
    fs.setUseDefaultExcludes(opts.isUseDefaultExcludes());

    final AddFileSetsTask task = new AddFileSetsTask(fs);
    task.setProject(depProject);
    task.setModuleProject(moduleProject);
    task.setLogger(logger);

    task.execute(archiver, configSource);
  }