2017-03-19 200 views
0

我有大約100請求/秒的系統。有時它會在我重新啓動我的go程序之前無法響應。我發現這是因爲我打開了交易,並沒有在某些地方關閉它。這就是爲什麼所有的連接被打開交易佔用的,我不能打開另一個在這之後我加入這個代碼Golang交易退出處理

defer func() { 
if r := recover(); r != nil { 
    tx.Rollback() 
    return 
} 

if err == nil { 
    err = tx.Commit() 
} else { 
    tx.Rollback() 
} 
}() 

這讓我一個月工作方案沒有中斷。但是現在它又發生了。可能是因爲這個問題。有沒有更好的方式來結束交易?或者,也許一種方式來關閉交易,如果它是開放1分鐘?

+0

什麼是錯誤您收到?此外,只是一個旁註,但'回滾'也可以返回一個錯誤,所以你應該處理它。 – MahlerFive

+0

@MahlerFive,我不確定,它恐慌並導致執行停止。是的,我知道Rollback和Commit也會返回錯誤,但我不知道如何處理它們 –

+0

你可以發佈你的整個功能嗎? – MahlerFive

回答

0

如果你想1分鐘後回滾事務,你可以使用標準的圍棋超時模式(如下圖)。

但是,可能有更好的方法來解決你的問題。你不會提供很多關於它的信息,但你可能使用帶有上下文的標準HTTP請求。在這種情況下,它可能會幫助你知道a transaction started within a context is automatically rolled back when the context is cancelled。一種方法可以確保上下文被取消,如果出現問題,可以給它一個deadline


Channels - Timeouts摘錄。原作者爲Chris Lucas,KwarrtzRodolfo Carvalho。您可以在contributor page上找到歸因細節。信息來源根據CC BY-SA 3.0獲得許可,可在Documentation archive中找到。參考主題ID:1263和實例ID:6050

超時

通道經常被用來實現超時。

func main() { 
    // Create a buffered channel to prevent a goroutine leak. The buffer 
    // ensures that the goroutine below can eventually terminate, even if 
    // the timeout is met. Without the buffer, the send on the channel 
    // blocks forever, waiting for a read that will never happen, and the 
    // goroutine is leaked. 
    ch := make(chan struct{}, 1) 

    go func() { 
     time.Sleep(10 * time.Second) 
     ch <- struct{}{} 
    }() 

    select { 
    case <-ch: 
     // Work completed before timeout. 
    case <-time.After(1 * time.Second): 
     // Work was not completed after 1 second. 
    } 
} 
+0

您能否提供一個使用它的例子?我在互聯網上找不到任何東西 –

+0

Golang博客(https://blog.golang.org/context)提供瞭如何使用Context的示例,並且Context包本身已有詳細記錄(https:// golang。組織/ PKG /上下文/)。 – Zoyd