// Copyright 2015 The Bazel Authors. All rights reserved.
//
// 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
//
//    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.

package com.google.devtools.build.lib.bazel.repository;

import com.google.common.base.Optional;
import com.google.devtools.build.lib.bazel.repository.DecompressorValue.Decompressor;
import com.google.devtools.build.lib.rules.repository.RepositoryFunction.RepositoryFunctionException;
import com.google.devtools.build.lib.vfs.Path;
import java.util.Objects;
import javax.annotation.Nullable;

/**
 * Description of an archive to be decompressed.
 * TODO(bazel-team): this should be an autovalue class.
 */
public class DecompressorDescriptor {
  private final String targetKind;
  private final String targetName;
  private final Path archivePath;
  private final Path repositoryPath;
  private final Optional<String> prefix;
  private final boolean executable;
  private final Decompressor decompressor;

  private DecompressorDescriptor(
      String targetKind, String targetName, Path archivePath, Path repositoryPath,
      @Nullable String prefix, boolean executable, Decompressor decompressor) {
    this.targetKind = targetKind;
    this.targetName = targetName;
    this.archivePath = archivePath;
    this.repositoryPath = repositoryPath;
    this.prefix = Optional.fromNullable(prefix);
    this.executable = executable;
    this.decompressor = decompressor;
  }

  public String targetKind() {
    return targetKind;
  }

  public String targetName() {
    return targetName;
  }

  public Path archivePath() {
    return archivePath;
  }

  public Path repositoryPath() {
    return repositoryPath;
  }

  public Optional<String> prefix() {
    return prefix;
  }

  public boolean executable() {
    return executable;
  }

  public Decompressor getDecompressor() {
    return decompressor;
  }

  @Override
  public boolean equals(Object other) {
    if (this == other) {
      return true;
    }

    if (!(other instanceof DecompressorDescriptor)) {
      return false;
    }

    DecompressorDescriptor descriptor = (DecompressorDescriptor) other;
    return Objects.equals(targetKind, descriptor.targetKind)
        && Objects.equals(targetName, descriptor.targetName)
        && Objects.equals(archivePath, descriptor.archivePath)
        && Objects.equals(repositoryPath, descriptor.repositoryPath)
        && Objects.equals(prefix, descriptor.prefix)
        && Objects.equals(executable, descriptor.executable)
        && decompressor == descriptor.decompressor;
  }

  @Override
  public int hashCode() {
    return Objects.hash(targetKind, targetName, archivePath, repositoryPath, prefix);
  }

  public static Builder builder() {
    return new Builder();
  }

  /**
   * Builder for describing the file to be decompressed.  The fields set will depend on the type
   * of file.
   */
  public static class Builder {
    private String targetKind;
    private String targetName;
    private Path archivePath;
    private Path repositoryPath;
    private String prefix;
    private boolean executable;
    private Decompressor decompressor;

    private Builder() {
    }

    public DecompressorDescriptor build() throws RepositoryFunctionException {
      if (decompressor == null) {
        decompressor = DecompressorValue.getDecompressor(archivePath);
      }
      return new DecompressorDescriptor(
          targetKind, targetName, archivePath, repositoryPath, prefix, executable, decompressor);
    }

    public Builder setTargetKind(String targetKind) {
      this.targetKind = targetKind;
      return this;
    }

    public Builder setTargetName(String targetName) {
      this.targetName = targetName;
      return this;
    }

    public Builder setArchivePath(Path archivePath) {
      this.archivePath = archivePath;
      return this;
    }

    public Builder setRepositoryPath(Path repositoryPath) {
      this.repositoryPath = repositoryPath;
      return this;
    }

    public Builder setPrefix(String prefix) {
      this.prefix = prefix;
      return this;
    }

    public Builder setExecutable(boolean executable) {
      this.executable = executable;
      return this;
    }

    public Builder setDecompressor(Decompressor decompressor) {
      this.decompressor = decompressor;
      return this;
    }
  }
}
