开发者

JAXB XSLT Property substitution

I apologize for the elementary question. I have an XML file, as well as an XSL to translate it into another format (KML). Within the KML I wish to inject a dynamic attribute which is not present in the original XML document. I want to emit a node like the following:

<NetworkLinkControl>
    <message>This is a pop-up message. You will only see this once</message>
    <cookie>sessionID={@sessionID}</cookie>
    <minRefreshPeriod>5</minRefreshPeriod>
  </NetworkLinkControl>

In particular I want the {@sessionID} text to be replaced with a dynamic value that I insert into the template somehow (i.e. is NOT part of the source XML document that the XSLT is transforming).

Here's the code I'm using to marshal the KML:

DomainObject myObject = ...;

JAXBContext context = JAXBContext.newInstance(new Class[]{DomainObject.class});
Marshaller xmlMarshaller = context.createMarshaller();
xmlMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);


TransformerFactory transFact = TransformerFactory.newInstance();
// converts from jaxb XML representation into KML
Templates displayTemplate = transFact.newTemplates(new StreamSource(new File("conf/jaxbkml.xsl")));

Result outputResult = new StreamResult(System.out);

TransformerHandler handler = 
  ((SAXTransformerFactory) transFact).newTransformerHandler(displayTemplate);
handler.setResult(outputResult);

Transformer transformer = handler.getTransformer();
// TODO: what do I actually fill in here to ensure that the session ID comes thro开发者_高级运维ugh
// in the XSLT document? I can't make heads or tails of the javadocs
transformer.setOutputProperty("{http://xyz.foo.com/yada/baz.html}sessionID", "asdf");

xmlMarshaller.marshal(myObject, handler);

I have gathered that there is a way to substitute in values dynamically in the XSLT via Attribute Value Templates and I assume that there is a way to hookup the transformer's properties to be used with these Attribute Value Templates, but I don't quite see how it's done. Could someone shed some light? Thanks.


Thanks to @jtahlborn for setting me on the right track. It is possible to do this, but I wasn't putting all the pieces together. First, define xsl:param.

<!-- give it a default value if none is set -->
<xsl:param name="sessionID" select="''"/>

Second, insert a reference to this xsl:param. If you need to embed it within the content of a node, as I did, use an xsl:value-of node.

<cookie>sessionID=<xsl:value-of
select="$sessionID"/></cookie>

Otherwise, if you need to embed it within an attributes string:

<img src="{$sessionID}/sample.gif"/>

Next, pass in a value for that xsl:param from within Java.

Result outputResult = new StreamResult(outputStream);
TransformerHandler handler = 
 ((SAXTransformerFactory) transFact).newTransformerHandler(displayTemplate);

Transformer transformer = handler.getTransformer();
// Here is where the parameter is bound.
transformer.setParameter("sessionID", sessionID);

handler.setResult(outputResult);
xmlMarshaller.marshal(listWrapper, handler);


The attribute value templates are part of your XSL, not part of your XML, so what you are attempting won't work. You could use xpath to select the element which matches the pattern "sessionID={@sessionID}" and replace that with the text of your choice.

i believe you can set parameters for the stylesheet using the Transformer.setParameter() method which can then be referenced in the stylesheet using the syntax "{$param}", see examples here.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜