Skip to content

Commit

Permalink
Add commands for managing apps on device (#667)
Browse files Browse the repository at this point in the history
* Add command for listing apps installed on a given tidbyt

Example:

```
$ ./pixlet list coarsely-sunny-refreshed-blowfish-f9f
boris-bikes		MKBGQqUqZfRIAvQDADC9
tartan			EpxRBkyVx3XgOpXJrGlK
tube-status		tVGDbkTLIpeBGMEhNUCM
amazing			IxOnNFhmbyr5H3BjUuPp
tube			PE4KU0h3k9Jit7Dfj7GS
busy-tube		UAZrgEqv58XV27dIXGbW
tube			2RTeEpncRe9T7T5EtCfS
busy-tube		vEGu50hl59fpxQYaiNUE
tube			d0eHVa3g1NaTDz7EG91l
tube			WxH2uHMmME7CT6KBvCUJ
tube			EdXutAKiSGryn9W0DJ7O
busy-tube		XoYkwjDbyOc7yoSpPEGN
mind-the-gap		mTbYjHAtBwHC2GMICacF
london-bus-stop		engEBag2Nini9nm7Fwet
london-bus-stop		UUQUbjEUI5W1Uh0KqaGg
london-bus-stop		FcUt1ZgEYvlE8DIwp9WJ
london-bus-stop		KsF57VpF70M0610WI8zf
london-bus-stop		5hFDlBKIigd1xYqAojmm
sunrise-sunset		cR47CGrB2yHsuTBYlf8T
weather			8BxjDROVyZ2BE3Z8J1eG
clock-by-henry		MCWwnWVcQflVZge3usXC
jwst			dUxcwMJvBBNpxGepbCNH
life			kIs0z9DRVt80AhiQLU1g
random-cats		2Tf77dm191pxSiokKP9h
national-rail		BxXPJYzjgeQRMcE41Icd
earthquake-map		zOl1GofQfeAkxohCcmZC
yule-log		DUDIQ1figTTK3mqlvGyd
superbowl		NNKsGirwYUlBdEpuAj6r
```

* Add command for deleting scripts from a Tidbyt

push.go has a comment saying installation-id should be a flag. I think it makes sense as an argument here, since it's required. You can push without an installation ID but you can't delete one. Feel free to let me know if you'd prefer a flag though.

This let me get rid of the broken app that I couldn't delete from my phone. So I'm happy.
  • Loading branch information
dinosaursrarr authored Jul 31, 2023
1 parent 591288e commit 67cad9b
Show file tree
Hide file tree
Showing 3 changed files with 160 additions and 0 deletions.
68 changes: 68 additions & 0 deletions cmd/delete.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package cmd

import (
"fmt"
"io/ioutil"
"net/http"
"os"

"github.com/spf13/cobra"
)

const (
TidbytAPIDelete = "https://api.tidbyt.com/v0/devices/%s/installations/%s"
)

func init() {
DeleteCmd.Flags().StringVarP(&apiToken, "api-token", "t", "", "Tidbyt API token")
}

var DeleteCmd = &cobra.Command{
Use: "delete [device ID] [installation ID]",
Short: "Delete a pixlet script from a Tidbyt",
Args: cobra.MinimumNArgs(2),
RunE: delete,
}

func delete(cmd *cobra.Command, args []string) error {
deviceID := args[0]
installationID := args[1]

if apiToken == "" {
apiToken = os.Getenv(APITokenEnv)
}

if apiToken == "" {
apiToken = oauthTokenFromConfig(cmd.Context())
}

if apiToken == "" {
return fmt.Errorf("blank Tidbyt API token (use `pixlet login`, set $%s or pass with --api-token)", APITokenEnv)
}

client := &http.Client{}
req, err := http.NewRequest(
"DELETE",
fmt.Sprintf(TidbytAPIDelete, deviceID, installationID),
nil,
)
if err != nil {
return fmt.Errorf("creating DELETE request: %w", err)
}

req.Header.Add("Authorization", fmt.Sprintf("Bearer %s", apiToken))

resp, err := client.Do(req)
if err != nil {
return fmt.Errorf("deleting via API: %w", err)
}

if resp.StatusCode != 200 {
fmt.Printf("Tidbyt API returned status %s\n", resp.Status)
body, _ := ioutil.ReadAll(resp.Body)
fmt.Println(string(body))
return fmt.Errorf("Tidbyt API returned status: %s", resp.Status)
}

return nil
}
90 changes: 90 additions & 0 deletions cmd/list.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
package cmd

import (
"encoding/json"
"fmt"
"io/ioutil"
"net/http"
"os"
"text/tabwriter"

"github.com/spf13/cobra"
)

const (
TidbytAPIList = "https://api.tidbyt.com/v0/devices/%s/installations"
)

type TidbytInstallationJSON struct {
Id string `json:"id"`
AppId string `json:"appID"`
}

type TidbytInstallationListJSON struct {
Installations []TidbytInstallationJSON `json:"installations"`
}

func init() {
ListCmd.Flags().StringVarP(&apiToken, "api-token", "t", "", "Tidbyt API token")
}

var ListCmd = &cobra.Command{
Use: "list [device ID]",
Short: "Lists all apps installed on a Tidbyt",
Args: cobra.MinimumNArgs(1),
RunE: listInstallations,
}

func listInstallations(cmd *cobra.Command, args []string) error {
deviceID := args[0]

if apiToken == "" {
apiToken = os.Getenv(APITokenEnv)
}

if apiToken == "" {
apiToken = oauthTokenFromConfig(cmd.Context())
}

if apiToken == "" {
return fmt.Errorf("blank Tidbyt API token (use `pixlet login`, set $%s or pass with --api-token)", APITokenEnv)
}

client := &http.Client{}
req, err := http.NewRequest(
"GET",
fmt.Sprintf(TidbytAPIList, deviceID), nil)
if err != nil {
return fmt.Errorf("creating GET request: %w", err)
}

req.Header.Add("Authorization", fmt.Sprintf("Bearer %s", apiToken))

resp, err := client.Do(req)
if err != nil {
return fmt.Errorf("listing installations from API: %w", err)
}

body, _ := ioutil.ReadAll(resp.Body)
if resp.StatusCode != 200 {
fmt.Printf("Tidbyt API returned status %s\n", resp.Status)
fmt.Println(string(body))
return fmt.Errorf("Tidbyt API returned status: %s", resp.Status)
}

var installations TidbytInstallationListJSON
err = json.Unmarshal(body, &installations)
if err != nil {
return fmt.Errorf("failed to unmarshal json: %w", err)
}

w := new(tabwriter.Writer)
w.Init(os.Stdout, 22, 8, 0, '\t', 0)
defer w.Flush()

for _, inst := range installations.Installations {
fmt.Fprintf(w, "%s\t%s\n", inst.AppId, inst.Id)
}

return nil
}
2 changes: 2 additions & 0 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ func init() {
rootCmd.AddCommand(cmd.ProfileCmd)
rootCmd.AddCommand(cmd.LoginCmd)
rootCmd.AddCommand(cmd.DevicesCmd)
rootCmd.AddCommand(cmd.ListCmd)
rootCmd.AddCommand(cmd.DeleteCmd)
rootCmd.AddCommand(cmd.FormatCmd)
rootCmd.AddCommand(cmd.LintCmd)
rootCmd.AddCommand(cmd.CheckCmd)
Expand Down

0 comments on commit 67cad9b

Please sign in to comment.