/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* $Id: ResourceSetImpl.java 518460 2007-03-15 03:47:19Z vgritsenko $
*/
package org.apache.xindice.client.xmldb;
import org.apache.xindice.client.xmldb.resources.XMLResourceImpl;
import org.apache.xindice.xml.NodeSource;
import org.apache.xindice.xml.SymbolTable;
import org.apache.xindice.xml.TextWriter;
import org.apache.xindice.xml.dom.DOMCompressor;
import org.apache.xindice.xml.dom.DocumentImpl;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xmldb.api.base.Resource;
import org.xmldb.api.base.ResourceIterator;
import org.xmldb.api.base.ResourceSet;
import org.xmldb.api.base.XMLDBException;
import org.xmldb.api.modules.XMLResource;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
/**
* <code>ResourceSet</code> contains a set of resources as returned from a query
* or other operation.
*
* @version $Revision: 518460 $, $Date: 2007-03-14 23:47:19 -0400 (Wed, 14 Mar 2007) $
*/
public class ResourceSetImpl implements ResourceSet {
public static final String RESOURCE_SET_NS = "http://www.xmldb.org/xapi/ResourceSet";
protected List resources;
protected org.xmldb.api.base.Collection collection;
private SymbolTable symbols;
private byte[] bytes;
public ResourceSetImpl(org.xmldb.api.base.Collection collection,
Document doc) throws XMLDBException {
this.collection = collection;
if (doc != null) {
initResources(doc);
} else {
resources = Collections.synchronizedList(new ArrayList());
}
}
public ResourceSetImpl(org.xmldb.api.base.Collection collection,
SymbolTable symbols, byte[] bytes) throws XMLDBException {
this.collection = collection;
this.symbols = symbols;
this.bytes = bytes;
initResources(new DocumentImpl(bytes, symbols, null));
}
protected void initResources(Document document) throws XMLDBException {
NodeList nodes = document.getDocumentElement().getChildNodes();
this.resources = Collections.synchronizedList(new ArrayList(nodes.getLength()));
int i = 0;
while (i < nodes.getLength()) {
Node n = nodes.item(i);
String documentId = null;
if (n instanceof Element) {
documentId = ((Element) n).getAttributeNS(NodeSource.SOURCE_NS, NodeSource.SOURCE_KEY);
}
XMLResource resource;
if (bytes != null) {
DocumentImpl doc = new DocumentImpl();
doc.setSymbols(symbols);
doc.importNode(n, true);
doc.appendChild(n);
byte[] b = DOMCompressor.compress(doc, symbols);
resource = new XMLResourceImpl(null, documentId, collection, symbols, b);
} else {
resource = new XMLResourceImpl(null, documentId, collection, TextWriter.toString(n));
}
i++;
resources.add(resource);
}
}
/**
* Returns an iterator over all <code>Resource</code> instances stored in
* the set.
*
* @return a ResourceIterator over all <code>Resource</code> instances in the
* set.
* @exception XMLDBException
*/
public ResourceIterator getIterator() throws XMLDBException {
return new ResourceIteratorImpl(resources);
}
/**
* Returns the <code>Resource</code> instance stored at the index specified
* by <code>index</code>.
*
* @param index the index of the resource to retrieve.
* @return the <code>Resource</code> instance.
* @exception XMLDBException
*/
public Resource getResource(long index) throws XMLDBException {
return (XMLResource) resources.get((int) index);
}
/**
* Returns the number of resources contained in the set.
*
* @return the number of <code>Resource</code> instances in the set.
* @exception XMLDBException
*/
public long getSize() throws XMLDBException {
return resources.size();
}
/**
* Adds a <code>Resource</code> instance to the set.
*
* @exception XMLDBException
*/
public void addResource(Resource res) throws XMLDBException {
resources.add(res);
}
/**
* Removes all <code>Resource</code> instances from the set.
*
* @exception XMLDBException
*/
public void clear() throws XMLDBException {
resources.clear();
}
/**
* Removes the <code>Resource</code> located at <code>index</code> from the
* set.
*
* @param index The index of the <code>Resource</code> instance to remove.
* @exception XMLDBException
*/
public void removeResource(long index) throws XMLDBException {
resources.remove((int) index);
}
/**
* Returns a <code>Resource</code> containing an XML representation of all
* resources stored in the set.
*
* @return A <code>Resource</code> instance containing an XML representation
* of all set members.
* @exception XMLDBException
*/
public Resource getMembersAsResource() throws XMLDBException {
// This impl works but it would be nice if we just got the result set from
// the server in this format instead of having to build it. Right now it's
// pretty innefficient
Document doc = new DocumentImpl();
Element set = doc.createElementNS(RESOURCE_SET_NS, "xapi:resourceSet");
set.setAttributeNS(RESOURCE_SET_NS, "xapi:collectionURI",
"xmldb:xindice://" + ((XindiceCollection) collection).getCanonicalName());
set.setAttribute("xmlns:xapi", RESOURCE_SET_NS);
doc.appendChild(set);
int i = 0;
while (i < resources.size()) {
XMLResource res = (XMLResource) resources.get(i);
Element resource = doc.createElementNS(RESOURCE_SET_NS,
"xapi:resource");
resource.setAttributeNS(RESOURCE_SET_NS, "xapi:documentID",
res.getDocumentId());
resource.appendChild(doc.importNode(
((Document) res.getContentAsDOM()).getDocumentElement(), true));
set.appendChild(resource);
i++;
}
return new XMLResourceImpl(null, null, collection, TextWriter.toString(doc));
}
}