# (callable) Get the destination for the given source files, or return `.NOTDEF/$1´.
#
# The fallback here is because destinations are used to generate targets and thus must always be non·empty and should be unique, even when they haven’t been generated yet.
-override destination = $(foreach file,$1,$(or $(patsubst $(file)|%,%,$(filter $(file)|%,$(sourcedestinationpair))),.NOTDEF/$1))
+override destination = $(foreach file,$1,$(subst ;, ,$(or $(patsubst $(file)|%,%,$(filter $(file)|%,$(sourcedestinationpair))),.NOTDEF/$1)))
# Pair each source file with its compiled location.
-override sourcecompiledpair := $(foreach file,$(sourcefiles),$(file)|$(BUILDDIR)/results/$(call destination,$(file)))
+override sourcecompiledpair := $(foreach file,$(sourcefiles),$(file)|$(subst $(space),;,$(patsubst %,$(BUILDDIR)/results/%,$(call destination,$(file)))))
# (callable) Get the location of the transformed X·M·L files for the given source files.
-override compiled = $(foreach file,$1,$(patsubst $(file)|%,%,$(filter $(file)|%,$(sourcecompiledpair))))
+override compiled = $(foreach file,$1,$(subst ;, ,$(patsubst $(file)|%,%,$(filter $(file)|%,$(sourcecompiledpair)))))
# (callable) Get the location of the source files for the given compiled file.
-override uncompiled = $(foreach file,$1,$(patsubst %|$(file),%,$(filter %|$(file),$(sourcecompiledpair))))
+override uncompiled = $(foreach pair,$(sourcecompiledpair),$(foreach src,$(firstword $(subst |, , $(pair))),$(if $(filter $(subst ;, ,$(patsubst $(src)|%,%,$(pair))),$1),$(src),)))
# (callable) Get the location of the final built files for the given source files.
override built = $(foreach file,$1,$(patsubst $(BUILDDIR)/results/%,$(BUILDDIR)/public/%,$(call compiled,$(file))))
override unbuilt = $(foreach file,$1,$(call uncompiled,$(patsubst $(BUILDDIR)/public/%,$(BUILDDIR)/results/%,$(file))))
# (callable) Get the installed locations for the given source files.
-override installed = $(foreach file,$1,$(DESTDIR)/$(call destination,$(file)))
+override installed = $(foreach file,$1,$(patsubst %,$(DESTDIR)/%,$(call destination,$(file))))
# ─ ¶ Recipe Variable Definitions ─────────────────────────────────────
# List all source files and includes and their computed types.
list :
- @$(PRINTF) '%b' $(call quote,$(foreach file,$(sort $(sourcefiles)) $(sort $(sourceincludes)),\0033[1m$(file)\0033[22m|$(call typeoffile,$(file))|[\0033[3m$(if $(filter $(file),$(xmlfiles)),xml,$(if $(filter $(file),$(plaintextfiles)),text,asset))$(if $(filter $(file),$(sourceincludes)),|include,)\0033[23m]$(if $(call dependencies,$(file))$(call recursives,$(file)), $(strip $(foreach recursive,$(call recursives,$(file)),\0033[93;41m•|Recursive|Dependency|\0033[39;49m|$(recursive)) $(foreach dependency,$(call dependencies,$(file)),\0033[2m•|Dependency|\0033[22m|$(dependency))))$(if $(filter $(file),$(sourcefiles)), →|<\0033[4m/$(call destination,$(file))\0033[24m>,) )) | $(TR) ' |' '\n '
+ @$(PRINTF) '%b' $(call quote,$(foreach file,$(sort $(sourcefiles)) $(sort $(sourceincludes)),\0033[1m$(file)\0033[22m|$(call typeoffile,$(file))|[\0033[3m$(if $(filter $(file),$(xmlfiles)),xml,$(if $(filter $(file),$(plaintextfiles)),text,asset))$(if $(filter $(file),$(sourceincludes)),|include,)\0033[23m]$(if $(call dependencies,$(file))$(call recursives,$(file)), $(strip $(foreach recursive,$(call recursives,$(file)),\0033[93;41m•|Recursive|Dependency|\0033[39;49m|$(recursive)) $(foreach dependency,$(call dependencies,$(file)),\0033[2m•|Dependency|\0033[22m|$(dependency))))$(if $(filter $(file),$(sourcefiles)), $(foreach dest,$(call destination,$(file)),→|<\0033[4m/$(dest)\0033[24m>),) )) | $(TR) ' |' '\n '
# Lists out the destinations of all resulting files (relative to `DESTDIR´).
listout :
$(call compiled,$(compilablefiles)) : $(BUILDDIR)/results/% : $$(call parseresult,$$(call uncompiled,$$@)) $$(call parseresult,$$(call dependencies,$$(call uncompiled,$$@))) $(BUILDDIR)/transform.catalog $(THISDIR)/lib/catalog2transform.xslt $(TRANSFORMLIBS) $$(call metadata,$$(call dependencies,$$(call uncompiled,$$@)))
$(call inform,$(PRINTF) '%s\n' $(call quote,Compiling </$*>…) >&2)
$(silent)$(call ensuredirectory,$(dir $@))
- $(silent)$(XSLTPROC) --nonet --novalid --nomkdir --nowrite --stringparam METADATA 'metadata' --stringparam BUILDTIME $$($(DATE) -u '+%Y-%m-%dT%H:%M:%SZ') --stringparam IDENTIFIER $(call quote,$(call localuri,$(call uncompiled,$@)))$(if $(THISREV), --stringparam THISREV $(call quote,$(THISREV)),)$(if $(SRCREV), --stringparam SRCREV $(call quote,$(SRCREV)),) $(call quote,$(BUILDDIR)/transform.xslt) $(call quote,$<) >|$(call quote,$@)
+ $(silent)$(XSLTPROC) --nonet --novalid --nomkdir --nowrite --stringparam METADATA 'metadata' --stringparam BUILDTIME $$($(DATE) -u '+%Y-%m-%dT%H:%M:%SZ') --stringparam IDENTIFIER $(call quote,$(call localuri,$(call uncompiled,$@)))$(if $(THISREV), --stringparam THISREV $(call quote,$(THISREV)),)$(if $(SRCREV), --stringparam SRCREV $(call quote,$(SRCREV)),) --stringparam DESTINATION $(call quote,$*) $(call quote,$(BUILDDIR)/transform.xslt) $(call quote,$<) >|$(call quote,$@)
# Create the final files from the compiled results (or error in the case of recursive ones).
$(call built,$(compilablefiles)) : $(BUILDDIR)/public/% : $(BUILDDIR)/results/% $(THISDIR)/lib/archive2extractor.xslt
<transform
xmlns="http://www.w3.org/1999/XSL/Transform"
xmlns:exsl="http://exslt.org/common"
+ xmlns:exslstr="http://exslt.org/strings"
xmlns:nie="http://www.semanticdesktop.org/ontologies/2007/01/19/nie#"
xmlns:nfo="http://www.semanticdesktop.org/ontologies/2007/03/22/nfo#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:书社="urn:fdc:ladys.computer:20231231:Shu1She4"
xmlns:书社vocab="urn:fdc:ladys.computer:20231231:Shu1She4:vocab:"
- extension-element-prefixes="exsl"
+ extension-element-prefixes="exsl exslstr"
version="1.0"
>
<variable name="builddir" select="//书社vocab:BuildDirectory/@nfo:fileUrl"/>
<template match="//书社vocab:SourceFile[not(nie:interpretedAs/nfo:PlainTextDocument)]" priority="1">
<copy>
<apply-templates select="@*"/>
- <attribute name="书社vocab:destination">
- <value-of select="@书社vocab:path"/>
- </attribute>
<apply-templates select="node()"/>
+ <element name="书社vocab:destination">
+ <value-of select="@书社vocab:path"/>
+ </element>
</copy>
</template>
<template match="//书社vocab:SourceFile[nie:interpretedAs/nfo:PlainTextDocument]" priority="1">
<variable name="parsed" select="document(书社vocab:hasParsedFile/@nfo:fileUrl)"/>
- <variable name="destination-delim" select="concat('/', $parsed/*/@书社:destination, '/')"/>
- <variable name="destination">
- <choose>
- <when test="not(contains($destination-delim, '//') or contains($destination-delim, '/./') or contains($destination-delim, '/../'))">
- <value-of select="$parsed/*/@书社:destination"/>
- </when>
- <otherwise>
- <value-of select="@书社vocab:path"/>
- </otherwise>
- </choose>
+ <variable name="provided-destinations" select="normalize-space($parsed/*/@书社:destination)"/>
+ <variable name="destinations-fragment">
+ <if test="$provided-destinations!=''">
+ <for-each select="exslstr:tokenize($provided-destinations)">
+ <element name="书社vocab:destination">
+ <value-of select="."/>
+ </element>
+ </for-each>
+ </if>
</variable>
<variable name="dependencies-fragment">
<apply-templates select="." mode="书社:dependencies"/>
</variable>
<variable name="dependencies" select="exsl:node-set($dependencies-fragment)"/>
+ <variable name="destinations" select="exsl:node-set($destinations-fragment)/node()"/>
+ <variable name="bad-destinations-fragment">
+ <for-each select="$destinations">
+ <variable name="destination-delim" select="concat('/', ., '/')"/>
+ <if test="contains($destination-delim, '//') or contains($destination-delim, '/./') or contains($destination-delim, '/../')">
+ <copy-of select="."/>
+ </if>
+ </for-each>
+ </variable>
+ <variable name="bad-destinations" select="exsl:node-set($bad-destinations-fragment)/node()"/>
<copy>
<apply-templates select="@*"/>
- <attribute name="书社vocab:destination">
- <value-of select="$destination"/>
- </attribute>
<apply-templates select="node()"/>
<for-each select="$dependencies/书社:dependency">
<书社vocab:hasDependencyOn rdf:resource="{.}"/>
<for-each select="$dependencies/书社:recursive-dependency">
<书社vocab:hasRecursiveDependencyOn rdf:resource="{.}"/>
</for-each>
+ <choose>
+ <when test="not($destinations)">
+ <element name="书社vocab:destination">
+ <value-of select="@书社vocab:path"/>
+ </element>
+ </when>
+ <when test="$bad-destinations">
+ <message terminate="no">
+ <text>Bad destinations: </text>
+ <for-each select="$bad-destinations">
+ <if test="position()>1">
+ <text> </text>
+ </if>
+ <text><</text>
+ <value-of select="."/>
+ <text>></text>
+ </for-each>
+ </message>
+ <element name="书社vocab:destination">
+ <value-of select="@书社vocab:path"/>
+ </element>
+ </when>
+ <otherwise>
+ <for-each select="$destinations">
+ <element name="书社vocab:destination">
+ <value-of select="."/>
+ </element>
+ </for-each>
+ </otherwise>
+ </choose>
</copy>
</template>
<template match="//书社vocab:IncludeFile[nie:interpretedAs/nfo:PlainTextDocument]" priority="1">
<for-each select="$result//书社vocab:SourceFile">
<value-of select="@rdf:about"/>
<text>|</text>
- <value-of select="@书社vocab:destination"/>
+ <for-each select="书社vocab:destination">
+ <if test="position()>1">
+ <text>;</text>
+ </if>
+ <value-of select="."/>
+ </for-each>
<text>
</text>
</for-each>
</exsl:document>