// Copyright 2014 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.cmdline;

import com.google.common.base.Predicate;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Sets;

import java.util.Collection;
import java.util.Set;

import javax.annotation.concurrent.Immutable;

/**
 * Contains the result of the target pattern evaluation. This is a specialized container class for
 * the result of target pattern resolution. There is no restriction on the element type, but it will
 * usually be {@code Target}.
 */
@Immutable
public final class ResolvedTargets<T> {
  private static final ResolvedTargets<?> FAILED_RESULT =
      new ResolvedTargets<>(ImmutableSet.of(), ImmutableSet.of(), true);

  private static final ResolvedTargets<?> EMPTY_RESULT =
      new ResolvedTargets<>(ImmutableSet.of(), ImmutableSet.of(), false);

  @SuppressWarnings("unchecked")
  public static <T> ResolvedTargets<T> failed() {
    return (ResolvedTargets<T>) FAILED_RESULT;
  }

  @SuppressWarnings("unchecked")
  public static <T> ResolvedTargets<T> empty() {
    return (ResolvedTargets<T>) EMPTY_RESULT;
  }

  public static <T> ResolvedTargets<T> of(T target) {
    return new ResolvedTargets<>(ImmutableSet.<T>of(target), false);
  }

  private final boolean hasError;
  private final ImmutableSet<T> targets;
  private final ImmutableSet<T> filteredTargets;

  public ResolvedTargets(Set<T> targets, Set<T> filteredTargets, boolean hasError) {
    this.targets = ImmutableSet.copyOf(targets);
    this.filteredTargets = ImmutableSet.copyOf(filteredTargets);
    this.hasError = hasError;
  }

  public ResolvedTargets(Set<T> targets, boolean hasError) {
    this.targets = ImmutableSet.copyOf(targets);
    this.filteredTargets = ImmutableSet.of();
    this.hasError = hasError;
  }

  @Override
  public String toString() {
    return "ResolvedTargets(" + targets + ", filtered=" + filteredTargets
        + ", hasError=" + hasError + ")";
  }

  public boolean hasError() {
    return hasError;
  }

  public ImmutableSet<T> getTargets() {
    return targets;
  }

  public ImmutableSet<T> getFilteredTargets() {
    return filteredTargets;
  }

  /**
   * Returns a builder using concurrent sets, as long as you don't call filter.
   */
  public static <T> ResolvedTargets.Builder<T> concurrentBuilder() {
    return new ResolvedTargets.Builder<>(
        Sets.<T>newConcurrentHashSet(),
        Sets.<T>newConcurrentHashSet());
  }

  public static <T> ResolvedTargets.Builder<T> builder() {
    return new ResolvedTargets.Builder<>();
  }

  public static final class Builder<T> {
    private Set<T> targets;
    private Set<T> filteredTargets;
    private volatile boolean hasError = false;

    private Builder() {
      this(Sets.<T>newLinkedHashSet(), Sets.<T>newLinkedHashSet());
    }

    private Builder(Set<T> targets, Set<T> filteredTargets) {
      this.targets = targets;
      this.filteredTargets = filteredTargets;
    }

    public ResolvedTargets<T> build() {
      return new ResolvedTargets<>(targets, filteredTargets, hasError);
    }

    public Builder<T> merge(ResolvedTargets<T> other) {
      removeAll(other.filteredTargets);
      addAll(other.targets);
      if (other.hasError) {
        hasError = true;
      }
      return this;
    }

    public Builder<T> add(T target) {
      targets.add(target);
      filteredTargets.remove(target);
      return this;
    }

    public Builder<T> addAll(Collection<T> targets) {
      this.targets.addAll(targets);
      this.filteredTargets.removeAll(targets);
      return this;
    }

    public void remove(T target) {
      targets.remove(target);
      filteredTargets.add(target);
    }

    public Builder<T> removeAll(Collection<T> targets) {
      this.filteredTargets.addAll(targets);
      this.targets.removeAll(targets);
      return this;
    }

    public Builder<T> filter(Predicate<T> predicate) {
      Set<T> oldTargets = targets;
      targets = Sets.newLinkedHashSet();
      for (T target : oldTargets) {
        if (predicate.apply(target)) {
          add(target);
        } else {
          remove(target);
        }
      }
      return this;
    }

    public Builder<T> setError() {
      this.hasError = true;
      return this;
    }

    public Builder<T> mergeError(boolean hasError) {
      this.hasError |= hasError;
      return this;
    }

    public boolean isEmpty() {
      return targets.isEmpty();
    }
  }
}
