/*
 * Copyright 2000-2012 JetBrains s.r.o.
 *
 * 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.intellij.psi.codeStyle.arrangement.match;

import com.intellij.openapi.util.MultiValuesMap;
import com.intellij.psi.codeStyle.arrangement.ArrangementEntry;
import com.intellij.psi.codeStyle.arrangement.model.*;
import com.intellij.psi.codeStyle.arrangement.std.ArrangementSettingsToken;
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementSettingsToken;
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokenType;
import com.intellij.psi.codeStyle.arrangement.std.StdArrangementTokens;
import com.intellij.util.containers.ContainerUtilRt;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.util.Collection;
import java.util.List;

/**
 * {@link ArrangementEntryMatcher} which is based on standard match conditions in form of {@link ArrangementSettingsToken}.
 * <p/>
 * Implementations of this interface are expected to be thread-safe.
 *
 * @author Denis Zhdanov
 * @since 8/26/12 11:07 PM
 */
public class StdArrangementEntryMatcher implements ArrangementEntryMatcher {

  @NotNull private final ArrangementMatchCondition myCondition;
  @NotNull private final ArrangementEntryMatcher   myDelegate;

  public StdArrangementEntryMatcher(@NotNull ArrangementMatchCondition condition) {
    this(condition, new StdMatcherBuilderImpl());
  }

  public StdArrangementEntryMatcher(@NotNull ArrangementMatchCondition condition, @NotNull StdMatcherBuilder builder) {
    myCondition = condition;
    myDelegate = doBuildMatcher(condition, builder);
  }

  @NotNull
  public ArrangementMatchCondition getCondition() {
    return myCondition;
  }

  @Override
  public boolean isMatched(@NotNull ArrangementEntry entry) {
    return myDelegate.isMatched(entry);
  }

  @Override
  public int hashCode() {
    return myCondition.hashCode();
  }

  @Override
  public boolean equals(Object o) {
    if (this == o) {
      return true;
    }
    if (o == null || getClass() != o.getClass()) {
      return false;
    }

    StdArrangementEntryMatcher matcher = (StdArrangementEntryMatcher)o;
    return myCondition.equals(matcher.myCondition);
  }

  @Override
  public String toString() {
    return myCondition.toString();
  }

  @NotNull
  private static ArrangementEntryMatcher doBuildMatcher(@NotNull ArrangementMatchCondition condition, @NotNull StdMatcherBuilder builder) {
    MyVisitor visitor = new MyVisitor(builder);
    condition.invite(visitor);
    return visitor.getMatcher();
  }

  /**
   * Used by inner visitor to build matchers from atom conditions.
   */
  public interface StdMatcherBuilder {

    /**
     * Parses given condition storing all data required to later produce a matcher based on the condition. It is called each time an
     * {@link ArrangementAtomMatchCondition} is encountered when traversing {@link ArrangementMatchCondition} on the
     * {@link StdArrangementEntryMatcher} creation.
     * @param condition condition to parse
     */
    void onCondition(@NotNull ArrangementAtomMatchCondition condition);

    /**
     * Returns a collection of matchers obtained through {@link #addMatcher(ArrangementEntryMatcher) addMatcher} calls or
     * built from info gained by {@link #onCondition(ArrangementAtomMatchCondition) onCondition} calls.
     * @return a collection of matchers
     */
    @Nullable Collection<ArrangementEntryMatcher> buildMatchers();

    /**
     * Adds given matcher to collection provided by {@link #buildMatchers() buildMatchers} calls.
     * @param matcher matcher to be added
     */
    void addMatcher(@NotNull ArrangementEntryMatcher matcher);
  }

  /**
   * Standard implementation of {@link StdMatcherBuilder}. Constructs entry matchers of types {@link ByTypeArrangementEntryMatcher},
   * {@link ByModifierArrangementEntryMatcher}, {@link ByNameArrangementEntryMatcher}, {@link ByNamespaceArrangementEntryMatcher}.
   */
  public static class StdMatcherBuilderImpl implements StdMatcherBuilder {

    @NotNull private final List<ArrangementEntryMatcher> myMatchers  = ContainerUtilRt.newArrayList();
    /**
     * Maps token type to all arrangement tokens that were encountered so far by parsing conditions with
     * {@link #onCondition(ArrangementAtomMatchCondition) onCondition} calls.
     */
    @NotNull protected final MultiValuesMap<StdArrangementTokenType, ArrangementSettingsToken > context =
      new MultiValuesMap<StdArrangementTokenType, ArrangementSettingsToken>();
    @Nullable private String myNamePattern;
    @Nullable private String myNamespacePattern;
    @Nullable private String myText;

    /**
     * Adds given entry to context by given entry type.
     * @param token token added to context
     */
    protected void addToContext(@NotNull StdArrangementSettingsToken token) {
      StdArrangementTokenType tokenType = token.getTokenType();
      context.put(tokenType, token);
    }

    @Override
    public void onCondition(@NotNull ArrangementAtomMatchCondition condition) {
      if (StdArrangementTokens.Regexp.NAME.equals(condition.getType())) {
        myNamePattern = condition.getValue().toString();
        return;
      }
      else if (StdArrangementTokens.Regexp.XML_NAMESPACE.equals(condition.getType())) {
        myNamespacePattern = condition.getValue().toString();
      }
      else if (StdArrangementTokens.Regexp.TEXT.equals(condition.getType())) {
        myText = condition.getValue().toString();
      }
      Object v = condition.getValue();
      //Process any StdArrangementSettingsToken. No need to change it when new types of tokens will be processed.
      if (v instanceof StdArrangementSettingsToken) {
        StdArrangementSettingsToken token = (StdArrangementSettingsToken)v;
        addToContext(token);
      }
    }

    @Nullable
    @Override
    public Collection<ArrangementEntryMatcher> buildMatchers() {
      List<ArrangementEntryMatcher> result = ContainerUtilRt.newArrayList(myMatchers);
      Collection<ArrangementSettingsToken> entryTokens = context.get(StdArrangementTokenType.ENTRY_TYPE);
      if (entryTokens!= null) {
        result.add(new ByTypeArrangementEntryMatcher(entryTokens));
      }
      Collection<ArrangementSettingsToken> modifierTokens = context.get(StdArrangementTokenType.MODIFIER);
      if (modifierTokens != null) {
        result.add(new ByModifierArrangementEntryMatcher(modifierTokens));
      }
      if (myNamePattern != null) {
        result.add(new ByNameArrangementEntryMatcher(myNamePattern));
      }
      if (myNamespacePattern != null) {
        result.add(new ByNamespaceArrangementEntryMatcher(myNamespacePattern));
      }
      if (myText != null) {
        result.add(new ByTextArrangementEntryMatcher(myText));
      }
      return result;
    }

    @Override
    public void addMatcher(@NotNull ArrangementEntryMatcher matcher) {
      myMatchers.add(matcher);
    }
  }

  private static class MyVisitor implements ArrangementMatchConditionVisitor {

    @NotNull private final StdMatcherBuilder myMatcherBuilder;
    private boolean nestedComposite;

    private MyVisitor(@NotNull StdMatcherBuilder matcherBuilder) {
      myMatcherBuilder = matcherBuilder;
    }

    @Override
    public void visit(@NotNull ArrangementAtomMatchCondition condition) {
      myMatcherBuilder.onCondition(condition);
    }

    @Override
    public void visit(@NotNull ArrangementCompositeMatchCondition condition) {
      if (!nestedComposite) {
        nestedComposite = true;
        for (ArrangementMatchCondition c : condition.getOperands()) {
          c.invite(this);
        }
      }
      else {
        myMatcherBuilder.addMatcher(doBuildMatcher(condition, myMatcherBuilder));
      }
    }

    @SuppressWarnings("ConstantConditions")
    @NotNull
    public ArrangementEntryMatcher getMatcher() {
      Collection<ArrangementEntryMatcher> matchers = myMatcherBuilder.buildMatchers();

      if (matchers.size() == 1) {
        return matchers.iterator().next();
      } else {
        CompositeArrangementEntryMatcher result = new CompositeArrangementEntryMatcher();
        for (ArrangementEntryMatcher matcher: matchers) {
          result.addMatcher(matcher);
        }
        return result;
      }
    }
  }
}
