com.ctc.wstx.evt.MergedNsContext Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of woodstox-core Show documentation
Show all versions of woodstox-core Show documentation
Woodstox is a high-performance XML processor that implements Stax (JSR-173),
SAX2 and Stax2 APIs
The newest version!
package com.ctc.wstx.evt;
import java.io.IOException;
import java.io.Writer;
import java.util.*;
import javax.xml.XMLConstants;
import javax.xml.namespace.NamespaceContext;
import javax.xml.stream.XMLStreamException;
import javax.xml.stream.XMLStreamWriter;
import javax.xml.stream.events.Namespace;
import com.ctc.wstx.util.BaseNsContext;
import com.ctc.wstx.util.DataUtil;
/**
* Hierarchic {@link NamespaceContext} implementation used when constructing
* event and namespace information explicitly via
* {@link javax.xml.stream.XMLEventFactory},
* not by a stream reader.
*
* TODO:
*
* - Figure out a way to check for namespace masking; tricky but not
* impossible to determine
*
*
*/
public class MergedNsContext
extends BaseNsContext
{
final NamespaceContext mParentCtxt;
/**
* List of {@link Namespace} instances.
*/
final List mNamespaces;
Map mNsByPrefix = null;
Map mNsByURI = null;
protected MergedNsContext(NamespaceContext parentCtxt, List localNs)
{
mParentCtxt = parentCtxt;
if (localNs == null){
mNamespaces = Collections.emptyList();
} else {
mNamespaces = localNs;
}
}
public static BaseNsContext construct(NamespaceContext parentCtxt,
List localNs)
{
return new MergedNsContext(parentCtxt, localNs);
}
/*
/////////////////////////////////////////////
// NamespaceContext API
/////////////////////////////////////////////
*/
@Override
public String doGetNamespaceURI(String prefix)
{
// Note: base class checks for 'known' problems and prefixes:
if (mNsByPrefix == null) {
mNsByPrefix = buildByPrefixMap();
}
Namespace ns = mNsByPrefix.get(prefix);
if (ns == null && mParentCtxt != null) {
return mParentCtxt.getNamespaceURI(prefix);
}
return (ns == null) ? null : ns.getNamespaceURI();
}
@Override
public String doGetPrefix(String nsURI)
{
// Note: base class checks for 'known' problems and prefixes:
if (mNsByURI == null) {
mNsByURI = buildByNsURIMap();
}
Namespace ns = mNsByURI.get(nsURI);
if (ns == null && mParentCtxt != null) {
return mParentCtxt.getPrefix(nsURI);
}
return (ns == null) ? null : ns.getPrefix();
}
@Override
public Iterator doGetPrefixes(String nsURI)
{
// Note: base class checks for 'known' problems and prefixes:
ArrayList l = null;
for (int i = 0, len = mNamespaces.size(); i < len; ++i) {
Namespace ns = mNamespaces.get(i);
String uri = ns.getNamespaceURI();
if (uri == null) {
uri = "";
}
if (uri.equals(nsURI)) {
if (l == null) {
l = new ArrayList();
}
String prefix = ns.getPrefix();
l.add((prefix == null) ? "" : prefix);
}
}
if (mParentCtxt != null) {
@SuppressWarnings("unchecked")
Iterator it = /*(Iterator)*/mParentCtxt.getPrefixes(nsURI);
if (l == null) {
return it;
}
while (it.hasNext()) {
l.add(it.next());
}
}
if (l == null) {
return DataUtil.emptyIterator();
}
return l.iterator();
}
/*
/////////////////////////////////////////////
// Extended API
/////////////////////////////////////////////
*/
/**
* Method that returns information about namespace definition declared
* in this scope; not including ones declared in outer scopes.
*/
@Override
public Iterator getNamespaces() {
return mNamespaces.iterator();
}
@Override
public void outputNamespaceDeclarations(Writer w) throws IOException
{
for (int i = 0, len = mNamespaces.size(); i < len; ++i) {
Namespace ns = mNamespaces.get(i);
w.write(' ');
w.write(XMLConstants.XMLNS_ATTRIBUTE);
if (!ns.isDefaultNamespaceDeclaration()) {
w.write(':');
w.write(ns.getPrefix());
}
w.write("=\"");
w.write(ns.getNamespaceURI());
w.write('"');
}
}
/**
* Method called by the matching start element class to
* output all namespace declarations active in current namespace
* scope, if any.
*/
@Override
public void outputNamespaceDeclarations(XMLStreamWriter w) throws XMLStreamException
{
for (int i = 0, len = mNamespaces.size(); i < len; ++i) {
Namespace ns = mNamespaces.get(i);
if (ns.isDefaultNamespaceDeclaration()) {
w.writeDefaultNamespace(ns.getNamespaceURI());
} else {
w.writeNamespace(ns.getPrefix(), ns.getNamespaceURI());
}
}
}
/*
/////////////////////////////////////////////
// Private methods:
/////////////////////////////////////////////
*/
private Map buildByPrefixMap()
{
int len = mNamespaces.size();
if (len == 0) {
return Collections.emptyMap();
}
LinkedHashMap m = new LinkedHashMap(1 + len + (len>>1));
for (int i = 0; i < len; ++i) {
Namespace ns = mNamespaces.get(i);
String prefix = ns.getPrefix();
if (prefix == null) { // shouldn't happen but...
prefix = "";
}
m.put(prefix, ns);
}
return m;
}
private Map buildByNsURIMap()
{
int len = mNamespaces.size();
if (len == 0) {
return Collections.emptyMap();
}
LinkedHashMap m = new LinkedHashMap(1 + len + (len>>1));
for (int i = 0; i < len; ++i) {
Namespace ns = mNamespaces.get(i);
String uri = ns.getNamespaceURI();
if (uri == null) { // shouldn't happen but...
uri = "";
}
m.put(uri, ns);
}
return m;
}
}