Skip to content

Commit

Permalink
Refactored FieldGetter support to be an actual trait
Browse files Browse the repository at this point in the history
  • Loading branch information
darkfrog26 committed Sep 19, 2024
1 parent f42b255 commit d0c0021
Show file tree
Hide file tree
Showing 44 changed files with 117 additions and 88 deletions.
4 changes: 2 additions & 2 deletions all/src/test/scala/spec/AbstractAsyncSpec.scala
Original file line number Diff line number Diff line change
Expand Up @@ -237,8 +237,8 @@ abstract class AbstractAsyncSpec extends AsyncWordSpec with AsyncIOSpec with Mat
object Person extends DocumentModel[Person] with JsonConversion[Person] {
implicit val rw: RW[Person] = RW.gen

val name: F[String] = field("name", _.name)
val age: F[Int] = field.index("age", _.age)
val name: F[String] = field("name", (p: Person) => p.name)
val age: F[Int] = field.index("age", (p: Person) => p.age)
}

object InitialSetupUpgrade extends AsyncDatabaseUpgrade {
Expand Down
2 changes: 1 addition & 1 deletion async/src/main/scala/lightdb/async/AsyncCollection.scala
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package lightdb.async

import cats.effect.IO
import lightdb._
import lightdb.Field._
import lightdb.field.Field._
import lightdb.collection.Collection
import lightdb.doc.{Document, DocumentModel}
import lightdb.transaction.Transaction
Expand Down
5 changes: 3 additions & 2 deletions async/src/main/scala/lightdb/async/AsyncQuery.scala
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,11 @@ import cats.effect.IO
import fabric.Json
import lightdb.aggregate.AggregateFunction
import lightdb._
import lightdb.Field._
import lightdb.field.Field._
import lightdb.collection.Collection
import lightdb.distance.Distance
import lightdb.doc.{Document, DocumentModel}
import lightdb.field.Field
import lightdb.filter._
import lightdb.materialized.MaterializedIndex
import lightdb.spatial.{DistanceAndDoc, Geo}
Expand Down Expand Up @@ -190,7 +191,7 @@ case class AsyncQuery[Doc <: Document[Doc], Model <: DocumentModel[Doc]](collect
.search
.docs
.iterator).map { iterator =>
val grouped = GroupedIterator[Doc, F](iterator, doc => field.get(doc))
val grouped = GroupedIterator[Doc, F](iterator, doc => field.get(doc, field))
fs2.Stream.fromBlockingIterator[IO](grouped, 512)
}
fs2.Stream.force(io)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ package lightdb.async
import cats.effect.IO
import lightdb.doc.{Document, DocumentModel}
import lightdb._
import lightdb.Field._
import lightdb.field.Field._

case class AsyncTransactionConvenience[Doc <: Document[Doc], Model <: DocumentModel[Doc]](collection: AsyncCollection[Doc, Model]) {
def insert(doc: Doc): IO[Doc] = collection.transaction { implicit transaction =>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,9 @@ import lightdb.doc.{Document, DocumentModel, JsonConversion}
import lightdb.sql.SQLConversion
import lightdb.store.StoreManager
import lightdb.upgrade.DatabaseUpgrade
import lightdb.{Field, Id, LightDB}
import lightdb.{Id, LightDB}
import fabric.rw._
import lightdb.field.Field

import java.nio.file.Path
import java.sql.ResultSet
Expand Down
3 changes: 2 additions & 1 deletion core/src/main/scala/lightdb/KeyValue.scala
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,12 @@ package lightdb
import fabric.Json
import fabric.rw._
import lightdb.doc.{Document, DocumentModel, JsonConversion}
import lightdb.field.Field

case class KeyValue(_id: Id[KeyValue], json: Json) extends Document[KeyValue]

object KeyValue extends DocumentModel[KeyValue] with JsonConversion[KeyValue] {
override implicit val rw: RW[KeyValue] = RW.gen

val json: Field[KeyValue, Json] = field("json", _.json)
val json: Field[KeyValue, Json] = field("json", (doc: KeyValue) => doc.json)
}
5 changes: 3 additions & 2 deletions core/src/main/scala/lightdb/Query.scala
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
package lightdb

import fabric.Json
import lightdb.Field._
import lightdb.field.Field._
import lightdb.aggregate.{AggregateFunction, AggregateQuery}
import lightdb.collection.Collection
import lightdb.distance.Distance
import lightdb.doc.{Document, DocumentModel}
import lightdb.error.NonIndexedFieldException
import lightdb.facet.FacetQuery
import lightdb.field.Field
import lightdb.filter._
import lightdb.materialized.MaterializedIndex
import lightdb.spatial.{DistanceAndDoc, Geo}
Expand Down Expand Up @@ -152,7 +153,7 @@ case class Query[Doc <: Document[Doc], Model <: DocumentModel[Doc]](collection:
.search
.docs
.iterator
GroupedIterator[Doc, F](iterator, doc => field.get(doc))
GroupedIterator[Doc, F](iterator, doc => field.get(doc, field))
}
}

Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/SearchResults.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package lightdb

import lightdb.Field._
import lightdb.field.Field._
import lightdb.doc.{Document, DocumentModel}
import lightdb.facet.FacetResult
import lightdb.transaction.Transaction
Expand Down
1 change: 1 addition & 0 deletions core/src/main/scala/lightdb/Sort.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package lightdb

import lightdb.doc.Document
import lightdb.field.Field
import lightdb.spatial.Geo

trait Sort
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package lightdb.aggregate

import fabric.{Json, Str}
import lightdb.Field
import lightdb.doc.Document
import lightdb.field.Field
import lightdb.spatial.Geo

sealed trait AggregateFilter[Doc <: Document[Doc]] {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ package lightdb.aggregate

import fabric.rw._
import lightdb.distance.Distance
import lightdb.Field
import lightdb.doc.Document
import lightdb.field.Field
import lightdb.filter.FilterSupport
import lightdb.materialized.Materializable
import lightdb.spatial.Geo
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package lightdb.aggregate

import fabric.rw._
import lightdb.Field
import lightdb.doc.Document
import lightdb.field.Field

trait AggregateSupport[Doc <: Document[Doc], V] {
this: Field[Doc, V] =>
Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/collection/Collection.scala
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import lightdb.transaction.Transaction
import lightdb.trigger.CollectionTriggers
import lightdb.util.Initializable
import lightdb._
import lightdb.Field._
import lightdb.field.Field._

import java.util.concurrent.ConcurrentHashMap
import scala.jdk.CollectionConverters.IteratorHasAsScala
Expand Down
15 changes: 8 additions & 7 deletions core/src/main/scala/lightdb/doc/DocumentModel.scala
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,8 @@ import lightdb.collection.Collection
import lightdb.facet.FacetValue
import lightdb.filter.FilterBuilder
import lightdb._
import lightdb.Field._
import lightdb.field.{Field, FieldGetter}
import lightdb.field.Field._

import scala.language.implicitConversions

Expand All @@ -14,7 +15,7 @@ trait DocumentModel[Doc <: Document[Doc]] {

private var _fields = List.empty[Field[Doc, _]]

val _id: UniqueIndex[Doc, Id[Doc]] = field.unique("_id", _._id)
val _id: UniqueIndex[Doc, Id[Doc]] = field.unique("_id", (doc: Doc) => doc._id)

def id(value: String = Unique()): Id[Doc] = Id(value)

Expand Down Expand Up @@ -43,18 +44,18 @@ trait DocumentModel[Doc <: Document[Doc]] {
field
}

def apply[V: RW](name: String, get: Doc => V): Field[Doc, V] = {
def apply[V: RW](name: String, get: FieldGetter[Doc, V]): Field[Doc, V] = {
add[V, Field[Doc, V]](Field(name, get))
}

def index[V: RW](name: String, get: Doc => V): Indexed[Doc, V] =
def index[V: RW](name: String, get: FieldGetter[Doc, V]): Indexed[Doc, V] =
add[V, Indexed[Doc, V]](Field.indexed(name, get))

def unique[V: RW](name: String, get: Doc => V): UniqueIndex[Doc, V] =
def unique[V: RW](name: String, get: FieldGetter[Doc, V]): UniqueIndex[Doc, V] =
add[V, UniqueIndex[Doc, V]](Field.unique(name, get))

def tokenized(name: String, get: Doc => String): Tokenized[Doc] =
add[String, Tokenized[Doc]](Field.tokenized(name, doc => get(doc)))
def tokenized(name: String, get: FieldGetter[Doc, String]): Tokenized[Doc] =
add[String, Tokenized[Doc]](Field.tokenized(name, get))

def facet(name: String,
get: Doc => List[FacetValue],
Expand Down
10 changes: 5 additions & 5 deletions core/src/main/scala/lightdb/doc/RecordDocumentModel.scala
Original file line number Diff line number Diff line change
@@ -1,21 +1,21 @@
package lightdb.doc

import lightdb.Field
import fabric.rw._
import lightdb.field.Field

trait RecordDocumentModel[Doc <: RecordDocument[Doc]] extends DocumentModel[Doc] {
protected def indexCreated: Boolean = false
protected def indexModified: Boolean = false

val created: Field[Doc, Long] = if (indexCreated) {
field.index("created", _.created)
field.index("created", (doc: Doc) => doc.created)
} else {
field("created", _.created)
field("created", (doc: Doc) => doc.created)
}

val modified: Field[Doc, Long] = if (indexModified) {
field.index("modified", _.modified)
field.index("modified", (doc: Doc) => doc.modified)
} else {
field("modified", _.modified)
field("modified", (doc: Doc) => doc.modified)
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package lightdb.error

import lightdb.{Field, Query}
import lightdb.Query
import lightdb.field.Field

case class NonIndexedFieldException(query: Query[_, _], fields: List[Field[_, _]]) extends RuntimeException(s"Attempting to execute a query with non-indexed fields in an indexed store mode. Not indexed fields: ${fields.map(_.name).mkString(", ")}")
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/facet/FacetQuery.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package lightdb.facet

import lightdb.Field.FacetField
import lightdb.field.Field.FacetField
import lightdb.doc.Document

case class FacetQuery[Doc <: Document[Doc]](field: FacetField[Doc],
Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/facet/FacetValue.scala
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
package lightdb.facet

import fabric.rw.RW
import fabric.rw._

case class FacetValue(path: List[String])

Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
package lightdb
package lightdb.field

import fabric.{Json, Null, arr, bool, num, str}
import fabric.define.DefType
import fabric.io.JsonParser
import fabric.rw._
import fabric.{Json, Null, arr, bool, num, str}
import lightdb.aggregate.AggregateSupport
import lightdb.distance.Distance
import lightdb.doc.Document
Expand All @@ -14,7 +14,7 @@ import lightdb.materialized.Materializable
import lightdb.spatial.Geo

sealed class Field[Doc <: Document[Doc], V](val name: String,
val get: Doc => V,
val get: FieldGetter[Doc, V],
val getRW: () => RW[V],
val indexed: Boolean = false) extends FilterSupport[V, Doc, Filter[Doc]] with AggregateSupport[Doc, V] with Materializable[Doc, V] {
implicit def rw: RW[V] = getRW()
Expand All @@ -37,7 +37,7 @@ sealed class Field[Doc <: Document[Doc], V](val name: String,

lazy val isSpatial: Boolean = className.exists(_.startsWith("lightdb.spatial.Geo"))

def getJson(doc: Doc): Json = get(doc).json
def getJson(doc: Doc): Json = get(doc, this).json

override def is(value: V): Filter[Doc] = Filter.Equals(name, value)

Expand Down Expand Up @@ -76,9 +76,9 @@ sealed class Field[Doc <: Document[Doc], V](val name: String,
parsed(words, allowLeadingWildcard = matchEndsWith)
}

def opt: Field[Doc, Option[V]] = new Field[Doc, Option[V]](name, doc => Option(get(doc)), () => implicitly[RW[Option[V]]], indexed)
def opt: Field[Doc, Option[V]] = new Field[Doc, Option[V]](name, (doc: Doc) => Option(get(doc, this)), () => implicitly[RW[Option[V]]], indexed)

def list: Field[Doc, List[V]] = new Field[Doc, List[V]](name, doc => List(get(doc)), () => implicitly[RW[List[V]]], indexed)
def list: Field[Doc, List[V]] = new Field[Doc, List[V]](name, (doc: Doc) => List(get(doc, this)), () => implicitly[RW[List[V]]], indexed)

override def distance(from: Geo.Point, radius: Distance): Filter[Doc] =
Filter.Distance(name, from, radius)
Expand All @@ -91,13 +91,13 @@ object Field {

var MaxIn: Option[Int] = Some(1_000)

def apply[Doc <: Document[Doc], V](name: String, get: Doc => V)(implicit getRW: => RW[V]): Field[Doc, V] = new Field[Doc, V](
def apply[Doc <: Document[Doc], V](name: String, get: FieldGetter[Doc, V])(implicit getRW: => RW[V]): Field[Doc, V] = new Field[Doc, V](
name = name,
get = get,
getRW = () => getRW
)

def indexed[Doc <: Document[Doc], V](name: String, get: Doc => V)(implicit getRW: => RW[V]): Indexed[Doc, V] = new Field[Doc, V](
def indexed[Doc <: Document[Doc], V](name: String, get: FieldGetter[Doc, V])(implicit getRW: => RW[V]): Indexed[Doc, V] = new Field[Doc, V](
name = name,
get = get,
getRW = () => getRW,
Expand All @@ -106,7 +106,7 @@ object Field {
override def toString: String = s"Indexed(name = ${this.name})"
}

def tokenized[Doc <: Document[Doc]](name: String, get: Doc => String): Tokenized[Doc] = new Field[Doc, String](
def tokenized[Doc <: Document[Doc]](name: String, get: FieldGetter[Doc, String]): Tokenized[Doc] = new Field[Doc, String](
name = name,
get = get,
getRW = () => stringRW,
Expand All @@ -115,7 +115,7 @@ object Field {
override def toString: String = s"Tokenized(name = ${this.name})"
}

def unique[Doc <: Document[Doc], V](name: String, get: Doc => V)(implicit getRW: => RW[V]): UniqueIndex[Doc, V] = new Field[Doc, V](
def unique[Doc <: Document[Doc], V](name: String, get: FieldGetter[Doc, V])(implicit getRW: => RW[V]): UniqueIndex[Doc, V] = new Field[Doc, V](
name = name,
get = get,
getRW = () => getRW,
Expand All @@ -125,7 +125,7 @@ object Field {
}

def facet[Doc <: Document[Doc]](name: String,
get: Doc => List[FacetValue],
get: FieldGetter[Doc, List[FacetValue]],
hierarchical: Boolean,
multiValued: Boolean,
requireDimCount: Boolean): FacetField[Doc] = new FacetField[Doc](
Expand Down Expand Up @@ -164,7 +164,7 @@ object Field {
trait Tokenized[Doc <: Document[Doc]] extends Indexed[Doc, String]

class FacetField[Doc <: Document[Doc]](name: String,
get: Doc => List[FacetValue],
get: FieldGetter[Doc, List[FacetValue]],
val hierarchical: Boolean,
val multiValued: Boolean,
val requireDimCount: Boolean) extends Field[Doc, List[FacetValue]](name, get, getRW = () => implicitly[RW[List[FacetValue]]], indexed = true) with Indexed[Doc, List[FacetValue]] {
Expand Down
15 changes: 15 additions & 0 deletions core/src/main/scala/lightdb/field/FieldGetter.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package lightdb.field

import lightdb.doc.Document

import scala.language.implicitConversions

trait FieldGetter[Doc <: Document[Doc], V] {
def apply(doc: Doc, field: Field[Doc, V]): V
}

object FieldGetter {
implicit def function2Getter[Doc <: Document[Doc], V](f: Doc => V): FieldGetter[Doc, V] = new FieldGetter[Doc, V] {
override def apply(doc: Doc, field: Field[Doc, V]): V = f(doc)
}
}
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/filter/Filter.scala
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package lightdb.filter

import fabric.{Json, Str}
import lightdb.Field
import lightdb.doc.{Document, DocumentModel}
import lightdb.field.Field
import lightdb.spatial.Geo

sealed trait Filter[Doc <: Document[Doc]] {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
package lightdb.materialized

import fabric.Json
import lightdb.Field
import lightdb.doc.{Document, DocumentModel}
import lightdb.field.Field

case class MaterializedIndex[Doc <: Document[Doc], Model <: DocumentModel[Doc]](json: Json, model: Model) extends Materialized[Doc, Model] {
def get[V](f: Model => Field[Doc, V]): Option[V] = {
Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/store/Conversion.scala
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package lightdb.store

import lightdb.Field
import lightdb.doc.{Document, DocumentModel}
import lightdb.field.Field
import lightdb.materialized.MaterializedIndex
import lightdb.spatial.{DistanceAndDoc, Geo}

Expand Down
2 changes: 1 addition & 1 deletion core/src/main/scala/lightdb/store/InMemoryIndexes.scala
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
package lightdb.store

import lightdb._
import lightdb.Field._
import lightdb.field.Field._
import lightdb.collection.Collection
import lightdb.doc.{Document, DocumentModel}
import lightdb.transaction.Transaction
Expand Down
Loading

0 comments on commit d0c0021

Please sign in to comment.