postgresql - 将 Scala Slick 与数据库枚举结合使用

标签 postgresql scala slick slick-3.0

使用 Slick 3 和 PostgreSQL,我需要查询和更新具有枚举类型列的表:

create type WeekDay as ENUM('sun','mon','tue','wed','thu','fri','sat');

create table shifts(
    id serial PRIMARY KEY,
    user_id INTEGER,
    branch_id INTEGER,
    start INTEGER,
    duration INTEGER,
    day WeekDay
    -- foreign keys etc.
);

我尝试使用 Slick 的 MappedColumnType[java.time.DayOfWeek,String],但这不满足 Postgres 的类型检查器(TBH,理所当然):

org.postgresql.util.PSQLException: ERROR: column "day" is of type weekday but expression is of type character varying
  Hint: You will need to rewrite or cast the expression.
  Position: 92
    at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2412)
    at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:2125)
    at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:297)
    at org.postgresql.jdbc.PgStatement.executeInternal(PgStatement.java:428)
    at org.postgresql.jdbc.PgStatement.execute(PgStatement.java:354)
    at org.postgresql.jdbc.PgPreparedStatement.executeWithFlags(PgPreparedStatement.java:169)
    at org.postgresql.jdbc.PgPreparedStatement.executeUpdate(PgPreparedStatement.java:136)
    at com.zaxxer.hikari.pool.ProxyPreparedStatement.executeUpdate(ProxyPreparedStatement.java:61)
    at com.zaxxer.hikari.pool.HikariProxyPreparedStatement.executeUpdate(HikariProxyPreparedStatement.java)
    at slick.jdbc.JdbcActionComponent$InsertActionComposerImpl$SingleInsertAction.$anonfun$run$15(JdbcActionComponent.scala:520)

表类:

class ShiftTable(tag:Tag) extends Table[Shift](tag, "shifts") {
  import Mappers.dayOfWeekMapper
  def id = column[Long]("id", O.AutoInc, O.PrimaryKey)
  def userId = column[Long]("user_id")
  def branchId = column[Long]("branch_id")
  def start = column[Int]("start")
  def duration = column[Int]("duration")
  def day = column[DayOfWeek]("day")    // <- problematic column

  // keys etc/
  def * = (id, userId, branchId, start, duration, day) <> (Shift.tupled, Shift.unapply)
}

如何将 Scala 值映射到自定义 PostgreSQL 类型?

最佳答案

看起来您可以使用字符串映射到枚举,而无需 pg-slick。

诀窍是向数据库添加强制转换,如 PG JDBC Issue 1420 中所述。 :

CREATE CAST (character varying AS WeekDay) WITH INOUT AS ASSIGNMENT

documentation for CAST描述了WITH INOUT(避免编写用于转换的函数)和AS ASSIGNMENT(在分配值时隐式应用转换)。

然后,您可以使用 MappedColumnType.base[java.time.DayOfWeek, String] 定义从列到 DayOfWeek 的映射。

我在这里放置了一个可运行的示例:https://github.com/d6y/pg-enum/blob/master/src/main/scala/main.scala

关于postgresql - 将 Scala Slick 与数据库枚举结合使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60378921/

相关文章:

postgresql - 可空的自然 id?

php - 将任何日期字符串转换为没有时区的时间戳

java - 用最少的字符表示长

scala - reduceLeft可以并行执行吗?

playframework - 如何通过 Play Slick Evolution 重新生成 SQL 脚本

android - 圆滑的 android ProguardCache 错误

mysql - PostgreSQL - 如何使用?

正则表达式检查字符串是否只有空格

scala - Intellij Idea 和 Play Framework 中的库导入问题

scala - 如何使用 Slick 进行 INSERT IGNORE 查询?