package com.chenyang.nse.bussiness.tools.xml;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import org.dom4j.Attribute;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.Node;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.SAXReader;
import org.dom4j.io.XMLWriter;

public class DomUtils {
   private static String fixed = "POWERMART/REPOSITORY/FOLDER/";
   private static String fixeds = "POWERMART/REPOSITORY/FOLDER/MAPPLET/";
   private static String fixedss = "POWERMART/REPOSITORY/FOLDER/";
   private static String fixedsss = "POWERMART/REPOSITORY/FOLDER/MAPPLET/TRANSFORMATION[1]/";

   public static Document addEditElement(Document doc, String path, Map<String, String> editMap) {
      Element ruleElement = (Element)doc.selectSingleNode(fixed + path);
      Element newRuleElement = ruleElement.createCopy();
      if (editMap != null) {
         for(String key : editMap.keySet()) {
            Attribute isSelfAttr = newRuleElement.attribute(key);
            isSelfAttr.setValue((String)editMap.get(key));
         }
      }

      ruleElement.getParent().add(newRuleElement);
      return doc;
   }

   public static Document addEditElements(Document doc, String path, Map<String, String> editMap) {
      Element ruleElement = (Element)doc.selectSingleNode(fixeds + path);
      Element newRuleElement = ruleElement.createCopy();
      if (editMap != null) {
         for(String key : editMap.keySet()) {
            Attribute isSelfAttr = newRuleElement.attribute(key);
            isSelfAttr.setValue((String)editMap.get(key));
         }
      }

      ruleElement.getParent().add(newRuleElement);
      return doc;
   }

   public static Document addEditElementss(Document doc, String path, Map<String, String> editMap) {
      Element ruleElement = (Element)doc.selectSingleNode(fixedss + path);
      Element newRuleElement = ruleElement.createCopy();
      if (editMap != null) {
         for(String key : editMap.keySet()) {
            Attribute isSelfAttr = newRuleElement.attribute(key);
            isSelfAttr.setValue((String)editMap.get(key));
         }
      }

      ruleElement.getParent().add(newRuleElement);
      return doc;
   }

   public static Document addEditElementsss(Document doc, String path, Map<String, String> editMap) {
      Element ruleElement = (Element)doc.selectSingleNode(fixedsss + path);
      Element newRuleElement = ruleElement.createCopy();
      if (editMap != null) {
         for(String key : editMap.keySet()) {
            Attribute isSelfAttr = newRuleElement.attribute(key);
            isSelfAttr.setValue((String)editMap.get(key));
         }
      }

      ruleElement.getParent().add(newRuleElement);
      return doc;
   }

   public static Document editElement(Document doc, Map<String, String> editMap) {
      for(String key : editMap.keySet()) {
         doc = editAttribute(doc, key, (String)editMap.get(key));
      }

      return doc;
   }

   public static Document editElements(Document doc, Map<String, String> editMap) {
      for(String key : editMap.keySet()) {
         doc = editAttributes(doc, key, (String)editMap.get(key));
      }

      return doc;
   }

   public static Document removeElement(Document doc, String deleteKey) {
      Element ruleElement = (Element)doc.selectSingleNode(fixed + deleteKey);
      if (ruleElement != null) {
         ruleElement.getParent().remove(ruleElement);
         doc.remove(ruleElement);
      }

      return doc;
   }

   public static Document removeElements(Document doc, String deleteKey) {
      Element ruleElement = (Element)doc.selectSingleNode(fixeds + deleteKey);
      if (ruleElement != null) {
         ruleElement.getParent().remove(ruleElement);
         doc.remove(ruleElement);
      }

      return doc;
   }

   public static Document removeElementss(Document doc, String deleteKey) {
      Element ruleElement = (Element)doc.selectSingleNode(fixedss + deleteKey);
      if (ruleElement != null) {
         ruleElement.getParent().remove(ruleElement);
         doc.remove(ruleElement);
      }

      return doc;
   }

   public static Document removeElementList(Document doc, String deleteKey) {
      for(Node ruleElement : doc.selectNodes(fixed + deleteKey)) {
         ruleElement.getParent().remove(ruleElement);
         doc.remove(ruleElement);
      }

      return doc;
   }

   public static void addText(Document doc, String editKey, String editText) {
      Element ruleElement = (Element)doc.selectSingleNode(fixed + editKey);
      ruleElement.setText(editText);
   }

   public static Document editAttribute(Document doc, String editKey, String editVal) {
      String[] editPosition = editKey.split("--");
      Element ruleElement = (Element)doc.selectSingleNode(fixed + editPosition[0]);
      Attribute isSelfAttr = ruleElement.attribute(editPosition[1]);
      isSelfAttr.setValue(editVal);
      doc.remove(ruleElement);
      doc.setParent(ruleElement);
      return doc;
   }

   public static Document editAttributes(Document doc, String editKey, String editVal) {
      String[] editPosition = editKey.split("--");
      Element ruleElement = (Element)doc.selectSingleNode(fixeds + editPosition[0]);
      Attribute isSelfAttr = ruleElement.attribute(editPosition[1]);
      isSelfAttr.setValue(editVal);
      doc.remove(ruleElement);
      doc.setParent(ruleElement);
      return doc;
   }

   public static Document addEditAttribute(Document doc, String editKey, String editVal) {
      String[] editPosition = editKey.split("--");
      Element ruleElement = (Element)doc.selectSingleNode(fixed + editPosition[0]);
      Attribute isSelfAttr = ruleElement.attribute(editPosition[1]);
      isSelfAttr.setValue(editVal);
      ruleElement.getParent().add((Element)ruleElement.clone());
      return doc;
   }

   public static int generateXML(String xmlLocation, String xmlmapplet) {
      System.out.println("********************************************");
      File file = new File(xmlLocation);
      InputStream in = PowerXml.class.getClassLoader().getResourceAsStream("xmlTemplateq" + File.separator + xmlmapplet);
      System.out.println(PowerXml.class.getClassLoader().getResource("xmlTemplateq" + File.separator + xmlmapplet));

      try {
         file.createNewFile();
         OutputStream os = new FileOutputStream(file);
         int bytesRead = 0;
         byte[] buffer = new byte[8192];

         while((bytesRead = in.read(buffer, 0, 8192)) != -1) {
            os.write(buffer, 0, bytesRead);
         }

         os.close();
         in.close();
         return 1;
      } catch (Exception e) {
         e.printStackTrace();
         return 0;
      }
   }

   public static Document editSpecialAttribute(Document doc, String editKey, String editVal) {
      String[] editPosition = editKey.split("--");
      Element ruleElement = (Element)doc.selectSingleNode(editPosition[0]);
      Attribute isSelfAttr = ruleElement.attribute(editPosition[1]);
      isSelfAttr.setValue(editVal);
      return doc;
   }

   public static Document editSpecialElement(Document doc, Map<String, String> editMap) {
      for(String key : editMap.keySet()) {
         doc = editSpecialAttribute(doc, key, (String)editMap.get(key));
      }

      return doc;
   }

   public static Document readMapTypeXML() {
      Document doc = null;

      try {
         InputStream in = PowerXml.class.getClassLoader().getResourceAsStream("xmlTemplate" + File.separator + "mapType.xml");
         SAXReader reader = new SAXReader();
         doc = reader.read(in);
      } catch (Exception e) {
         e.printStackTrace();
      }

      return doc;
   }

   public static String readAttribute(Document doc, String readKey) {
      String[] editPosition = readKey.split("--");
      Element ruleElement = (Element)doc.selectSingleNode(editPosition[0]);
      Attribute isSelfAttr = ruleElement.attribute(editPosition[1]);
      return isSelfAttr.getText();
   }

   public static String readMapTypeDB(Document typeDoc, String dbType, String fieldType) {
      String location = "DATABASETYPE/" + dbType + "/" + fieldType + "--MAP";
      return readAttribute(typeDoc, location);
   }

   public static String readMapTypeFile(Document typeDoc, String dbType, String fieldType) {
      String location = "DATABASETYPE/" + dbType + "/" + fieldType + "--FILEMAP";
      return readAttribute(typeDoc, location);
   }

   public static String readMapDB(Document typeDoc, String dbType) {
      String location = "DATABASETYPE/" + dbType + "--MAP";
      return readAttribute(typeDoc, location);
   }

   public static String readBinaryType(Document typeDoc, String dbType) {
      String location = "DATABASETYPE/" + dbType + "--BINARYTYPE";
      return readAttribute(typeDoc, location);
   }

   public static void writeXml(Document document, String filePath) throws Exception {
      File xmlFile = new File(filePath);

      try {
         if (xmlFile.exists()) {
            xmlFile.delete();
         }

         FileOutputStream out = new FileOutputStream(filePath);
         OutputFormat format = OutputFormat.createPrettyPrint();
         format.setEncoding("UTF-8");
         XMLWriter writer = new XMLWriter(out);
         writer.write(document);
         writer.close();
      } catch (Exception e) {
         e.printStackTrace();
      }

   }

   public static Document tableAttributeCopy(Document doc, String path) {
      Element parent = (Element)doc.selectSingleNode(fixed + path);

      for(Element attr : parent.elements("TABLEATTRIBUTE")) {
         Element newattr = attr.createCopy();
         parent.add(newattr);
         parent.remove(attr);
      }

      return doc;
   }

   public static void main(String[] args) {
      SAXReader reader = new SAXReader();

      try {
         Document document = reader.read(new File("D://sh_phone.XML"));
         Element node = document.getRootElement();
         Iterator iterss = node.elementIterator("body");

         List list = document.selectNodes("//POWERMART/REPOSITORY/FOLDER/MAPPLET/TRANSFORMATION/METADATAEXTENSION/@VALUE");
         for (Iterator<Attribute> it = list.iterator(); it.hasNext(); ) {
            Attribute attr = it.next();
            Pattern pattern = Pattern.compile("SEED=\"([\\s\\S]*?)\"");
            Matcher matcher = pattern.matcher(attr.getValue());
            if (matcher.find() &&
                    matcher.group().length() > 7) {
               String attrvalue = attr.getValue();
               attr.setValue(attrvalue.replace(matcher.group(), "SEED=\"123\""));
            }
         }

         writeXml(document, "D://sh_phone.XML");
      } catch (DocumentException e) {
         e.printStackTrace();
      } catch (TransformerConfigurationException e) {
         e.printStackTrace();
      } catch (TransformerException e) {
         e.printStackTrace();
      } catch (Exception e) {
         e.printStackTrace();
      }

   }

   public static void listNodes(Element node) {
      System.out.println("当前节点的名称：：" + node.getName());

      for(Attribute attr : node.attributes()) {
         System.out.println(attr.getText() + "-----" + attr.getName() + "---" + attr.getValue());
      }

      if (!node.getTextTrim().equals("")) {
         System.out.println("文本内容：：：：" + node.getText());
      }

      Iterator<Element> it = node.elementIterator();

      while(it.hasNext()) {
         Element e = (Element)it.next();
         listNodes(e);
      }

   }
}
