How to exclude namespace (re)declarations in Schematron Quick fixes
This should cover W3C XML Schema, Relax NG and DTD related problems.
-
- Posts: 3
- Joined: Wed Jul 09, 2025 1:35 pm
How to exclude namespace (re)declarations in Schematron Quick fixes
I'm working with XML documents that have the relevant namespaces declared solely on the root element, and (for mostly stylistic reasons) I'd like to retain that.
When a schematron quick fix containing an xsl template operates on a fragment within the document, the XSLT processor will insert a (redundant) xmlns="..." declaration onto descendants of the element being replaced, thus ignoring the declarations already present in the broader, original document context.
Are there any methods that can be used to avoid this behaviour?
Here's a simplified example to reproduce the behaviour:
Input XML:
Schematron:
Output after fix:
Note the xmlns:xlink="http://www.w3.org/1999/xlink" declaration on the new title element.
I'm working with oXygen XML Editor version 26.
When a schematron quick fix containing an xsl template operates on a fragment within the document, the XSLT processor will insert a (redundant) xmlns="..." declaration onto descendants of the element being replaced, thus ignoring the declarations already present in the broader, original document context.
Are there any methods that can be used to avoid this behaviour?
Here's a simplified example to reproduce the behaviour:
Input XML:
Code: Select all
<?xml version="1.0" encoding="UTF-8"?>
<article xmlns:xlink="http://www.w3.org/1999/xlink">
<fig>
<caption>
<p>This is the title <ext-link ext-link-type="uri" xlink:href="https://schematron.com/">link</ext-link>.</p>
<p>This is the caption.</p>
</caption>
</fig>
</article>
Code: Select all
<?xml version="1.0" encoding="UTF-8"?>
<schema
xmlns="http://purl.oclc.org/dsdl/schematron"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:sqf="http://www.schematron-quickfix.com/validator/process"
queryBinding="xslt3">
<xsl:template match="." mode="customCopy">
<xsl:copy copy-namespaces="no">
<xsl:apply-templates select="*|@*|text()|comment()|processing-instruction()" mode="customCopy"/>
</xsl:copy>
</xsl:template>
<sqf:fixes>
<sqf:fix id="replace-p-to-title">
<sqf:description>
<sqf:title>Change the p to title</sqf:title>
</sqf:description>
<sqf:replace match="./p[1]">
<xsl:element name="title">
<xsl:apply-templates select="node()|comment()|processing-instruction()" mode="customCopy"/>
</xsl:element>
</sqf:replace>
</sqf:fix>
</sqf:fixes>
<pattern id="fig">
<rule context="fig/caption" id="fig-caption-checks">
<report test="not(title) and (count(p) gt 1)"
role="warning"
sqf:fix="replace-p-to-title"
id="fig-caption-1">Caption for fig doesn't have a title, but there are mutliple paragraphs. Is the first paragraph actually the title?</report>
</rule>
</pattern>
</schema>
Code: Select all
<?xml version="1.0" encoding="UTF-8"?>
<article xmlns:xlink="http://www.w3.org/1999/xlink">
<fig>
<caption>
<title>This is the title <ext-link ext-link-type="uri" xlink:href="https://schematron.com/" xmlns:xlink="http://www.w3.org/1999/xlink">link</ext-link>.</title>
<p>This is the caption.</p>
</caption>
</fig>
</article>
I'm working with oXygen XML Editor version 26.
-
- Posts: 391
- Joined: Thu Jul 01, 2004 12:29 pm
Re: How to exclude namespace (re)declarations in Schematron Quick fixes
This is not an Oxygen issue; it's more of an XSLT issue. The copy template will always add the namespace declaration to the result element. I don't think there's any way to avoid this. If you create an XSLT with a copy template, you will get the same result.
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xlink="http://www.w3.org/1999/xlink" exclude-result-prefixes="xlink" version="3.0">
<xsl:template match="p">
<xsl:element name="title">
<xsl:apply-templates mode="customCopy" select="node()"/>
</xsl:element>
</xsl:template>
<xsl:template match="node() | @*" mode="customCopy">
<xsl:copy copy-namespaces="false">
<xsl:apply-templates select="node() | @*" mode="customCopy"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
In Oxygen, you can avoid adding this namespace declaration if you use the quick fix option in the Author page. In this case, post-processing is performed to remove the namespace declaration when the namespace is already declared on the root element.
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xlink="http://www.w3.org/1999/xlink" exclude-result-prefixes="xlink" version="3.0">
<xsl:template match="p">
<xsl:element name="title">
<xsl:apply-templates mode="customCopy" select="node()"/>
</xsl:element>
</xsl:template>
<xsl:template match="node() | @*" mode="customCopy">
<xsl:copy copy-namespaces="false">
<xsl:apply-templates select="node() | @*" mode="customCopy"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
In Oxygen, you can avoid adding this namespace declaration if you use the quick fix option in the Author page. In this case, post-processing is performed to remove the namespace declaration when the namespace is already declared on the root element.
Octavian Nadolu
<oXygen/> XML Editor
http://www.oxygenxml.com
<oXygen/> XML Editor
http://www.oxygenxml.com
-
- Posts: 3
- Joined: Wed Jul 09, 2025 1:35 pm
Re: How to exclude namespace (re)declarations in Schematron Quick fixes
That makes sense, and good to know about the Author mode trick.
Sounds like I have a couple of options (use author mode and/or do my own post-processing), or I can just stop being so picky.
Thanks very much for your time looking into this.
Sounds like I have a couple of options (use author mode and/or do my own post-processing), or I can just stop being so picky.
Thanks very much for your time looking into this.
-
- Site Admin
- Posts: 2096
- Joined: Thu Jan 09, 2003 2:58 pm
Re: How to exclude namespace (re)declarations in Schematron Quick fixes
Hi Fred,
I discussed with Octavian to see what can be done and it turns out we do perform a namespace normalization in the sense of removing unnecessary namespace declarations, but only on the root element that is inserted, not deep on any element. Thus, if you add the in-scope namespaces on the element that you want to insert, that will solve your problem
. The namespaces will not be declared again inside the fragment, because they are already declared on the root element of the fragment, and the ones from the root element will be normalized on insertion.
So, instead of
--- use -->
Best Regards,
George
I discussed with Octavian to see what can be done and it turns out we do perform a namespace normalization in the sense of removing unnecessary namespace declarations, but only on the root element that is inserted, not deep on any element. Thus, if you add the in-scope namespaces on the element that you want to insert, that will solve your problem
So, instead of
Code: Select all
<sqf:replace match="./p[1]" >
<xsl:element name="title">
<xsl:apply-templates select="node() | comment() | processing-instruction()"
mode="customCopy"/>
</xsl:element>
</sqf:replace>
--- use -->
Code: Select all
<sqf:replace match="./p[1]" >
<xsl:element name="title">
<xsl:copy-of select="namespace-node()"/>
<xsl:apply-templates select="node() | comment() | processing-instruction()"
mode="customCopy"/>
</xsl:element>
</sqf:replace>
Best Regards,
George
George Cristian Bina
-
- Posts: 3
- Joined: Wed Jul 09, 2025 1:35 pm
Re: How to exclude namespace (re)declarations in Schematron Quick fixes
Hi George,
Many thanks for this - very helpful, it solves my use-case. After scratching my head for a while, not understanding why it worked in the sample file but not in my real implementation, I realised that the inclusion of schematron namespace declaration interfered:
Removing this from the schema (and using a wildcard prefix where required) solved the issue. Just mentioning in case this is helpful for anyone else.
Thanks once again for your time in helping me with this.
All the best,
Fred
Many thanks for this - very helpful, it solves my use-case. After scratching my head for a while, not understanding why it worked in the sample file but not in my real implementation, I realised that the inclusion of schematron namespace declaration interfered:
Code: Select all
<schema xmlns="http://purl.oclc.org/dsdl/schematron">
...
<ns uri="http://www.w3.org/1999/xlink" prefix="xlink"/>
...
Thanks once again for your time in helping me with this.
All the best,
Fred
Jump to
- Oxygen XML Editor/Author/Developer
- ↳ Feature Request
- ↳ Common Problems
- ↳ DITA (Editing and Publishing DITA Content)
- ↳ Artificial Intelligence (AI Positron Assistant add-on)
- ↳ SDK-API, Frameworks - Document Types
- ↳ DocBook
- ↳ TEI
- ↳ XHTML
- ↳ Other Issues
- Oxygen XML Web Author
- ↳ Feature Request
- ↳ Common Problems
- Oxygen Content Fusion
- ↳ Feature Request
- ↳ Common Problems
- Oxygen JSON Editor
- ↳ Feature Request
- ↳ Common Problems
- Oxygen PDF Chemistry
- ↳ Feature Request
- ↳ Common Problems
- Oxygen Feedback
- ↳ Feature Request
- ↳ Common Problems
- Oxygen XML WebHelp
- ↳ Feature Request
- ↳ Common Problems
- XML
- ↳ General XML Questions
- ↳ XSLT and FOP
- ↳ XML Schemas
- ↳ XQuery
- NVDL
- ↳ General NVDL Issues
- ↳ oNVDL Related Issues
- XML Services Market
- ↳ Offer a Service