Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add obs-start command #17

Merged
merged 2 commits into from
Sep 16, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 14 additions & 5 deletions cmd/darsrec/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,13 +30,22 @@ func (ac *AsyncConf) Confs() []*rec.RecordConfig {

func main() {

password := os.Getenv("OBS_WEBSOCKET_PASSWORD")
if password == "" {
fmt.Println("OBS_WEBSOCKET_PASSWORD is unset, cannot proceed")
os.Exit(1)
var host, password string
{
host = os.Getenv("OBS_WEBSOCKET_HOST")
if host == "" {
host = "localhost:4455"
fmt.Printf("OBS_WEBSOCKET_HOST not set, using default %s\f", host)
}

password = os.Getenv("OBS_WEBSOCKET_PASSWORD")
if password == "" {
fmt.Println("OBS_WEBSOCKET_PASSWORD is unset, cannot proceed")
os.Exit(1)
}
}

client, err := rec.New(password)
client, err := rec.New(host, password)
if err != nil {
panic(err)
}
Expand Down
2 changes: 1 addition & 1 deletion cmd/discord_bot/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,5 +16,5 @@ var (
func init() { flag.Parse() }

func main() {
discord.Run(GuildID, BotToken, RemoveCommands)
go discord.Run(GuildID, BotToken, RemoveCommands, nil)
}
49 changes: 44 additions & 5 deletions cmd/monolith/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,13 @@ import (
"io"
"net/http"
"os"
"os/signal"
"strings"
"time"

"github.com/ccil-kbw/robot/discord"
v1 "github.com/ccil-kbw/robot/iqama/v1"
"github.com/ccil-kbw/robot/rec"
)

var (
Expand All @@ -33,16 +37,51 @@ type Config struct {
}

func main() {
var err error
msgs := make(chan string)
stop := make(chan os.Signal, 1)

signal.Notify(stop, os.Interrupt)

if config.Features.Proxy {
go proxy()
}

var obs *rec.Recorder

if config.Features.Record {
host := os.Getenv("MDROID_OBS_WEBSOCKET_HOST")
password := os.Getenv("MDROID_OBS_WEBSOCKET_PASSWORD")
obs, err = rec.New(host, password)
if err != nil {
fmt.Printf("could not reach or authenticate to OBS at %s, with password %s[...]%s", host, password[0:2], password[len(password)-3:len(password)-1])
}
}

if config.Features.DiscordBot {
go bot()
go bot(obs)
}

out:
for {
select {
// discord msgs dispatcher
case msg := <-msgs:
fmt.Printf("%v, operation received from discord: %s\n", time.Now(), msg)
if strings.HasPrefix(msg, "obs-") {
if config.Features.Record {
fmt.Println("feature enabled")
obs.DispatchOperation(msg)
}
}
case <-stop:
// simplest way to wait for the nested go routines to clean up
// takes < 2 ms but better be safe
time.Sleep(10 * time.Second)
break out
}
}

// handle erroring, for now just block
<-make(chan struct{})
}

// proxy, move to apis, maybe pkg/apis/proxyserver/proxyserver.go
Expand All @@ -56,10 +95,10 @@ func proxy() {
_ = http.ListenAndServe(":3333", nil)
}

func bot() {
func bot(obs *rec.Recorder) {
guildID := os.Getenv("MDROID_BOT_GUILD_ID")
botToken := os.Getenv("MDROID_BOT_TOKEN")
removeCommands := true

discord.Run(&guildID, &botToken, &removeCommands)
discord.Run(&guildID, &botToken, &removeCommands, obs)
}
82 changes: 68 additions & 14 deletions discord/discord.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,11 +4,14 @@
package discord

import (
"fmt"
"log"
"os"
"os/signal"
"time"

"github.com/ccil-kbw/robot/mappers"
"github.com/ccil-kbw/robot/rec"

"github.com/bwmarrin/discordgo"
iqamav1 "github.com/ccil-kbw/robot/iqama/v1"
Expand All @@ -21,34 +24,84 @@ var (
Description: "Get Today's Iqama",
},
{
Name: "test",
Description: "Some test command",
Name: "obs-start",
Description: "Start Recording on the Main Camera (e.g unscheduled speech @ccil-kbw)",
},
{
Name: "obs-status",
Description: "See OBS and Recording Status on the Main Camera",
},
}

commandHandlers = map[string]func(s *discordgo.Session, i *discordgo.InteractionCreate){
"iqama": func(s *discordgo.Session, i *discordgo.InteractionCreate) {
commandHandlers = map[string]func(s *discordgo.Session, i *discordgo.InteractionCreate, obs *rec.Recorder){
"iqama": func(s *discordgo.Session, i *discordgo.InteractionCreate, obs *rec.Recorder) {
s.InteractionRespond(i.Interaction, &discordgo.InteractionResponse{
Type: discordgo.InteractionResponseChannelMessageWithSource,
Data: mappers.IqamaTimesToDiscordInteractionResponseData(iqamav1.Get()),
})
},
"test": func(s *discordgo.Session, i *discordgo.InteractionCreate) {
"obs-start": func(s *discordgo.Session, i *discordgo.InteractionCreate, obs *rec.Recorder) {
s.InteractionRespond(i.Interaction, &discordgo.InteractionResponse{
Type: discordgo.InteractionResponseChannelMessageWithSource,
Data: &discordgo.InteractionResponseData{
Embeds: []*discordgo.MessageEmbed{
{
URL: "https://ccil-kbw.com/iqama",
Type: discordgo.EmbedTypeRich,
Title: "Iqama Time",
Description: "Iqama pulled from https://ccil-kbw.com/iqama",
Color: 0x05993e,
Title: "Scheduling Start",
Description: "OBS Scheduling Start Operation",
Color: 0x05294e,
Fields: func() []*discordgo.MessageEmbedField {
fmt.Println("discord command called: /obs-start")
if obs == nil {
return []*discordgo.MessageEmbedField{
{Name: "Error", Value: "OBS Client not initialized"},
}
}
now := time.Now()
return []*discordgo.MessageEmbedField{
{
Name: "Test",
Value: "Test",
Name: "OBS Recording Started",
Value: fmt.Sprintf("Will be scheduling until %d:%d", now.Hour(), now.Minute()),
},
}
}(),
},
},
},
},
)
},
"obs-status": func(s *discordgo.Session, i *discordgo.InteractionCreate, obs *rec.Recorder) {
s.InteractionRespond(i.Interaction, &discordgo.InteractionResponse{
Type: discordgo.InteractionResponseChannelMessageWithSource,
Data: &discordgo.InteractionResponseData{
Embeds: []*discordgo.MessageEmbed{
{
Type: discordgo.EmbedTypeRich,
Title: "Scheduling Status",
Description: "OBS Scheduling Status Operation",
Color: 0x05294e,
Fields: func() []*discordgo.MessageEmbedField {
fmt.Println("discord command called: /obs-status")
if obs == nil {
return []*discordgo.MessageEmbedField{
{Name: "Error", Value: "OBS Client not initialized"},
}
}
isRecording, err := obs.IsRecording()
if err != nil {
return []*discordgo.MessageEmbedField{
{
Name: "Record Status",
Value: "Could not access OBS",
},
}
}

return []*discordgo.MessageEmbedField{
{
Name: "Record Status",
Value: fmt.Sprintf("recording: %v", isRecording),
},
}
}(),
Expand All @@ -62,7 +115,7 @@ var (
)

// Run the Discord bot. NOTE: Function can be split
func Run(guildID, botToken *string, removeCommands *bool) {
func Run(guildID, botToken *string, removeCommands *bool, obs *rec.Recorder) {
var err error
var s *discordgo.Session

Expand All @@ -73,13 +126,14 @@ func Run(guildID, botToken *string, removeCommands *bool) {

s.AddHandler(func(s *discordgo.Session, i *discordgo.InteractionCreate) {
if h, ok := commandHandlers[i.ApplicationCommandData().Name]; ok {
h(s, i)
h(s, i, obs)
}
})

s.AddHandler(func(s *discordgo.Session, r *discordgo.Ready) {
log.Printf("Logged in as: %v#%v", s.State.User.Username, s.State.User.Discriminator)
})

err = s.Open()
if err != nil {
log.Fatalf("Cannot open the session: %v", err)
Expand All @@ -99,7 +153,7 @@ func Run(guildID, botToken *string, removeCommands *bool) {

stop := make(chan os.Signal, 1)
signal.Notify(stop, os.Interrupt)
log.Println("Press Ctrl+C to exit")
fmt.Println("Press Ctrl+C to exit")
<-stop

if *removeCommands {
Expand Down
3 changes: 3 additions & 0 deletions mappers/iqamadiscord.go
Original file line number Diff line number Diff line change
@@ -1,11 +1,14 @@
package mappers

import (
"fmt"

"github.com/bwmarrin/discordgo"
iqamav1 "github.com/ccil-kbw/robot/iqama/v1"
)

func IqamaTimesToDiscordInteractionResponseData(resp iqamav1.Resp) *discordgo.InteractionResponseData {
fmt.Println("discord command called: /iqama")
return &discordgo.InteractionResponseData{
Embeds: []*discordgo.MessageEmbed{
{
Expand Down
13 changes: 11 additions & 2 deletions rec/rec.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,13 @@ type Recorder struct {
client *goobs.Client
}

func New(password string) (*Recorder, error) {
func New(host, password string) (*Recorder, error) {

client, err := goobs.New("localhost:4455", goobs.WithPassword(password))
if host == "" {
host = "localhost:4455"
}

client, err := goobs.New(host, goobs.WithPassword(password))
if err != nil {
return nil, err
}
Expand All @@ -32,6 +36,11 @@ func New(password string) (*Recorder, error) {
}, nil
}

func (o *Recorder) DispatchOperation(msg string) error {
fmt.Printf("[todo] dispatching operation: %s\n", msg)
return nil
}

func (o *Recorder) Disconnect() error {
return o.client.Disconnect()
}
Expand Down