2009-05-28 12 views
6

Sto provando a eseguire una trasformazione XSLT da un file ant.Come eseguire XSLT 2.0 con ant?

Sto usando un foglio di stile XSLT 2.0 con un parser saxon 9 (che supporta XSLT 2.0).

Il problema è che sembra che formica sempre un parser XSLT 1.0.

Ecco il mio file ant:

<xslt style="stylesheet.xslt" 
    basedir="core/"  
    extension=".xml" 
    destdir="core/" 
    classpath="D:\\DevTools\\saxon\\bin\\saxon9.jar"> 
</xslt> 

Se io lo chiamo direttamente (senza formica), sta funzionando.

Qualche idea?

+0

Questo può essere interessante http://www.xml.com/pub/a/2002/12/11/ant-xml.html ma un po 'vecchio (l'ultimo aggiornamento di mtxslt è 2002 - http: //mtxslt.sf .net /) – paulgreg

risposta

17

Il problema è che, mentre Sassone viene aggiunto al classpath, il meccanismo di JAXP di default per determinare quale TransformerFactory è usato e userà il default che è Xalan. Si sia necessario:

  • Impostare javax.xml.transform.TransformerFactory variabile di sistema per net.sf.saxon.TransformerFactoryImpl,
  • Aggiungere saxon9.jar alla variabile di sistema CLASSPATH, o
  • Usa <factory name="net.sf.saxon.TransformerFactoryImpl"/> all'interno dell'elemento xslt
3

Questo tutorial sembra dare istruzioni passo passo su come fare quello che stanno chiedendo:

http://www.abbeyworkshop.com/howto/xslt/ant-saxon/index.html

Da che sembra si sta facendo la cosa giusta. Sei sicuro di aver bisogno delle doppie barre?

Update: La documentazione Ant XSLT menziona la proprietà 'fabbrica' che può aiutare ci si avvicina:

http://ant.apache.org/manual/Tasks/style.html

+0

Su Windows, penso di aver bisogno. Aggiornato – paulgreg

+0

- possibilmente utilizzare l'attributo 'factory'. – samjudson

1

EDIT:Dr. Michael Kay ha sottolineato che AntTransform non è più supportato, né consigliato.

Creare un taskdef dal sassone AntTransform class:

<taskdef name="saxon-xslt" classname="net.sf.saxon.ant.AntTransform" classpath="${basedir}/lib/saxon/saxon9.jar;${basedir}/lib/saxon/saxon9-ant.jar"/> 

    <saxon-xslt 
    in="${source.xml}" 
    out="${out.dir}/${output.xml}" 
    style="${basedir}/${stylesheet.xsl}" 
    force="true"> 
    </saxon-xslt> 


ho iniziato a utilizzare il <xslt> compito di serie con il vaso saxon specificato in un <classpath>, ma erano stati incorrere in problemi di prestazioni. Sembrava "bloccarsi" per un po 'quando veniva chiamato l'attività. Ho trovato che aggiungere processor="trax" e specificare <factory name="net.sf.saxon.TransformerFactoryImpl"/> aiuta a funzionare molto più velocemente.

<xslt in="${source.xml}" 
     out="${out.dir}/${output.xml}" 
     style="${basedir}/${stylesheet.xsl}" 
     processor="trax"> 
     <factory name="net.sf.saxon.TransformerFactoryImpl"/> 
     <classpath refid="saxon-classpath" /> 
</xslt> 
+0

Si noti che l'attività AntTransform non è più consigliata. Ha dimostrato di essere bacato e non c'era una strategia fattibile per testarlo correttamente dal momento che Apache non rilasciava una suite di test completa per Ant. –

+0

Notato. Ho iniziato a utilizzare l'attività standard '' con il vaso saxon specificato in un '', ma ho riscontrato problemi di prestazioni. Sembrava "bloccarsi" per un po 'quando veniva chiamato l'attività. Recentemente, ho trovato che l'aggiunta di 'processor =" trax "' e la specifica di '' lo aiuta a funzionare molto più velocemente. –

6

Se si hanno questo problema, verificare che non si utilizza 1.8.1 Ant, perché c'è un bug in 1.8.1 Ant che impedisce questo di lavorare. (Anche se questo non è il problema nel post originale, perché era antecedente alla pubblicazione di Ant 1.8.1).

Le opzioni disponibili sono:

  1. utilizza una versione di Ant che non ha il bug (ad esempio Ant 1.7.1).
  2. specificare esplicitamente saxon9.jar nel CLASSPATH per Ant prima del suo inizio, mediante:
    • Impostazione della variabile d'ambiente CLASSPATH, o
    • Utilizzare l'opzione della riga di comando per -libant
  3. Definire il tuo compito utilizzando SAXON Ant (come descritto da un'altra risposta su questo thread).
  4. Soluzione alternativa aggiungendo processor="org.apache.tools.ant.taskdefs.optional.TraXLiaison" come attributo dell'elemento attività xslt.

vorrei suggerimento usando l'opzione 1, seguita da l'opzione 4.

Opzione 2 funzionerà, ma pone la responsabilità sulla persona che esegue formica per configurare il loro ambiente ed eseguire ant correttamente. Presumo che tu non lo voglia, motivo per cui stai cercando di ottenere l'attributo classpath nell'attività xslt per funzionare.

L'opzione 3 presenta limitazioni, poiché SAXON Ant richiede il download e l'installazione del relativo file JAR. Inoltre, SAXON Ant non funziona con SAXON 9.2 o successivo (e SAXON Ant non è stato aggiornato da quando è stato creato nel giugno 2008). In teoria, specificare un sottoelemento factory rende il processore XSLT che si desidera utilizzare esplicitamente, per impedire al caricatore di classi di trovare un processore XSLT diverso nella sua ricerca e utilizzarlo al posto del processore XSLT che è ulteriormente giù nel CLASSPATH. In pratica (almeno nella form 1.7.0, 1.7.1 e 1.8.0) se viene specificato il sottoelemento factory, l'attività xslt ignora l'attributo classpath, il che significa che è necessario ricorrere alla specifica esplicita di CLASSPATH (opzione 2). Quindi non aiuta a risolvere il problema originale. Tuttavia, questo sembra essere stato risolto nel codice sorgente di Ant, quindi potrebbe funzionare nelle versioni successive alla 1.8.1.

+0

questo è il link al bug delle attività di ant 1.8.1 xslt: https://issues.apache.org/bugzilla/show_bug.cgi?id=49271 –

1

Anziché aspettare che questo venga risolto in 1.8.2 e quindi attendere che tutti eseguano l'aggiornamento alla 1.8.2, è possibile eseguire il rollover della propria macro XSLT (per le situazioni in cui si desidera utilizzare in modo esplicito Saxon, anziché utente del motore XSLT selezionato)

<macrodef name="xslt" uri="com.mycompany.mydepartment"> 
    <attribute name="in" /> 
    <attribute name="out" /> 
    <attribute name="style" /> 
    <attribute name="classpath" default="${saxon.jar.path}" /> 
    <attribute name="taskname" default="mydep:xslt" /> 
    <element name="params" optional="true" implicit="true" /> 
    <sequential> 
     <java classname="net.sf.saxon.Transform" 
       classpath="@{classpath}" 
       taskname="@{taskname}"> 
      <classpath path="${saxon.jar.path}" /> 
      <arg value="-s:@{in}" /> 
      <arg value="-xsl:@{style}" /> 
      <arg value="-o:@{out}" /> 
      <params /> 
     </java> 
    </sequential> 
</macrodef> 

si può quindi richiamare piace (supponendo xmlns: mydep = "com.mycompany.mydepartment" è impostato sull'elemento del progetto)

<mydep:xslt in="${myinput}" 
      out="${myoutput}" 
      style="${myxslt}"> 
    <arg value="param1=value1" /> 
    <arg value="param2=value2" /> 
    <arg value="+param3=somefile.xml" /> 
</mydep:xslt> 

è possibile trovare la documentazione per passare i parametri a Saxon a http://www.saxonica.com/documentation/using-xsl/commandline.xml

0

Almeno in ant 1.8.0, l'attività xslt con un percorso di classe specificato è molto lenta. Il problema sembra essere il caricamento del percorso di classe. Ho eseguito la formica sotto JDB e ha speso tutto il tempo extra in org.apache.tools.ant.AntClassLoader.loadClass leggendo i file zip.

ho provato questo prima di eseguire formica che è andato molto più veloce:

formica -LIB /path/to/saxon/saxon9.jar

Il macrodef da Tom Howard funziona meglio, e sebbene abbia una sintassi dispari per i parametri XSLT, almeno è possibile.