Написание довольно XML-файла с использованием Javascript [duplicate]

Чтобы использовать методы и член объекта, вам сначала нужно создать этот объект. Если вы его не создали (переменная, которая должна содержать объект, не инициализируется), но вы пытаетесь использовать его методы или переменные, вы получите эту ошибку.

Иногда вы можете просто забыть инициализировать .

Отредактировано: new не может вернуть значение null, но исключение огня при ошибке. Давно это было на некоторых языках, но не больше. Спасибо @John Saunders за указание на это.

100
задан Dimitre Novatchev 17 October 2010 в 21:29
поделиться

19 ответов

Из текста вопроса создается впечатление, что ожидается результат строки, в отличие от результата в формате HTML.

Если это так, самый простой способ добиться этого - обработать XML-документ с преобразованием идентичности и с инструкцией <xsl:output indent="yes"/> :

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>

    <xsl:template match="node()|@*">
      <xsl:copy>
        <xsl:apply-templates select="node()|@*"/>
      </xsl:copy>
    </xsl:template>
</xsl:stylesheet>

При применении этого преобразования на предоставленном XML-документе:

<root><node/></root>

большинство XSLT-процессоров (.NET XslCompiledTransform, Saxon 6.5.4 и Saxon 9.0.0.2, AltovaXML) создают желаемый результат:

<root>
  <node />
</root>
48
ответ дан Dimitre Novatchev 24 August 2018 в 03:21
поделиться

Используйте метод выше для довольно печатной печати, а затем добавьте это в любой div с помощью метода jquery text (). например id id div xmldiv, используйте:

$("#xmldiv").text(formatXml(youXmlString));

1
ответ дан Ajo Koshy 24 August 2018 в 03:21
поделиться

как создать узел-заглушку (document.createElement ('div') - или использовать эквивалент вашей библиотеки), заполняя его строкой xml (через innerHTML) и вызывая простую рекурсивную функцию для корневого элемента / или элемента-заглушки в случае, если у вас нет корня. Функция будет вызывать себя для всех дочерних узлов.

Вы могли бы затем синтаксически выделить на этом пути, убедитесь, что разметка хорошо сформирована (выполняется автоматически браузером при добавлении через innerHTML) и т. Д. Это не будет 't быть таким кодом и, вероятно, достаточно быстро.

3
ответ дан aprilchild 24 August 2018 в 03:21
поделиться

Нашел этот поток, когда у меня было подобное требование, но я упростил код OP следующим образом:

function formatXml(xml, tab) { // tab = optional indent value, default is tab (\t)
    var formatted = '', indent= '';
    tab = tab || '\t';
    xml.split(/>\s*</).forEach(function(node) {
        if (node.match( /^\/\w/ )) indent = indent.substring(tab.length); // decrease indent by one 'tab'
        formatted += indent + '<' + node + '>\r\n';
        if (node.match( /^<?\w[^>]*[^\/]$/ )) indent += tab;              // increase indent
    });
    return formatted.substring(1, formatted.length-3);
}

работает для меня!

2
ответ дан arcturus 24 August 2018 в 03:21
поделиться

Это можно сделать, используя собственные инструменты javascript, без сторонних библиотек, расширяя ответ @Dimitre Novatchev:

var prettifyXml = function(sourceXml)
{
    var xmlDoc = new DOMParser().parseFromString(sourceXml, 'application/xml');
    var xsltDoc = new DOMParser().parseFromString([
        // describes how we want to modify the XML - indent everything
        '<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform">',
        '  <xsl:output omit-xml-declaration="yes" indent="yes"/>',
        '    <xsl:template match="node()|@*">',
        '      <xsl:copy><xsl:apply-templates select="node()|@*"/></xsl:copy>',
        '    </xsl:template>',
        '</xsl:stylesheet>',
    ].join('\n'), 'application/xml');

    var xsltProcessor = new XSLTProcessor();    
    xsltProcessor.importStylesheet(xsltDoc);
    var resultDoc = xsltProcessor.transformToDocument(xmlDoc);
    var resultXml = new XMLSerializer().serializeToString(resultDoc);
    return resultXml;
};

console.log(prettifyXml('<root><node/></root>'));

Выходы:

<root>
  <node/>
</root>

JSFiddle

6
ответ дан Artur Klesun 24 August 2018 в 03:21
поделиться

Все функции javascript, приведенные здесь, не будут работать для XML-документа с неопределенными пробелами между конечным тегом '>' и стартовым тегом '& lt;'. Чтобы исправить их, вам просто нужно заменить первую строку в функциях

var reg = /(>)(<)(\/*)/g;

на

var reg = /(>)\s*(<)(\/*)/g;
5
ответ дан Chuan Ma 24 August 2018 в 03:21
поделиться

https://www.npmjs.com/package/js-beautify

Эта библиотека работает для меня. Поддерживает вкладку, поддерживает веб-версию и версию узла. Также поддерживает JS, HTML, CSS. Также доступен как CDN.

0
ответ дан ColacX 24 August 2018 в 03:21
поделиться

Если вы ищете решение для JavaScript, просто возьмите код из инструмента Pretty Diff в http://prettydiff.com/?m=beautify

Вы также можете отправьте файлы в инструмент с помощью параметра s, например: http://prettydiff.com/?m=beautify&s=https://stackoverflow.com/

3
ответ дан Community 24 August 2018 в 03:21
поделиться

Personnaly, я использую google-code-prettify с помощью этой функции:

prettyPrintOne('<root><node1><root>', 'xml')
18
ответ дан Igor 24 August 2018 в 03:21
поделиться

Или, если вам просто нужна другая функция js, я изменил Дарина (много):

var formatXml = this.formatXml = function (xml) {
    var reg = /(>)(<)(\/*)/g;
    var wsexp = / *(.*) +\n/g;
    var contexp = /(<.+>)(.+\n)/g;
    xml = xml.replace(reg, '$1\n$2$3').replace(wsexp, '$1\n').replace(contexp, '$1\n$2');
    var pad = 0;
    var formatted = '';
    var lines = xml.split('\n');
    var indent = 0;
    var lastType = 'other';
    // 4 types of tags - single, closing, opening, other (text, doctype, comment) - 4*4 = 16 transitions 
    var transitions = {
        'single->single'    : 0,
        'single->closing'   : -1,
        'single->opening'   : 0,
        'single->other'     : 0,
        'closing->single'   : 0,
        'closing->closing'  : -1,
        'closing->opening'  : 0,
        'closing->other'    : 0,
        'opening->single'   : 1,
        'opening->closing'  : 0, 
        'opening->opening'  : 1,
        'opening->other'    : 1,
        'other->single'     : 0,
        'other->closing'    : -1,
        'other->opening'    : 0,
        'other->other'      : 0
    };

    for (var i=0; i < lines.length; i++) {
        var ln = lines[i];
        var single = Boolean(ln.match(/<.+\/>/)); // is this line a single tag? ex. <br />
        var closing = Boolean(ln.match(/<\/.+>/)); // is this a closing tag? ex. </a>
        var opening = Boolean(ln.match(/<[^!].*>/)); // is this even a tag (that's not <!something>)
        var type = single ? 'single' : closing ? 'closing' : opening ? 'opening' : 'other';
        var fromTo = lastType + '->' + type;
        lastType = type;
        var padding = '';

        indent += transitions[fromTo];
        for (var j = 0; j < indent; j++) {
            padding += '    ';
        }

        formatted += padding + ln + '\n';
    }

    return formatted;
};
7
ответ дан Issac Kelly 24 August 2018 в 03:21
поделиться
var reg = /(>)\s*(<)(\/*)/g;
xml = xml.replace(/\r|\n/g, ''); //deleting already existing whitespaces
xml = xml.replace(reg, '$1\r\n$2$3');
0
ответ дан Jason Im 24 August 2018 в 03:21
поделиться

Небольшая модификация функции javascript efnx clckclcks. Я изменил форматирование с пробелов на вкладку, но, самое главное, я разрешил текст оставаться в одной строке:

var formatXml = this.formatXml = function (xml) {
        var reg = /(>)\s*(<)(\/*)/g; // updated Mar 30, 2015
        var wsexp = / *(.*) +\n/g;
        var contexp = /(<.+>)(.+\n)/g;
        xml = xml.replace(reg, '$1\n$2$3').replace(wsexp, '$1\n').replace(contexp, '$1\n$2');
        var pad = 0;
        var formatted = '';
        var lines = xml.split('\n');
        var indent = 0;
        var lastType = 'other';
        // 4 types of tags - single, closing, opening, other (text, doctype, comment) - 4*4 = 16 transitions 
        var transitions = {
            'single->single': 0,
            'single->closing': -1,
            'single->opening': 0,
            'single->other': 0,
            'closing->single': 0,
            'closing->closing': -1,
            'closing->opening': 0,
            'closing->other': 0,
            'opening->single': 1,
            'opening->closing': 0,
            'opening->opening': 1,
            'opening->other': 1,
            'other->single': 0,
            'other->closing': -1,
            'other->opening': 0,
            'other->other': 0
        };

        for (var i = 0; i < lines.length; i++) {
            var ln = lines[i];

            // Luca Viggiani 2017-07-03: handle optional <?xml ... ?> declaration
            if (ln.match(/\s*<\?xml/)) {
                formatted += ln + "\n";
                continue;
            }
            // ---

            var single = Boolean(ln.match(/<.+\/>/)); // is this line a single tag? ex. <br />
            var closing = Boolean(ln.match(/<\/.+>/)); // is this a closing tag? ex. </a>
            var opening = Boolean(ln.match(/<[^!].*>/)); // is this even a tag (that's not <!something>)
            var type = single ? 'single' : closing ? 'closing' : opening ? 'opening' : 'other';
            var fromTo = lastType + '->' + type;
            lastType = type;
            var padding = '';

            indent += transitions[fromTo];
            for (var j = 0; j < indent; j++) {
                padding += '\t';
            }
            if (fromTo == 'opening->closing')
                formatted = formatted.substr(0, formatted.length - 1) + ln + '\n'; // substr removes line break (\n) from prev loop
            else
                formatted += padding + ln + '\n';
        }

        return formatted;
    };
29
ответ дан lviggiani 24 August 2018 в 03:21
поделиться

здесь другая функция для форматирования xml

function formatXml(xml){
    var out = "";
    var tab = "    ";
    var indent = 0;
    var inClosingTag=false;
    var dent=function(no){
        out += "\n";
        for(var i=0; i < no; i++)
            out+=tab;
    }


    for (var i=0; i < xml.length; i++) {
        var c = xml.charAt(i);
        if(c=='<'){
            // handle </
            if(xml.charAt(i+1) == '/'){
                inClosingTag = true;
                dent(--indent);
            }
            out+=c;
        }else if(c=='>'){
            out+=c;
            // handle />
            if(xml.charAt(i-1) == '/'){
                out+="\n";
                //dent(--indent)
            }else{
              if(!inClosingTag)
                dent(++indent);
              else{
                out+="\n";
                inClosingTag=false;
              }
            }
        }else{
          out+=c;
        }
    }
    return out;
}
1
ответ дан michael hancock 24 August 2018 в 03:21
поделиться

XMLSpectrum форматирует XML, поддерживает отступ атрибутов, а также выделяет синтаксис для XML и любых встроенных выражений XPath:

XMLSpectrum formatted XML [/g2]

XMLSpectrum - проект с открытым исходным кодом, закодированный в XSLT 2.0, поэтому вы можете запускать эту серверную часть с процессором, например Saxon-HE (рекомендуется) или на стороне клиента, используя Saxon-CE.

XMLSpectrum еще не оптимизирован для работы в браузере - следовательно, рекомендуется запустить эту серверную сторону.

1
ответ дан pgfearo 24 August 2018 в 03:21
поделиться

Вы можете получить довольно форматированный xml с помощью xml-beautify

var prettyXmlText = new XmlBeautify().beautify(xmlText, 
                    {indent: "  ",useSelfClosingElement: true});

indent: отступы, такие как пробелы

useSelfClosingElement: true => use самозакрывающийся элемент при пустом элементе.

JSFiddle

Оригинал (до)

<?xml version="1.0" encoding="utf-8"?><example version="2.0">
  <head><title>Original aTitle</title></head>
  <body info="none" ></body>
</example>

Украшен (после)

<?xml version="1.0" encoding="utf-8"?>
<example version="2.0">
  <head>
    <title>Original aTitle</title>
  </head>
  <body info="none" />
</example>
0
ответ дан riversun 24 August 2018 в 03:21
поделиться
var formatXml = this.formatXml = function (xml) {
        var reg = /(>)(<)(\/*)/g;
        var wsexp = / *(.*) +\n/g;
        var contexp = /(<.+>)(.+\n)/g;
        xml = xml.replace(reg, '$1\n$2$3').replace(wsexp, '$1\n').replace(contexp, '$1\n$2');
        var pad = 0;
        var formatted = '';
        var lines = xml.split('\n');
        var indent = 0;
        var lastType = 'other';
1
ответ дан sanjaykumar 24 August 2018 в 03:21
поделиться

Эта библиотека делает именно то, что вы хотите!

https://code.google.com/p/vkbeautify/

4
ответ дан Shivanshu Goyal 24 August 2018 в 03:21
поделиться
Or just print out the special HTML characters?

Ex: <xmlstuff>&#10; &#09;<node />&#10;</xmlstuff>   


&#09;   Horizontal tab  
&#10;   Line feed
1
ответ дан Tobias 24 August 2018 в 03:21
поделиться

считают использование vkBeautify плагина

http://www.eslinstructor.net/vkbeautify/

написано на простом javascript, очень мало: менее 1,5 К, если оно было уменьшено, очень быстро: менее 5 мс. для обработки XML-текста 50K.

58
ответ дан vadimk 24 August 2018 в 03:21
поделиться
Другие вопросы по тегам:

Похожие вопросы: