| 
					
				 | 
			
			
				@@ -0,0 +1,120 @@ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+var FilterBaseDocumentSource = module.exports = (function(){ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	// CONSTRUCTOR 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * A base class for filter document sources 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 *  
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @class FilterBaseDocumentSource 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @namespace munge.pipepline.documentsource 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @module munge 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @constructor 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @param	{ExpressionContext}	 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	var klass = module.exports = FilterBaseDocumentSource = function FilterBaseDocumentSource(/*pCtx*/){ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if(arguments.length !== 0) throw new Error("zero args expected"); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		base.call(this); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		this.unstarted = true; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		this.hasNext = false; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		this.pCurrent = null; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}, base = require('./DocumentSource'), proto = klass.prototype = Object.create(base.prototype, {constructor:{value:klass}}); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * Find the next acceptable source document, if there are any left. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @method findNext 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.findNext = function findNext() { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		/* only do this the first time */ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if (this.unstarted) { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.hasNext = !this.pSource.eof(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.unstarted = false; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		} 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		while(this.hasNext) { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			pDocument = this.pSource.getCurrent(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.hasNext = this.pSource.advance(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			if (this.accept(pDocument)) { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+				this.pCurrent = pDocument; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+				return; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			} 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		} 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		this.pCurrent.reset(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * Is the source at EOF? 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 *  
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @method	eof 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.eof = function eof() { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if (this.unstarted) 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.findNext(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		return (this.pCurrent.get() === null); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * Advance the state of the DocumentSource so that it will return the next Document.   
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * The default implementation returns false, after checking for interrupts.  
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * Derived classes can call the default implementation in their own implementations in order to check for interrupts. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 *  
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @method	advance 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @returns	{Boolean}	whether there is another document to fetch, i.e., whether or not getCurrent() will succeed.  This default implementation always returns false. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.advance = function advance() { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		base.prototype.advance.call(this); // check for interrupts 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if (this.unstarted) 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.findNext(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		* This looks weird after the above, but is correct.  Note that calling 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		* getCurrent() when first starting already yields the first document 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		* in the collection.  Calling advance() without using getCurrent() 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		* first will skip over the first item. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		this.findNext(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		return (this.pCurrent.get() !== null); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * some implementations do the equivalent of verify(!eof()) so check eof() first 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 *  
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @method	getCurrent 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	 * @returns	{Document}	the current Document without advancing 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.getCurrent = function getCurrent() { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if (this.unstarted) 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+			this.findNext(); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		if (this.pCurrent.get() === null) throw new Error("This should never happen"); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		return pCurrent; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* Test the given document against the predicate and report if it 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* should be accepted or not. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* @param {object} pDocument the document to test 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* @returns {bool} true if the document matches the filter, false otherwise 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.accept = function accept(pDocument) { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		throw new Error("not implemented"); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	/** 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* Create a BSONObj suitable for Matcher construction. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* This is used after filter analysis has moved as many filters to 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* as early a point as possible in the document processing pipeline. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* See db/Matcher.h and the associated wiki documentation for the 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* format.  This conversion is used to move back to the low-level 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* find() Cursor mechanism. 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	* @param pBuilder the builder to write to 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	**/ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	proto.toMatcherBson = function toMatcherBson(pBuilder) { 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+		throw new Error("not implemented"); 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	}; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+ 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+	return klass; 
			 | 
		
	
		
			
				 | 
				 | 
			
			
				+})(); 
			 |