Skip to content

Commit

Permalink
Add support for recurring events and add year to channel name (#3)
Browse files Browse the repository at this point in the history
  • Loading branch information
yeslayla committed Mar 5, 2023
1 parent 97c9006 commit 228c293
Show file tree
Hide file tree
Showing 7 changed files with 81 additions and 15 deletions.
1 change: 1 addition & 0 deletions ReadMe.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ Bird Bot is a discord bot for managing and organizing events for a small discord
- Notifying when events are created & cancelled
- Delete text channels after events
- Archive text channels after events
- Create recurring weekly events

## Usage

Expand Down
15 changes: 14 additions & 1 deletion app/bot.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"fmt"
"log"
"os"
"strings"

"github.com/ilyakaznacheev/cleanenv"
"github.com/yeslayla/birdbot/core"
Expand Down Expand Up @@ -104,7 +105,7 @@ func (app *Bot) Notify(message string) {
}

func (app *Bot) onReady(d *discord.Discord) {
app.Notify(fmt.Sprintf("BirdBot %s is ready!", Version))
app.session.SetStatus(fmt.Sprintf("with fire! (%s)", Version))
}

func (app *Bot) onEventCreate(d *discord.Discord, event *core.Event) {
Expand Down Expand Up @@ -184,6 +185,18 @@ func (app *Bot) onEventComplete(d *discord.Discord, event *core.Event) {

log.Printf("Deleted channel: '%s'", channel.Name)
}

if strings.Contains(strings.ToLower(event.Description), "recurring weekly") {
startTime := event.DateTime.AddDate(0, 0, 7)
finishTime := event.CompleteTime.AddDate(0, 0, 7)
nextEvent := event
nextEvent.DateTime = startTime
nextEvent.CompleteTime = finishTime

if err := app.session.CreateEvent(nextEvent); err != nil {
log.Print("Failed to create recurring event: ", err)
}
}
}

func NewBot() *Bot {
Expand Down
16 changes: 10 additions & 6 deletions core/event.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,11 +10,14 @@ import (
const REMOTE_LOCATION string = "online"

type Event struct {
Name string
ID string
Location string
Completed bool
DateTime time.Time
Name string
ID string
Location string
Completed bool
DateTime time.Time
CompleteTime time.Time
Description string
Image string

Organizer *User
}
Expand All @@ -25,8 +28,9 @@ func (event *Event) Channel() *Channel {
month := event.GetMonthPrefix()
day := event.DateTime.Day()
city := event.GetCityFromLocation()
year := event.DateTime.Year()

channel := fmt.Sprint(month, "-", day, city, "-", event.Name)
channel := fmt.Sprint(month, "-", day, city, "-", event.Name, "-", year)
channel = strings.ReplaceAll(channel, " ", "-")
channel = strings.ToLower(channel)

Expand Down
10 changes: 5 additions & 5 deletions core/event_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ func TestGetChannelName(t *testing.T) {
Location: "1234 Place Rd, Ann Arbor, MI 00000",
DateTime: time.Date(2022, time.January, 5, 0, 0, 0, 0, time.UTC),
}
assert.Equal("jan-5-ann-arbor-hello-world", event.Channel().Name)
assert.Equal("jan-5-ann-arbor-hello-world-2022", event.Channel().Name)

// Test Unparsable Location
// lmanley: Note it'd be nice to expand support for this
Expand All @@ -25,31 +25,31 @@ func TestGetChannelName(t *testing.T) {
Location: "Michigan Theater, Ann Arbor",
DateTime: time.Date(2022, time.January, 5, 0, 0, 0, 0, time.UTC),
}
assert.Equal("jan-5-hello-world", event.Channel().Name)
assert.Equal("jan-5-hello-world-2022", event.Channel().Name)

// Test Short Location
event = Event{
Name: "Hello World",
Location: "Monroe, MI",
DateTime: time.Date(2022, time.January, 5, 0, 0, 0, 0, time.UTC),
}
assert.Equal("jan-5-monroe-hello-world", event.Channel().Name)
assert.Equal("jan-5-monroe-hello-world-2022", event.Channel().Name)

// Test Short Location
event = Event{
Name: "Hello World",
Location: "Monroe St, Monroe , MI",
DateTime: time.Date(2022, time.January, 5, 0, 0, 0, 0, time.UTC),
}
assert.Equal("jan-5-monroe-hello-world", event.Channel().Name)
assert.Equal("jan-5-monroe-hello-world-2022", event.Channel().Name)

// Test Remote Event
event = Event{
Name: "Hello World",
Location: REMOTE_LOCATION,
DateTime: time.Date(2022, time.January, 5, 0, 0, 0, 0, time.UTC),
}
assert.Equal("jan-5-online-hello-world", event.Channel().Name)
assert.Equal("jan-5-online-hello-world-2022", event.Channel().Name)
}

func TestMonthPrefix(t *testing.T) {
Expand Down
6 changes: 6 additions & 0 deletions discord/discord.go
Original file line number Diff line number Diff line change
Expand Up @@ -95,3 +95,9 @@ func (discord *Discord) OnEventUpdate(handler func(*Discord, *core.Event)) {
handler(discord, event)
})
}

func (discord *Discord) SetStatus(status string) {
if err := discord.session.UpdateGameStatus(0, status); err != nil {
log.Fatal("Failed to update status: ", err)
}
}
38 changes: 36 additions & 2 deletions discord/event.go
Original file line number Diff line number Diff line change
@@ -1,19 +1,30 @@
package discord

import (
"time"

"github.com/bwmarrin/discordgo"
"github.com/yeslayla/birdbot/core"
)

// NewEvent converts a discordgo.GuildScheduledEvent to birdbot event
func NewEvent(guildEvent *discordgo.GuildScheduledEvent) *core.Event {
event := &core.Event{
Name: guildEvent.Name,
ID: guildEvent.ID,
Name: guildEvent.Name,
Description: guildEvent.Description,
ID: guildEvent.ID,
Organizer: &core.User{
ID: guildEvent.CreatorID,
},
DateTime: guildEvent.ScheduledStartTime,
Image: guildEvent.Image,
}

if guildEvent.ScheduledEndTime != nil {
event.CompleteTime = *guildEvent.ScheduledEndTime
} else {
year, month, day := guildEvent.ScheduledStartTime.Date()
event.CompleteTime = time.Date(year, month, day, 0, 0, 0, 0, guildEvent.ScheduledStartTime.Location())
}

event.Completed = guildEvent.Status == discordgo.GuildScheduledEventStatusCompleted
Expand All @@ -26,3 +37,26 @@ func NewEvent(guildEvent *discordgo.GuildScheduledEvent) *core.Event {

return event
}

func (discord *Discord) CreateEvent(event *core.Event) error {

params := &discordgo.GuildScheduledEventParams{
Name: event.Name,
Description: event.Description,
ScheduledStartTime: &event.DateTime,
ScheduledEndTime: &event.CompleteTime,
Image: event.Image,
EntityType: discordgo.GuildScheduledEventEntityTypeExternal,
PrivacyLevel: discordgo.GuildScheduledEventPrivacyLevelGuildOnly,
}

if event.Location != "" {
params.EntityMetadata = &discordgo.GuildScheduledEventEntityMetadata{
Location: event.Location,
}
}

_, err := discord.session.GuildScheduledEventCreate(discord.guildID, params)

return err
}
10 changes: 9 additions & 1 deletion main.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,21 @@ import (
"flag"
"fmt"
"log"
"os"
"path"

"github.com/yeslayla/birdbot/app"
)

func main() {

configDir, _ := os.UserConfigDir()

defaultConfigPath := path.Join(configDir, "birdbot", "config.yaml")

var config_file string
var version bool
flag.StringVar(&config_file, "c", "birdbot.yaml", "Path to config file")
flag.StringVar(&config_file, "c", defaultConfigPath, "Path to config file")
flag.BoolVar(&version, "v", false, "List version")
flag.Parse()

Expand All @@ -21,6 +28,7 @@ func main() {
}

bot := app.NewBot()

if err := bot.Initialize(config_file); err != nil {
log.Fatal("Failed to initialize: ", err)
}
Expand Down

0 comments on commit 228c293

Please sign in to comment.