package org.jbake.parser;

import com.vladsch.flexmark.ast.Node;
import com.vladsch.flexmark.html.HtmlRenderer;
import com.vladsch.flexmark.parser.Parser;
import com.vladsch.flexmark.profiles.pegdown.Extensions;
import com.vladsch.flexmark.profiles.pegdown.PegdownOptionsAdapter;
import com.vladsch.flexmark.util.options.DataHolder;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.lang.reflect.Field;

/**
 * Renders documents in the Markdown format.
 *
 * @author Cédric Champeau
 */
public class MarkdownEngine extends MarkupEngine {

    private Logger logger = LoggerFactory.getLogger(MarkdownEngine.class);

    @Override
    public void processBody(final ParserContext context) {
        String[] mdExts = context.getConfig().getStringArray("markdown.extensions");

        int extensions = Extensions.NONE;
        if (mdExts.length > 0) {
            for (int index = 0; index < mdExts.length; index++) {
                String ext = mdExts[index];
                if (ext.startsWith("-")) {
		    ext = ext.substring(1);
                    extensions=removeExtension(extensions, extensionFor(ext));
                } else {
                    if (ext.startsWith("+")) {
		      ext = ext.substring(1);
                    }
                    extensions=addExtension(extensions, extensionFor(ext));
                }
            }
        }

        DataHolder options = PegdownOptionsAdapter.flexmarkOptions(
                extensions
        );

        Parser parser = Parser.builder(options).build();
        HtmlRenderer renderer = HtmlRenderer.builder(options).build();

        Node document = parser.parse(context.getBody());
        context.setBody(renderer.render(document));
    }

    private int extensionFor(String name) {
        int extension = Extensions.NONE;

        try {
            Field extField = Extensions.class.getDeclaredField(name);
            extension = extField.getInt(null);
        } catch (NoSuchFieldException | IllegalAccessException e) {
            logger.debug("Undeclared extension field '{}', fallback to NONE", name);
        }
        return extension;
    }

    private int addExtension(int previousExtensions, int additionalExtension) {
    	return previousExtensions | additionalExtension;
    }
    private int removeExtension(int previousExtensions, int unwantedExtension) {
    	return previousExtensions & (~unwantedExtension);
    }

}

@@ -833,51 +833,17 @@
 NE;%0A
-        if (mdExts.length %3E 0) %7B%0A  
+%0A
         
   fo
@@ -842,80 +842,13 @@
     
-  
 for (
-int index = 0; index %3C mdExts.length; index++) %7B%0A                
 Stri
@@ -858,29 +858,20 @@
 ext 
-=
+:
  mdExts
-%5Bindex%5D;%0A    
+) %7B%0A
     
@@ -901,26 +901,36 @@
 ith(%22-%22)) %7B%0A
-%09%09
+            
     ext = ex
@@ -953,36 +953,32 @@
                 
-   
- 
 extensions=remov
@@ -971,17 +971,19 @@
 tensions
-=
+ = 
 removeEx
@@ -1014,36 +1014,32 @@
 nsionFor(ext));%0A
-    
             %7D el
@@ -1051,36 +1051,32 @@
                 
-    
 if (ext.startsWi
@@ -1090,10 +1090,22 @@
 ) %7B%0A
-%09%09
+              
     
@@ -1142,34 +1142,26 @@
             
-    %7D%0A    
+%7D%0A
             
@@ -1174,17 +1174,19 @@
 tensions
-=
+ = 
 addExten
@@ -1214,36 +1214,32 @@
 nsionFor(ext));%0A
-    
             %7D%0A  
@@ -1236,30 +1236,16 @@
       %7D%0A
-            %7D%0A
         
@@ -1314,33 +1314,16 @@
 Options(
-%0A                
 extensio
@@ -1324,25 +1324,16 @@
 tensions
-%0A        
 );%0A%0A    

Refactor a bit