Configuring a Reference Resolver
This information is helpful if you need to provide a handler for resolving references and obtain the content they reference. For example, suppose the element that has references is ref and the attribute indicating the referenced resource is location. You need to implement a Java extension class for obtaining the referenced resources.
-
Create the class simple.documentation.framework.ReferencesResolver. This class
must implement the ro.sync.ecss.extensions.api.AuthorReferenceResolver interface.
import ro.sync.ecss.extensions.api.AuthorReferenceResolver; import ro.sync.ecss.extensions.api.AuthorAccess; import ro.sync.ecss.extensions.api.node.AttrValue; import ro.sync.ecss.extensions.api.node.AuthorElement; import ro.sync.ecss.extensions.api.node.AuthorNode; public class ReferencesResolver implements AuthorReferenceResolver {
-
The hasReferences method verifies if the handler considers the node to have
references. It takes AuthorNode as an argument that represents the node that will
be verified. The method will return
true
if the node is considered to have references. In the following example, to be a reference, the node must be an element with the name ref and it must have an attribute named location.public boolean hasReferences(AuthorNode node) { boolean hasReferences = false; if (node.getType() == AuthorNode.NODE_TYPE_ELEMENT) { AuthorElement element = (AuthorElement) node; if ("ref".equals(element.getLocalName())) { AttrValue attrValue = element.getAttribute("location"); hasReferences = attrValue != null; } } return hasReferences; }
-
The method getDisplayName returns the display name of the node that contains the
expanded referenced content. It takes AuthorNode as an argument that represents the
node that needs the display name. The referenced content engine will ask this
AuthorReferenceResolver implementation for the display name for each node that is
considered a reference. In the following example, the display name is the value of the
location attribute from the ref element.
public String getDisplayName(AuthorNode node) { String displayName = "ref-fragment"; if (node.getType() == AuthorNode.NODE_TYPE_ELEMENT) { AuthorElement element = (AuthorElement) node; if ("ref".equals(element.getLocalName())) { AttrValue attrValue = element.getAttribute("location"); if (attrValue != null) { displayName = attrValue.getValue(); } } } return displayName; }
-
The method resolveReference resolves the reference of the node and returns a
SAXSource with the parser and its input source. It takes AuthorNode as an
argument that represents the node that needs the reference resolved, the
systemID
of the node, the AuthorAccess with access methods to the Author mode data model and a SAX EntityResolver that resolves resources that are already opened in another editor or resolve resources through the XML Catalog. In the implementation, you need to resolve the reference relative to thesystemID
, and create a parser and an input source over the resolved reference.public SAXSource resolveReference( AuthorNode node, String systemID, AuthorAccess authorAccess, EntityResolver entityResolver) { SAXSource saxSource = null; if (node.getType() == AuthorNode.NODE_TYPE_ELEMENT) { AuthorElement element = (AuthorElement) node; if ("ref".equals(element.getLocalName())) { AttrValue attrValue = element.getAttribute("location"); if (attrValue != null) { String attrStringVal = attrValue.getValue(); try { URL absoluteUrl = new URL(new URL(systemID), authorAccess.getUtilAccess().correctURL(attrStringVal)); InputSource inputSource = entityResolver.resolveEntity(null, absoluteUrl.toString()); if(inputSource == null) { inputSource = new InputSource(absoluteUrl.toString()); } XMLReader xmlReader = authorAccess.newNonValidatingXMLReader(); xmlReader.setEntityResolver(entityResolver); saxSource = new SAXSource(xmlReader, inputSource); } catch (MalformedURLException e) { logger.error(e, e); } catch (SAXException e) { logger.error(e, e); } catch (IOException e) { logger.error(e, e); } } } } return saxSource; }
-
The method getReferenceUniqueID should return a unique identifier for the node
reference. The unique identifier is used to avoid resolving the references recursively.
The method takes AuthorNode as an argument that represents the node with the
reference. In the following example, the unique identifier is the value of the
location attribute from the ref element.
public String getReferenceUniqueID(AuthorNode node) { String id = null; if (node.getType() == AuthorNode.NODE_TYPE_ELEMENT) { AuthorElement element = (AuthorElement) node; if ("ref".equals(element.getLocalName())) { AttrValue attrValue = element.getAttribute("location"); if (attrValue != null) { id = attrValue.getValue(); } } } return id; }
-
The method getReferenceSystemIDshould return the
systemID
of the referenced content. It takes AuthorNode as an argument that represents the node with the reference and the AuthorAccess with access methods to the Author mode data model. For example, the value of the location attribute is used from the ref element and resolved relatively to the XML base URL of the node.public String getReferenceSystemID(AuthorNode node, AuthorAccess authorAccess) { String systemID = null; if (node.getType() == AuthorNode.NODE_TYPE_ELEMENT) { AuthorElement element = (AuthorElement) node; if ("ref".equals(element.getLocalName())) { AttrValue attrValue = element.getAttribute("location"); if (attrValue != null) { String attrStringVal = attrValue.getValue(); try { URL absoluteUrl = new URL(node.getXMLBaseURL(), authorAccess.getUtilAccess().correctURL(attrStringVal)); systemID = absoluteUrl.toString(); } catch (MalformedURLException e) { logger.error(e, e); } } } } return systemID; }
In the listing below, the XML document contains the ref element:
<ref location="referenced.xml">Reference</ref>
When no reference resolver is specified, the reference has the following layout:
When the above implementation is configured, the reference has the expected layout:
Note: The complete source code for framework customization
examples can be found in the oxygen-sample-framework module of the Oxygen
SDK, available as a Maven archetype on the Oxygen XML Author Eclipse plugin website.