import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Properties;


public class CoverageLister {

  public static Properties config = new Properties();
  public static Properties references = new Properties();
	public static ArrayList<String> foo = new ArrayList<String>();
	public static HashSet<String> atsDirectories = new HashSet<String>();
	public static ArrayList<File> atsFiles = new ArrayList<File>();
	public static HashSet<String> coveredClauses = new HashSet<String>();
	
	
	public String clauseEnhancer(String str) {
		String[] parts = str.split("\\.");
		
		String composed = "";
		
		for (int i=0; i < parts.length; i++) {
			try {
				int number = Integer.parseInt(parts[i]);
				composed += String.format("%02d", number);
			} catch (NumberFormatException e) {
				composed += parts[i];
			}
			if (i+1 < parts.length)
				composed += ".";
		}
		return composed;
	}
	
	public void run() {
	  try {
	    FileUtils.loadConfig(config);
	    FileUtils.loadReferences(references);
	  } catch (IOException e) {
	    System.err.println("[ERROR] Cannot load config file or config file is incomplete.");
	    return;
	  }
    String atsPath = config.get("ATSPath").toString();
    System.out.println("Scanning files in "+atsPath+"...");
	  FileUtils.visitAllFiles(new File(atsPath), atsFiles);

		for (int i=0; i < atsFiles.size(); i++) {
			atsDirectories.add(atsFiles.get(i).getParentFile().getName());
		}
		
		Iterator<String> it = atsDirectories.iterator();

		while (it.hasNext()) {
			String entry = it.next();
			String[] parts = entry.split("_");
			String clause = clausePreparer(parts[1]);
			coveredClauses.add(clause);
//			System.out.println(clause);
		}

		Iterator<Entry<Object, Object>> it2 = references.entrySet().iterator();
		
		while (it2.hasNext()) {
			Entry<Object, Object> entry = it2.next();
			
			String str = "";
			str += clauseEnhancer(entry.getKey().toString());
			str += "\t";
			str += entry.getValue();
			str += "\t";
			if  (coveredClauses.contains(clauseEnhancer(entry.getKey().toString())))
					str += "**covered**";
			
			foo.add(str);
		}
		
		Collections.sort(foo);
		
		System.out.println("Sections not covered by tests, please note that only one section was referenced by a test. There are tests that cover multiple standard sections.");
		for (int i=0; i < foo.size(); i++) {
			if (!foo.get(i).contains("**covered**"))
//				System.out.println(foo.get(i));
				System.out.println(foo.get(i).replaceAll("\\*\\*covered\\*\\*", ""));
		}
	
	}
	
	public String clausePreparer(String str) {
		int index = 0;
		String targetStr = "";

		while (index < str.length()) {
			char prefixChar = str.charAt(index);
			if (prefixChar >= 'A' && prefixChar <= 'E') {
				targetStr += str.substring(index,index+1);
				index++;
				if (index < str.length())
					targetStr += ".";
			} else {
				targetStr += str.substring(index,index+2);
				index += 2;
				if (index < str.length())
					targetStr += ".";
			}
		}

		return targetStr;
	}
	
	public CoverageLister() {
	}
	
	public static void main(String[] args) {
		new CoverageLister().run();
	}

}
