/* This file is part of the db4o object database http://www.db4o.com
Copyright (C) 2004 - 2011 Versant Corporation http://www.versant.com
db4o is free software; you can redistribute it and/or modify it under
the terms of version 3 of the GNU General Public License as published
by the Free Software Foundation.
db4o is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with this program. If not, see http://www.gnu.org/licenses/. */
package com.db4o.internal.marshall;
import com.db4o.foundation.*;
import com.db4o.internal.*;
import com.db4o.internal.activation.*;
import com.db4o.internal.query.processor.*;
import com.db4o.marshall.*;
import com.db4o.typehandlers.*;
/**
* @exclude
*/
public class QueryingReadContext extends AbstractReadContext implements HandlerVersionContext, AspectVersionContext, ObjectIdContext {
private final QCandidates _candidates;
private final int _collectionID;
private final int _handlerVersion;
private IdObjectCollector _collector;
private int _declaredAspectCount;
private int _id;
private QueryingReadContext(Transaction transaction, QCandidates candidates, int handlerVersion, ReadBuffer buffer, int collectionID, IdObjectCollector collector) {
super(transaction, buffer);
_candidates = candidates;
_activationDepth = new LegacyActivationDepth(0);
_collectionID = collectionID;
_handlerVersion = handlerVersion;
_collector = collector;
}
public QueryingReadContext(Transaction transaction, QCandidates candidates, int handlerVersion, ReadBuffer buffer, int collectionID) {
this(transaction, candidates, handlerVersion, buffer, collectionID, new IdObjectCollector());
}
public QueryingReadContext(Transaction transaction, int handlerVersion, ReadBuffer buffer, int id) {
this(transaction, null, handlerVersion, buffer, 0);
_id = id;
}
public QueryingReadContext(Transaction transaction, int handlerVersion, ReadBuffer buffer,
int collectionID, IdObjectCollector collector) {
this(transaction, null, handlerVersion, buffer, collectionID, collector);
}
public int collectionID() {
return _collectionID;
}
public QCandidates candidates(){
return _candidates;
}
public int handlerVersion() {
return _handlerVersion;
}
public void addId(int id) {
_collector.addId(id);
}
public TreeInt ids() {
return _collector.ids();
}
public void add(Object obj) {
int id = getID(obj);
if(id > 0){
addId(id);
return;
}
addObjectWithoutId(obj);
}
private int getID(Object obj) {
return container().getID(transaction(), obj);
}
public void readId(TypeHandler4 handler) {
ObjectID objectID = ObjectID.NOT_POSSIBLE;
try {
int offset = offset();
if(handler instanceof ReadsObjectIds){
objectID = ((ReadsObjectIds)handler).readObjectID(this);
}
if(objectID.isValid()){
addId(objectID._id);
return;
}
if(objectID == ObjectID.NOT_POSSIBLE){
seek(offset);
// FIXME: there's no point in activating the object
// just find its id
// type handlers know how to do it
Object obj = read(handler);
if(obj != null){
int id = (int) getID(obj);
if (id > 0) {
addId(id);
} else {
addObjectWithoutId(obj);
}
}
}
} catch (Exception e) {
// FIXME: Catchall
}
}
private void addObjectWithoutId(Object obj) {
_collector.add(obj);
}
public void skipId(TypeHandler4 handler) {
if(handler instanceof ReadsObjectIds){
((ReadsObjectIds)handler).readObjectID(this);
return;
}
// TODO: Optimize for just doing a seek here.
read(handler);
}
public Iterator4 objectsWithoutId(){
return _collector.objects();
}
public int declaredAspectCount() {
return _declaredAspectCount;
}
public void declaredAspectCount(int count) {
_declaredAspectCount = count;
}
public IdObjectCollector collector(){
return _collector;
}
public int objectId() {
return _id;
}
}