All Downloads are FREE. Search and download functionalities are using the official Maven repository.

scray.cassandra.rows.GenericCassandraRowStoreMapper.scala Maven / Gradle / Ivy

The newest version!
// See the LICENCE.txt file distributed with this work for additional
// information regarding copyright ownership.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
package scray.cassandra.rows

import java.nio.ByteBuffer

import com.datastax.driver.core.{ColumnDefinitions, Row => CassRow}
import com.websudos.phantom.CassandraPrimitive
import scray.cassandra.CassandraQueryableSource
import scray.querying.description._
import scray.querying.queries.DomainQuery

import scala.annotation.tailrec
import scala.collection.JavaConverters._
import scala.collection.mutable.{ArrayBuffer, ListBuffer}

/**
 * a generic mapper to map cassandra rows emitted by CQLCassandraRowStore to scray rows 
 */
object GenericCassandraRowStoreMapper {

  val defaultCassPrimitives: List[CassandraPrimitive[_]] = List(
    CassandraPrimitive.BigDecimalCassandraPrimitive,
    CassandraPrimitive.BigIntCassandraPrimitive,
    CassandraPrimitive.BlobIsCassandraPrimitive,
    CassandraPrimitive.BooleanIsCassandraPrimitive,
    CassandraPrimitive.DateIsCassandraPrimitive,
    CassandraPrimitive.DoubleIsCassandraPrimitive,
    CassandraPrimitive.FloatIsCassandraPrimitive,
    CassandraPrimitive.InetAddressCassandraPrimitive,
    CassandraPrimitive.IntIsCassandraPrimitive,
    CassandraPrimitive.LongIsCassandraPrimitive,
    CassandraPrimitive.StringIsCassandraPrimitive,
    CassandraPrimitive.UUIDIsCassandraPrimitive
  )
  
  val additionalCassMappings: List[(String, CassandraPrimitive[_])] = List(
    "varchar" -> CassandraPrimitive.StringIsCassandraPrimitive,
    "ascii" -> CassandraPrimitive.StringIsCassandraPrimitive,
    "counter" -> CassandraPrimitive.LongIsCassandraPrimitive,
    "timeuuid" -> CassandraPrimitive.UUIDIsCassandraPrimitive
  )
  
  def cassTypeMap(cassPrimitives: List[CassandraPrimitive[_]], additionalMappings: List[(String, CassandraPrimitive[_])] = List()): 
    Map[String, CassandraPrimitive[_]] = (cassPrimitives.map(prim => prim.cassandraType -> prim) ++ additionalMappings).toMap
  
  implicit val cassandraPrimitiveTypeMap = cassTypeMap(defaultCassPrimitives, additionalCassMappings)

  @tailrec private final def columnsTransform(in: List[ColumnDefinitions.Definition], 
      buf: ListBuffer[RowColumn[_]],
      ti: TableIdentifier,
      typeMap: Map[String, CassandraPrimitive[_]],
      cassrow: CassRow): ListBuffer[RowColumn[_]] = 
  if(in.isEmpty) {
    buf
  } else {
    val tm = typeMap.get(in.head.getType.getName.toString).get.fromRow(cassrow, in.head.getName)
    val buffer = tm match {
      case Some(value) => value match {
        case bytes: ByteBuffer =>
          val byteArray = new Array[Byte](bytes.remaining())
          bytes.get(byteArray)
          buf += RowColumn(Column(in.head.getName, ti), byteArray)
        case _ => buf += RowColumn(Column(in.head.getName, ti), value)
      }
      case None => buf
    }
    columnsTransform(in.tail, buffer, ti, typeMap, cassrow)
  }
  
//  def rowMapper[K: CassandraPrimitive](store: CQLCassandraRowStore[K], tableName: Option[String])(implicit typeMap: Map[String, CassandraPrimitive[_]]): 
//    ((K, CassRow)) => Row = (kv) => {
//    val (key, cassrow) = kv
//    val ti = tableName.map(TableIdentifier(CassandraExtractor.DB_ID, store.columnFamily.session.getKeyspacename, _)).getOrElse {
//        TableIdentifier(CassandraExtractor.DB_ID, store.columnFamily.session.getKeyspacename, store.columnFamily.getName)}
//    val lb = columnsTransform(cassrow.getColumnDefinitions().asList().asScala.toList, ListBuffer.empty[RowColumn[_]], ti, typeMap, cassrow)
//    SimpleRow(new ArrayBuffer[RowColumn[_]](lb.size).++=(lb))
//  }
  
  def cassandraRowToScrayRowMapper[Q <: DomainQuery](ti: TableIdentifier)(implicit typeMap: Map[String, CassandraPrimitive[_]]): CassRow => Row = row => {
    val definitionIterator = row.getColumnDefinitions().asList().asScala
    val lb = columnsTransform(definitionIterator.toList, ListBuffer.empty[RowColumn[_]], ti, typeMap, row)
    SimpleRow(new ArrayBuffer[RowColumn[_]](lb.size).++=(lb))    
  }
  
  def cassandraRowToScrayRowMapper[Q <: DomainQuery](store: CassandraQueryableSource[Q])(implicit typeMap: Map[String, CassandraPrimitive[_]]): CassRow => Row = 
    cassandraRowToScrayRowMapper(store.getScrayCoordinates)(typeMap)

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy