Permalink
Browse files

General cleanup, no semantic changes

  • Loading branch information...
jorgeortiz85 committed Feb 21, 2012
1 parent a5a0d68 commit 6e5f95f8d555c4b4ea22f9aaa65f3e80341f1bf7
@@ -4,7 +4,7 @@ package com.foursquare.rogue
import com.foursquare.rogue.Rogue.{GenericBaseQuery, GenericQuery}
import scala.collection.immutable.ListMap
import net.liftweb.common.Loggable
-import net.liftweb.mongodb.record._
+import net.liftweb.mongodb.record.MongoRecord
import net.liftweb.util.Props
/**
@@ -0,0 +1,216 @@
+// Copyright 2011 Foursquare Labs Inc. All Rights Reserved.
+
+package com.foursquare.rogue
+
+import com.foursquare.rogue.MongoHelpers.AndCondition
+import net.liftweb.mongodb.record.{MongoRecord, MongoMetaRecord}
+import net.liftweb.record.Field
+
+// ***************************************************************************
+// *** Indexes
+// ***************************************************************************
+
+class IndexEnforcerBuilder[M <: MongoRecord[M]](meta: M with MongoMetaRecord[M] with IndexedRecord[M]) {
+ type MetaM = M with MongoMetaRecord[M] with IndexedRecord[M]
+
+ def useIndex[F1 <: Field[_, M]](i: MongoIndex1[M, F1, _]): IndexEnforcer1[M, NoIndexInfo, F1, HasntUsedIndex] = {
+ new IndexEnforcer1[M, NoIndexInfo, F1, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+
+ def useIndex[F1 <: Field[_, M], F2 <: Field[_, M]](i: MongoIndex2[M, F1, _, F2, _]): IndexEnforcer2[M, NoIndexInfo, F1, F2, HasntUsedIndex] = {
+ new IndexEnforcer2[M, NoIndexInfo, F1, F2, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+
+ def useIndex[F1 <: Field[_, M], F2 <: Field[_, M], F3 <: Field[_, M]](i: MongoIndex3[M, F1, _, F2, _, F3, _]): IndexEnforcer3[M, NoIndexInfo, F1, F2, F3, HasntUsedIndex] = {
+ new IndexEnforcer3[M, NoIndexInfo, F1, F2, F3, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+
+ def useIndex[F1 <: Field[_, M], F2 <: Field[_, M], F3 <: Field[_, M], F4 <: Field[_, M]](i: MongoIndex4[M, F1, _, F2, _, F3, _, F4, _]): IndexEnforcer4[M, NoIndexInfo, F1, F2, F3, F4, HasntUsedIndex] = {
+ new IndexEnforcer4[M, NoIndexInfo, F1, F2, F3, F4, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+
+ def useIndex[F1 <: Field[_, M], F2 <: Field[_, M], F3 <: Field[_, M], F4 <: Field[_, M], F5 <: Field[_, M]](i: MongoIndex5[M, F1, _, F2, _, F3, _, F4, _, F5, _]): IndexEnforcer5[M, NoIndexInfo, F1, F2, F3, F4, F5, HasntUsedIndex] = {
+ new IndexEnforcer5[M, NoIndexInfo, F1, F2, F3, F4, F5, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+
+ def useIndex[F1 <: Field[_, M], F2 <: Field[_, M], F3 <: Field[_, M], F4 <: Field[_, M], F5 <: Field[_, M], F6 <: Field[_, M]](i: MongoIndex6[M, F1, _, F2, _, F3, _, F4, _, F5, _, F6, _]): IndexEnforcer6[M, NoIndexInfo, F1, F2, F3, F4, F5, F6, HasntUsedIndex] = {
+ new IndexEnforcer6[M, NoIndexInfo, F1, F2, F3, F4, F5, F6, HasntUsedIndex](meta, new BaseQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause](meta, None, None, None, None, None, AndCondition(Nil, None), None, None, None))
+ }
+}
+
+case class IndexEnforcer1[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = {
+ q.where(_ => clause(f1Func(meta)))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = {
+ q.and(_ => clause(f1Func(meta)))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = {
+ q.iscan(_ => clause(f1Func(meta)))
+ }
+
+ def rangeScan(f1Func: M => F1)(implicit ev: UsedInd <:< UsedIndex): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = q
+}
+
+case class IndexEnforcer2[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ F2 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer1[M, Index, F2, UsedIndex] = {
+ new IndexEnforcer1[M, Index, F2, UsedIndex](meta, q.where(_ => clause(f1Func(meta))))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer1[M, Index, F2, UsedIndex] = {
+ new IndexEnforcer1[M, Index, F2, UsedIndex](meta, q.and(_ => clause(f1Func(meta))))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): IndexEnforcer1[M, IndexScan, F2, UsedIndex] = {
+ new IndexEnforcer1[M, IndexScan, F2, UsedIndex](meta, q.iscan(_ => clause(f1Func(meta))))
+ }
+
+ def rangeScan(f1Func: M => F1)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer1[M, IndexScan, F2, UsedIndex] = {
+ new IndexEnforcer1[M, IndexScan, F2, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2)(implicit ev: UsedInd <:< UsedIndex): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = q
+}
+
+case class IndexEnforcer3[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ F2 <: Field[_, M],
+ F3 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer2[M, Index, F2, F3, UsedIndex] = {
+ new IndexEnforcer2[M, Index, F2, F3, UsedIndex](meta, q.where(_ => clause(f1Func(meta))))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer2[M, Index, F2, F3, UsedIndex] = {
+ new IndexEnforcer2[M, Index, F2, F3, UsedIndex](meta, q.and(_ => clause(f1Func(meta))))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): IndexEnforcer2[M, IndexScan, F2, F3, UsedIndex] = {
+ new IndexEnforcer2[M, IndexScan, F2, F3, UsedIndex](meta, q.iscan(_ => clause(f1Func(meta))))
+ }
+
+ def rangeScan(f1Func: M => F1)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer2[M, IndexScan, F2, F3, UsedIndex] = {
+ new IndexEnforcer2[M, IndexScan, F2, F3, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer1[M, IndexScan, F3, UsedIndex] = {
+ new IndexEnforcer1[M, IndexScan, F3, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2, f3Func: M => F3)(implicit ev: UsedInd <:< UsedIndex): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = q
+}
+
+case class IndexEnforcer4[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ F2 <: Field[_, M],
+ F3 <: Field[_, M],
+ F4 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer3[M, Index, F2, F3, F4, UsedIndex] = {
+ new IndexEnforcer3[M, Index, F2, F3, F4, UsedIndex](meta, q.where(_ => clause(f1Func(meta))))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer3[M, Index, F2, F3, F4, UsedIndex] = {
+ new IndexEnforcer3[M, Index, F2, F3, F4, UsedIndex](meta, q.and(_ => clause(f1Func(meta))))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): IndexEnforcer3[M, IndexScan, F2, F3, F4, UsedIndex] = {
+ new IndexEnforcer3[M, IndexScan, F2, F3, F4, UsedIndex](meta, q.iscan(_ => clause(f1Func(meta))))
+ }
+
+ def rangeScan(f1Func: M => F1)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer3[M, IndexScan, F2, F3, F4, UsedIndex] = {
+ new IndexEnforcer3[M, IndexScan, F2, F3, F4, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer2[M, IndexScan, F3, F4, UsedIndex] = {
+ new IndexEnforcer2[M, IndexScan, F3, F4, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2, f3Func: M => F3)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer1[M, IndexScan, F4, UsedIndex] = {
+ new IndexEnforcer1[M, IndexScan, F4, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2, f3Func: M => F3, f4Func: M => F4)(implicit ev: UsedInd <:< UsedIndex): AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause] = q
+}
+
+case class IndexEnforcer5[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ F2 <: Field[_, M],
+ F3 <: Field[_, M],
+ F4 <: Field[_, M],
+ F5 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer4[M, Index, F2, F3, F4, F5, UsedIndex] = {
+ new IndexEnforcer4[M, Index, F2, F3, F4, F5, UsedIndex](meta, q.where(_ => clause(f1Func(meta))))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer4[M, Index, F2, F3, F4, F5, UsedIndex] = {
+ new IndexEnforcer4[M, Index, F2, F3, F4, F5, UsedIndex](meta, q.and(_ => clause(f1Func(meta))))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): IndexEnforcer4[M, IndexScan, F2, F3, F4, F5, UsedIndex] = {
+ new IndexEnforcer4[M, IndexScan, F2, F3, F4, F5, UsedIndex](meta, q.iscan(_ => clause(f1Func(meta))))
+ }
+
+ def rangeScan(f1Func: M => F1)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer4[M, IndexScan, F2, F3, F4, F5, UsedIndex] = {
+ new IndexEnforcer4[M, IndexScan, F2, F3, F4, F5, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer3[M, IndexScan, F3, F4, F5, UsedIndex] = {
+ new IndexEnforcer3[M, IndexScan, F3, F4, F5, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2, f3Func: M => F3)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer2[M, IndexScan, F4, F5, UsedIndex] = {
+ new IndexEnforcer2[M, IndexScan, F4, F5, UsedIndex](meta, q)
+ }
+
+ def rangeScan(f1Func: M => F1, f2Func: M => F2, f3Func: M => F3, f4Func: M => F4)(implicit ev: UsedInd <:< UsedIndex): IndexEnforcer1[M, IndexScan, F5, UsedIndex] = {
+ new IndexEnforcer1[M, IndexScan, F5, UsedIndex](meta, q)
+ }
+}
+
+case class IndexEnforcer6[M <: MongoRecord[M],
+ Ind <: MaybeIndexed,
+ F1 <: Field[_, M],
+ F2 <: Field[_, M],
+ F3 <: Field[_, M],
+ F4 <: Field[_, M],
+ F5 <: Field[_, M],
+ F6 <: Field[_, M],
+ UsedInd <: MaybeUsedIndex](meta: M with MongoMetaRecord[M],
+ q: AbstractQuery[M, M, Unordered, Unselected, Unlimited, Unskipped, HasNoOrClause]) {
+ def where[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer5[M, Index, F2, F3, F4, F5, F6, UsedIndex] = {
+ new IndexEnforcer5[M, Index, F2, F3, F4, F5, F6, UsedIndex](meta, q.where(_ => clause(f1Func(meta))))
+ }
+
+ def and[F, ClauseInd <: Indexable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd])(implicit ev: Ind <:< Indexable): IndexEnforcer5[M, Index, F2, F3, F4, F5, F6, UsedIndex] = {
+ new IndexEnforcer5[M, Index, F2, F3, F4, F5, F6, UsedIndex](meta, q.and(_ => clause(f1Func(meta))))
+ }
+
+ def iscan[F, ClauseInd <: IndexScannable](f1Func: M => F1)(clause: F1 => IndexableQueryClause[F, ClauseInd]): IndexEnforcer5[M, IndexScan, F2, F3, F4, F5, F6, UsedIndex] = {
+ new IndexEnforcer5[M, IndexScan, F2, F3, F4, F5, F6, UsedIndex](meta, q.iscan(_ => clause(f1Func(meta))))
+ }
+
+ // IndexEnforcer6 doesn't have methods to scan any later fields in the index
+ // because there's no way that we got here via an iscan on a bigger index --
+ // there are no bigger indexes. We require that the first column on the index
+ // gets used.
+}
+
@@ -3,8 +3,8 @@
package com.foursquare.rogue
import com.mongodb.{BasicDBObjectBuilder, Bytes, DBObject, DBCursor, WriteConcern}
-import net.liftweb.mongodb._
-import net.liftweb.mongodb.record._
+import net.liftweb.mongodb.MongoDB
+import net.liftweb.mongodb.record.MongoRecord
import scala.collection.immutable.ListMap
object MongoHelpers extends Rogue {
@@ -0,0 +1,47 @@
+// Copyright 2011 Foursquare Labs Inc. All Rights Reserved.
+
+package com.foursquare.rogue
+
+// ***************************************************************************
+// *** Phantom types
+// ***************************************************************************
+
+abstract sealed class MaybeOrdered
+abstract sealed class Ordered extends MaybeOrdered
+abstract sealed class Unordered extends MaybeOrdered
+
+abstract sealed class MaybeSelected
+abstract sealed class Selected extends MaybeSelected
+abstract sealed class Unselected extends MaybeSelected
+
+abstract sealed class MaybeLimited
+abstract sealed class Limited extends MaybeLimited
+abstract sealed class Unlimited extends MaybeLimited
+
+abstract sealed class MaybeSkipped
+abstract sealed class Skipped extends MaybeSkipped
+abstract sealed class Unskipped extends MaybeSkipped
+
+abstract sealed class MaybeHasOrClause
+abstract sealed class HasOrClause extends MaybeHasOrClause
+abstract sealed class HasNoOrClause extends MaybeHasOrClause
+
+sealed trait MaybeIndexed
+sealed trait Indexable extends MaybeIndexed
+sealed trait IndexScannable extends MaybeIndexed
+
+abstract sealed class NoIndexInfo extends Indexable with IndexScannable
+abstract sealed class Index extends Indexable with IndexScannable
+abstract sealed class PartialIndexScan extends IndexScannable
+abstract sealed class IndexScan extends IndexScannable
+abstract sealed class DocumentScan extends MaybeIndexed
+
+case object NoIndexInfo extends NoIndexInfo
+case object Index extends Index
+case object PartialIndexScan extends PartialIndexScan
+case object IndexScan extends IndexScan
+case object DocumentScan extends DocumentScan
+
+abstract sealed class MaybeUsedIndex
+abstract sealed class UsedIndex extends MaybeUsedIndex
+abstract sealed class HasntUsedIndex extends MaybeUsedIndex
Oops, something went wrong.

0 comments on commit 6e5f95f

Please sign in to comment.