diff --git a/commands/commands.go b/commands/commands.go index c3c09ef..a30f35d 100644 --- a/commands/commands.go +++ b/commands/commands.go @@ -3,6 +3,10 @@ package commands import ( "encoding/json" "fmt" + "io/ioutil" + "os" + "path/filepath" + "strings" "gospt/ctx" @@ -13,12 +17,23 @@ func Play(ctx *ctx.Context, client *spotify.Client) error { var err error err = client.Play(ctx) if err != nil { + if isNoActiveError(err) { + return playWithTransfer(ctx, client) + } return err } ctx.Println("Playing!") return nil } +func Devices(ctx *ctx.Context, client *spotify.Client) error { + devices, err := client.PlayerDevices(ctx) + if err != nil { + return err + } + return PrintDevices(devices) +} + func Pause(ctx *ctx.Context, client *spotify.Client) error { err := client.Pause(ctx) if err != nil { @@ -72,3 +87,68 @@ func PrintState(state *spotify.PlayerState) error { fmt.Println(string(out)) return nil } + +func PrintDevices(devices []spotify.PlayerDevice) error { + out, err := json.MarshalIndent(devices, "", " ") + if err != nil { + return err + } + fmt.Println(string(out)) + return nil +} + +func SetDevice(ctx *ctx.Context, client *spotify.Client, args []string) error { + if len(args) < 2 { + return fmt.Errorf("Please provide your device ID") + } + devices, err := client.PlayerDevices(ctx) + if err != nil { + return err + } + var set_device spotify.PlayerDevice + for _, device := range devices { + if device.ID.String() == args[1] { + set_device = device + break + } + } + out, err := json.MarshalIndent(set_device, "", " ") + if err != nil { + return err + } + homdir, _ := os.UserHomeDir() + err = ioutil.WriteFile(filepath.Join(homdir, ".config/gospt/device.json"), out, 0o644) + if err != nil { + return err + } + fmt.Println("Your device has been set to: ", set_device.Name) + return nil +} + +func isNoActiveError(err error) bool { + return strings.Contains(err.Error(), "No active device found") +} + +func playWithTransfer(ctx *ctx.Context, client *spotify.Client) error { + configDir, _ := os.UserConfigDir() + deviceFile, err := os.Open(filepath.Join(configDir, "gospt/device.json")) + if err != nil { + return err + } + defer deviceFile.Close() + deviceValue, err := ioutil.ReadAll(deviceFile) + if err != nil { + return err + } + var device *spotify.PlayerDevice + err = json.Unmarshal(deviceValue, &device) + if err != nil { + return err + } + err = client.TransferPlayback(ctx, device.ID, true) + if err != nil { + return err + } + ctx.Println("Playing!") + return nil +} diff --git a/config/config.go b/config/config.go index ee95100..248baaa 100644 --- a/config/config.go +++ b/config/config.go @@ -12,6 +12,7 @@ var Values struct { ClientSecret string `yaml:"client_secret"` DeviceId string `yaml:"device_id"` Port int `yaml:"port"` + DeviceName string `yaml:"device_name"` } func LoadConfig(configDir string) { diff --git a/runner/runner.go b/runner/runner.go index 094a5f6..605e002 100644 --- a/runner/runner.go +++ b/runner/runner.go @@ -32,6 +32,10 @@ func Run(ctx *ctx.Context, client *spotify.Client, args []string) error { return tui.DisplayList(ctx, client) case "status": return commands.Status(ctx, client) + case "devices": + return commands.Devices(ctx, client) + case "setdevice": + return commands.SetDevice(ctx, client, args) default: return fmt.Errorf("Unsupported Command") }