如何在使用Slick的VARCHAR列中使用UUID?

我有一个MySQL 5.7数据库,其中有几个表,它们将UUID存储在具有VARCHAR数据类型的列中。 我正在尝试将我们的代码库转换为使用Slick 3.1.1,但我正面临着UUID到String转换的问题。 这是我的专栏定义:

def myCol: Rep[UUID] = column[UUID]("myCol", SqlType("VARCHAR"))

当我运行查询时,我得到这样的异常:

Got the exception java.sql.SQLException: Incorrect string value: 'xDAxFDxDAuOL...' for column 'myCol' at row 1

据我所知,Slick假定UUID应该被存储为二进制列类型,所以我试图隐式转换为字符串使用:

implicit val uuidToString = MappedColumnType.base[UUID, String](_.toString, UUID.fromString)
def myCol: Rep[UUID] = column[UUID]("myCol", SqlType("VARCHAR"))(uuidToString)

这适用于插入,但是当我使用myCol结果选择值时为空。 任何人都知道如何强制Slick使用VARCHAR而不是BINARY(16)进行数据转换?

编辑:

隐含的这个查询不会返回任何结果:

db.run { table.filter(_.myCol === val)).result }

但是这个确实如此:

db.run { table.result }.map(_.filter(_.myCol == val))

EDIT2:

我在这里有一个带有演示的小项目:https://github.com/nmatpt/slick-uuid-test


你确定来自数据库的空值? 我只是检查了我的实现(在其中一个项目中,完全相同的解决方案),它似乎完美工作。 确保您的物理列(在数据库中)实际上是VARCHAR类型(而不是某些二进制文件)。

编辑:好的,我们有的问题是, UUID定义为BINARY已包含在MySQL配置文件中。 快速(虽然也许有点肮脏)在全球重新定义它会是这样的:

package profile

import java.sql.{PreparedStatement, ResultSet}

import slick.ast._
import slick.jdbc.MySQLProfile

object CustomMySqlProfile  extends MySQLProfile {
  import java.util.UUID

  override val columnTypes = new JdbcTypes

  class JdbcTypes extends super.JdbcTypes {
    override val uuidJdbcType = new UUIDJdbcType {
      override def sqlTypeName(sym: Option[FieldSymbol]) = "UUID"
      override def valueToSQLLiteral(value: UUID) = "'" + value + "'"
      override def hasLiteralForm = true

      override def setValue(v: UUID, p: PreparedStatement, idx: Int) = p.setString(idx, toString(v))
      override def getValue(r: ResultSet, idx: Int) = fromString(r.getString(idx))
      override def updateValue(v: UUID, r: ResultSet, idx: Int) = r.updateString(idx, toString(v))

      private def toString(uuid: UUID) = if(uuid != null) uuid.toString else null
      private def fromString(uuidString: String) = if(uuidString != null) UUID.fromString(uuidString) else null
    }
  }
}

然后导入它而不是常规的api

import profile.CustomMySqlProfile.api._

这绝对有效 - 但请记住,现在UUID将映射到整个应用程序中的字符串(而不是默认二进制文件)。 基本上我需要覆盖配置文件,因为UUID转换是内置的。通常你会使用类型映射。

类似的东西在这里以类似的方式得到解决:https://github.com/slick/slick/issues/1446(也是UUID,但对于Oracle驱动程序)。

链接地址: http://www.djcxy.com/p/37339.html

上一篇: How to use UUID in a VARCHAR column with Slick?

下一篇: Do I need a WOW64 dump for GDI Handle analysis?