/ / Załaduj XML i XSL ze zmiennych i przekształć w przeglądarce - xml, xslt, klient

Załaduj XML i XSL ze zmiennych i transformuj w przeglądarce - xml, xslt, client

Poniższy fragment kodu jest minimalnym odtworzeniem problemu, który mam. Celem jest przekształcenie XML za pomocą XSL i uzyskanie wyniku w zmiennej.

Błąd występuje w komentowanej linii. Co ja robię źle?

Większy obraz jest taki, że chcę mócmieć adres URL pliku XML i adres URL pliku XSL, zarówno w przeglądarce, jak i do przekształcenia XML za pomocą XSL. Mam cały proces wczytywania plików z instalacji wodociągowej serwera, ale pojawia się ten błąd i nie mogę znaleźć zrozumiałej odpowiedzi w Google. Transformacja XML u klienta wydaje się mieć niewielki nacisk od około 2014 r., Więc zastanawiam się, czy jest albo bardziej nowoczesna technika lub wtyczka.

Z radością przyjmuję zwykłą odpowiedź w JS lub jQuery lub wtyczkę.

Wiem, że ten minimalny przykład nie jest cross-browser (brak rozwiązania dla smaków IE), ale powinienem powiedzieć, że potrzebuję rozwiązania cross-browser jako ostatecznej odpowiedzi.

Wreszcie wiem, że możesz dokonać transformacji na serwerze, czego nie ma w specyfikacji.

Oto błąd z konsoli i haczyk.

err = TypeError: Nie udało się wykonać „importStylesheet” na „XSLTProcessor”: parametr 1 nie jest typu „Węzeł”.

Komunikat o błędzie": „Uncaught TypeError: Failed to execute„ transformToFragment ”on „XSLTProcessor”: parametr 1 nie jest typu „Węzeł”. ”,„ Nazwa pliku ”: "https://stacksnippets.net/js"," lineno ": 26," colno ": 32}

Oto kod, który powoduje błąd.

var xsltProcessor, resultDocument, xml, xsl;

var xml = "<?xml version="1.0" encoding="utf-8"?><catalog><cd><title>Empire Burlesque</title></cd></catalog>";
var xsl = "<?xml version="1.0" encoding="utf-8"?><xsl:stylesheet version="1.0"xmlns:xsl="http://www.w3.org/1999/XSL/Transform"><xsl:template match="/">  <h2>My CD Collection</h2>  <table border="1">    <tr bgcolor="#9acd32">      <th style="text-align:left">Title</th>      <th style="text-align:left">Artist</th>    </tr>    <xsl:for-each select="catalog/cd">    <tr>      <td><xsl:value-of select="title" /></td>    </tr>    </xsl:for-each>  </table></xsl:template></xsl:stylesheet>"


xsltProcessor = new XSLTProcessor();
try {
xsltProcessor.importStylesheet(xsl);  // < error here !
} catch (error) {
console.log("err=" + error);
}
resultDocument = xsltProcessor.transformToFragment(xml, document);

console.log(resultDocument);

Odpowiedzi:

0 dla odpowiedzi № 1

Znalazłem własną odpowiedź, więc piszę na wypadek, gdyby pomogło to komukolwiek innemu w przyszłości. Kluczem do rozwiązania jest użycie DomParser do przeanalizowania XML i XSL z ich postaci łańcuchowej do dokumentów.

Inspiracja wyszła z tego pytania SO Obejście problemu dla wysp danych XML co do tego doprowadziło Artykuł w MDN o używaniu wysp danych XML w Mozilli gdzie wyjaśniają obejście i robią coś podobnego do ładowania „bloków danych” HTML5.

UWAGA:Jeśli spojrzysz na swoją konsolę deweloperską, możesz zobaczyć wiele błędów związanych z wyjątkami DOM i różnymi źródłami. Wygląda na to, że ten kod jest niewygodny w maszynie z fragmentami SO, ale jeśli wytniesz i wkleisz do własnego kodu HTML jako blok skryptu, działa on dobrze, tworząc przyjemny "# fragment dokumentu" w konsoli.

var xsltProcessor, resultDocument, xml, xsl;

var xml = "<?xml version="1.0" encoding="utf-8"?><catalog><cd><title>Empire Burlesque</title></cd></catalog>";
var xsl = "<?xml version="1.0" encoding="utf-8"?><xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"><xsl:template match="/">    <xsl:for-each select="catalog/cd">      <xsl:value-of select="title" />    </xsl:for-each></xsl:template></xsl:stylesheet>";

// Secret sauce start.
var parser = new DOMParser();
var xsl_doc = parser.parseFromString(xsl, "application/xml");
var xml_doc = parser.parseFromString(xml, "application/xml");
// end of secret sauce.

xsltProcessor = new XSLTProcessor();
try {
xsltProcessor.importStylesheet(xsl_doc);
} catch (error) {
console.log("err=" + error);
}
resultDocument = xsltProcessor.transformToFragment(xml_doc, document);

console.log(resultDocument);


0 dla odpowiedzi nr 2

Aby odpowiedzieć na tę część pytania:

Wydaje się, że transformacja XML u klienta miała niewielki nacisk od około 2014 roku, więc zastanawiam się, czy nie ma bardziej nowoczesnego technika lub wtyczka.

Powiedziałbym, że producenci przeglądarek nie skupiali się na nim od około 2004 roku.

Ale jeśli chcesz czegoś bardziej nowoczesnego, to jestSaxon-JS, który jest czystą implementacją XSLT 3.0 w języku JavaScript. Nie tylko obsługuje standard 3.0, ale ma również rozszerzenia, które sprawiają, że jest interaktywny, więc możesz przetwarzać zdarzenia wejściowe użytkownika bezpośrednio w kodzie XSLT. Szczegóły na http://www.saxonica.com/saxon-js/index.xml

Zastrzeżenie: Saxon-JS jest produkowany przez moją firmę Saxonica.