# (callable) Get the types of the given files.
override typeoffile = $(patsubst $(foreach file,$1,$(file)?type=%),%,$(filter $(foreach file,$1,$(file)?type=%),$(types)))
+# (callable) Get the identifier for the given transform.
+override id = $(or $(shell $(XMLLINT) --xpath '/*/*[local-name()="id" and namespace-uri()="urn:fdc:ladys.computer:20231231:Shu1She4"]/text()[1]' $1),$(basename $(notdir $1)) | $(SED))
+
# (callable) Get base64 data u·r·i’s for the given files.
override datauri = $(foreach file,$1,data:$(call typeoffile,$(file));base64,$(shell $(UUENCODE) -m -r $(call quote,$(file)) _ | tr -d ' \n'))
$(BUILDDIR)/parser.catalog: $(PARSERS)
@$(ECHO) "Generating catalog of parsers…"
$(silent)$(XMLCATALOG) --create --noout $(call quote,$@)
- $(foreach parser,$(PARSERS),$(silent)$(XMLCATALOG) --add uri $(call quote,$(basename $(notdir $(parser)))) $(call quote,../$(parser)) --noout $(call quote,$@)$(newline))
+ $(foreach parser,$(PARSERS),$(silent)$(XMLCATALOG) --add uri $(call quote,$(call id,$(parser))) $(call quote,../$(parser)) --noout $(call quote,$@)$(newline))
$(BUILDDIR)/parser.xslt: $(BUILDDIR)/parser.catalog $(THISDIR)/lib/catalog2parser.xslt
@$(ECHO) "Generating main parser…"
$(silent)$(XSLTPROC) -o $(call quote,$@) $(call quote,$(THISDIR)/lib/catalog2parser.xslt) $(call quote,$<)
$(BUILDDIR)/transform.catalog: $(TRANSFORMS)
@$(ECHO) "Generating catalog of transforms…"
$(silent)$(XMLCATALOG) --create --noout $(call quote,$@)
- $(foreach transform,$(TRANSFORMS),$(silent)$(XMLCATALOG) --add uri $(call quote,$(basename $(notdir $(transform)))) $(call quote,../$(transform)) --noout $(call quote,$@)$(newline))
+ $(foreach transform,$(TRANSFORMS),$(silent)$(XMLCATALOG) --add uri $(call quote,$(call id,$(transform))) $(call quote,../$(transform)) --noout $(call quote,$@)$(newline))
$(BUILDDIR)/transform.xslt: $(BUILDDIR)/transform.catalog $(THISDIR)/lib/catalog2transform.xslt
@$(ECHO) "Generating main transform…"
$(silent)$(XSLTPROC) -o $(call quote,$@) $(call quote,$(THISDIR)/lib/catalog2transform.xslt) $(call quote,$<)
⛩️📰 书社 will wrap the final output of the transforms in appropriate
`<html:html>` and `<html:body>` elements, so it is not necessary for
transforms to do this explicitly.
-The `<html:head>` of the output will contain the result tree generated
- by matching the root node in the `书社:metadata` mode; the provided
- `transforms/metadata.xslt` transform uses this mode to generate basic
- metadata, but it is possible for other transforms to add their own.
+After performing the initial transform, ⛩️📰 书社 will match the root
+ node of the result in the following modes to fill in areas of the
+ wrapper :—
+
+- **`书社:metadata`:**
+ The result of matching in this mode is inserted into the
+ `<html:head>` of the output.
+
+In addition to being called with the transform result, each of these
+ modes will additionally be called with a `<xslt:include>` element
+ corresponding to each transform.
+If a transform has a `<书社:id>` top‐level element whose value is an
+ i·r·i, its `<xslt:import>` element will have a corresponding
+ `@书社:id` attribute.
+This mechanism can be used to allow transforms to insert content
+ without matching any elements in the result; for example, the
+ following transform adds a link to a stylesheet to the `<html:head>`
+ of every page :—
+
+```xml
+<?xml version="1.0"?>
+<transform
+ xmlns="http://www.w3.org/1999/XSL/Transform"
+ xmlns:html="http://www.w3.org/1999/xhtml"
+ xmlns:xslt="http://www.w3.org/1999/XSL/Transform"
+ xmlns:书社="urn:fdc:ladys.computer:20231231:Shu1She4"
+ exclude-result-prefixes="书社"
+ version="1.0"
+>
+ <书社:id>example:add-stylesheet-links.xslt</书社:id>
+ <template match="xslt:include[@书社:id='example:add-stylesheet-links.xslt']" mode="书社:metadata">
+ <html:link rel="stylesheet" type="text/css" href="/style.css"/>
+ </template>
+</transform>
+```
## License
<!--
⁌ ⛩️📰 书社 ∷ lib/catalog2parser.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
<transform
xmlns="http://www.w3.org/1999/XSL/Transform"
xmlns:catalog="urn:oasis:names:tc:entity:xmlns:xml:catalog"
- xmlns:xsla="http://www.w3.org/1999/XSL/TransformAlias"
+ xmlns:xslt="http://www.w3.org/1999/XSL/TransformAlias"
+ xmlns:书社="urn:fdc:ladys.computer:20231231:Shu1She4"
exclude-result-prefixes="catalog"
version="1.0"
>
- <namespace-alias stylesheet-prefix="xsla" result-prefix="#default"/>
+ <namespace-alias stylesheet-prefix="xslt" result-prefix="#default"/>
<template match="/">
- <xsla:transform version="1.0">
+ <xslt:transform version="1.0">
<for-each select="//catalog:uri">
- <xsla:include href="{@uri}"/>
+ <xslt:include href="{@uri}">
+ <if test="contains(@name, ':')">
+ <attribute name="书社:id">
+ <value-of select="@name"/>
+ </attribute>
+ </if>
+ </xslt:include>
</for-each>
- <xsla:template match="@*|node()" priority="-1">
- <xsla:copy>
- <xsla:apply-templates select="@*|node()"/>
- </xsla:copy>
- </xsla:template>
- </xsla:transform>
+ <xslt:template match="@*|node()" priority="-1">
+ <xslt:copy>
+ <xslt:apply-templates select="@*|node()"/>
+ </xslt:copy>
+ </xslt:template>
+ </xslt:transform>
</template>
</transform>
<!--
⁌ ⛩️📰 书社 ∷ lib/catalog2transform.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
<template match="/">
<xslt:transform exclude-result-prefixes="catalog exsl" version="1.0">
<xslt:param name="catalog" select="'catalog'"/>
+ <xslt:variable name="书社:expansion">
+ <xslt:apply-templates select="/" mode="书社:expand"/>
+ </xslt:variable>
+ <xslt:variable name="书社:result">
+ <xslt:apply-templates select="exsl:node-set($书社:expansion)/*"/>
+ </xslt:variable>
<for-each select="//catalog:uri">
- <xslt:include href="{@uri}"/>
+ <xslt:include href="{@uri}">
+ <if test="contains(@name, ':')">
+ <attribute name="书社:id">
+ <value-of select="@name"/>
+ </attribute>
+ </if>
+ </xslt:include>
</for-each>
<xslt:template match="/" priority="1">
- <xslt:variable name="expansion">
- <xslt:apply-templates select="." mode="书社:expand"/>
- </xslt:variable>
- <xslt:variable name="result">
- <xslt:apply-templates select="exsl:node-set($expansion)/*"/>
- </xslt:variable>
<xslt:variable name="metadata">
- <xslt:copy-of select="exsl:node-set($result)/html/head/*"/>
- <xslt:apply-templates select="exsl:node-set($result)" mode="书社:metadata"/>
+ <xslt:copy-of select="exsl:node-set($书社:result)/html/head/*"/>
+ <xslt:apply-templates select="exsl:node-set($书社:result)" mode="书社:metadata"/>
+ <xslt:apply-templates select="document('')/xslt:transform/xslt:include" mode="书社:metadata"/>
</xslt:variable>
<html:html>
- <xslt:copy-of select="exsl:node-set($result)/html:html/@*"/>
+ <xslt:copy-of select="exsl:node-set($书社:result)/html:html/@*"/>
<html:head>
- <xslt:copy-of select="exsl:node-set($result)/html:html/html:head/@*"/>
+ <xslt:copy-of select="exsl:node-set($书社:result)/html:html/html:head/@*"/>
<html:title>
<xslt:for-each select="exsl:node-set($metadata)/html:title">
<xslt:value-of select="."/>
</xslt:for-each>
</html:title>
- <xslt:copy-of select="exsl:node-set($metadata)/*[not(self::html:title)]"/>
+ <xslt:copy-of select="exsl:node-set($metadata)/node()[self::comment() or self::* and not(self::html:title)]"/>
<xslt:if test="not(exsl:node-set($metadata)/html:meta[@name='generator'])">
<html:meta name="generator" content="⛩️📰 书社"/>
</xslt:if>
</html:head>
<html:body>
- <xslt:copy-of select="exsl:node-set($result)/*[not(self::html:html or self::html:body)]|exsl:node-set($result)/html:html/*[not(self::html:head or self::html:body)]|exsl:node-set($result)/html:html/html:body/*|exsl:node-set($result)/html:body/*"/>
+ <xslt:copy-of select="exsl:node-set($书社:result)/*[not(self::html:html or self::html:body)]|exsl:node-set($书社:result)/html:html/*[not(self::html:head or self::html:body)]|exsl:node-set($书社:result)/html:html/html:body/*|exsl:node-set($书社:result)/html:body/*"/>
</html:body>
</html:html>
</xslt:template>
<!--
⁌ ⛩️📰 书社 ∷ parsers/plain.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
<transform
xmlns="http://www.w3.org/1999/XSL/Transform"
xmlns:html="http://www.w3.org/1999/xhtml"
+ xmlns:书社="urn:fdc:ladys.computer:20231231:Shu1She4"
version="1.0"
>
+ <书社:id>urn:fdc:ladys.computer:20231231:Shu1She4:plain.xslt</书社:id>
<template match="html:script[@type='text/plain']">
- <html:pre><value-of select="."/></html:pre>
+ <html:pre class="plain"><value-of select="."/></html:pre>
</template>
</transform>
<!--
⁌ ⛩️📰 书社 ∷ parsers/tsv.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
xmlns:exsl="http://exslt.org/common"
xmlns:exslstr="http://exslt.org/strings"
xmlns:html="http://www.w3.org/1999/xhtml"
+ xmlns:书社="urn:fdc:ladys.computer:20231231:Shu1She4"
exclude-result-prefixes="exsl exslstr"
version="1.0"
>
+ <书社:id>urn:fdc:ladys.computer:20231231:Shu1She4:tsv.xslt</书社:id>
<template match="html:script[@type='text/tab-separated-values']">
<variable name="rows" select="exslstr:tokenize(., '
')[normalize-space(.) and not(starts-with(., '#'))]"/>
- <variable name="head" select="exsl:node-set($rows)[1]"/>
- <variable name="body" select="exsl:node-set($rows)[not(position()=1)]"/>
- <html:table>
+ <variable name="head" select="$rows[1]"/>
+ <variable name="body" select="$rows[not(position()=1)]"/>
+ <html:table class="tsv">
<html:thead>
<html:tr>
<for-each select="exslstr:tokenize($head, '	')">
- <html:th scope="row">
+ <html:th scope="col">
<value-of select="."/>
</html:th>
</for-each>
</html:tr>
</html:thead>
<html:tbody>
- <for-each select="exsl:node-set($body)">
+ <for-each select="$body">
<html:tr>
<for-each select="exslstr:tokenize(., '	')">
<html:td>
<!--
⁌ ⛩️📰 书社 ∷ transforms/asset.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
exclude-result-prefixes="书社"
version="1.0"
>
+ <书社:id>urn:fdc:ladys.computer:20231231:Shu1She4:asset.xslt</书社:id>
<template match="html:object[@type='text/css']">
<comment>
<text>[书社:CSS] </text>
<!--
⁌ ⛩️📰 书社 ∷ transforms/metadata.xslt
-© 2023 Lady [@ Lady’s Computer]
+© 2023–2024 Lady [@ Lady’s Computer]
This Source Code Form is subject to the terms of the Mozilla Public License, v 2.0.
If a copy of the M·P·L was not distributed with this file, You can obtain one at <https://mozilla.org/MPL/2.0/>.
exclude-result-prefixes="书社"
version="1.0"
>
+ <书社:id>urn:fdc:ladys.computer:20231231:Shu1She4:metadata.xslt</书社:id>
<template match="html:*[@itemscope][1]//html:meta[not(@name) and starts-with(@itemprop, 'urn:fdc:ladys.computer:20231231:Shu1She4:')]">
<comment>
<text>[书社:META] </text>