/*
 * Copyright 2016 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.idea.blaze.base.sync.projectview;

import com.google.common.annotations.VisibleForTesting;
import com.google.common.collect.ImmutableCollection;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableSet;
import com.google.idea.blaze.base.bazel.BuildSystemProvider;
import com.google.idea.blaze.base.model.primitives.Label;
import com.google.idea.blaze.base.model.primitives.WorkspacePath;
import com.google.idea.blaze.base.model.primitives.WorkspaceRoot;
import com.google.idea.blaze.base.projectview.ProjectViewSet;
import com.google.idea.blaze.base.projectview.section.sections.DirectoryEntry;
import com.google.idea.blaze.base.projectview.section.sections.DirectorySection;
import com.google.idea.blaze.base.settings.Blaze.BuildSystem;
import com.google.idea.blaze.base.util.WorkspacePathUtil;
import java.util.Collection;
import java.util.Set;

/** The roots to import. Derived from project view. */
public final class ImportRoots {
  /** Builder for import roots */
  public static class Builder {
    private final ImmutableCollection.Builder<WorkspacePath> rootDirectoriesBuilder =
        ImmutableList.builder();
    private final ImmutableSet.Builder<WorkspacePath> excludeDirectoriesBuilder =
        ImmutableSet.builder();

    private final WorkspaceRoot workspaceRoot;
    private final BuildSystem buildSystem;

    private Builder(WorkspaceRoot workspaceRoot, BuildSystem buildSystem) {
      this.workspaceRoot = workspaceRoot;
      this.buildSystem = buildSystem;
    }

    public Builder add(ProjectViewSet projectViewSet) {
      for (DirectoryEntry entry : projectViewSet.listItems(DirectorySection.KEY)) {
        add(entry);
      }
      return this;
    }

    @VisibleForTesting
    public Builder add(DirectoryEntry entry) {
      if (entry.included) {
        rootDirectoriesBuilder.add(entry.directory);
      } else {
        excludeDirectoriesBuilder.add(entry.directory);
      }
      return this;
    }

    public ImportRoots build() {
      // Remove any duplicates and any overlapping directories
      ImmutableSet<WorkspacePath> minimalRootDirectories =
          WorkspacePathUtil.calculateMinimalWorkspacePaths(rootDirectoriesBuilder.build());

      // for bazel projects, if we're including the workspace root,
      // we force-exclude the bazel artifact directories
      // (e.g. bazel-bin, bazel-genfiles).
      if (buildSystem == BuildSystem.Bazel && hasWorkspaceRoot(minimalRootDirectories)) {
        excludeBuildSystemArtifacts();
      }
      ImmutableSet<WorkspacePath> minimalExcludes =
          WorkspacePathUtil.calculateMinimalWorkspacePaths(excludeDirectoriesBuilder.build());

      return new ImportRoots(minimalRootDirectories, minimalExcludes);
    }

    private void excludeBuildSystemArtifacts() {
      for (String dir :
          BuildSystemProvider.getBuildSystemProvider(buildSystem)
              .buildArtifactDirectories(workspaceRoot)) {
        excludeDirectoriesBuilder.add(new WorkspacePath(dir));
      }
    }

    private static boolean hasWorkspaceRoot(ImmutableCollection<WorkspacePath> rootDirectories) {
      return rootDirectories.stream().anyMatch(WorkspacePath::isWorkspaceRoot);
    }
  }

  private final ImmutableCollection<WorkspacePath> rootDirectories;
  private final ImmutableSet<WorkspacePath> excludeDirectories;

  public static Builder builder(WorkspaceRoot workspaceRoot, BuildSystem buildSystem) {
    return new Builder(workspaceRoot, buildSystem);
  }

  private ImportRoots(
      ImmutableCollection<WorkspacePath> rootDirectories,
      ImmutableSet<WorkspacePath> excludeDirectories) {
    this.rootDirectories = rootDirectories;
    this.excludeDirectories = excludeDirectories;
  }

  public Collection<WorkspacePath> rootDirectories() {
    return rootDirectories;
  }

  public Set<WorkspacePath> excludeDirectories() {
    return excludeDirectories;
  }

  /** Returns true if this rule should be imported as source. */
  public boolean importAsSource(Label label) {
    return containsLabel(label);
  }

  private boolean containsLabel(Label label) {
    boolean included = false;
    boolean excluded = false;
    for (WorkspacePath workspacePath : rootDirectories()) {
      included = included || matchesLabel(workspacePath, label);
    }
    for (WorkspacePath workspacePath : excludeDirectories()) {
      excluded = excluded || matchesLabel(workspacePath, label);
    }
    return included && !excluded;
  }

  private static boolean matchesLabel(WorkspacePath workspacePath, Label label) {
    if (workspacePath.isWorkspaceRoot()) {
      return true;
    }
    String moduleLabelStr = label.toString();
    int packagePrefixLength = "//".length();
    int nextCharIndex = workspacePath.relativePath().length() + packagePrefixLength;
    if (moduleLabelStr.startsWith(workspacePath.relativePath(), packagePrefixLength)
        && moduleLabelStr.length() >= nextCharIndex) {
      char c = moduleLabelStr.charAt(nextCharIndex);
      return c == '/' || c == ':';
    }
    return false;
  }
}
