Oleh
а что лутше взять, что бы можно было так сказать хуки делать, когда что то поднялось выше или ниже нужной отметки
при чем каждый юзер задает самостоятельно
ну и timeseries данные
Oleh
?
Oleh
о
Vladimir
@MrTrooper для мониторинга - prometheus
Vladimir
собственно новый эксперементальный ifql анонсированный слизан с прома
Oleh
спасибо
а хуки позволяет делать?
Vladimir
я не знаю что такое хуки в твоей терминологии
Vladimir
если алерты то alertmanager
Vladimir
https://t.me/metrics_ru
Oleh
понял, спасибо
heavycharged
господа, дайте материал или подскажите, как правильно обыграть соединения с базой, мне нужно чтобы приложение не ждало пока произойдет соединение с базой. sync.Once пойдет для этого?
Oleh
через go запустить не?
Oleh
если все ровно на базу
Oleh
heavycharged
дак мне это по сути и надо...
heavycharged
в init go рутина, там sync.Once
heavycharged
в sync.Once connect, а в ней уже вся логика sql.Open и т.д. и т.п.
A
https://golang.org/doc/faq#git_https
https://stackoverflow.com/questions/27500861/whats-the-proper-way-to-go-get-a-private-repository
Пригорает тут. Неужели нет адекватного метода получать приватные репы через go get или dep, без добавления к именам пакетов ".git"?
A
https://github.com/golang/dep/issues/1041#issuecomment-327062980
A
Мда :(
Sebor▂▅▇█▓▒░
а подскажите, как концептуально правильно работать с подключением к БД
Sebor▂▅▇█▓▒░
пучтим, я делаю отдельную ф-ю:
func oracleCon(dsn string, maxOpenCon, maxIdleCon int) (*sql.DB, error) {
db, err := sql.Open("ora", dsn)
if err != nil {
log.Error(err)
}
db.SetMaxOpenConns(maxOpenCon)
db.SetMaxIdleConns(maxIdleCon)
return db, err
}
Sebor▂▅▇█▓▒░
а потом использую ее так:
func doQuery(param1, param2 string, db *sql.DB) {
query := `declare
nResult Number;
vTextP1 VARCHAR2(4000) := :1;
vSystemID VARCHAR2(128) := 'TEST';
vType VARCHAR2(128) := 'TestInfo';
vTextP2 VARCHAR2(20) := :2;
begin
nResult := TST.TEST_NOTIFICATIONS.SEND_TEST(pTextP1 => vTextP1, pSystemID => vSystemID, pType => vType, pTextP2 => vTextP2);
end;
`
defer db.Close()
if err := db.Ping(); err != nil {
log.Fatal("Connection error: ", err)
} else {
log.Debug("Connection established")
}
_, err := db.Exec(query, param1, param2)
if err != nil {
log.Error("Query execution error: ", err)
} else {
log.Debug("Query executed")
}
}
Sebor▂▅▇█▓▒░
на сколько это криво?)
Andrey
sql.Open можно вызывать 1 раз и потом хранить *sql.DB
Andrey
Он сам внутри разруливает когда подлючаться, а когда закрывать соединение
Andrey
Все, что потом надо делать, это не забывать освобождать соединение
Andrey
Т.е. сделали rows, err := db.Query(...)
Andrey
Не забыть его либо дочитать через rows.Next()
Andrey
Либо закрыть rows.Close()
Andrey
Да, но у тебя лишнее есть
Это не нужно делать:
db.Close()
db.Ping()
Andrey
Andrey
Ну, т.е. у тебя все правильно, но можно проще.
Sebor▂▅▇█▓▒░
а почему не нужен
defer db.Close()
?
Sebor▂▅▇█▓▒░
Вроде же всегда нужно закрывать соединение
Andrey
Andrey
Вот смотри
Ты ставишь эти параметры
db.SetMaxOpenConns(maxOpenCon)
db.SetMaxIdleConns(maxIdleCon)
Sebor▂▅▇█▓▒░
хм, сколько примеров смотрел, везде был defer
буду дальше читать
Andrey
1 - это сколько всего конкурентных соединений может быть
Andrey
2 - это сколько постоянно висящих соединений может быть
Andrey
Т.е. если твоему приложению на всем его времени выполнения нужна база - то смысла делать db.close() на каждый запрос нет
Sebor▂▅▇█▓▒░
а, теперь кажется понимаю
Andrey
Его следует вызывать перед завершением приложения
Sebor▂▅▇█▓▒░
спасибо!
Andrey
Чтобы mysql или oracle знал, что клиент отключился штатно
Andrey
без ошибок
Andrey
Хотя они и без этого работают нормально
Мерль
A Rough Proposal for Sum Types in Go - In Pursuit of Laziness
http://manishearth.github.io/blog/2018/02/01/a-rough-proposal-for-sum-types-in-go/
Slach
Ребят =) а кто нибудь named параметры в database/sql использует?
есть вот такой код
q := "INSERT INTO chats_history(created,chat_id,old_state,new_state) VALUES(@created,@chatId,@oldState,@newState)"
res, err = db.Exec(
q,
sql.Named("created", history.Created),
sql.Named("chatId", history.ChatID),
sql.Named("oldState", history.OldState),
sql.Named("newState", history.NewState),
)
if err == nil {
affectedRows, err = res.RowsAffected()
}
if err != nil || affectedRows == 0 {
log.Error().
Err(err).
Str("q", q).
Int64("affectedRows", affectedRows).
Msg("INSERT INTO chats_history saveChatHistoryChange error, please restart chatbot server")
на выходе в err получаю
{
"time": "2018-02-02T08:30:17Z",
"level": "error",
"error": "column index out of range",
"q": "INSERT INTO chats_history(created,chat_id,old_state,new_state) VALUES(@created,@chatId,@oldState,@newState)",
"affectedRows": 0,
"message": "INSERT INTO chats_history saveChatHistoryChange error, please restart chatbot server"
}
какой именно column index out of range???? о чем вообще разговор идет?
вроде кол-во параметров совпадает в запросе с тем которое передаю
и имена параметров совпадают
че ему надо то???
Andrey
хм, а где ты вычитал про именованые параметры?
Sebor▂▅▇█▓▒░
а что такое именованные параметры? я знаю только про биндинг параметров (как у меня выше)
Andrey
Ребят =) а кто нибудь named параметры в database/sql использует?
есть вот такой код
q := "INSERT INTO chats_history(created,chat_id,old_state,new_state) VALUES(@created,@chatId,@oldState,@newState)"
res, err = db.Exec(
q,
sql.Named("created", history.Created),
sql.Named("chatId", history.ChatID),
sql.Named("oldState", history.OldState),
sql.Named("newState", history.NewState),
)
if err == nil {
affectedRows, err = res.RowsAffected()
}
if err != nil || affectedRows == 0 {
log.Error().
Err(err).
Str("q", q).
Int64("affectedRows", affectedRows).
Msg("INSERT INTO chats_history saveChatHistoryChange error, please restart chatbot server")
на выходе в err получаю
{
"time": "2018-02-02T08:30:17Z",
"level": "error",
"error": "column index out of range",
"q": "INSERT INTO chats_history(created,chat_id,old_state,new_state) VALUES(@created,@chatId,@oldState,@newState)",
"affectedRows": 0,
"message": "INSERT INTO chats_history saveChatHistoryChange error, please restart chatbot server"
}
какой именно column index out of range???? о чем вообще разговор идет?
вроде кол-во параметров совпадает в запросе с тем которое передаю
и имена параметров совпадают
че ему надо то???
Пишут, что драйвер mysql еще не поддерживает именованые
https://github.com/go-sql-driver/mysql/issues/561
🎉
Andrey
Это когда параметров много и запрос большой, чтобы голова не болела их в нужном порядке в функции расставлять...
Andrey
В запросе указываются именованые параметры, например ?start ?end
а в функции ты их уже передаешь
(sql.Named('end', end), sql.Named('start', start))
🎉
@created,@chatId,@oldState,@newStat - а вот это у него что?
Andrey
тоже самое
Andrey
как передавать параметры зависит от драйвера
Andrey
могу врать =)
Slach
это оно и есть Named parameters ...
блин =( бесит "вопросики" писать
криво это но вообще очень странно когда авторы рассуждают про maintenance cost и не пытаются реализовать одну из базовых фич...
и странно что это тупо не реализовано через вызов Quote метода для named параметра
Aleksandr
Andrey
Andrey
Не уверен
Anonymous
Коллеги, подскажите, на чём проще всего можно запилить асинхронный двухсторонний обмен сообщений между двумя компами (оба на Go в одной локалке). Под простотой подразумеваю лёгкость понимания для программиста.
Andrey
формат в смысле?
Andrey
json
Илья
Andrey
Anonymous
Vasily
Andrey
Не, ну тут на что выдумки хватит... Я бы сокет поднял
Anonymous
grpc
Тут же вроде клиент-серверное общение? А мне нужно, чтобы на равных было. Можно так сделать?
Anonymous
Anonymous
udp, а вверху уже что угодно
Не подходит по критерию простоты. Пробовал писать свой велосипед на tcp, но асинхрон не сообразил как сделать.
Anonymous
Slach
Sqlx
=( да уже как то на database/sql написал, переписывать не хочется =(