Несогласованные данные запрашиваются из postgres в двух разных go приложениях - PullRequest
0 голосов
/ 09 марта 2020

Я создал два go приложения, скажем app1 и app2 , они оба подключены к одной и той же базе данных postgres. Для каждого приложения я использую gorm в качестве ORM.

app1 используется для обновления базы данных, а app2 - сервер API, созданный в gin , который запрашивает данные из базы данных.

В app2 Я создаю пул соединений с базой данных в начале программы, и он повторно используется во всех обработчиках конечных точек HTTP. Внутри функции обработчика я выполняю оператор SQL, используя gorm и возвращает результат.

Старое возвращаемое значение оператора SQL похоже на

select count(*) from t_publications --returns--> 2641

Когда я вставляю 4 новые записи в app1 , я могу получить правильные данные как в app1 и psql cli, так что это похоже на

select count(*) from t_publications --returns--> 2645

Однако, когда я проверяю конечную точку API app2 , которая выполняет тот же оператор SQL, он возвращает старые данные

curl localhost:8080/getPublications --returns--> 2641

Если я перезапущу app2 , я смогу получить правильные данные, которые мне нужны. Я не уверен, является ли это проблемой в отношении времени жизни соединений в пуле соединений, может кто-нибудь объяснить эту проблему? Спасибо.

---- редактировать ----

Вот одна из моих функций обработчика для app2

func GetOverview(db *gorm.DB) gin.HandlerFunc {
    var overview Overview
    // the query is just a simple select statement
    err := db.Raw(dbquery.GetOverview).Scan(&overview).Error
    return func(c *gin.Context) {
        if err == nil {
            c.JSON(http.StatusOK, gin.H{
                "status": "ok",
                "data":   overview,
            })
        } else {
            c.JSON(http.StatusInternalServerError, gin.H{
                "status": "internal server error",
                "data":   err,
            })
        }
    }
}

1 Ответ

0 голосов
/ 09 марта 2020

Вы выполняете запрос ровно один раз в своем GetOverview, а затем возвращаете результат этого запроса в закрытии, которое используется как gin.HandlerFunc, по существу кэшируя результат запроса во время регистрация обработчика навсегда.

Решение состоит в том, чтобы переместить код запроса в фактический обработчик:

func GetOverview(db *gorm.DB) gin.HandlerFunc {
    return func(c *gin.Context) {
        var overview Overview
        // the query is just a simple select statement
        err := db.Raw(dbquery.GetOverview).Scan(&overview).Error
        if err == nil {
            c.JSON(http.StatusOK, gin.H{
                "status": "ok",
                "data":   overview,
            })
        } else {
            c.JSON(http.StatusInternalServerError, gin.H{
                "status": "internal server error",
                "data":   err,
            })
        }
    }
}
...