我正在尝试使用具有多个数据源的GORM在Micronaut中构建应用程序。
Micronaut版本为3.6.2。
当我尝试获取以下错误的数据时:
org.springframework.dao.DataAccessResourceFailureException: Could not obtain current Hibernate Session; nested exception is org.hibernate.HibernateException: No Session found for current thread
at org.grails.orm.hibernate.GrailsHibernateTemplate.getSession(GrailsHibernateTemplate.java:335)
at org.grails.orm.hibernate.GrailsHibernateTemplate.doExecute(GrailsHibernateTemplate.java:284)
at org.grails.orm.hibernate.GrailsHibernateTemplate.get(GrailsHibernateTemplate.java:364)
at org.grails.orm.hibernate.AbstractHibernateGormStaticApi.get(AbstractHibernateGormStaticApi.groovy:120)
at org.grails.datastore.gorm.GormEntity$Trait$Helper.get(GormEntity.groovy:553)
at org.grails.datastore.gorm.GormEntity$Trait$Helper$get.call(Unknown Source)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:47)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:125)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:148)
at com.example.domain.Book.get(Book.groovy)
at com.example.service.$BookServiceImplementation.$tt__get(BookService.groovy)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.codehaus.groovy.reflection.CachedMethod.invoke(CachedMethod.java:107)
at groovy.lang.MetaMethod.doMethodInvoke(MetaMethod.java:323)
at groovy.lang.MetaClassImpl.invokeMethod(MetaClassImpl.java:1268)
at groovy.lang.MetaClassImpl.invokeMethod(MetaClassImpl.java:1035)
at org.codehaus.groovy.runtime.InvokerHelper.invokePogoMethod(InvokerHelper.java:1029)
at org.codehaus.groovy.runtime.InvokerHelper.invokeMethod(InvokerHelper.java:1012)
at org.codehaus.groovy.runtime.InvokerHelper.invokeMethodSafe(InvokerHelper.java:101)
at com.example.service.$BookServiceImplementation$_get_closure1.doCall(BookService.groovy)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.codehaus.groovy.reflection.CachedMethod.invoke(CachedMethod.java:107)
at groovy.lang.MetaMethod.doMethodInvoke(MetaMethod.java:323)
at org.codehaus.groovy.runtime.metaclass.ClosureMetaClass.invokeMethod(ClosureMetaClass.java:274)
at groovy.lang.MetaClassImpl.invokeMethod(MetaClassImpl.java:1035)
at groovy.lang.Closure.call(Closure.java:412)
at groovy.lang.Closure.call(Closure.java:428)
您可以在下面找到源代码:
Build.gradle
plugins {
id("groovy")
id("com.github.johnrengelman.shadow") version "7.1.2"
id("io.micronaut.application") version "3.5.3"
id("io.micronaut.test-resources") version "3.5.3"
}
version = "0.1"
group = "com.example"
repositories {
mavenCentral()
}
dependencies {
implementation("io.micronaut:micronaut-http-client")
implementation("io.micronaut:micronaut-jackson-databind")
implementation("io.micronaut:micronaut-management")
implementation("io.micronaut.beanvalidation:micronaut-hibernate-validator")
implementation("io.micronaut.groovy:micronaut-hibernate-gorm")
implementation("io.micronaut.groovy:micronaut-runtime-groovy")
implementation("io.micronaut.sql:micronaut-jdbc-hikari")
compileOnly("io.micronaut:micronaut-http-validation")
runtimeOnly("ch.qos.logback:logback-classic")
runtimeOnly("mysql:mysql-connector-java")
runtimeOnly("org.apache.tomcat:tomcat-jdbc")
implementation("io.micronaut:micronaut-validation")
annotationProcessor "io.micronaut:micronaut-inject-java"
annotationProcessor "io.micronaut:micronaut-inject-groovy"
implementation("io.micronaut.security:micronaut-security-jwt")
}
application {
mainClass.set("com.example.Application")
}
java {
sourceCompatibility = JavaVersion.toVersion("1.8")
targetCompatibility = JavaVersion.toVersion("1.8")
}
graalvmNative.toolchainDetection = false
micronaut {
runtime("netty")
testRuntime("junit5")
processing {
incremental(true)
annotations("com.example.*")
}
testResources {
additionalModules.add("jdbc-mysql")
}
}
控制器
package com.example.web.controller
import com.example.domain.Book
import com.example.service.BookService
import grails.gorm.transactions.Transactional
import io.micronaut.http.HttpResponse
import io.micronaut.http.MediaType
import io.micronaut.http.annotation.Controller
import io.micronaut.http.annotation.Get
import io.micronaut.http.annotation.PathVariable
import io.micronaut.security.annotation.Secured
import io.micronaut.security.rules.SecurityRule
import jakarta.inject.Inject
@Controller("/book")
@Secured(SecurityRule.IS_ANONYMOUS)
class BookController {
@Inject
BookService bookService
@Get(uri = '/{id}', produces = MediaType.APPLICATION_JSON)
@Transactional
HttpResponse<?> getBook(@PathVariable Long id) {
Book book = bookService.get(id)
HttpResponse.ok(booko)
}
}
服务
package com.example.service
import com.example.domain.Book
import grails.gorm.services.Service
@Service(Book)
interface BookService {
Book get(Serializable id)
}
域
package com.example.domain
import grails.gorm.annotation.Entity
@Entity
class Book {
String name
int pages
static mapping = {
version false
datasource 'olap'
}
}
更新:
我也试过下面这样的服务,但没有成功。
package com.example.service
import com.example.domain.Book
import grails.gorm.transactions.Transactional
import jakarta.inject.Singleton
@Transactional
@Singleton
class BookService {
Book get(Long bookId) {
Book.findById(bookId)
}
}
更新2:
只有在访问第二个数据源时才会出现“找不到当前线程的会话”错误。此错误似乎与多个数据源有关。
有人能用GORM为多个数据源提供正确的配置吗?
1条答案
按热度按时间syqv5f0l1#
在这里,只有当我们尝试访问配置了第二个数据源的域时,才会发生问题。
在上面的示例中,Book域配置了名为
olap
的第二个数据源。但在服务中,我只添加了
@Transactional
。这意味着服务使用默认数据源。但Book
域有olap
数据源。因此,我们收到No session found
错误。为了解决这个问题,我将
@Transactional(connection="olap")
添加到访问Book
域的方法中。以致域和服务都将使用相同数据源。修复后,我的服务等级如下所示: