I wrote in the
introduction to this chapter that the
notions of “extensible” and
“open” are largely independent.
After all you have seen, you might even think that opening a schema
can be an impediment to its extensibility. Let’s say
I have written an open model for the content of the
book
element that allows foreign nodes:
<define name="book-content"> <interleave> <attribute name="id"/> <attribute name="available"/> <element name="isbn"> <ref name="isbn-content"/> </element> <element name="title"> <ref name="title-content"/> </element> <zeroOrMore> <element name="author"> <ref name="author-content"/> </element> </zeroOrMore> <zeroOrMore> <element name="character"> <ref name="character-content"/> </element> </zeroOrMore> <ref name="foreign-nodes"/> </interleave> </define>
or:
book-content = attribute id { text } & attribute available { text } & element isbn { isbn-content } & element title { title-content } & element author { author-content }* & element character { character-content }* & foreign-nodes
I have independently applied the tips for building an extensible
schema (using interleave
and containers) and also
for defining an open schema (referencing a wildcard to allow foreign
nodes). Unfortunately, if my schema is open, it’s no
longer very extensible.
Imagine that I want to add a couple of XLink attributes to define a
link to a web page. I can’t combine this new
attribute with the existing schema using
interleave
. This new attribute would be considered
a duplicate of the implicit definition of
xlink:href
already contained in the
foreign-nodes
wildcard.
The situation is similar for the addition of new elements. If I want
to add an optional
dc:copyright
element, for instance, I can, but the
constraint applied to this element will be in conflict with the lax
definition of dc:copyright
implicitly contained in
the foreign-nodes
wildcard. If the new constraint
isn’t met, RELAX NG will still find a match for a
bogus dc:copyright
element in the wildcard.
Does that mean that open schemas can’t be extensible? Yes and no. While wildcards make open schemas less extensible, I can overcome that problem by extending schemas before opening them. To come back to the example, I’d better write a closed schema first (closed-schema.rng ):
<define name="book-content"> <interleave> <attribute name="id"/> <attribute name="available"/> <element name="isbn"> <ref name="isbn-content"/> </element> <element name="title"> <ref name="title-content"/> </element> <zeroOrMore> <element name="author"> <ref name="author-content"/> </element> </zeroOrMore> <zeroOrMore> <element name="character"> <ref name="character-content"/> </element> </zeroOrMore> </interleave> </define>
or, in the compact syntax, closed-schema.rnc :
book-content = attribute id { text } & attribute available { text } & element isbn { isbn-content } & element title { title-content } & element author { author-content }* & element character { character-content }*
I can then carefully keep this closed schema in a first document and extend it by inclusion and combination to become open:
<include href="closed-schema.rng"/> <define name="book-content" combine="interleave"> <ref name="foreign-nodes"/> </define>
or:
include "closed-schema.rnc" book-content &= foreign-nodes
Applications would then use the open schema (the one produced by
inclusion and combination) and derive the benefit as if the schema
were natively open. The closed-schema would be available to extend
the content model, redefine the foreign-node
wildcard, and open the schema again in different ways.
3.141.197.93