This Bugzilla instance is a read-only archive of historic NetBeans bug reports. To report a bug in NetBeans please follow the project's instructions for reporting issues.

View | Details | Raw Unified | Return to bug 179720
Collapse All | Expand All

(-)a/openide.util/src/org/openide/xml/XMLUtil.java (-83 / +13 lines)
Lines 44-77 Link Here
44
import java.io.CharConversionException;
44
import java.io.CharConversionException;
45
import java.io.IOException;
45
import java.io.IOException;
46
import java.io.OutputStream;
46
import java.io.OutputStream;
47
import java.io.StringReader;
48
import java.util.ArrayList;
47
import java.util.ArrayList;
49
import java.util.Arrays;
48
import java.util.Arrays;
50
import java.util.HashMap;
49
import java.util.HashMap;
51
import java.util.HashSet;
52
import java.util.List;
50
import java.util.List;
53
import java.util.logging.Level;
51
import java.util.logging.Level;
54
import java.util.logging.Logger;
52
import java.util.logging.Logger;
55
import java.util.Map;
53
import java.util.Map;
56
import java.util.Set;
57
import javax.xml.parsers.DocumentBuilder;
54
import javax.xml.parsers.DocumentBuilder;
58
import javax.xml.parsers.DocumentBuilderFactory;
55
import javax.xml.parsers.DocumentBuilderFactory;
59
import javax.xml.parsers.FactoryConfigurationError;
56
import javax.xml.parsers.FactoryConfigurationError;
60
import javax.xml.parsers.ParserConfigurationException;
57
import javax.xml.parsers.ParserConfigurationException;
61
import javax.xml.parsers.SAXParserFactory;
58
import javax.xml.parsers.SAXParserFactory;
62
import javax.xml.transform.OutputKeys;
63
import javax.xml.transform.Result;
64
import javax.xml.transform.Source;
65
import javax.xml.transform.Transformer;
66
import javax.xml.transform.TransformerFactory;
67
import javax.xml.transform.dom.DOMSource;
59
import javax.xml.transform.dom.DOMSource;
68
import javax.xml.transform.stream.StreamResult;
69
import javax.xml.transform.stream.StreamSource;
70
import javax.xml.validation.Schema;
60
import javax.xml.validation.Schema;
71
import javax.xml.validation.Validator;
61
import javax.xml.validation.Validator;
72
import org.openide.util.Exceptions;
62
import org.openide.util.Exceptions;
73
import org.w3c.dom.Attr;
63
import org.w3c.dom.Attr;
74
import org.w3c.dom.CDATASection;
75
import org.w3c.dom.DOMException;
64
import org.w3c.dom.DOMException;
76
import org.w3c.dom.DOMImplementation;
65
import org.w3c.dom.DOMImplementation;
77
import org.w3c.dom.Document;
66
import org.w3c.dom.Document;
Lines 81-86 Link Here
81
import org.w3c.dom.Node;
70
import org.w3c.dom.Node;
82
import org.w3c.dom.NodeList;
71
import org.w3c.dom.NodeList;
83
import org.w3c.dom.Text;
72
import org.w3c.dom.Text;
73
import org.w3c.dom.ls.DOMImplementationLS;
74
import org.w3c.dom.ls.LSOutput;
75
import org.w3c.dom.ls.LSSerializer;
84
import org.xml.sax.EntityResolver;
76
import org.xml.sax.EntityResolver;
85
import org.xml.sax.ErrorHandler;
77
import org.xml.sax.ErrorHandler;
86
import org.xml.sax.InputSource;
78
import org.xml.sax.InputSource;
Lines 355-381 Link Here
355
    }
347
    }
356
348
357
    /**
349
    /**
358
     * Identity transformation in XSLT with indentation added.
359
     * Just using the identity transform and calling
360
     * t.setOutputProperty(OutputKeys.INDENT, "yes");
361
     * t.setOutputProperty("{http://xml.apache.org/xslt}indent-amount", "4");
362
     * does not work currently.
363
     * You really have to use this bogus stylesheet.
364
     * @see "JDK bug #5064280"
365
     */
366
    private static final String IDENTITY_XSLT_WITH_INDENT =
367
            "<xsl:stylesheet version='1.0' " + // NOI18N
368
            "xmlns:xsl='http://www.w3.org/1999/XSL/Transform' " + // NOI18N
369
            "xmlns:xalan='http://xml.apache.org/xslt' " + // NOI18N
370
            "exclude-result-prefixes='xalan'>" + // NOI18N
371
            "<xsl:output method='xml' indent='yes' xalan:indent-amount='4'/>" + // NOI18N
372
            "<xsl:template match='@*|node()'>" + // NOI18N
373
            "<xsl:copy>" + // NOI18N
374
            "<xsl:apply-templates select='@*|node()'/>" + // NOI18N
375
            "</xsl:copy>" + // NOI18N
376
            "</xsl:template>" + // NOI18N
377
            "</xsl:stylesheet>"; // NOI18N
378
    /**
379
     * Writes a DOM document to a stream.
350
     * Writes a DOM document to a stream.
380
     * The precise output format is not guaranteed but this method will attempt to indent it sensibly.
351
     * The precise output format is not guaranteed but this method will attempt to indent it sensibly.
381
     * 
352
     * 
Lines 398-455 Link Here
398
            throw new NullPointerException("You must set an encoding; use \"UTF-8\" unless you have a good reason not to!"); // NOI18N
369
            throw new NullPointerException("You must set an encoding; use \"UTF-8\" unless you have a good reason not to!"); // NOI18N
399
        }
370
        }
400
        Document doc2 = normalize(doc);
371
        Document doc2 = normalize(doc);
401
        try {
372
        DOMImplementationLS ls = (DOMImplementationLS) doc2.getImplementation().getFeature("LS", "3.0"); // NOI18N
402
            Transformer t = TransformerFactory.newInstance().newTransformer(
373
        assert ls != null : "No DOM 3 LS supported in " + doc2.getClass().getName();
403
                    new StreamSource(new StringReader(IDENTITY_XSLT_WITH_INDENT)));
374
        LSOutput output = ls.createLSOutput();
404
            DocumentType dt = doc2.getDoctype();
375
        output.setEncoding(enc);
405
            if (dt != null) {
376
        output.setByteStream(out);
406
                String pub = dt.getPublicId();
377
        LSSerializer ser = ls.createLSSerializer();
407
                if (pub != null) {
378
        String fpp = "format-pretty-print"; // NOI18N
408
                    t.setOutputProperty(OutputKeys.DOCTYPE_PUBLIC, pub);
379
        if (ser.getDomConfig().canSetParameter(fpp, true)) {
409
                }
380
            ser.getDomConfig().setParameter(fpp, true);
410
                String sys = dt.getSystemId();
411
                if (sys != null) {
412
                    t.setOutputProperty(OutputKeys.DOCTYPE_SYSTEM, sys);
413
                }
414
            }
415
            t.setOutputProperty(OutputKeys.ENCODING, enc);
416
417
            // See #123816
418
            Set<String> cdataQNames = new HashSet<String>();
419
            collectCDATASections(doc2, cdataQNames);
420
            if (cdataQNames.size() > 0) {
421
                StringBuilder cdataSections = new StringBuilder();
422
                for(String s : cdataQNames) {
423
                    cdataSections.append(s).append(' '); //NOI18N
424
                }
425
                t.setOutputProperty(OutputKeys.CDATA_SECTION_ELEMENTS, cdataSections.toString());
426
            }
427
            
428
            Source source = new DOMSource(doc2);
429
            Result result = new StreamResult(out);
430
            t.transform(source, result);
431
        } catch (Exception e) {
432
            throw new IOException(e);
433
        }
381
        }
434
    }
382
        ser.write(doc2, output);
435
436
    private static void collectCDATASections(Node node, Set<String> cdataQNames) {
437
        if (node instanceof CDATASection) {
438
            Node parent = node.getParentNode();
439
            if (parent != null) {
440
                String uri = parent.getNamespaceURI();
441
                if (uri != null) {
442
                    cdataQNames.add("{" + uri + "}" + parent.getNodeName()); //NOI18N
443
                } else {
444
                    cdataQNames.add(parent.getNodeName());
445
                }
446
            }
447
        }
448
        
449
        NodeList children = node.getChildNodes();
450
        for(int i = 0; i < children.getLength(); i++) {
451
            collectCDATASections(children.item(i), cdataQNames);
452
        }
453
    }
383
    }
454
384
455
    /**
385
    /**

Return to bug 179720