Ir para conteúdo

Arquivado

Este tópico foi arquivado e está fechado para novas respostas.

RSS iMasters

[Resolvido] Formatar XML com XSL usando .NET

Recommended Posts

Com o advento deintegração SOA e Web Services, cada dia mais temos que adaptar oconteúdo de nossos dados com agilidade. No meu caso, eu atuo em umaempresa na qual temos vários parceiros comerciais que consomem nossocatálogo de produtos, e a forma de integração que temos é com ouso de XML - bom para acelerar o desenvolvimento do XML para cadaparceiro.

Nós criávamos um XML para cada um, só que isso não erafeito de forma automática. A codificação de cada XML era feitaindividualmente e os objetos eram reutilizados. Só que então tivemosproblemas com performance pois a consulta era feita em tempo real,ou seja, os parceiros concorriam com os clientes que navegavam nosite.

O XML demorava para ser carregado e, quando era necessárioefetuar algum filtro por categoria, gênero, marca, isso erafeito na aplicação, ou seja, o catálogo era carregado inteiro efiltrado através de um delegate. Quando eram poucos parceiros e poucos clientes, tudo bem. Mas um ano depois com muito mais acessos onegócio ficou ruim. É isso que vou mostrar como fazer aqui, comoesse problema foi resolvido e os passos abaixo:

  1. Não acessar mais o banco diretamente, mas sim um XML base;
  2. Efetuar a formatação dos dados baseado em um XSL e não mais fazer isso na codificação;
  3. Colocar os critérios dentro do XSL em vez de fazer na aplicação ou em query.

Neste artigo, utilizeiVisual C# 2010 Express, Framework 4.0 e para o aplicativo teste fizum console application.

O que é um arquivo XSL e para que serve

Segundo a Wikpedia, XSL Transformations ou XSLT (eXtensible Stylesheet Language forTransformation - linguagem extensível para folhas de estilo detransformações) é uma linguagem de marcação XML usada paracriar documentos XSL que, por sua vez, definem a apresentação dosdocumentos XML nos browsers e outros aplicativos que a suportem. Ou seja, serve para formatar a saída de dados do XML

Fonte: XSLT - Wikipédia

Agora que estamosalinhados com o cenário, vamos começar.

XML Base

Isso é algo muitotranquilo. Foi criado um JOB que gera um XML em uma pasta visívelpela aplicação com todo catálogo de produtos.

Para esse estudo,vamos usar o exemplo abaixo:


<?xml version="1.0"

encoding="utf-8" ?>

<catalogo>

<item>

<Sku>500135</Sku>

 

<Descricao><![CDATA[bola de Tênis Wilson

Championship ]]></Descricao>

 

<CodigoCategoria>102</CodigoCategoria>

<Categoria>RACKET

</Categoria>

 

<CodigoMarca>15</CodigoMarca>

 

<Marca>WILSON</Marca>

</item>

<item>

<Sku>500139</Sku>

 

<Descricao><![CDATA[Haltere Ferro Centauro Meio

Kg]]></Descricao>

 

<CodigoCategoria>107</CodigoCategoria>

<Categoria>BODY

</Categoria>

 

<CodigoMarca>999</CodigoMarca>

 

<Marca>FORTE</Marca>

</item>

<item>

<Sku>500140</Sku>

 

<Descricao><![CDATA[Halteres Ferro Centauro 1 Kg

]]></Descricao>

 

<CodigoCategoria>107</CodigoCategoria>

<Categoria>BODY

</Categoria>

 

<CodigoMarca>999</CodigoMarca>

 

<Marca>FORTE</Marca>

</item>

<item>

<Sku>500141</Sku>

 

<Descricao><![CDATA[Halteres Ferro Centauro 2Kg

]]></Descricao>

 

<CodigoCategoria>107</CodigoCategoria>

<Categoria>BODY

</Categoria>

 

<CodSubGrupo>34</CodSubGrupo>

 

<Marca>FORTE</Marca>

</item>

<item>

<Sku>500142</Sku>

 

<Descricao><![CDATA[Halteres Ferro Centauro 3

kg]]></Descricao>

 

<CodigoCategoria>107</CodigoCategoria>

<Categoria>BODY

</Categoria>

 

<CodigoMarca>999</CodigoMarca>

 

<Marca>FORTE</Marca>

</item>

<item>

<Sku>500143</Sku>

 

<Descricao><![CDATA[Halteres Ferro Centauro 4Kg

]]></Descricao>

 

<CodigoCategoria>107</CodigoCategoria>

<Categoria>BODY

</Categoria>

 

<CodigoMarca>999</CodigoMarca>

 

<Marca>FORTE</Marca>

</item>

</catalogo>

XSL

Bom, o XSL pode ficarao gosto de cada um, eu vou colocar dois exemplos aqui. O primeironos dará a seguinte saída do XML Base:

<xsl:stylesheet

version="1.0"

xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output

method='xml' indent='yes' version='1.0' encoding='UTF-8'

standalone='yes' cdata-section-elements='NOME'/>

<xsl:template

match="/">

<produtos>

<xsl:for-each

select="catalogo/item[CodigoCategoria=102' and

CodigoMarca='999]">

<PRODUTO>

<SKU>

 

<xsl:value-of select="Sku"/>

</SKU>

<NOME>

 

<xsl:value-of select="Descricao"/>

</NOME>

<CATEGORIA>

 

<xsl:value-of select="Categoria"/>

</CATEGORIA>

</PRODUTO>

</xsl:for-each>

</produtos>

</xsl:template>

</xsl:stylesheet>

O segundo oferece asaída abaixo:

<xsl:stylesheet

version="1.0"

xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:output

method='xml' indent='yes' version='1.0' encoding='UTF-8'

standalone='yes' cdata-section-elements='NOME'/>

<xsl:template

match="/">

<produtos>

<xsl:for-each

select="catalogo/item[CodigoCategoria=102]">

<ITEM>

<CODIGO>

 

<xsl:value-of select="Sku"/>

</CODIGO>

<DESCRICAO>

 

<xsl:value-of select="Descricao"/>

</DESCRICAO>

</ITEM>

</xsl:for-each>

</produtos>

</xsl:template>

</xsl:stylesheet>

Esses arquivos devemser criados em um local no qual a aplicação possa lê-los.

Agora vamos entenderalgumas tags do XSL:

Aqui é feita adeclaração do XSL, a versão e qual namespace (xmlns) é utilizado,a tag deve ser fechada.

	<xsl:stylesheet

version="1.0"

xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

A saída do arquivo édefinida aqui, além do método/formato (method), a versão do formato(version), a codificação (encoding) e as tags que terão a saídacom CDATA (cdata-section-elements).

	<xsl:output

method='xml' version='1.0' encoding='UTF-8'

cdata-section-elements='NOME'/>

Nesse momento, o nóraiz é escolhido para trabalhar, a tag deve ser fechada.

	<xsl:template

match="/">

Tudo o que nãoestiver usando o prefixo xsl será escrito da mesma forma comoestiver no XSL. Vamos ver o loop agora. Aqui é o começo doloop:

	<xsl:for-each

select="catalogo/item">

E aqui é o seu final:

	</xsl:for-each>

Tudo o que estiverentre essas tags será repetido até que todos os nós tenham sidolidos. Para escrever osvalores que estão no XML, basta usar a tag value-of e, no atributoselect, colocar o campo que deseja, conforme o exemplo abaixo.

	<xsl:value-of

select="Sku"/>

Adicionando critérios ao XSL

Assim como em uma query, é possível adicionarcritérios a XSL, basta adicioná-los conforme o código abaixo natag for-each.

No primeiro exemplo, o XSL trará apenas os produtos como campo CodigoCategoria igual a 102, já no segundo exemplo todos comCodigoCategoria igual a 102 e o CodigoMarca igual 999.

<xsl:for-each

select="catalogo/item[CodigoCategoria=102]">

<xsl:for-each

select="catalogo/item[CodigoCategoria=102' and

CodigoMarca='999]">

Usando XSL para formatar o XML

O .NET Frameworknos dá suporte para trabalhar com arquivos XML através do NamespaceSystem.Xml e para trabalhar com XSL com o Namespace System.Xml.Xsl.

Vamos utilizar aclasse XslCompiledTransformpara formatar o XML com nosso XSL. Essa classe éum processador de XSL e XSLT. Ela ainda é a sucessora da classeXslTransform e, segundo a MSDN, oferece ganhos de performance comrelação à classe antiga (e obsoleta na versão 4.0 do .NET Framework).

Uma das sobrecargas doconstrutor do XslCompiledTransform recebe um XmlReader, entãocarreguei o XSL dentro de um XmlReader e criei o objeto doXslCompiledTransform.

O método Transform de nosso objetoXslCompiledTransform tem uma sobrecarga que recebe o xml base, umalista de argumentos de XSLT que será passada como nulo e um objetoque terá o resultado da transformação - nesse caso, é passado umStringWriter. Pronto, agora o objeto StringWriter tem o XML carregadoconforme as definições do XSL, tudo bem simples.

Código

Aqui está todo ocódigo utilizado para a aplicação funcionar corretamente. Confira abaixo:

using System;

using System.Xml;

using System.Xml.Xsl;

using System.IO;

namespace

GeradorXmlParceiro

{

class Program

{

static string

caminhoXmlBase = @"C:XmlBaseXmlBase.xml";

static string

caminhoXsl = @"C:XslXsl1.xsl";

static string

caminhoXmlFormatado = @"C:XmlTransformadoXmlTransformado.xml";

static void

Main(string[] args)

{

 

CriarXmlComXsl();

}

static void

CriarXmlComXsl()

{

XmlDocument

xml = new XmlDocument();

xml =

FormartarXmlBaseParaFormatoComXsl(caminhoXsl);

 

xml.Save(caminhoXmlFormatado);

}

static

XmlDocument FormartarXmlBaseParaFormatoComXsl(string caminhoXsl)

{

XmlDocument

xml = new XmlDocument();

 

XslCompiledTransform xsl = new XslCompiledTransform();

XmlDocument

xmlBase = ObterXmlBase();

try

{

 

XmlReader reader = XmlReader.Create(caminhoXsl);

 

xsl.Load(reader);

 

StringWriter writer = new StringWriter();

 

xsl.Transform(xmlBase, null, writer);

 

xml.LoadXml(writer.ToString());

}

catch

(Exception ex)

{

throw

new Exception("Ocorreu um erro ao efetuar a transformação do

XML.", ex.InnerException);

}

return xml;

}

static

XmlDocument ObterXmlBase()

{

XmlDocument

xml = new XmlDocument();

try

{

 

xml.Load(caminhoXmlBase);

}

catch

(Exception ex)

{

throw

new Exception("Ocorreu um erro ao carregar o XML.",

ex.InnerException);

}

return xml;

}

}

}

É isso aí! Espero queeste artigo possa contribuir para o crescimento da comunidade. Até apróxima!

Referências

 

http://imasters.com.br/artigo/21408/xml/formatar-xml-com-xsl-usando-net

Compartilhar este post


Link para o post
Compartilhar em outros sites

×

Informação importante

Ao usar o fórum, você concorda com nossos Termos e condições.