/**
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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 org.apache.tajo.rule;

import java.util.*;

public class SelfDiagnosisRuleEngine {

  private final Map<String, Map<String, RuleWrapper>> wrapperMap;
  private static volatile SelfDiagnosisRuleEngine instance;
  
  private SelfDiagnosisRuleEngine() {
    wrapperMap = new HashMap<>();
    loadPredefinedRules();
  }
  
  public static SelfDiagnosisRuleEngine getInstance() {
    if (instance == null) {
      synchronized (SelfDiagnosisRuleEngine.class) {
        if (instance == null) {
          instance = new SelfDiagnosisRuleEngine();
        }
      }
    }
    return instance;
  }
  
  public void reset() {
    if (wrapperMap != null) {
      wrapperMap.clear();
    }
    loadPredefinedRules();
  }
  
  public SelfDiagnosisRuleSession newRuleSession() {
    return new SelfDiagnosisRuleSession(this);
  }
  
  protected Map<String, Map<String, RuleWrapper>> getRules() {
    return wrapperMap;    
  }
  
  private void loadRuleData(List<SelfDiagnosisRule> ruleList) {
    for (SelfDiagnosisRule rule: ruleList) {
      RuleWrapper wrapper = new RuleWrapper(rule);
      if (wrapper.isEnabled()) {
        Map<String, RuleWrapper> categoryMap = wrapperMap.get(wrapper.getCategoryName());

        if (categoryMap == null) {
          categoryMap = new HashMap<>();
          wrapperMap.put(wrapper.getCategoryName(), categoryMap);
        }

        categoryMap.put(wrapper.getRuleName(), wrapper);
      }
    }
  }

  protected void loadPredefinedRules() {
    ClassLoader cl = Thread.currentThread().getContextClassLoader();
    ServiceLoader<SelfDiagnosisRuleProvider> serviceLoader = ServiceLoader.load(SelfDiagnosisRuleProvider.class, cl);
    Iterator<SelfDiagnosisRuleProvider> iterator = serviceLoader.iterator();
    
    wrapperMap.clear();
    while (iterator.hasNext()) {
      SelfDiagnosisRuleProvider ruleProvider = iterator.next();
      loadRuleData(ruleProvider.getDefinedRules());
    }
  }
  
  static class RuleWrapper implements Comparable<RuleWrapper> {
    private final String categoryName;
    private final String ruleName;
    private final int priority;
    private final boolean enabled;
    private final Class<?>[] acceptedCallers;
    private final SelfDiagnosisRule rule;
    
    public RuleWrapper(SelfDiagnosisRule rule) {
      this.rule = rule;
      
      SelfDiagnosisRuleDefinition ruleDefinition = rule.getClass().getAnnotation(SelfDiagnosisRuleDefinition.class);
      if (ruleDefinition == null) {
        throw new IllegalArgumentException(rule.getClass().getName() + " is not a valid runtime rule.");
      }
      categoryName = ruleDefinition.category();
      ruleName = ruleDefinition.name();
      priority = ruleDefinition.priority();
      enabled = ruleDefinition.enabled();
      
      SelfDiagnosisRuleVisibility.LimitedPrivate limitedPrivateScope = 
          rule.getClass().getAnnotation(SelfDiagnosisRuleVisibility.LimitedPrivate.class);
      if (limitedPrivateScope != null) {
        acceptedCallers =
            Arrays.copyOf(limitedPrivateScope.acceptedCallers(), 
                limitedPrivateScope.acceptedCallers().length);
      } else {
        acceptedCallers = new Class<?>[0];
      }
    }

    public String getCategoryName() {
      return categoryName;
    }

    public String getRuleName() {
      return ruleName;
    }

    public Class<?>[] getAcceptedCallers() {
      return acceptedCallers;
    }

    public SelfDiagnosisRule getRule() {
      return rule;
    }
    
    public int getPriority() {
      return priority;
    }

    public boolean isEnabled() {
      return enabled;
    }

    @Override
    public int compareTo(RuleWrapper o) {
      if (getPriority() < 0 && o.getPriority() < 0) {
        return 0;
      } else if (getPriority() < 0) {
        return 1;
      } else if (o.getPriority() < 0) {
        return -1;
      }
      return (int) Math.signum(getPriority() - o.getPriority());
    }

    @Override
    public int hashCode() {
      final int prime = 31;
      int result = 1;
      result = prime * result + Arrays.hashCode(acceptedCallers);
      result = prime * result + ((categoryName == null) ? 0 : categoryName.hashCode());
      result = prime * result + (enabled ? 1231 : 1237);
      result = prime * result + priority;
      result = prime * result + ((rule == null) ? 0 : rule.hashCode());
      result = prime * result + ((ruleName == null) ? 0 : ruleName.hashCode());
      return result;
    }

    @Override
    public boolean equals(Object obj) {
      if (this == obj)
        return true;
      if (obj == null)
        return false;
      if (getClass() != obj.getClass())
        return false;
      RuleWrapper other = (RuleWrapper) obj;
      if (!Arrays.equals(acceptedCallers, other.acceptedCallers))
        return false;
      if (categoryName == null) {
        if (other.categoryName != null)
          return false;
      } else if (!categoryName.equals(other.categoryName))
        return false;
      if (enabled != other.enabled)
        return false;
      if (priority != other.priority)
        return false;
      if (rule == null) {
        if (other.rule != null)
          return false;
      } else if (!rule.equals(other.rule))
        return false;
      if (ruleName == null) {
        if (other.ruleName != null)
          return false;
      } else if (!ruleName.equals(other.ruleName))
        return false;
      return true;
    }
    
  }
  
}
