第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

有什么辦法可以阻止默認的golang程序完成

有什么辦法可以阻止默認的golang程序完成

Go
繁花如伊 2023-07-26 10:07:36
我有一個使用 websocket 連接和數(shù)據(jù)庫的服務(wù)器。有些用戶可以通過套接字連接,所以我需要在db中增加他們的“在線”;在他們斷開連接的那一刻,我還減少了他們在數(shù)據(jù)庫中的“在線”字段。但為了防止服務(wù)器崩潰,我使用在線用戶的本地變量副本map[string]int。因此,我需要推遲服務(wù)器關(guān)閉,直到它完成一個數(shù)據(jù)庫請求,該請求根據(jù)我的變量副本減少所有“在線”用戶,因為這樣套接字連接不會發(fā)送默認的“關(guān)閉”事件。我找到了一個包 github.com/xlab/closer ,它可以處理一些系統(tǒng)調(diào)用,并且可以在程序完成之前執(zhí)行一些操作,但我的數(shù)據(jù)庫請求不能以這種方式工作(代碼如下)func main() {  ...  // trying to handle program finish event  closer.Bind(cleanupSocketConnections(&pageHandler))  ...}// function that handles program finish eventfunc cleanupSocketConnections(p *controllers.PageHandler) func() {    return func() {        p.PageService.ResetOnlineUsers()    }}// this map[string]int contains key=userId, value=count of socket connectionstype PageService struct {    Users map[string]int}func (p *PageService) ResetOnlineUsers() {    for userId, count := range p.Users {        // decrease online of every user in program variable        InfoService{}.DecreaseInfoOnline(userId, count)    }}也許我使用不正確,或者可能有更好的方法來防止默認程序完成?
查看完整描述

2 回答

?
ibeautiful

TA貢獻1993條經(jīng)驗 獲得超6個贊

首先,正如您所說,當(dāng)服務(wù)器“崩潰”時執(zhí)行任務(wù)是相當(dāng)復(fù)雜的,因為崩潰可能意味著很多事情,并且當(dāng)服務(wù)器中出現(xiàn)嚴(yán)重問題時,沒有什么可以保證清理功能的執(zhí)行。


從工程角度來看(如果在故障時將用戶設(shè)置為離線如此重要),最好是在另一臺服務(wù)器上有一個輔助服務(wù),該服務(wù)接收用戶連接和斷開連接事件以及 ping 事件(如果它在某個時間段內(nèi)沒有收到任何更新)設(shè)置超時該服務(wù)會認為您的服務(wù)器已關(guān)閉并繼續(xù)將每個用戶設(shè)置為離線。


回到你的問題,使用 defer 和等待終止信號應(yīng)該覆蓋 99% 的情況。我對代碼進行了注釋以解釋邏輯。


// AllUsersOffline is called when the program is terminated, it takes a *sync.Once to make sure this function is performed only

// one time, since it might be called from different goroutines.

func AllUsersOffline(once *sync.Once) {

    once.Do(func() {

        fmt.Print("setting all users offline...")

        // logic to set all users offline

    })

}


// CatchSigs catches termination signals and executes f function at the end

func CatchSigs(f func()) {

    cSig := make(chan os.Signal, 1)

    // watch for  these signals

    signal.Notify(cSig, syscall.SIGKILL, syscall.SIGTERM, syscall.SIGINT, syscall.SIGQUIT, syscall.SIGHUP) // these are the termination signals in GNU =>  https://www.gnu.org/software/libc/manual/html_node/Termination-Signals.html

    // wait for them

    sig := <- cSig

    fmt.Printf("received signal: %s", sig)

    // execute f

    f()

}

func main() {

    /* code */

    // the once is used to make sure AllUsersOffline is performed ONE TIME.

    usersOfflineOnce := &sync.Once{}

    // catch termination signals

    go CatchSigs(func() {

        // when a termination signal is caught execute AllUsersOffline function

        AllUsersOffline(usersOfflineOnce)

    })

    // deferred functions are called even in case of panic events, although execution is not to take for granted (OOM errors etc)

    defer AllUsersOffline(usersOfflineOnce)

    /* code */

    // run server

    err := server.Run()

    if err != nil {

        // error logic here

    }

    // bla bla bla

}



查看完整回答
反對 回復(fù) 2023-07-26
?
慕哥9229398

TA貢獻1877條經(jīng)驗 獲得超6個贊

我認為你需要看看goroutineChannel。

查看完整回答
反對 回復(fù) 2023-07-26
  • 2 回答
  • 0 關(guān)注
  • 168 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學(xué)習(xí)伙伴

公眾號

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號