diff --git a/modules/fts-psql/src/main/scala/docspell/ftspsql/DoobieMeta.scala b/modules/fts-psql/src/main/scala/docspell/ftspsql/DoobieMeta.scala index 34a305946b..c0b331dc0a 100644 --- a/modules/fts-psql/src/main/scala/docspell/ftspsql/DoobieMeta.scala +++ b/modules/fts-psql/src/main/scala/docspell/ftspsql/DoobieMeta.scala @@ -9,17 +9,9 @@ package docspell.ftspsql import docspell.common._ import doobie._ -import doobie.util.log.Success trait DoobieMeta { - implicit val sqlLogging: LogHandler = LogHandler { - case e @ Success(_, _, _, _) => - DoobieMeta.logger.debug("SQL " + e) - case e => - DoobieMeta.logger.error(s"SQL Failure: $e") - } - implicit val metaIdent: Meta[Ident] = Meta[String].timap(Ident.unsafe)(_.id) @@ -29,7 +21,3 @@ trait DoobieMeta { implicit val metaCollectiveId: Meta[CollectiveId] = Meta[Long].timap(CollectiveId(_))(_.value) } - -object DoobieMeta { - private val logger = org.log4s.getLogger -} diff --git a/modules/fts-psql/src/main/scala/docspell/ftspsql/PsqlFtsClient.scala b/modules/fts-psql/src/main/scala/docspell/ftspsql/PsqlFtsClient.scala index fafc92ad6f..6b3ac517c6 100644 --- a/modules/fts-psql/src/main/scala/docspell/ftspsql/PsqlFtsClient.scala +++ b/modules/fts-psql/src/main/scala/docspell/ftspsql/PsqlFtsClient.scala @@ -15,6 +15,7 @@ import fs2.Stream import docspell.common._ import docspell.ftsclient._ import docspell.logging.Logger +import docspell.store.impl.DoobieLogging import com.zaxxer.hikari.HikariDataSource import doobie._ @@ -157,7 +158,8 @@ object PsqlFtsClient { ds.setPassword(cfg.password.pass) ds.setDriverClassName("org.postgresql.Driver") } - xa = HikariTransactor[F](ds, connectEC) + logh = DoobieLogging[F](docspell.logging.getLogger[F]) + xa = HikariTransactor[F](ds, connectEC, Some(logh)) pc = new PsqlFtsClient[F](cfg, xa) } yield pc diff --git a/modules/store/src/main/scala/db/migration/common/TransactorSupport.scala b/modules/store/src/main/scala/db/migration/common/TransactorSupport.scala index 2fd50cc395..2b764e6e0d 100644 --- a/modules/store/src/main/scala/db/migration/common/TransactorSupport.scala +++ b/modules/store/src/main/scala/db/migration/common/TransactorSupport.scala @@ -9,6 +9,7 @@ package db.migration.common import cats.effect.IO import docspell.logging.Logger +import docspell.store.impl.DoobieLogging import doobie.util.transactor.{Strategy, Transactor} import org.flywaydb.core.api.migration.Context @@ -18,7 +19,8 @@ trait TransactorSupport { def logger: Logger[IO] def mkTransactor(ctx: Context): Transactor[IO] = { - val xa = Transactor.fromConnection[IO](ctx.getConnection) + val logHandler = DoobieLogging[IO](logger) + val xa = Transactor.fromConnection[IO](ctx.getConnection, Some(logHandler)) logger.asUnsafe.info(s"Creating transactor for db migrations from connection: $xa") Transactor.strategy.set(xa, Strategy.void) // transactions are handled by flyway } diff --git a/modules/store/src/main/scala/docspell/store/Store.scala b/modules/store/src/main/scala/docspell/store/Store.scala index 3e611fe4aa..101724a342 100644 --- a/modules/store/src/main/scala/docspell/store/Store.scala +++ b/modules/store/src/main/scala/docspell/store/Store.scala @@ -14,7 +14,7 @@ import fs2._ import fs2.io.file.Files import docspell.store.file.{FileRepository, FileRepositoryConfig} -import docspell.store.impl.StoreImpl +import docspell.store.impl.{DoobieLogging, StoreImpl} import com.zaxxer.hikari.HikariDataSource import doobie._ @@ -60,8 +60,9 @@ object Store { ds.setPassword(jdbc.password) ds.setDriverClassName(jdbc.dbms.driverClass) } - xa = HikariTransactor(ds, connectEC) - fr = FileRepository(xa, ds, fileRepoConfig, true) + logh = DoobieLogging[F](docspell.logging.getLogger[F]) + xa = HikariTransactor[F](ds, connectEC, Some(logh)) + fr = FileRepository(xa, ds, fileRepoConfig, withAttributeStore = true) st = new StoreImpl[F](fr, jdbc, schemaCfg, ds, xa) _ <- Resource.eval(st.migrate) } yield st diff --git a/modules/store/src/main/scala/docspell/store/impl/DoobieLogging.scala b/modules/store/src/main/scala/docspell/store/impl/DoobieLogging.scala new file mode 100644 index 0000000000..43552f9f9b --- /dev/null +++ b/modules/store/src/main/scala/docspell/store/impl/DoobieLogging.scala @@ -0,0 +1,53 @@ +/* + * Copyright 2020 Eike K. & Contributors + * + * SPDX-License-Identifier: AGPL-3.0-or-later + */ + +package docspell.store.impl + +import cats.Applicative +import cats.syntax.all._ + +import docspell.logging.Logger +import docspell.store.impl.DoobieLogging.LogLabel + +import doobie.util.log +import doobie.util.log.LogHandler + +final class DoobieLogging[F[_]: Applicative](logger: Logger[F]) extends LogHandler[F] { + override def run(logEvent: log.LogEvent): F[Unit] = + if (LogLabel.fromEvent(logEvent).contains(LogLabel.Silent)) ().pure[F] + else + logEvent match { + case log.Success(sql, args, _, exec, _) => + logger.trace(s"SQL: $sql ($args) executed in $exec") + + case log.ProcessingFailure(sql, args, _, _, _, failure) => + logger.error(failure)(s"SQL processing failed: $sql ($args)") + + case log.ExecFailure(sql, args, _, _, failure) => + logger.error(failure)(s"SQL exec failed: $sql ($args)") + } +} + +object DoobieLogging { + + def apply[F[_]: Applicative](logger: Logger[F]): DoobieLogging[F] = + new DoobieLogging[F](logger) + + sealed trait LogLabel extends Product { + lazy val name: String = productPrefix.toLowerCase + } + object LogLabel { + case object Silent extends LogLabel + + val all: List[LogLabel] = List(Silent) + + def fromString(str: String): Option[LogLabel] = + all.find(_.name.equalsIgnoreCase(str)) + + def fromEvent(e: log.LogEvent): Option[LogLabel] = + fromString(e.label) + } +} diff --git a/modules/store/src/main/scala/docspell/store/impl/DoobieMeta.scala b/modules/store/src/main/scala/docspell/store/impl/DoobieMeta.scala index 06c6f9136c..14d80d64a6 100644 --- a/modules/store/src/main/scala/docspell/store/impl/DoobieMeta.scala +++ b/modules/store/src/main/scala/docspell/store/impl/DoobieMeta.scala @@ -22,21 +22,12 @@ import binny.BinaryId import com.github.eikek.calev.CalEvent import doobie._ import doobie.implicits.legacy.instant._ -import doobie.util.log.Success import emil.doobie.EmilDoobieMeta -import io.circe.Json -import io.circe.{Decoder, Encoder} +import io.circe.{Decoder, Encoder, Json} import scodec.bits.ByteVector trait DoobieMeta extends EmilDoobieMeta { - implicit val sqlLogging: LogHandler = LogHandler { - case e @ Success(_, _, _, _) => - DoobieMeta.logger.trace(s"SQL: $e") - case e => - DoobieMeta.logger.warn(s"SQL Failure: $e") - } - def jsonMeta[A](implicit d: Decoder[A], e: Encoder[A]): Meta[A] = Meta[String].imap(str => str.parseJsonAs[A].fold(ex => throw ex, identity))(a => e.apply(a).noSpaces @@ -180,12 +171,9 @@ trait DoobieMeta extends EmilDoobieMeta { } object DoobieMeta extends DoobieMeta { - import org.log4s._ - private val logger = getLogger private def parseJsonUnsafe(str: String): Json = io.circe.parser .parse(str) .fold(throw _, identity) - } diff --git a/modules/store/src/main/scala/docspell/store/impl/StoreImpl.scala b/modules/store/src/main/scala/docspell/store/impl/StoreImpl.scala index b214b7591c..5da983be1a 100644 --- a/modules/store/src/main/scala/docspell/store/impl/StoreImpl.scala +++ b/modules/store/src/main/scala/docspell/store/impl/StoreImpl.scala @@ -30,7 +30,7 @@ final class StoreImpl[F[_]: Async: Files]( ) extends Store[F] { private[this] val xa = transactor - val dbms = jdbc.dbms + val dbms: Db = jdbc.dbms def createFileRepository( cfg: FileRepositoryConfig, diff --git a/modules/store/src/main/scala/docspell/store/qb/DML.scala b/modules/store/src/main/scala/docspell/store/qb/DML.scala index f53e3dc715..aa67f43756 100644 --- a/modules/store/src/main/scala/docspell/store/qb/DML.scala +++ b/modules/store/src/main/scala/docspell/store/qb/DML.scala @@ -8,7 +8,7 @@ package docspell.store.qb import cats.data.{NonEmptyList => Nel} -import docspell.store.impl.DoobieMeta +import docspell.store.impl.{DoobieLogging, DoobieMeta} import docspell.store.qb.impl._ import doobie._ @@ -34,7 +34,9 @@ object DML extends DoobieMeta { cols: Nel[Column[_]], values: Fragment ): ConnectionIO[Int] = - insertFragment(table, cols, List(values)).update(LogHandler.nop).run + insertFragment(table, cols, List(values)) + .updateWithLabel(DoobieLogging.LogLabel.Silent.name) + .run def insertMany( table: TableDef, diff --git a/project/Dependencies.scala b/project/Dependencies.scala index e0a5b56a5f..1a36282b14 100644 --- a/project/Dependencies.scala +++ b/project/Dependencies.scala @@ -16,8 +16,8 @@ object Dependencies { val CirceGenericExtrasVersion = "0.14.3" val CirceYamlVersion = "0.15.1" val ClipboardJsVersion = "2.0.11" - val DoobieVersion = "1.0.0-RC2" - val EmilVersion = "0.13.0" + val DoobieVersion = "1.0.0-RC4" + val EmilVersion = "0.15.0" val FlexmarkVersion = "0.64.8" val FlywayVersion = "10.0.0" val Fs2Version = "3.9.2"