package main import ( "encoding/json" "flag" "io" "io/ioutil" "net/http" "net/url" "os" "path/filepath" "strings" "github.com/rs/zerolog" "github.com/rs/zerolog/log" ) var ( token = flag.String("token", "", "Slack API token") path = flag.String("path", "./files", "Path to save files") ) func main() { flag.Parse() log.Logger = log.Output(zerolog.ConsoleWriter{Out: os.Stderr}) if *token == "" { log.Fatal().Msg("No token provided.") return } files := getFiles() for n, f := range files { downloadFile(n, f) } } func getFiles() map[string]string { files := fileResp{} log.Debug().Msgf("Getting files") body := mkReq("https://slack.com/api/emoji.list", "token", *token, ) err := json.Unmarshal(body, &files) checkErr(err) log.Debug().Msgf("Ok: %v", files.Ok) if !files.Ok { log.Debug().Msgf("%+v", files) } return files.Files } func downloadFile(n, f string) { url := strings.Replace(f, "\\", "", -1) // because fuck slack if strings.HasPrefix(url, "alias:") { log.Debug().Msgf("Skipping alias: %s", url) return } fileNameParts := strings.Split(url, `/`) ext := fileNameParts[len(fileNameParts)-1] fileNameParts = strings.Split(ext, ".") ext = fileNameParts[len(fileNameParts)-1] fname := filepath.Join(*path, n+"."+ext) log.Debug().Msgf("Downloading from: %s", url) client := &http.Client{} req, err := http.NewRequest("GET", url, nil) checkErr(err) req.Header.Add("Authorization", "Bearer "+*token) resp, err := client.Do(req) checkErr(err) defer resp.Body.Close() out, err := os.Create(fname) checkErr(err) defer out.Close() io.Copy(out, resp.Body) log.Debug().Msgf("Downloaded %s", f) } func checkErr(err error) { if err != nil { log.Fatal().Err(err) } } func mkReq(path string, arg ...string) []byte { if len(arg)%2 != 0 { log.Fatal().Msg("Bad request arg number.") } u, err := url.Parse(path) checkErr(err) q := u.Query() for i := 0; i < len(arg); i += 2 { key := arg[i] val := arg[i+1] if val != "" { q.Set(key, val) } } u.RawQuery = q.Encode() resp, err := http.Get(u.String()) checkErr(err) body, err := ioutil.ReadAll(resp.Body) checkErr(err) return body } type fileResp struct { Ok bool `json:"ok"` Files map[string]string `json:"emoji"` }