mirror of
https://github.com/lyx0/nourybot.git
synced 2024-11-13 19:49:55 +01:00
add redis storage for timers
This commit is contained in:
parent
79892fed17
commit
39288bfd1c
3
Makefile
3
Makefile
|
@ -1,6 +1,9 @@
|
|||
BINARY_NAME=Nourybot.out
|
||||
BINARY_NAME_API=NourybotApi.out
|
||||
|
||||
cup:
|
||||
sudo docker compose up
|
||||
|
||||
xd:
|
||||
cd cmd/bot && go build -o ${BINARY_NAME} && ./${BINARY_NAME} -env="dev"
|
||||
|
||||
|
|
|
@ -15,6 +15,7 @@ import (
|
|||
"github.com/lyx0/nourybot/internal/common"
|
||||
"github.com/lyx0/nourybot/internal/data"
|
||||
"github.com/nicklaw5/helix"
|
||||
"github.com/redis/go-redis/v9"
|
||||
"go.uber.org/zap"
|
||||
)
|
||||
|
||||
|
@ -39,9 +40,11 @@ type Application struct {
|
|||
Db *sql.DB
|
||||
Models data.Models
|
||||
Scheduler *cron.Cron
|
||||
Rdb *redis.Client
|
||||
}
|
||||
|
||||
var envFlag string
|
||||
var ctx = context.Background()
|
||||
|
||||
func init() {
|
||||
flag.StringVar(&envFlag, "env", "dev", "database connection to use: (dev/prod)")
|
||||
|
@ -115,6 +118,24 @@ func main() {
|
|||
sugar.Fatal(err)
|
||||
}
|
||||
|
||||
rdb := redis.NewClient(&redis.Options{
|
||||
Addr: "127.0.0.1:6379",
|
||||
Password: "",
|
||||
DB: 0,
|
||||
})
|
||||
|
||||
err = rdb.Set(ctx, "key", "value", 0).Err()
|
||||
if err != nil {
|
||||
sugar.Panic(err)
|
||||
}
|
||||
val, err := rdb.Get(ctx, "key").Result()
|
||||
if err != nil {
|
||||
sugar.Panic(err)
|
||||
}
|
||||
sugar.Infow("Redis initialization key",
|
||||
"key", val,
|
||||
)
|
||||
|
||||
// Initialize Application with the new values
|
||||
app := &Application{
|
||||
TwitchClient: tc,
|
||||
|
@ -123,6 +144,7 @@ func main() {
|
|||
Db: db,
|
||||
Models: data.NewModels(db),
|
||||
Scheduler: cron.New(),
|
||||
Rdb: rdb,
|
||||
}
|
||||
|
||||
// Received a PrivateMessage (normal chat message).
|
||||
|
|
|
@ -8,6 +8,7 @@ import (
|
|||
"github.com/gempir/go-twitch-irc/v3"
|
||||
"github.com/lyx0/nourybot/internal/common"
|
||||
"github.com/lyx0/nourybot/internal/data"
|
||||
"github.com/redis/go-redis/v9"
|
||||
)
|
||||
|
||||
// AddTimer slices the message into relevant parts, adding the values onto a
|
||||
|
@ -66,13 +67,28 @@ func (app *Application) AddTimer(name string, message twitch.PrivateMessage) {
|
|||
} else {
|
||||
// cronName is the internal, unique tag/name for the timer.
|
||||
// A timer named "sponsor" in channel "forsen" will be named "forsensponsor"
|
||||
cronName := fmt.Sprintf("%s%s", message.Channel, name)
|
||||
cronName := fmt.Sprintf("%s-%s", message.Channel, name)
|
||||
|
||||
app.Scheduler.AddFunc(fmt.Sprintf("@every %s", repeat), func() { app.newPrivateMessageTimer(message.Channel, text) }, cronName)
|
||||
app.Logger.Infow("Added new timer",
|
||||
"timer", timer,
|
||||
)
|
||||
|
||||
if _, err := app.Rdb.Pipelined(ctx, func(rdb redis.Pipeliner) error {
|
||||
rdb.HSet(ctx, cronName, "timer-name", name)
|
||||
rdb.HSet(ctx, cronName, "timer-cronname", cronName)
|
||||
rdb.HSet(ctx, cronName, "timer-text", text)
|
||||
rdb.HSet(ctx, cronName, "timer-channel", message.Channel)
|
||||
rdb.HSet(ctx, cronName, "timer-repeat", repeat)
|
||||
return nil
|
||||
}); err != nil {
|
||||
app.Logger.Panic(err)
|
||||
}
|
||||
app.Logger.Infow("Loaded timer into redis:",
|
||||
"key", cronName,
|
||||
"value", app.Rdb.HGetAll(ctx, cronName),
|
||||
)
|
||||
|
||||
reply := fmt.Sprintf("Successfully added timer %s repeating every %s", name, repeat)
|
||||
common.Send(message.Channel, reply, app.TwitchClient)
|
||||
return
|
||||
|
@ -104,9 +120,10 @@ func (app *Application) EditTimer(name string, message twitch.PrivateMessage) {
|
|||
}
|
||||
|
||||
// Delete the old timer
|
||||
cronName := fmt.Sprintf("%s%s", message.Channel, name)
|
||||
cronName := fmt.Sprintf("%s-%s", message.Channel, name)
|
||||
app.Scheduler.RemoveJob(cronName)
|
||||
|
||||
_ = app.Rdb.Del(ctx, cronName)
|
||||
err = app.Models.Timers.Delete(name)
|
||||
if err != nil {
|
||||
app.Logger.Errorw("Error deleting timer from database",
|
||||
|
@ -174,10 +191,9 @@ func (app *Application) EditTimer(name string, message twitch.PrivateMessage) {
|
|||
} else { // this is a bit scuffed. The else here is the end of a successful call.
|
||||
// cronName is the internal, unique tag/name for the timer.
|
||||
// A timer named "sponsor" in channel "forsen" will be named "forsensponsor"
|
||||
cronName := fmt.Sprintf("%s%s", message.Channel, name)
|
||||
cronName := fmt.Sprintf("%s-%s", message.Channel, name)
|
||||
|
||||
app.Scheduler.AddFunc(fmt.Sprintf("@every %s", repeat), func() { app.newPrivateMessageTimer(message.Channel, text) }, cronName)
|
||||
|
||||
app.Logger.Infow("Updated a timer",
|
||||
"Name", name,
|
||||
"Channel", message.Channel,
|
||||
|
@ -185,6 +201,21 @@ func (app *Application) EditTimer(name string, message twitch.PrivateMessage) {
|
|||
"New timer", timer,
|
||||
)
|
||||
|
||||
if _, err := app.Rdb.Pipelined(ctx, func(rdb redis.Pipeliner) error {
|
||||
rdb.HSet(ctx, cronName, "timer-name", name)
|
||||
rdb.HSet(ctx, cronName, "timer-cronname", cronName)
|
||||
rdb.HSet(ctx, cronName, "timer-text", text)
|
||||
rdb.HSet(ctx, cronName, "timer-channel", message.Channel)
|
||||
rdb.HSet(ctx, cronName, "timer-repeat", repeat)
|
||||
return nil
|
||||
}); err != nil {
|
||||
app.Logger.Panic(err)
|
||||
}
|
||||
app.Logger.Infow("Loaded timer into redis:",
|
||||
"key", cronName,
|
||||
"value", app.Rdb.HGetAll(ctx, cronName),
|
||||
)
|
||||
|
||||
reply := fmt.Sprintf("Successfully updated timer %s", name)
|
||||
common.Send(message.Channel, reply, app.TwitchClient)
|
||||
return
|
||||
|
@ -222,18 +253,38 @@ func (app *Application) InitialTimers() {
|
|||
|
||||
// cronName is the internal, unique tag/name for the timer.
|
||||
// A timer named "sponsor" in channel "forsen" will be named "forsensponsor"
|
||||
cronName := fmt.Sprintf("%s%s", v.Channel, v.Name)
|
||||
cronName := fmt.Sprintf("%s-%s", v.Channel, v.Name)
|
||||
|
||||
// Repeating is at what times the timer should repeat.
|
||||
// 2 minute timer is @every 2m
|
||||
repeating := fmt.Sprintf("@every %s", v.Repeat)
|
||||
|
||||
if _, err := app.Rdb.Pipelined(ctx, func(rdb redis.Pipeliner) error {
|
||||
rdb.HSet(ctx, cronName, "timer-id", v.ID)
|
||||
rdb.HSet(ctx, cronName, "timer-name", v.Name)
|
||||
rdb.HSet(ctx, cronName, "timer-cronname", cronName)
|
||||
rdb.HSet(ctx, cronName, "timer-text", v.Text)
|
||||
rdb.HSet(ctx, cronName, "timer-channel", v.Channel)
|
||||
rdb.HSet(ctx, cronName, "timer-repeat", v.Repeat)
|
||||
return nil
|
||||
}); err != nil {
|
||||
app.Logger.Panic(err)
|
||||
}
|
||||
app.Logger.Infow("Loaded timer into redis:",
|
||||
"key", cronName,
|
||||
"value", app.Rdb.HGetAll(ctx, v.Channel),
|
||||
)
|
||||
app.Scheduler.AddFunc(repeating, func() { app.newPrivateMessageTimer(v.Channel, v.Text) }, cronName)
|
||||
|
||||
// Add new value to the slice
|
||||
ts = append(ts, v)
|
||||
|
||||
app.Scheduler.AddFunc(repeating, func() { app.newPrivateMessageTimer(v.Channel, v.Text) }, cronName)
|
||||
}
|
||||
|
||||
// var model1 rdbVal
|
||||
// if err := app.Rdb.HGetAll(ctx, cronName).Scan(&model1); err != nil {
|
||||
// app.Logger.Panic(err)
|
||||
// }
|
||||
|
||||
app.Logger.Infow("Initial timers",
|
||||
"timer", ts,
|
||||
)
|
||||
|
@ -247,7 +298,7 @@ func (app *Application) newPrivateMessageTimer(channel, text string) {
|
|||
|
||||
// DeleteTimer takes in the name of a timer and tries to delete the timer from the database.
|
||||
func (app *Application) DeleteTimer(name string, message twitch.PrivateMessage) {
|
||||
cronName := fmt.Sprintf("%s%s", message.Channel, name)
|
||||
cronName := fmt.Sprintf("%s-%s", message.Channel, name)
|
||||
app.Scheduler.RemoveJob(cronName)
|
||||
|
||||
app.Logger.Infow("Deleting timer",
|
||||
|
@ -256,6 +307,7 @@ func (app *Application) DeleteTimer(name string, message twitch.PrivateMessage)
|
|||
"cronName", cronName,
|
||||
)
|
||||
|
||||
_ = app.Rdb.Del(ctx, cronName)
|
||||
err := app.Models.Timers.Delete(name)
|
||||
if err != nil {
|
||||
app.Logger.Errorw("Error deleting timer from database",
|
||||
|
|
3
go.mod
3
go.mod
|
@ -15,7 +15,10 @@ require (
|
|||
)
|
||||
|
||||
require (
|
||||
github.com/cespare/xxhash/v2 v2.2.0 // indirect
|
||||
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect
|
||||
github.com/golang-jwt/jwt v3.2.1+incompatible // indirect
|
||||
github.com/redis/go-redis/v9 v9.0.3 // indirect
|
||||
github.com/shkh/lastfm-go v0.0.0-20191215035245-89a801c244e0 // indirect
|
||||
go.uber.org/atomic v1.9.0 // indirect
|
||||
go.uber.org/multierr v1.8.0 // indirect
|
||||
|
|
6
go.sum
6
go.sum
|
@ -2,9 +2,13 @@ github.com/benbjohnson/clock v1.1.0 h1:Q92kusRqC1XV2MjkWETPvjJVqKetz1OzxZB7mHJLj
|
|||
github.com/benbjohnson/clock v1.1.0/go.mod h1:J11/hYXuz8f4ySSvYwY0FKfm+ezbsZBKZxNJlLklBHA=
|
||||
github.com/briandowns/openweathermap v0.18.0 h1:JYTtJ4bKjXZRmDTe7huJ5+dZ7CsjPUw10GUzMASkNV8=
|
||||
github.com/briandowns/openweathermap v0.18.0/go.mod h1:0GLnknqicWxXnGi1IqoOaZIw+kIe5hkt+YM5WY3j8+0=
|
||||
github.com/cespare/xxhash/v2 v2.2.0 h1:DC2CZ1Ep5Y4k3ZQ899DldepgrayRUGE6BBZ/cd9Cj44=
|
||||
github.com/cespare/xxhash/v2 v2.2.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs=
|
||||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f h1:lO4WD4F/rVNCu3HqELle0jiPLLBs70cWOduZpkS1E78=
|
||||
github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f/go.mod h1:cuUVRXasLTGF7a8hSLbxyZXjz+1KgoB3wDUb6vlszIc=
|
||||
github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4zYo=
|
||||
github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
|
||||
github.com/gempir/go-twitch-irc/v3 v3.2.0 h1:ENhsa7RgBE1GMmDqe0iMkvcSYfgw6ZsXilt+sAg32/U=
|
||||
|
@ -28,6 +32,8 @@ github.com/pkg/errors v0.8.1 h1:iURUrRGxPUNPdy5/HRSm+Yj6okJ6UtLINN0Q9M4+h3I=
|
|||
github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||
github.com/redis/go-redis/v9 v9.0.3 h1:+7mmR26M0IvyLxGZUHxu4GiBkJkVDid0Un+j4ScYu4k=
|
||||
github.com/redis/go-redis/v9 v9.0.3/go.mod h1:WqMKv5vnQbRuZstUwxQI195wHy+t4PuXDOjzMvcuQHk=
|
||||
github.com/shkh/lastfm-go v0.0.0-20191215035245-89a801c244e0 h1:cgqwZtnR+IQfUYDLJ3Kiy4aE+O/wExTzEIg8xwC4Qfs=
|
||||
github.com/shkh/lastfm-go v0.0.0-20191215035245-89a801c244e0/go.mod h1:n3nudMl178cEvD44PaopxH9jhJaQzthSxUzLO5iKMy4=
|
||||
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
|
||||
|
|
|
@ -8,11 +8,12 @@ import (
|
|||
)
|
||||
|
||||
type Timer struct {
|
||||
ID int `json:"id"`
|
||||
Name string `json:"name"`
|
||||
Text string `json:"text"`
|
||||
Channel string `json:"channel"`
|
||||
Repeat string `json:"repeat"`
|
||||
ID int `json:"id" redis:"timer-id"`
|
||||
Name string `json:"name" redis:"timer-name"`
|
||||
CronName string `redis:"timer-cronname"`
|
||||
Text string `json:"text" redis:"timer-text"`
|
||||
Channel string `json:"channel" redis:"timer-channel"`
|
||||
Repeat string `json:"repeat" redis:"timer-repeat"`
|
||||
}
|
||||
|
||||
type TimerModel struct {
|
||||
|
|
Loading…
Reference in a new issue