XSLT management - attaching metadata to a stylesheet for output and parameters - xslt

I am using about a dozen XSLT files to provide a large number of output formats. At the moment the user has to know the extension of the file format being exported to e.g. RTF, HTML, TXT.
I would also like to use parameters to allow more options. If I can embed the metadata in the XSL file itself then I can pick up the details by scanning through the files.
Here is what I am thinking about. In this example the program would have to parse the comments for the required information.
<?xml version="1.0" encoding="UTF-8"?>
<!-- Title: Export to Rich Text Format -->
<!-- Description: This Stylesheet converts to a Rich Text Format format which may be used in a word processor such as Word -->
<!-- FileFormat: RTF -->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:param name="CompanyName"/> <!-- Format:String, Description: Company name to be inserted in the footer -->
<xsl:param name="DateDue"/> <!-- Format:Date-yyyy-mm-dd, Description: Date Due -->
<xsl:param name="IncludePicture">true</xsl:param><!-- Format:Boolean, Description: Do you want to include a graphical representation? -->
<xsl:template match="/">
<!-- Stuff -->
</xsl:template>
</xsl:stylesheet>
Are there any standards out there? Do I need to butcher more than one (Dublin Core with a smattering of XML Schema)?
P.S. the project this is being applied to is Argumentative.

Here is what I am thinking about. In
this example the program would have to
parse the comments for the required
information.
You don't need to code the metadata within comments.
Metadata can be specified as part of the XSLT stylesheet using ordinary XML markup -- as rich in structure and meaning as we need.
Here is an example how to do that:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:meta="my:meta">
<xsl:output method="text"/>
<meta:metadata>
<title>Title: Export to Rich Text Format </title>
<description>
This Stylesheet converts to a Rich Text
Format format which may be used in a word processor
such as Word
</description>
<fileFormat>RTF</fileFormat>
<parameters>
<parameter name="CompanyName" format="xs:string"
Description="Company name to be inserted in the footer"/>
<parameter name="DateDue" format="xs:date"
Description="Date Due"/>
<parameter name="IncludePicture" format="xs:boolean"
Description="Do you want to include a graphical representation?"/>
</parameters>
</meta:metadata>
<xsl:param name="CompanyName"/>
<xsl:param name="DateDue"/>
<xsl:param name="IncludePicture" select="true"/>
<xsl:variable name="vMetadata" select=
"document('')/*/meta:metadata"/>
<xsl:template match="/">
This is a demo how we can access and use the metadats.
Metadata --> Description:
"<xsl:copy-of select="$vMetadata/description"/>"
</xsl:template>
</xsl:stylesheet>
when this transformation is applied on any XML document (not used), the result is:
This is a demo how we can access and use the metadats.
Metadata --> Description:
"
This Stylesheet converts to a Rich Text
Format format which may be used in a word processor
such as Word
"
Do note:
Any element that is in a namespace (of course not the no-namespace and not the xsl namespace) can be specified at the global level of any xslt stylesheet.
Such elements can be accessed using the xslt function document().

Related

Regex of XML with multiple tags

I'm trying to find all text that is not within the XML markup:
<transcript>
<text start="9.75" dur="5.94">welcome to about my property here you
can learn more about how your property</text>
<text start="15.69" dur="4.71">was assessed see the information impact
has on file and compare your property to</text>
<text start="20.4" dur="1.3">others in your neighborhood</text>
<text start="21.7" dur="5.32">interested in learning about market
trends in your municipality no problem</text>
<text start="105.79" dur="6.23">I have all of this and more about life property
. see your property assessment know more</text>
<text start="112.02" dur="0.11">about</text>
</transcript>
I am using the following regex pattern, but obviously it is not correct because it grabs all of the text between the opening and closing <transcript> tags:
<transcript>[\s\S]*?<\/transcript>
How can modify this regex pattern to select only the text that is not within any of the markup tags?
Use XSLT. XSLT is a language specifically designed to convert XML into another output format (back to valid XML again, or something else such as (X)HTML, plain text, or any other format – but preferably, based on plain text).
In this case the smallest XSLT necessary is just this:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="2.0" >
<xsl:output method="text" indent="no" />
<xsl:template match="text">
<!-- do NOTHING here! -->
</xsl:template>
</xsl:stylesheet>
This works because the default for processing a single XML tag is to recursively apply template matches to its containing tags, and plain text will always be copied. The only tag inside your <template> is <text>, and you process it by doing 'nothing' – i.e., by not copying its contents to the output. The line inside that template is just a comment.
All other "nodes", in XML terminology, are those without a surrounding tag and so are copied to the output.
Alternatively, if you have more types of tags than just <text> elements and you want to skip all of them, apply templates to / and transcript to process each and apply another to * (which will select all remaining tags not specified elsewhere) to not process them:
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="2.0" >
<xsl:output method="text" indent="no" />
<xsl:template match="/">
<xsl:apply-templates />
</xsl:template>
<xsl:template match="transcript">
<xsl:apply-templates />
</xsl:template>
<xsl:template match="*">
<!-- do NOTHING here! -->
</xsl:template>
</xsl:stylesheet>
Again, the plain untagged text will fall through and not get processed, so their contents will be copied to output.
Both XSLT stylesheets will output only I ha, the only part in your sample text that is not surrounded by tags.
Do you want to find
welcome to about my property here you can learn more about how your property
from
<text start="9.75" dur="5.94">welcome to about my property here you can learn more about how your property</text>
??
Than it will work.
(?<=>).+?(?=<)

how to call JBOSS service from stylesheet?

I have a project where I need to send an email from JBOSS 6. I'm hoping that I can do it from a stylesheet. Is there a way to call the 'sendmail' service in JBOSS 6 from XSL? I'm just not sure if its possible or even how to do it. If its not possible, maybe I can have the stylesheet output some text into a file somewhere for powershell to watch and send mail from it?
EDIT: I have added code
Here is some code that I am trying to make generate a ".txt" file, but it is not being generated. There are no errors that I can see from the transformer.
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:exsl="http://exslt.org/common"
extension-element-prefixes="exslt"
exclude-result-prefixes="exsl"
version="1.0">
<xsl:output method="text" indent="no"/>
<xsl:variable name="emailPID" select="attr[#tag='00100020']"/>
<xsl:variable name="emailPName" select="attr[#tag='00100010']"/>
<!-- overwritten by application with actual values -->
<xsl:param name="calling" select="'SAMPLE_MOD'"/>
<xsl:param name="called" select="'SERVER1'"/>
<xsl:param name="date" select="'20051206'"/>
<xsl:param name="time" select="'115600.000'"/>
<xsl:template match="/dataset">
<exsl:document href="c:\apps\foo.txt">
<xsl:copy-of select="$emailPID"/>
<xsl:copy-of select="$emailPName"/>
</exsl:document>
</xsl:template>
</xsl:stylesheet>
If my stylesheet is using XSLT1 can I use 'TWO' output methods in one file? One doing "method="xml"" for my applications' function and the other doing "method="text"" to generate a text file?
No, with pure XSLT 1.0 it is not possible to produce multiple output files.
You could use an extension function from EXSLT, see Dimitre Novatchev's answer here. Another solution to your problem is to write two separate XSLT stylesheets, one producing "text" output, the other "xml".
Moreover, the method attribut of the xsl:output element is unique and there cannot be both "xml" and "text" in an XSLT 1.0 stylesheet.
If you use XSLT 2.0, however, this functionality is covered by the xsl:result-document element. This element can be used multiple times and also has a method attribute.

xml not showing in Browser

Below is the input xml :
<?xml version="1.0" encoding="ISO-8859-1"?>
<?xml-stylesheet type="text/xsl" href="value-of.xsl"?>
<MemeberDetails>
<Employee>
<Name>Madhu</Name>
<Sex>Male</Sex>
<DOB>2/10/1982</DOB>
<Address>JP Nagar ,Bangalore</Address>
<MemberId>094631</MemberId>
<Designation>SSE</Designation>
<Department>SG</Department>
</Employee>
</MemeberDetails>
where, i am referring value-of.xsl file using HREF in above xml. and this file is residing in same folder.
Below is the value-of.xslt file:
<?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output indent="yes"/>
<xsl:template match="/">
<CGIEmployeeDetails>
<PersonalDetails>
<Name>
<xsl:value-of select="/MemeberDetails/Employee/Name"/>
</Name>
<Gender>
<xsl:value-of select="/MemeberDetails/Employee/Sex"/>
</Gender>
<ResidentialAddress>
<xsl:value-of select="/MemeberDetails/Employee/Address"/>
</ResidentialAddress>
</PersonalDetails>
<WorkingDetails>
<PSAID>
<xsl:value-of select="//MemberId"/>
</PSAID>
<Designation>
<xsl:value-of select="/MemeberDetails/Employee/Designation"/>
</Designation>
<Department>
<xsl:value-of select="/MemeberDetails/Employee/Department"/>
</Department>
</WorkingDetails>
</CGIEmployeeDetails>
</xsl:template>
</xsl:stylesheet>
When i run above xml in browser , the output will result as text but not as XML .
If i use editor like Oxygen and transform the same xml file , the output will be XML.
I am not getting why browser is failing to transform a XML output ?
Is there anything to do with browser ?
In browsers, the "XML format" view is mostly a stylesheet adding syntax highlighting and Emacscript event handlers (show and hide chlids nodes, etc.).
So, when the document has a XSLT stylesheet PI, browsers don't run that "XML format" stylesheet but they try to render the transformation result. This intent is not the same for each browser. Only one thing is guaranteed: if it's proper XHTML or HTML, is render as is.
If the transformation result is not proper XHTML nor HTML (plain text, other XML vocabulary), the render mechanism varies from one to another: i.e Chrome is the only one showing nothing for unknown XML vocabulary, others render this as HTML anyway (rendering only text).
Are you using internet explorer? That is the only browser I know of that would completely ignore your XSL stylesheet
#Alejandro provided a good explanation.
Using IE, you can see the result of the XSLT transformation by right-clicking on the IE window and selecting "View Source"

Generate dynamic xmlns

I would like to dynamically generate xmlns attributes.
I want to generate this in XSL :
<Common:MainPageBase xmlns:Common="clr-namespace:ThisPartIsDynamic;assembly=ThisPartIsDynamic">
</Common:MainPageBase>
How can I do that in XSL?
Thanks,
Alex
Update:
To be more precise, here is what I need to generate. The parts that I want to be able to change with variables are "THISPARTISDYNAMIC":
<Common:MainPageBase
xmlns:Common="clr-namespace:THISPARTISDYNAMIC;assembly=THISPARTISDYNAMIC"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:df="clr-namespace:System.Windows.Controls;assembly=System.Windows.Controls.Data.DataForm.Toolkit"
xmlns:controlsToolkit="clr-namespace:System.Windows.Controls;assembly=System.Windows.Controls.Toolkit"
xmlns:basics="clr-namespace:System.Windows.Controls;assembly=System.Windows.Controls"
xmlns:data="clr-namespace:System.Windows.Controls;assembly=System.Windows.Controls.Data"
xmlns:uc="clr-namespace:THISPARTISDYNAMIC"
mc:Ignorable="d" d:DesignWidth="640" d:DesignHeight="480"
></Common:MainPageBase>
Any ideas?
You can set the namespace of an element dynamically:
<param name="ns1" >http://localhost/ns1</param>
...
<xsl:element name="test" namespace="{$ns1}" >... </xsl:element>
But that doesn't output a namespace prefix -- it changes the default namespace on that element.
I don't think there is a way to output the prefixes with a dynamic namespace URI.
Something like: <xyz:test xmlns:xyz="{$ns1}">
outputs exactly that literally: <xyz:test xmlns:xyz="{$ns1}">
If that is really the exact output you require, then I think you either have
to modify the serializer, or just produce the output with a placeholder URI and
do a text replacement on the output xml text.
[ XSLT does not process XML syntax. It processes XML trees.
Parsing the input and serializing the output are outside of it's realm. ]
Take a look at the article Namespaces in XSLT, and at the section XSLT 1.0: Creating dynamic namespace nodes in particular.
This transformation:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes"/>
<xsl:variable name="vDynamicPart1" select="'DynPArt1'"/>
<xsl:variable name="vDynamicPart2" select="'DynPArt2'"/>
<xsl:template match="/">
<xsl:element name="Common:MainPageBase"
namespace="clr-namespace:{$vDynamicPart1};assembly={$vDynamicPart2}"/>
</xsl:template>
</xsl:stylesheet>
when applied on any XML document (not used), produces the desired result.

After transformation getting output in text instead of xml nodes

My problem is after executing xlst file i am getting the output in text all in one line, but not in xml as required. My xml as well as xslt file is as follows.
<root>
<Jobs Found="10" Returned="50">
<Job ID="8000000" PositionID="600002">
<Title>Development Manager</Title>
<Summary>
<![CDATA[ An experienced Development Manager with previous experience leading a small to mid-size team of developers in a Java/J2EE environment. A hands on role, you will be expected to manage and mentor a team of developers working on a mix of greenfield and maintenance projects.   My client, a well known investment bank, requires an experienced Development Manager to join their core technology team. This t
]]>
</Summary>
<DateActive Date="2009-10-06T19:36:43-05:00">10/6/2009</DateActive>
<DateExpires Date="2009-11-05T20:11:34-05:00">11/5/2009</DateExpires>
<DateUpdated Date="2009-10-06 20:12:00">10/6/2009</DateUpdated>
<Location>
<Country>xxxx</Country>
<State>xxx</State>
<City>xxx</City>
<PostalCode>xxx</PostalCode>
</Location>
<CompanyName>abc Technology</CompanyName>
<BuilderFields />
<DisplayOptions />
<AddressType>1234</AddressType>
</Job>
</Jobs>
</root>
XSLT stylesheet:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" media-type="application/xml"
cdata-section-elements="Summary"/>
<!-- default: copy everything using the identity transform -->
<xsl:template match="#*|node()">
<xsl:copy>
<xsl:apply-templates select="#*|node()"/>
</xsl:copy>
</xsl:template>
<!-- override: for Location and Salary nodes, just process the children -->
<xsl:template match="Location|Salary">
<xsl:apply-templates select="node()"/>
</xsl:template>
<!-- override: for selected elements, convert attributes to elements -->
<xsl:template match="Jobs/#*|Job/#*">
<xsl:element name="{name()}">
<xsl:value-of select="."/>
</xsl:element>
</xsl:template>
<!-- override: for selected elements, remove attributes -->
<xsl:template match="DateActive/#*|DateExpires/#*|DateUpdated/#*"/>
</xsl:stylesheet>
Current Output in text is:
492 50 83000003 61999998 Market-leading company With a newly created role High Profile Position With Responsibilty, Visibility & Opportunity Must Have Solid BA Skills Honed in a SDLC environment Market-leading company With a newly created role High Profile Position With Responsibilty, Visibility & Opportunity Must Have Solid BA Skills Honed in a SDLC environment My client is a market-leader who continue to go from strengt 10/5/2009 11/4/2009 10/5/2009 Australia NSW Sydney 2000 Skill Quest 90,000.00 120,000.00 Per Year AUD 6
This outout i want in xml. pls help me to get a solution.
Do you have a line like this at the top of your XSLT file??
<xsl:output method="xml" indent="yes"/>
That defines what the output format is - "text" is default, "html" and "xml" are the other options.
I don't know what you're doing, but when I run your XSLT file on the sample XML file provided, I get this as output:
<?xml version="1.0" encoding="utf-8"?>
<root>
<Jobs><Found>10</Found><Returned>50</Returned>
<Job><ID>8000000</ID><PositionID>600002</PositionID>
<Title>Development Manager</Title>
<Summary>
An experienced Development Manager with previous experience leading a small to mid-size team of developers in a Java/J2EE environment. A hands on role, you will be expected to manage and mentor a team of developers working on a mix of greenfield and maintenance projects.&#160;&#160; My client, a well known investment bank, requires an experienced Development Manager to join their core technology team. This t
</Summary>
<DateActive>10/6/2009</DateActive>
<DateExpires>11/5/2009</DateExpires>
<DateUpdated>10/6/2009</DateUpdated>
<Country>xxxx</Country>
<State>xxx</State>
<City>xxx</City>
<PostalCode>xxx</PostalCode>
<CompanyName>abc Technology</CompanyName>
<BuilderFields />
<DisplayOptions />
<AddressType>1234</AddressType>
</Job>
</Jobs>
</root>
Marc
I suspect you are watching the transformation result in a browser.
The transformation itself works perfectly, but the browser displays the plain text of the XML (since it expects HTML contents by default and ignores any tags it does not recognize, displaying their text contents only).
Try media-type="text/xml" and see if that makes any difference. If it doesn't, don't let the browser display confuse you - there is nothing wrong with the XSLT. You should use another XSLT processor to confirm/debug the XSLT.
You probably write out the inner text of an xml node instead of calling apply-templates in one of your nodes. I couldn't find your attached xsl, so it's not easy to guess. But post the xslt, and I'll tell you.