package com.grayben.riskExtractor.helpers;

import com.grayben.riskExtractor.htmlScorer.ScoredText;
import com.grayben.riskExtractor.htmlScorer.ScoredTextElement;
import com.grayben.riskExtractor.htmlScorer.partScorers.Scorer;
import com.grayben.riskExtractor.htmlScorer.partScorers.tagScorers.MapScorer;
import org.apache.commons.io.IOUtils;
import org.jsoup.nodes.Element;
import org.jsoup.nodes.Node;

import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * Created by beng on 20/04/2016.
 */
public final class ScoredTextReverseEngineerer {

    public static <T, U extends Scorer<T>> U appropriateScorerFrom(Iterable<U> scorerSet, String scorerLabel){
        for(U scorer : scorerSet){
            if (scorer.getScoreLabel().equals(scorerLabel)){
                return scorer;
            }
        }
        throw new IllegalArgumentException("The specified Iterable did not contain a matching element");
    }

    public static <K, Integer> List<K> keysSuchThatValuesSumTo(Map<K, Integer> map, Integer toSumTo){
        throw new UnsupportedOperationException("Not implemented");
    }

    public static String htmlFrom(Node tree){
        StringBuilder sb = new StringBuilder();
        tree.html(sb);
        return sb.toString();
    }

    //TODO: adapt to e.g. tags. Not elements: can't wrap text in an element!
    public static String htmlFrom(ScoredText scoredText, Set<MapScorer<Element>> elementScorers){
        List<String> textElementsSurroundedByAppropriateTags = new ArrayList<>();
        for(ScoredTextElement scoredTextElement : scoredText.getList()){
            String textElement = scoredTextElement.getTextElement();
            Map<String, Integer> scores = scoredTextElement.getScores();
            for(Map.Entry<String, Integer> labelScorePair : scores.entrySet()){
                String label = labelScorePair.getKey();
                Integer score = labelScorePair.getValue();
                MapScorer<Element> scorer = appropriateScorerFrom(elementScorers, label);
                List<Element> wrapWith = keysSuchThatValuesSumTo(scorer.getScoresMap(), score);
            }
        }
        String taggedTextSurroundedByFrame = null;
        return taggedTextSurroundedByFrame;
    }

    public static InputStream inputStreamFrom(String html){
        return IOUtils.toInputStream(html);
    }

    public static InputStream inputStreamFrom(Node tree){
        String html = htmlFrom(tree);
        return inputStreamFrom(html);
    }

    public static InputStream inputSteamFrom(ScoredText scoredText, Set<Scorer<Element>> elementScorers){
        String html = htmlFrom(scoredText, elementScorers);
        return inputStreamFrom(html);
    }

}

@@ -401,108 +401,64 @@
 de;%0A
-%0A
 import 
-java.io.InputStream;%0Aimport java.util.ArrayList;%0Aimport java.util.List;%0Aimport java.util.Map
+org.jsoup.parser.Tag;%0A%0Aimport java.io.InputStream
 ;%0Aim
@@ -472,19 +472,17 @@
 va.util.
-Set
+*
 ;%0A%0A/**%0A 
@@ -1269,24 +1269,325 @@
 g();%0A    %7D%0A%0A
+    public static %3CT%3E boolean mutuallyExclusiveNonZeroScores(Collection%3C? extends Scorer%3CT%3E%3E scorers, T item)%7B%0A        int numNonZeroScores = 0;%0A        for(Scorer%3CT%3E scorer : scorers)%7B%0A            if (scorer.score(item) %3E 0) numNonZeroScores++;%0A        %7D%0A        return numNonZeroScores %3C= 1;%0A    %7D%0A%0A
     //TODO: 
@@ -1722,33 +1722,25 @@
 pScorer%3C
-Element%3E%3E element
+Tag%3E%3E tag
 Scorers)
@@ -1753,82 +1753,60 @@
     
-List%3C
 String
-%3E textElementsSurroundedByAppropriateTags = new ArrayList%3C%3E
+Builder stringBuilder = new StringBuilder
 ();%0A
+%0A
     
@@ -1870,24 +1870,25 @@
 getList())%7B%0A
+%0A
             
@@ -1894,20 +1894,23 @@
  String 
-text
+htmlFor
 Element 
@@ -1943,24 +1943,26 @@
 tElement();%0A
+%0A%0A
             
@@ -2021,16 +2021,134 @@
 cores();
+%0A%0A            List%3CMapScorer%3CTag%3E%3E scorerList = new ArrayList%3C%3E();%0A            List%3CTag%3E wrapWith = new ArrayList%3C%3E();
 %0A       
@@ -2218,17 +2218,19 @@
 rySet())
-%7B
+ %7B%0A
 %0A       
@@ -2333,24 +2333,25 @@
 getValue();%0A
+%0A
             
@@ -2364,23 +2364,19 @@
 pScorer%3C
-Element
+Tag
 %3E scorer
@@ -2400,23 +2400,19 @@
 rerFrom(
-element
+tag
 Scorers,
@@ -2416,24 +2416,25 @@
 rs, label);%0A
+%0A
             
@@ -2441,21 +2441,47 @@
     
-List%3CElement%3E
+scorerList.add(scorer);%0A               
  wra
@@ -2485,19 +2485,24 @@
 wrapWith
- = 
+.addAll(
 keysSuch
@@ -2546,16 +2546,17 @@
 , score)
+)
 ;%0A      
@@ -2559,32 +2559,37 @@
           %7D%0A
+%0A    
         
 %7D%0A        St
@@ -2580,103 +2580,302 @@
     
-%7D%0A        String taggedTextSurroundedByFrame = null;%0A        return taggedTextSurroundedByFrame
+for(Tag tag : wrapWith)%7B%0A                assert mutuallyExclusiveNonZeroScores(scorerList, tag);%0A                htmlForElement = new Element(tag, %22%22).wrap(htmlForElement).html();%0A            %7D%0A%0A            stringBuilder.append(htmlForElement);%0A        %7D%0A        return stringBuilder.toString()
 ;%0A  
@@ -3207,22 +3207,21 @@
 Set%3C
+Map
 Scorer%3C
-Element
+Tag
 %3E%3E e

Complete implementation