Eseguire managed code con XSLT

3 pagine in totale: <<Indietro 1 [2] 3 Avanti >>

Eseguire codice nel foglio

Una novità che il .NET Framework ci mette a disposizione è la possibilità di richiamare funzioni in managed code (scritto in VB.NET, C# o JScript.Net) direttamente dall'interno del nostro file XSLT. Riprendiamo l'esempio precedente, modificando il foglio di stile in questo modo:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  xmlns:msxsl="urn:schemas-microsoft-com:xslt"
  xmlns:az="urn:az-scripts"
  version="1.0">
<msxsl:script implements-prefix="az" language="VB">
<![CDATA[
public function CalcolaData(data as string) as string
  dim dt1,dt2 as DateTime
  dim diff as TimeSpan
  dt1=DateTime.Now()
  dt2=DateTime.Parse(data)
  diff = dt1.Subtract(dt2)
  return diff.Days.ToString()
end function
]]>
</msxsl:script>
<xsl:template match="/">
<table border="1" cellspacing="0" cellpadding="1">
<tr>
  <th>Codice</th>
  <th>Descrizione</th>
  <th>Data inserimento</th>
  <th>Giorni giacenza</th>
</tr>
<xsl:for-each select="//articoli">
  <xsl:apply-templates select="articolo" />
</xsl:for-each>
</table>
</xsl:template>
 
<xsl:template match="articolo">
<tr>
  <td><xsl:value-of select="codice" /></td>
  <td><xsl:value-of select="descrizione" /></td>
  <td><xsl:value-of select="data_inserimento" /></td>
  <td><xsl:value-of select="az:CalcolaData(data_inserimento)" /></td>
</tr>
</xsl:template>
</xsl:stylesheet>

In grassetto sono evidenziate le novità rispetto all'esempio precedente.

Nel prologo del documento XML abbiamo inserito degli identificatori. Il primo parametro ci serve perché il .NET Framework accetta codice da elaborare server-side solo all'interno di questo elemento:

xmlns:msxsl="urn:schemas-microsoft-com:xslt"

Con la successiva istruzione, invece, specifichiamo il prefisso che utilizzeremo per richiamare la funzione presente all'interno del blocco "msxsl:script":

<msxsl:script implements-prefix="az" language="VB">
<![CDATA[
...
</msxsl:script>

E' consigliato inserire il codice all'interno del blocco

<![CDATA...
per evitare problemi con caratteri interpretabili come parti della struttura.

Una volta che il control Xml avrà elaborato questo codice, sarà compilato in modo autonomo quanto presente all'interno del blocco.

A questo punto occorre aggiungere una nota sulla compilazione. I namespace inclusi saranno i seguenti:

  • System
  • System.Xml
  • System.Xml.XPath
  • System.Xsl
  • System.Text
  • System.Text.RegularExpressions
  • System.Collections
  • Microsoft.VisualBasic

Per utilizzare classi presenti in altri namespace, sarà necessario utilizzare il full qualifier, in questo modo:

Dim database as new System.Data.OleDbConnection

Il risultato del codice sarà il seguente:

Immagine

E' stata aggiunta una colonna alla tabella, rispetto all'esempio precedente, in cui è presente la differenza di giorni rispetto alla data attuale per l'articolo presente in magazzino, differenza calcolata dalla nostra funzione scritta in VB.NET.

I Primi problemi e la nostra soluzione

L'approccio usato finora presenta un grosso problema: non è possibile accedere a classi esterne e la compilazione dinamica ad ogni richiamo della pagina comporta sempre un leggero rallentamento nella risposta, visto che per ogni richiesta viene effettuata una nuova compilazione (anche se questo svantaggio può essere usato per la compilazione dinamica di codice).

I realizzatori del .NET Framework hanno pensato anche a questo, offrendoci la possibilità di richiamare una qualsiasi classe all'interno del nostro documento XSLT, con poche e semplici modifiche.

Ecco quindi come diventa il foglio di stile:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  xmlns:az="urn:az-object"
  version="1.0">
<xsl:template match="/">
<table border="1" cellspacing="0" cellpadding="1">
<tr>
  <th>Codice</th>
  <th>Descrizione</th>
  <th>Data inserimento</th>
  <th>Giorni giacenza</th>
</tr>
<xsl:for-each select="//articoli">
  <xsl:apply-templates select="articolo" />
</xsl:for-each>
</table>
</xsl:template>
 
<xsl:template match="articolo">
<tr>
  <td><xsl:value-of select="codice" /></td>
  <td><xsl:value-of select="descrizione" /></td>
  <td><xsl:value-of select="data_inserimento" /></td>
  <td><xsl:value-of select="az:CalcolaData(data_inserimento)" /></td>
</tr>
</xsl:template>
</xsl:stylesheet>

Come si può notare, è sparita la sezione del codice e la dichiarazione del blocco per lo schema:

xmlns:msxsl="urn:schemas-microsoft-com:xslt

A questo punto bisogna aggiungere un'ulteriore proprietà al control Xml, questa volta però da codice:

private void Page_Load(object sender, System.EventArgs e)
{
  XsltArgumentList args=new XsltArgumentList();
  args.AddExtensionObject("urn:az-object",this);
  Xml1.TransformSource="esempio_3.xslt";
  Xml1.TransformArgumentList=args;
}
public string CalcolaData(string data)
{
  DateTime dt1,dt2;
  TimeSpan diff;
  dt1=DateTime.Now;
  dt2=DateTime.Parse(data);
  diff = dt1.Subtract(dt2);
  return diff.Days.ToString();
}

Innanzitutto possiamo che la funzione CalcolaData è presente all'interno della classe di cui è composta la pagina, quindi da essa potremo utilizzare qualsiasi altra istanza di classe presente nella nostra web application.

All'interno dell'evento Page_Load abbiamo creato un'istanza della classe XsltArgumentList , attraverso la quale inseririamo le proprietà per informare il nostro control sulla classe che contiene la definizione.

In questo caso è stato inserito come parametro this, cioè l'istanza di classe della pagina stessa.

Com'è facile intuire, invece di this, possiamo inserire qualsiasi altra istanza di classe attiva:

Dim mia_classe as new MiaClasse()
XsltArgumentList args=new XsltArgumentList();
args.AddExtensionObject("urn:az-object",mia_classe);

3 pagine in totale: <<Indietro 1 [2] 3 Avanti >>

Attenzione: Questo articolo contiene un allegato

Contenuti dell'articolo

Commenti
Dai un voto a questo articolo, ci aiuterà a migliorare il nostro sito (1 è il voto minimo, 5 il massimo).

Per procedere al rating dell'articolo devi essere autenticato.

Aggiungi un nuovo commento »»»
Per inserire un commento, devi registrarti alla nostra community.


TUTORIALS
TOP TEN ARTICOLI
NOTIFICHE

Iscriviti alla nostra newsletter nuoviarticoli per ricevere e-mail le notifiche!

Indirizzo e-mail:
PROVIDER ASP.NET 2.0

Seleziona il database per avere il web.config pronto per Membership, Roles e Profile API.



IN EVIDENZA
MISC