Last active
February 2, 2018 00:00
-
-
Save steinybot/8c3986dd15112c7811a14bc001650042 to your computer and use it in GitHub Desktop.
Understanding Slick Projections
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
case class Inner(a: String, b: Int) | |
case class Outer(a: String, i: Inner) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class InnerTable(tag: Tag) extends Table[Inner](tag, "inner") { | |
type UnpackedA = String | |
type UnpackedB = Int | |
type PackedA = Rep[UnpackedA] | |
type PackedB = Rep[UnpackedB] | |
type PackedAB = (PackedA, PackedB) | |
type UnpackedAB = (UnpackedA, UnpackedB) | |
type PackedAShape = Shape[FlatShapeLevel, PackedA, UnpackedA, PackedA] | |
type PackedBShape = Shape[FlatShapeLevel, PackedB, UnpackedB, PackedB] | |
type PackedABShape = Shape[FlatShapeLevel, PackedAB, UnpackedAB, PackedAB] | |
type ShapedABValue = ShapedValue[PackedAB, UnpackedAB] | |
type ColumnAType = BaseTypedType[UnpackedA] | |
type ColumnBType = BaseTypedType[UnpackedB] | |
type ProjectionAB = MappedProjection[Inner, UnpackedAB] | |
type ProjectionABShape = Shape[FlatShapeLevel, ProjectionAB, Inner, ProjectionAB] | |
def a: PackedA = column[UnpackedA]("a") | |
def b: PackedB = column[UnpackedB]("b") | |
def construct(u: UnpackedAB): Inner = Inner.tupled(u) | |
def deconstruct(v: Inner): Option[UnpackedAB] = Inner.unapply(v) | |
override def * : ProvenShape[Inner] = { | |
val columnAType: ColumnAType = stringColumnType | |
val columnBType: ColumnBType = intColumnType | |
val columnAShape: PackedAShape = Shape.repColumnShape[UnpackedA, FlatShapeLevel](columnAType) | |
val columnBShape: PackedBShape = Shape.repColumnShape[UnpackedB, FlatShapeLevel](columnBType) | |
val tupleABShape: PackedABShape = Shape.tuple2Shape[FlatShapeLevel, PackedA, PackedB, UnpackedA, UnpackedB, PackedA, PackedB](columnAShape, columnBShape) | |
val shapedABTuple: ShapedABValue = anyToShapedValue[PackedAB, UnpackedAB]((a, b))(tupleABShape) | |
val innerProjection: ProjectionAB = shapedABTuple.<>[Inner](construct, deconstruct) | |
val innerProjectionShape: ProjectionABShape = Shape.mappedProjectionShape[FlatShapeLevel, Inner, UnpackedAB] | |
ProvenShape.proveShapeOf[ProjectionAB, Inner](innerProjection)(innerProjectionShape) | |
// (a, b) <> (Inner.tupled, Inner.unapply) | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class OuterTable(tag: Tag) extends Table[Outer](tag, "outer") { | |
type UnpackedA = String | |
type UnpackedB = Int | |
type PackedA = Rep[UnpackedA] | |
type PackedB = Rep[UnpackedB] | |
type PackedAB = (PackedA, PackedB) | |
type UnpackedAB = (UnpackedA, UnpackedB) | |
type MixedAI = (UnpackedA, Inner) | |
type PackedAShape = Shape[FlatShapeLevel, PackedA, UnpackedA, PackedA] | |
type PackedBShape = Shape[FlatShapeLevel, PackedB, UnpackedB, PackedB] | |
type PackedABShape = Shape[FlatShapeLevel, PackedAB, UnpackedAB, PackedAB] | |
type ShapedABValue = ShapedValue[PackedAB, UnpackedAB] | |
type ShapedMixedAIValue = ShapedValue[(PackedA, ProjectionAB), MixedAI] | |
type ColumnAType = BaseTypedType[UnpackedA] | |
type ColumnBType = BaseTypedType[UnpackedB] | |
type ProjectionAB = MappedProjection[Inner, UnpackedAB] | |
type ProjectionMixedAI = MappedProjection[Outer, MixedAI] | |
type ProjectionMixedAIShape = Shape[FlatShapeLevel, ProjectionMixedAI, Outer, ProjectionMixedAI] | |
def a: PackedA = column[UnpackedA]("a") | |
def ia: PackedA = column[UnpackedA]("ia") | |
def ib: PackedB = column[UnpackedB]("ib") | |
def constructInner(u: UnpackedAB): Inner = Inner.tupled(u) | |
def deconstructInner(v: Inner): Option[UnpackedAB] = Inner.unapply(v) | |
def constructOuter(u: MixedAI): Outer = Outer.tupled(u) | |
def deconstructOuter(v: Outer): Option[MixedAI] = Outer.unapply(v) | |
override def * : ProvenShape[Outer] = { | |
val columnAType: ColumnAType = stringColumnType | |
val columnBType: ColumnBType = intColumnType | |
val columnAShape: PackedAShape = Shape.repColumnShape[UnpackedA, FlatShapeLevel](columnAType) | |
val columnBShape: PackedBShape = Shape.repColumnShape[UnpackedB, FlatShapeLevel](columnBType) | |
val tupleABShape: PackedABShape = Shape.tuple2Shape[FlatShapeLevel, PackedA, PackedB, UnpackedA, UnpackedB, PackedA, PackedB](columnAShape, columnBShape) | |
val shapedABTuple: ShapedABValue = anyToShapedValue[PackedAB, UnpackedAB]((a, ib))(tupleABShape) | |
val innerProjection: ProjectionAB = shapedABTuple.<>[Inner](constructInner, deconstructInner) | |
val shapedMixedAITuple: ShapedMixedAIValue = anyToShapedValue((a, innerProjection)) | |
val outerMixedProjection: ProjectionMixedAI = shapedMixedAITuple.<>[Outer](constructOuter, deconstructOuter) | |
val outerMixedProjectionShape: ProjectionMixedAIShape = Shape.mappedProjectionShape[FlatShapeLevel, Outer, MixedAI] | |
ProvenShape.proveShapeOf[ProjectionMixedAI, Outer](outerMixedProjection)(outerMixedProjectionShape) | |
// val i = (ia, ib) <> (constructInner, deconstructInner) | |
// (a, i) <> (constructOuter, deconstructOuter) | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment