Subject: RE: [xsl] Generic Lookup (Element Mapping) From: "Faroukh Fekravar" <fekravar@xxxxxxxxxxxxxxxxxx> Date: Wed, 8 May 2002 08:46:27 -0500 |
Thanks Ken, That looks great. The reason that I did not consider more than stylesheet is that I will have more than one mapping file (most likely 3) and am not sure how complicated will the whole thing with that and if it's at all possible. Having said that I did not know that it has an impact on the performance. My concern at this moment is whether XSLT is a proper approach to solve the problem and if yes which patterns/techniques can be used to achieve that. I try to explain my second mapping file to see whether the technique proposed by you can handle that one too. My second mapping file defines the inter relationships of the traget elements. That looks like: Target.xml <?xml version="1.0" encoding="UTF-8"?> <TragetMaps> <TragetMap> <TEname>aa_1</TEname> <!-- That's the name of target element --> <SEname>aa1</SEname> <!-- Info for aa_1 in context of aa1> --> <Attribute> <!-- Add an attribute to aa_1, called aa_a_1 --> <aa_a_1 value="UNId"/> <!-- The value of attribute is an Unique (in whole doc) Numeric Id --> </Attribute> <Element> <!-- Add an element to aa_1, called aa_e_1 --> <aa_e_1 constant="aa_1_Type"/> <!-- The value of the element is a constant (aa_1_Type) --> </Element> <Element> <!-- Add another element to aa_1, called aa_e_2 --> <aa_e_2 constant="some text"/> <!-- The value of the element is a constant (some text) --> </Element> </TragetMap> <TragetMap> <TEname>aa_H_1</TEname> <!-- That's the name of target element, note it's does not appear in the first mapping file --> <SEname>aa1</SEname> <!-- Info for aa_H_1 in context of aa1> --> <Attribute> <!-- Add an attribute to aa_H_1, called aa_H_a_1 --> <aa_H_a_1 value="UNId"/> <!-- The value of attribute is an Unique (in whole doc) Numeric Id --> </Attribute> <Element> <!-- Add an element to aa_H_1, called aa_H_e_1 --> <aa_H_e_1 Link="aa_1_Type"/> <!-- The value is equal the value of aa_a_1 value. Note the names (aa_a_1) are unique in the mapping file, It's also possible to add the whole address/path of the source to make the life easier for XSLT to get the data.--> </Element> <Element> <!-- Add another element to aa_H_1, called aa_H_e_2 --> <aa_H_e_2 constant="some text"/> <!-- The value of the element is a constant (some text) --> </Element> </TragetMap> </TragetMaps> Some notes: 1) value, constant and link are mutually exclusive 2) A TEname can have more than one attribute. 3) Attributes have always Is as values 4) Link can be just part of an element The output file will look like: <project> <aa_1 aa_a_1="1234567"> <aa_e_1>aa_1_Type</aa_e_1> <aa_e_2>Some Text</aa_e_2> <aa_11>aa11_value</aa_11> <aa_12>aa12_value</aa_12> </aa_1> <aa_H_1 aa_H_a_1=12345678> <aa_H_e_1>1234567</aa_H_e_1> <!-- same value as aa_1.aa_a_1 --> </aa_H_1> <aa_1A> <aa_13>aa13_value</aa_13> </aa_1A> <aa_2> <aa_21>aa21_value</aa_21> </aa_2> <aa_3> <aa_31>aa31_value</aa_31> </aa_3> </project> My last mapping file describes the "not one-to-one mappings" between the source and target. Some of the conditional mappings and some of them require call to hand-crafted template, espcilly for cases when we calculate something in the source (cumulative data) and assign the value to an element in the target. I'm working on a simple example on that. I really appreicate any help, Thanks, Faroukh -----Original Message----- From: owner-xsl-list@xxxxxxxxxxxxxxxxxxxxxx [mailto:owner-xsl-list@xxxxxxxxxxxxxxxxxxxxxx]On Behalf Of G. Ken Holman Sent: Tuesday, May 07, 2002 10:24 AM To: XSL-List@xxxxxxxxxxxxxxxxxxxxxx Subject: Re: [xsl] Generic Lookup (Element Mapping) At 2002-05-07 08:15 -0500, Faroukh Fekravar wrote: >I have been trying to write a generic xslt template to map the element names >based on a lookup table. Is there a reason you want to do this in one stylesheet with both the mapping file and the data file? >The lookup xml file has always a subset of the elements and therefore I do >not want to hard code the element names. Then you need a customized stylesheet based on your mappings, especially for speed in order to do a single pass on the input data. >The output file is a flat xml file in opposite to the input file. This was a particularly difficult criterion to meet. >But my main problem is how navigate through the input file in a generic >approach. >I'm also just a little concern about the overall performance because the >input file might be MBs big. For performance reasons, I recommend you write a stylesheet that, based on your mapping, emits a single stylesheet that is then run against your data. This emitted stylesheet does simple matches and should meet your performance requirements. An example of writing a stylesheet that writes a stylesheet is in Chapter 5 of "Definitive XSLT and XPath" which happens to be the freely-downloadable chapter made available by Prentice Hall on the Amazon site. It is also in Chapter 5 of our electronic book from which the paper book was derived. A working answer to your requirements is below. I hope this helps. ...................... Ken t:\ftemp>type data.xml <?xml version="1.0" encoding="iso-8859-1"?> <project> <aa1> <aa11>aa11_value</aa11> <aa12>aa12_value</aa12> <aa13>aa13_value</aa13> <aa2> <aa21>aa21_value</aa21> <aa22>aa22_value</aa22> <aa3> <aa31>aa31_value</aa31> <aa4> <aa41>aa41_value</aa41> </aa4> </aa3> </aa2> </aa1> </project> t:\ftemp>type lookup.xml <?xml version="1.0" encoding="iso-8859-1"?> <Maps> <Map> <!-- combination of SEName, SAname and TEname is unique through the file.--> <SEname>aa1</SEname> <!-- element name in the input file--> <SAname>aa11</SAname> <!-- element name in the input file, it's always the child element of SEName--> <TEname>aa_1</TEname> <!-- element name in output--> <TAname>aa_11</TAname> <!-- element nemae in output, it should be the child element of TEname--> </Map> <Map> <SEname>aa1</SEname> <SAname>aa12</SAname> <TEname>aa_1</TEname> <TAname>aa_12</TAname> </Map> <Map> <SEname>aa1</SEname> <SAname>aa13</SAname> <TEname>aa_1A</TEname> <TAname>aa_13</TAname> </Map> <Map> <SEname>aa2</SEname> <SAname>aa21</SAname> <TEname>aa_2</TEname> <TAname>aa_21</TAname> </Map> <!-- no mapping for aa22 --> <Map> <SEname>aa3</SEname> <SAname>aa31</SAname> <TEname>aa_3</TEname> <TAname>aa_31</TAname> </Map> </Maps> t:\ftemp>type faroukh.xsl <?xml version="1.0" encoding="iso-8859-1"?> <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xslo="junk" version="1.0"> <xsl:namespace-alias stylesheet-prefix="xslo" result-prefix="xsl"/> <xsl:key name="parents" match="Map" use="SEname"/> <xsl:key name="children" match="Map" use="concat(SEname,' ',TEname)"/> <xsl:template match="/"> <xslo:stylesheet version="1.0"> <xslo:output indent="yes"/> <xslo:template match="/project"><!--preserve project element--> <project> <xslo:apply-templates/> </project> </xslo:template> <xslo:template match="*"/><!--throw away unmapped--> <xslo:template match="text()"/><!--only keep explicitly copied text--> <xsl:apply-templates/> </xslo:stylesheet> </xsl:template> <xsl:template match="Map"> <!--only put out a single template for the parent--> <xsl:if test="generate-id(.)=generate-id(key('parents',SEname))"> <xslo:template match="{SEname}"> <!--needs as many apply templates as unique parent mappings--> <xsl:for-each select="key('parents',SEname)[generate-id(.)= generate-id(key('children',concat(SEname,' ',TEname)))]"> <xslo:element name="{TEname}"> <xslo:apply-templates mode="mapping"> <xsl:attribute name="select"> <xsl:for-each select="key('children',concat(SEname,' ',TEname))"> <xsl:if test="position()>1">|</xsl:if> <xsl:value-of select="SAname"/> </xsl:for-each> </xsl:attribute> </xslo:apply-templates> </xslo:element> </xsl:for-each> <xslo:apply-templates/> </xslo:template> </xsl:if> <xslo:template match="{SEname}/{SAname}" mode="mapping"> <xslo:element name="{TAname}"> <xslo:value-of select="."/> </xslo:element> </xslo:template> </xsl:template> </xsl:stylesheet> t:\ftemp>saxon -o mapping.xsl lookup.xml faroukh.xsl t:\ftemp>saxon -o faroukh.out data.xml mapping.xsl t:\ftemp>type faroukh.out <?xml version="1.0" encoding="utf-8"?> <project> <aa_1> <aa_11>aa11_value</aa_11> <aa_12>aa12_value</aa_12> </aa_1> <aa_1A> <aa_13>aa13_value</aa_13> </aa_1A> <aa_2> <aa_21>aa21_value</aa_21> </aa_2> <aa_3> <aa_31>aa31_value</aa_31> </aa_3> </project> t:\ftemp>rem Done! -- Upcoming: 3-days XSLT/XPath and/or 2-days XSLFO: June 17-21, 2002 - : 3-days XML Information Modeling: July 31-August 2, 2002 G. Ken Holman mailto:gkholman@xxxxxxxxxxxxxxxxxxxx Crane Softwrights Ltd. http://www.CraneSoftwrights.com/s/ Box 266, Kars, Ontario CANADA K0A-2E0 +1(613)489-0999 (Fax:-0995) ISBN 0-13-065196-6 Definitive XSLT and XPath ISBN 1-894049-08-X Practical Transformation Using XSLT and XPath ISBN 1-894049-07-1 Practical Formatting Using XSLFO XSL/XML/DSSSL/SGML/OmniMark services, books(electronic, printed), articles, training(instructor-live,Internet-live,web/CD,licensed) Next public training: 2002-05-06,07,09,10,13,15,20, - 06-04,07,10,11,13,14,17,20,07-31,08-05,27,30 XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
Re: [xsl] Generic Lookup (Element M, G. Ken Holman | Thread | RE: [xsl] Generic Lookup (Element M, G. Ken Holman |
Re: RE: [xsl] Filtering elements of, william locksman | Date | RE: [xsl] xsl:sort and datatypes, Michael Kay |
Month |