Перейти/Golang в SQL.Повторное использование БД в функциях
sql.Open () возвращает переменную типа *sql.DB
у меня есть функция, которая вызывает 10 других функций, которые все должны делать вызовы базы данных
это более правильно / эффективно:
- отправить * sql.DB указатель на каждую функцию или
- создайте новый * sql.Объект DB в каждой функции
смысл
func DoLotsOfThings() {
db, _ := sql.Open()
defer db.Close()
DoTask1(db)
DoTask2(db)
}
или
func DoLotsOfThings() {
DoTask1()
DoTask2()
}
func DoTask1() {
db, _ := sql.Open()
defer db.Close()
}
func DoTask1() {
db, _ := sql.Open()
defer db.Close()
}
причина, по которой я спрашиваю, заключается в том, что я в настоящее время отправляю указатель на каждую функцию и мой драйвер, кажется, ломаются. Я использую http://code.google.com/p/odbc, что заставляет меня полагать, что каждая функция должна иметь свою собственную, и что я могу положиться на внутренние органы водителя.
редактировать
обрыв водителя ре, оно только случается под высокими окружающими средами движения. И это происходит, скажем, минут через десять. Это заставляет меня поверить, что есть какая-то утечка памяти, которая заставляет использовать водитель перестает работать. Однако я откладываю db.Close () для каждого экземпляра *sql.DB, поэтому я не знаю, что еще я могу сделать, чтобы решить эту проблему.
andybalholm говорит, что пул соединений обрабатывается внутри, что кажется точным, потому что он ломается только после попытки выполнить что-то, а не при вызове sql.Open ()
Если я оставлю приложение Go запущенным, оно не сможет выполнять какие-либо SQL-запросы, но если я попытаюсь запустить другие тесты Go отдельно для MSSQL и запущенных запросов он работает.
2 ответов
вам не нужно открывать соединения с базой данных повсюду. Пакет database / sql выполняет пул соединений внутри, открывая и закрывая соединения по мере необходимости, обеспечивая иллюзию одного соединения, которое может использоваться одновременно.
Возможно, вам нужно искать в другом месте причину поломки вашего водителя. Более подробная информация об этом облегчит людям понимание того, что происходит.
объявления var db *sql.DB
глобально, а затем повторно использовать его в коде. Вот пример (упрощенный):
var db *sql.DB
func DoLotsOfThings() {
DoTask1(db)
DoTask2(db)
}
func main() {
db, _ = sql.Open() # or whatever you use
defer db.Close()
DoLotsOfThings()
}
объявления *sql.DB
глобально также имеют некоторые дополнительные преимущества, такие как SetMaxIdleConns (регулируя размер пула соединения) или подготовка операторы SQL в вашем приложении.