[英]HibernateException: No Hibernate Session bound to thread
[英]grails thread -> hibernateException: No Hibernate session bound to thread
我正在嘗試在服務中創建一些線程,但出現了hibernateException:沒有會話...。 我已經在stackoverflow中看到了有關拋出RuntimeException的解決方案的討論。 就我而言是行不通的。 這是我的服務代碼:
class MatchService {
static transactional = true
def void start(Match match) {
Thread.start {
Match updateMatch = matchSituation(match)
if(!updateMatch.save()) {
throw new RuntimeException("match is not valid and cannot be saved!")
}
}
}
def Match matchSituation(Match m) {
Random random = new Random()
if(m.teamH.averagePlayerValue > m.teamA.averagePlayerValue) {
m.golTeamH = random.nextInt(5)
}
else {
m.golTeamA = random.nextInt(4)
}
return m
}
}
工作類別:
class TestJob {
def matchService
List<Match> matchList = new ArrayList()
static triggers = {
cron name: 'trigger', cronExpression: "0 0/1 15 ? * WED"
}
def group = "threadGroup"
def execute() {
Cal.get(1).matches.each{
match ->
matchList.add(match)
}
for(Match m: matchList) {
if(!m.validate()) {
throw new MatchException( message: "match not valid!!" , match:m)
}
matchService.start(m)
}
}
}
編輯
使用backgroundThread插件(應該處理休眠會話):
backgroundService.execute("Calculating match", {
def backgroundMatch = match
backgroundMatch = matchSituation(backgroundMatch)
if(!backgroundMatch.save()) {
throw new RuntimeException("match is not valid and cannot be saved!")
}
})
我收到此錯誤ERROR events.PatchedDefaultFlushEventListener-無法將數據庫狀態與會話同步
我們使用的石英插件效果很好。
在不同的情況下,我之前遇到過相同的問題,解決該問題的方法是將域訪問代碼包裝在
DomainClass.withTransaction {
}
例如:
def execute() {
Cal.withTransaction {
Cal.get(1).matches.each{
match ->
matchList.add(match)
}
for(Match m: matchList) {
if(!m.validate()) {
throw new MatchException( message: "match not valid!!" , match:m)
}
matchService.start(m)
}
}
}
通過將Domain-class中的fetchmode設置為eager,可以修復來自Hibernate的懶惰異常。
我認為您的問題在於將實際的域對象傳遞給線程。 嘗試僅將域對象ID傳遞給函數,然后在函數/線程中獲取並保存。 將域對象傳遞給另一個線程可能會導致問題。
現在正在工作。 這是我所做的更改:
class TestJob {
def matchService
List<Match> matchList = new ArrayList()
static triggers = {
cron name: 'trigger', cronExpression: "0 0/1 13 ? * THU"
}
def group = "threadGroup"
def execute() {
Cal.get(1).matches.each{ match ->
matchList.add(match)
}
for(Match m: matchList) {
if(!m.validate()) {
throw new MatchException( message: "match not valid!!" , match:m)
}
matchService.run(m.id)
}
}
}
class MatchService {
static transactional = true
// Match updateMatch
def backgroundService
public void run(Long matchId) {
backgroundService.execute("Calculating match", {
def backgroundMatch = Match.findById(matchId)
backgroundMatch = matchSituation(backgroundMatch)
println backgroundMatch.teamH.name + " - " + backgroundMatch.teamA.name + ": " + backgroundMatch.golTeamH + " - " + backgroundMatch.golTeamA
if(!backgroundMatch.save()) {
throw new RuntimeException("match is not valid and cannot be saved!")
}
})
// Thread.start {
// println "run thread (" + matchId + ") : " + String.format('%tH:%<tM:%<tS.%<tL',System.currentTimeMillis())
// this.updateMatch = matchSituation(Match.findById(matchId))
// println updateMatch.teamH.name + " - " + updateMatch.teamA.name + ": " + updateMatch.golTeamH + " - " + updateMatch.golTeamA
// if(!updateMatch.save(flush: true)) {
// throw new RuntimeException("match is not valid and cannot be saved!")
// }
// }
}
def Match matchSituation(Match m) {
Random random = new Random()
if(m.teamH.averagePlayerValue > m.teamA.averagePlayerValue) {
m.golTeamH = random.nextInt(5)
}
else {
m.golTeamA = random.nextInt(4)
}
return m
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.