package jp.sf.amateras.mirage.scala

/**
 * This is the wrapper for the primary key property which is set value by the database side.
 *
 * {{{
 * case class Book(
 *   @(PrimaryKey @field)(generationType = IDENTITY)
 *   bookId: Pk[Long],
 *   bookName: String)
 * }}}
 */
abstract sealed class Pk[+T] {
  def get(): T
}

/**
 * Use this class to give the value to the property which is Pk[T].
 *
 * {{{
 * case class Book(
 *   @(PrimaryKey @field)(generationType = APPLICATION)
 *   bookId: Pk[Long],
 *   bookName: String)
 *
 * val book = Book(Id(1), "Mirage in Action")
 * sqlManager.insert(book)
 * }}}
 */
case class Id[+T](x: T) extends Pk[T]{
  override def get(): T = x
}

/**
 * Use this object when you don't want to specify the value of the primary key
 * which is auto incremented at inserting the entity.
 *
 * {{{
 * case class Book(
 *   @(PrimaryKey @field)(generationType = IDENTITY)
 *   bookId: Pk[Long],
 *   bookName: String)
 *
 * val book = Book(Auto, "Mirage in Action")
 * sqlManager.insert(book)
 * }}}
 */
case object Auto extends Pk[Nothing] {
  override def get(): Nothing = throw new NoSuchElementException("Auto.get")
}

object Sample extends App {
  println(classOf[Pk[_]].getName())
}

