<?xml version="1.0" encoding="UTF-8"?> | |
<p:declare-step | |
xmlns:p="http://www.w3.org/ns/xproc" | |
xmlns:c="http://www.w3.org/ns/xproc-step" | |
xmlns:pxp="http://exproc.org/proposed/steps" | |
version="1.0" | |
name="xsl-to-zip" | |
exclude-inline-prefixes="#all"> | |
<p:documentation>Store XSLT transformation results in a zip file. | |
Invocation: | |
java -jar path/to/xmlcalabash-1.1.5-96.jar xsl-to-zip.xpl</p:documentation> | |
<p:output port="result" primary="true" sequence="true"> | |
<p:pipe port="secondary" step="xsl"/> | |
<p:pipe port="result" step="manifest"/> | |
<p:pipe port="result" step="zip"/> | |
</p:output> | |
<p:serialization port="result" indent="true"/> | |
<p:import href="http://xmlcalabash.com/extension/steps/library-1.0.xpl"/> | |
<p:xslt name="xsl" template-name="main"> | |
<p:input port="source"> | |
<p:empty/> | |
<p:documentation>If there is an input port 'source' on 'xsl-to-zip', you can connect it here, | |
instead of p:empty:</p:documentation> | |
<!--<p:pipe port="source" step="xsl-to-zip"/>--> | |
</p:input> | |
<p:input port="parameters"><p:empty/></p:input> | |
<p:input port="stylesheet"> | |
<p:inline> | |
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> | |
<xsl:template name="main"> | |
<xsl:for-each select="(1 to 4)"> | |
<xsl:result-document href="file:/path/doc{.}.xml"> | |
<doc>This is doc #<xsl:value-of select="."/></doc> | |
</xsl:result-document> | |
</xsl:for-each> | |
</xsl:template> | |
</xsl:stylesheet> | |
</p:inline> | |
</p:input> | |
</p:xslt> | |
<p:sink/> | |
<p:for-each name="manifest-entry-iteration"> | |
<p:documentation>Create the manifest entries, see http://exproc.org/proposed/steps/other.html#zip</p:documentation> | |
<p:iteration-source> | |
<p:pipe port="secondary" step="xsl"> | |
<p:documentation>The secondary port of the p:xslt step contains the files written via xsl:result-document, | |
with their respective hrefs as base URIs (so that you can later iterate over them and for example store them to | |
their base URIs).</p:documentation> | |
</p:pipe> | |
</p:iteration-source> | |
<p:add-attribute attribute-name="name" match="/*"> | |
<p:with-option name="attribute-value" select="replace(base-uri(), '^file:/path/', 'path/')"/> | |
<p:input port="source"> | |
<p:documentation>We have to create a manifest entry for each output file. The name (intra-zip path) attribute | |
is computed from the result-document href.</p:documentation> | |
<p:inline> | |
<c:entry/> | |
</p:inline> | |
</p:input> | |
</p:add-attribute> | |
<p:add-attribute attribute-name="href" match="/*"> | |
<p:with-option name="attribute-value" select="base-uri()"> | |
<p:documentation>Caveat: now that the c:entry document appears on the primary input, we have to explicitly | |
state that base-uri() should be evaluated in the context of the iteration source documents.</p:documentation> | |
<p:pipe port="current" step="manifest-entry-iteration"/> | |
</p:with-option> | |
</p:add-attribute> | |
</p:for-each> | |
<p:wrap-sequence wrapper="c:zip-manifest" name="manifest"/> | |
<pxp:zip name="zip" compression-level="default" compression-method="deflated" command="create"> | |
<p:with-option name="href" select="resolve-uri('out.zip')"> | |
<p:documentation>Stores it relative to the static base URI (the pipeline’s directory)</p:documentation> | |
</p:with-option> | |
<p:input port="source"> | |
<p:documentation>The input files (if they were read from disk, we wouldn’t need a document on this port)</p:documentation> | |
<p:pipe port="secondary" step="xsl"/> | |
</p:input> | |
<p:input port="manifest"> | |
<p:documentation>We need a manifest where each entry has a href attribute that matches the corresponding source | |
document’s base URI and each entry also has a name attribute that specifies the relative location of the stored | |
file within the zip archive.</p:documentation> | |
<p:pipe port="result" step="manifest"/> | |
</p:input> | |
</pxp:zip> | |
<p:sink/> | |
</p:declare-step> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment