Re: [xsl] Transforming a non-hierarchical XML into a hierarchical one

Subject: Re: [xsl] Transforming a non-hierarchical XML into a hierarchical one
From: SEXpeare <sexpeare@xxxxxxxxx>
Date: Thu, 8 Mar 2007 18:34:42 +0100
NOW THIS IS DIFFICULT (OR MAYBE NOT):

Continuing with the same flat document I have now this problem (i'll
try to do my best explaining myself, sorry if my english is not
perfect):

Having this XML code:

	<anuncios>
		<p style="0GEN_Tit_Seccion">...</p>
		<p style="1PA_Tit1_SubSecc">...</p>
		<p style="1PA_Tit2_Consejeria">...</p>
		<adstart TextId="" Section="" Subsection="" Organism="" Suborganism=""/>
		<p style="1PA_Sum_Anuncio">...</p>
		<p style="NormalParagraphStyle"/>
		<p style="0GEN_Parrafo">...</p>
		<p style="0GEN_Parrafo">...</p>
		<p style="0GEN_Parrafo">...</p>
		<p style="0GEN_Tabla">
			<table>
				<cell row="0" col="0">
					<p style="0GEN_Parrafo">...</p>
				</cell>
				<cell row="0" col="1">
					<p style="0GEN_Parrafo">...</p>
				</cell>
				<cell row="1" col="0">
					<p style="0GEN_Parrafo">...</p>
				</cell>
				<cell row="1" col="1">
					<p style="0GEN_Parrafo">...</p>
				</cell>
			</table>
		</p>
		....
		<p style="1PA_Tit2_Consejeria">...</p>
		<adstart TextId="" Section="" Subsection="" Organism="" Suborganism=""/>
		<p style="1PA_Sum_Anuncio">...</p>
		<p style="NormalParagraphStyle"/>
		<p style="0GEN_Parrafo">...</p>
		<p style="0GEN_Parrafo">...</p>
		<p style="0GEN_Parrafo">...</p>
		<p style="1PA_Resol_Fundamentos">...</p>
		<p style="1PA_Ley_Articulo">...</p>
		<p style="1PA_Resol_Fundamentos">...</p>
		<p style="0GEN_Anexo">...</p>
		<p style="0GEN_Anexo_Tit">...</p>
		<p style="0GEN_Lista  ">...</p>
		...
	</anuncios>

Let me explain the situation: there are some nodes that we have to put
into hierarchical form, and others that we have to leave as they are,
the result must be this:

	<anuncios>
		<seccion id="">
			<subseccion id="">
				<organismo id="">
					<suborganismo id="">
						<anuncio>
							<infoAnuncio>
								<codigo>...</codigo>
								<titulo>...</titulo>
							</infoAnuncio>
							<contenido>
<!-- From this point, all the nodes of this "anuncio" must remain as
in the original -->
								<p style="NormalParagraphStyle"/>
								<p style="0GEN_Parrafo">...</p>
								<p style="0GEN_Parrafo">...</p>
								<p style="0GEN_Parrafo">...</p>											</contenido>
						</anuncio>
						  ...
					</suborganismo>
				</organismo>
			</subseccion>
		</seccion>
		 ...
	</anuncios>

What I have atm is this:

...code of main template...
			<anuncios>
				<xsl:for-each select="anuncios/p[1]">
					<xsl:call-template name="anuncios"/>
				</xsl:for-each>
			<\anuncios>
...code of main template...

	<xsl:template name="anuncios">
		<xsl:variable name="estilo" select="@style"/>
		<xsl:for-each-group select="self::* | following-sibling::*"
group-starting-with="*[@style = $estilo]">
			<xsl:choose>

<!-- CASE SECCION -->

				<xsl:when test="@style = &quot;0GEN_Tit_Seccion&quot;">
					<seccion id="{.}">
						<xsl:variable name="group">
							<xsl:copy-of select="current-group()"/>
						</xsl:variable>
						<xsl:for-each select="$group/*[2]">
							<xsl:call-template name="anuncios"/>
						</xsl:for-each>
					</seccion>
				</xsl:when>

<!-- END CASE SECCION -->

<!-- CASE SUBSECCION -->

				<xsl:when test="@style = &quot;1PA_Tit1_SubSecc&quot;">
					<subseccion id="{.}">
						<xsl:variable name="group">
							<xsl:copy-of select="current-group()"/>
						</xsl:variable>
						<xsl:for-each select="$group/*[2]">
							<xsl:call-template name="anuncios"/>
						</xsl:for-each>
					</subseccion>
				</xsl:when>

<!-- END CASE SUBSECCION -->

<!-- CASE ORGANISMO -->

				<xsl:when test="@style = &quot;1PA_Tit2_Consejeria&quot;">
					<organismo id="{.}">
						<xsl:variable name="group">
							<xsl:copy-of select="current-group()"/>
						</xsl:variable>
						<xsl:for-each select="$group/*[2]">
							<xsl:call-template name="anuncios"/>
						</xsl:for-each>
					</organismo>
				</xsl:when>

<!-- END CASE ORGANISMO -->

<!-- CASE SUBORGANISMO -->

				<xsl:when test="@style = &quot;DONT_HAVE_THE_STYLE_YET&quot;">
					<suborganismo id="{.}">
						<xsl:variable name="group">
							<xsl:copy-of select="current-group()"/>
						</xsl:variable>
						<xsl:for-each select="$group/*[2]">
							<xsl:call-template name="anuncios"/>
						</xsl:for-each>
					</suborganismo>
				</xsl:when>

<!-- END CASE SUBORGANISMO -->

<!-- THIS NODE adstart DONT HAS TO BE SHOWN -->
				<xsl:when test="following-sibling::*[1]/@style =
&quot;1PA_Sum_Anuncio&quot;">
					<xsl:variable name="group">
						<xsl:copy-of select="current-group()"/>
					</xsl:variable>
					<xsl:for-each select="$group/*[2]">
						<xsl:call-template name="anuncios"/>
					</xsl:for-each>
				</xsl:when>

<!-- CASE ANUNCIO -->

				<xsl:when test="@style = &quot;1PA_Sum_Anuncio&quot;">
					<anuncio>
						<infoAnuncio>
							<codigo><xsl:value-of
select="preceding-sibling::adstart[1]/@TextId"/></codigo>
							<titulo><xsl:value-of select="substring(., 2)"/></titulo>
						</infoAnuncio>
						<contenido>
(THIS IS THE PLACE WHERE I NEED TO PUT THE CODE THAT WILL SHOW ALL THE
NODES AFTER THIS ONE AS THEY ARE IN THE ORIGINAL)
						</contenido>
					</anuncio>
				</xsl:when>

<!-- FIN CASO ANUNCIO -->

			</xsl:choose>
		</xsl:for-each-group>
	</xsl:template>

What I have achieved till the moment is this:

	<anuncios>
		<seccion id="I. Principado de Asturias">
			<subseccion id="Otras Disposiciones">
				<organismo id="Consejerma de Economma y Administracisn Pzblica">
					<anuncio>
						<infoAnuncio>
							<codigo>2007-169</codigo>
							<titulo>Resolucisn de 12 de enero de 2007, de la Consejerma de
Economma y Administracisn Pzblica, por la que se dispone el
cumplimiento de la sentencia dictada por el Juzgado de lo Contencioso
Administrativo n: 4 de Oviedo, en el recurso n: 104/2004</titulo>
							<paginaInicio/>
							<paginaFin/>
							<tipoAnuncio/>
						</infoAnuncio>
						<contenido/> (THERE IS WHERE THE NODES MUST BE)
					</anuncio>
				</organismo>
				</organismo>
			</subseccion>
		</seccion>
	</anuncios>

Well I don't know if I have explained myself or if all this crap will
have any sense for you guys, but as always I thank you so much and
apologize for your time wasting.

Let me know if you need more data, and thx again ;)

2007/3/8, SEXpeare <sexpeare@xxxxxxxxx>:
thx very much both of U, you have solved my problem, now i'm trying to
apply this to another part of the document where the nodes are all the
same with an attribute giving their class, I think I can do it but if
I can't I will have to disturb you again with my questions, thx in
advance

2007/3/8, Michael Kay <mike@xxxxxxxxxxxx>:
>
> If the sections aren't recursive (different element name used at each
level)
> then you can do something like
>
> <xsl:for-each-group select="*"
>                     group-starting-with="section">
>   <section>
>     <h1>...</h1>
>     <xsl:for-each-group select="current-group()[position() ne 1]"
>                         group-starting-with="sub-section">
>        <h2>...</h2>
>           <xsl:for-each-group select="current-group()[position() ne 1]"
>                               group-starting-with="sub-sub-section">
>            <h3>...</h3>
>
> Michael Kay
> http://www.saxonica.com/
>
>
> > -----Original Message-----
> > From: SEXpeare [mailto:sexpeare@xxxxxxxxx]
> > Sent: 08 March 2007 11:23
> > To: xsl-list@xxxxxxxxxxxxxxxxxxxxxx
> > Subject: Re: [xsl] Transforming a non-hierarchical XML into a
> > hierarchical one
> >
> > a 2.0 solution would be great, thx for your time, i have been
> > working with xsl-fo for a time, but never had to do
> > complicated transformations like this one, i want to learn
> > all i can from you ;)
> >
> > 2007/3/8, Michael Kay <mike@xxxxxxxxxxxx>:
> > >
> > > I'm guessing from your choice of element names that your hierarchic
> > > structure is positional rather than defined by pointers.
> > >
> > > This makes it a positional grouping problem. Such problems
> > are always
> > > much easier in XSLT 2.0, so you need to make it clear
> > whether you want
> > > a 1.0 or a 2.0 solution.
> > >
> > > Michael Kay
> > > http://www.saxonica.com/
> > >
> > > > -----Original Message-----
> > > > From: SEXpeare [mailto:sexpeare@xxxxxxxxx]
> > > > Sent: 08 March 2007 10:20
> > > > To: xsl-list@xxxxxxxxxxxxxxxxxxxxxx
> > > > Subject: [xsl] Transforming a non-hierarchical XML into a
> > > > hierarchical one
> > > >
> > > > Hello everybody, I have to transform a non hierarchical XML:
> > > >
> > > >       <sumario>
> > > >               <seccion txt=""/>
> > > >               <subseccion txt=""/>
> > > >               <organismo txt=""/>
> > > >               <anuncio txt=""/>
> > > >               <organismo txt=""/>
> > > >               <anuncio txt=""/>
> > > >               <organismo txt=""/>
> > > >               <anuncio txt=""/>
> > > >               <subseccion txt=""/>
> > > >               <organismo txt=""/>
> > > >               <anuncio txt=""/>
> > > >               <seccion txt=""/>
> > > >               <subseccion txt=""/>
> > > >               <organismo txt=""/>
> > > >               <anuncio txt=""/>
> > > >               ...
> > > >       </sumario>
> > > >
> > > > into a hierarchical XML, doing this via XSLT. The result must be
> > > > like this:
> > > >
> > > >       <sumario>
> > > >               <seccion id="">
> > > >                       <subseccion id="">
> > > >                               <organismo id="">
> > > >                                       <anuncio>
> > > >                                       </anuncio>
> > > >                                       ...
> > > >
> > > >                               </organismo>
> > > >                       </subseccion>
> > > >               </seccion>
> > > >               ...
> > > >       </sumario>
> > > >
> > > > I would apreciate any idea or advice, thx.

Current Thread