Při používání XSLT jsem narazil na problematiku zpracování jednoho dokumentu několika následnými XSLT transformacemi. Možná se Vám stalo (podobně jako mě), že předchozí transformace upravila dokument a odstranila některé tagy, které chceme v další transformaci zpracovat (poznámka autora: neobjevuji tu kolo, jen poukazuji na možné řešení).
Příklad (pouze obsah xml dokumentu)
<tagProZpracovani_DRUHOU_Transformac>
<tagProZpracováni_PRVNI_transformaci />
</tagProZpracováni_DRUHOU_transformaci>
Pokud bychom použil transformaci T1, a ve které bychm zpracovali pouze vnitřní tag, vnější tagy by byli odstraněny.
Celý "problém" řeší následující XSLT - neboli transformace T1.
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="tagProZpracováni_PRVNI_transformaci" >
<!-- tělo transformace -->
</xsl:template>
</xsl:stylesheet>
Pokud si neumíte představit kdy něco takového použít, vydržte, popíšu v příštím článku jak ulehčit práci při psaní DocBooku. Třeba tím, že si vygenerujeme vlastním tagem obsah tabulky - tzn. první transformací (T1) si vytvoříme validní dokument a druhou (T2) přeložené html. :)
20 července 2009
17 července 2009
XSLT a spouštění Java procedur (se Saxonem)
XSLT transformace - mocný nástroj, avšak čas od času se potýkám s nějakou nejasností, která komplikuje práci. Jak spouštět vlastní java kód (který provede konkrétní výpočet, něco vytáhne z databáze apod. ) na internetu naleznete mraky. Co mě ale dělalo problém - rozchodit celý proces z příkazové řádky. Pojďme se tedy na to podívat. V popisu předpokládám základní znalost XSLT a Javy.
Co budeme potřebovat:
Vytvoříme si adresářovou strukturu:
/
Src - kde budou zdrojový soubory
Tools - kde budou nástroje
|
|-- preprocessors - balík s java třídami
|-- xslt - kde budou transfomace
|-- saxon_6.5.5 - kde bude saxon
Vytvoříme si java třídu a transformaci. Předpokládejme, že v třídě je statická metoda, která se jmenuje getNum() - vrátí nám nějaké číslo, třeba číslo 2 (třídu si před použitím musíme přeložit, tak aby na daném místě byl class soubor).
Zdrojový soubor xml:
<?xml version="1.0" encoding="UTF-8"?>
<mutag>
<javatag />
</mutag>
Transformace bude vypadat následovně:
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:proc="preprocessors.TestClass"
exclude-result-prefixes="proc"
>
<xsl:template match="javatag">
<para><xsl:value-of select="proc:getNum()" /></para>
</xsl:template>
</xsl:stylesheet>
SET CLASSPATH=.\saxon_6.5.5\saxon.jar;.
REM SET CLASSPATH=.\saxon_9.1\saxon9.jar;.
REM saxon v6.5.5
@java com.icl.saxon.StyleSheet -o javaCallResult.xml ..\Src\javaCall.xml xslt\preprocessor.xsl
REM saxon v9.1
REM @java net.sf.saxon.Transform -o javaResult.xml ..\Src\javaCall.xml xslt\preprocessor.xsl
@echo on
Povšiměte si voláme Saxon ne přes Jar soubor, ale přes třídu. Přes jar soubor se mi to nepodařilo zprovoznit (v dávkovém souboru vidíte zakomentovaný příklad i pro Saxon 9.1).
Výsledkem je tedy javaCallResult.xml soubor který obsahuje pouze 2.
Pokud by Vám příklad nefungoval stahněte si celou ukázku.
Spoluautorem ukázky je Martin Augusta, kterému děkuju za spolupráci.
Co budeme potřebovat:
- Saxon 6.5 (pro XSLT 1.0) nebo Saxon 9.1 (pro XSLT 2.0) třeba z http://saxon.sourceforge.net
- vlastní xml soubor, který chceme překládat
- transformace, kterou budeme překládat xml soubor
- chceme zavolat java metodu, tak java třídu
Vytvoříme si adresářovou strukturu:
/
Src - kde budou zdrojový soubory
Tools - kde budou nástroje
|
|-- preprocessors - balík s java třídami
|-- xslt - kde budou transfomace
|-- saxon_6.5.5 - kde bude saxon
Vytvoříme si java třídu a transformaci. Předpokládejme, že v třídě je statická metoda, která se jmenuje getNum() - vrátí nám nějaké číslo, třeba číslo 2 (třídu si před použitím musíme přeložit, tak aby na daném místě byl class soubor).
Zdrojový soubor xml:
<?xml version="1.0" encoding="UTF-8"?>
<mutag>
<javatag />
</mutag>
Transformace bude vypadat následovně:
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:proc="preprocessors.TestClass"
exclude-result-prefixes="proc"
>
<xsl:template match="javatag">
<para><xsl:value-of select="proc:getNum()" /></para>
</xsl:template>
</xsl:stylesheet>
Za zmínku stojí xmlns:proc - kde se odkazujeme na daný balík s danou třídou (místo prefixu proc můžete použít cokoli třeba oblíbené foo :-)). A následně samotné zavolání funkce .
A teď to vše uvedeme do chodu. Uďěláme si dávkový soubor - "baťák".
@echo offSET CLASSPATH=.\saxon_6.5.5\saxon.jar;.
REM SET CLASSPATH=.\saxon_9.1\saxon9.jar;.
REM saxon v6.5.5
@java com.icl.saxon.StyleSheet -o javaCallResult.xml ..\Src\javaCall.xml xslt\preprocessor.xsl
REM saxon v9.1
REM @java net.sf.saxon.Transform -o javaResult.xml ..\Src\javaCall.xml xslt\preprocessor.xsl
@echo on
Povšiměte si voláme Saxon ne přes Jar soubor, ale přes třídu. Přes jar soubor se mi to nepodařilo zprovoznit (v dávkovém souboru vidíte zakomentovaný příklad i pro Saxon 9.1).
Výsledkem je tedy javaCallResult.xml soubor který obsahuje pouze 2.
Pokud by Vám příklad nefungoval stahněte si celou ukázku.
Spoluautorem ukázky je Martin Augusta, kterému děkuju za spolupráci.
Přihlásit se k odběru:
Příspěvky (Atom)