add cmd/mstdn
parent
48c393bd8b
commit
a3cc5fd9e6
|
@ -0,0 +1,143 @@
|
|||
package main
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"bytes"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"runtime"
|
||||
"strings"
|
||||
|
||||
"github.com/mattn/go-mastodon"
|
||||
"github.com/mattn/go-tty"
|
||||
"golang.org/x/net/html"
|
||||
)
|
||||
|
||||
var blockTags = []string{"div", "br", "p", "blockquote", "pre", "h1", "h2", "h3", "h4", "h5", "h6"}
|
||||
|
||||
func extractText(node *html.Node, w *bytes.Buffer) {
|
||||
if node.Type == html.TextNode {
|
||||
data := strings.Trim(node.Data, "\r\n")
|
||||
if data != "" {
|
||||
w.WriteString(data)
|
||||
}
|
||||
} else if node.Type == html.ElementNode {
|
||||
if node.Data == "li" {
|
||||
w.WriteString("\n* ")
|
||||
}
|
||||
}
|
||||
for c := node.FirstChild; c != nil; c = c.NextSibling {
|
||||
extractText(c, w)
|
||||
}
|
||||
if node.Type == html.ElementNode {
|
||||
for _, bt := range blockTags {
|
||||
if strings.ToLower(node.Data) == bt {
|
||||
w.WriteString("\n")
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func prompt() (string, string, error) {
|
||||
t, err := tty.Open()
|
||||
if err != nil {
|
||||
return "", "", err
|
||||
}
|
||||
defer t.Close()
|
||||
|
||||
fmt.Print("E-Mail: ")
|
||||
b, _, err := bufio.NewReader(os.Stdin).ReadLine()
|
||||
if err != nil {
|
||||
return "", "", err
|
||||
}
|
||||
email := string(b)
|
||||
|
||||
fmt.Print("Password: ")
|
||||
password, err := t.ReadPassword()
|
||||
if err != nil {
|
||||
return "", "", err
|
||||
}
|
||||
return email, password, nil
|
||||
}
|
||||
|
||||
func getConfig() (string, *mastodon.Config, error) {
|
||||
dir := os.Getenv("HOME")
|
||||
if dir == "" && runtime.GOOS == "windows" {
|
||||
dir = os.Getenv("APPDATA")
|
||||
if dir == "" {
|
||||
dir = filepath.Join(os.Getenv("USERPROFILE"), "Application Data", "mstdn")
|
||||
}
|
||||
dir = filepath.Join(dir, "mstdn")
|
||||
} else {
|
||||
dir = filepath.Join(dir, ".config", "mstdn")
|
||||
}
|
||||
if err := os.MkdirAll(dir, 0700); err != nil {
|
||||
return "", nil, err
|
||||
}
|
||||
file := filepath.Join(dir, "settings.json")
|
||||
b, err := ioutil.ReadFile(file)
|
||||
if err != nil && !os.IsNotExist(err) {
|
||||
return "", nil, err
|
||||
}
|
||||
config := &mastodon.Config{
|
||||
Server: "https://mstdn.jp",
|
||||
ClientID: "654a15390204e70d74f8d9264526e017e26d323e20e3f983409c157115009862",
|
||||
ClientSecret: "17274242a0846ebadcdda77727666c9d475f1989b56ad9bd959021f62f92a84c",
|
||||
}
|
||||
if err == nil {
|
||||
err = json.Unmarshal(b, &config)
|
||||
if err != nil {
|
||||
return "", nil, fmt.Errorf("could not unmarshal %v: %v", file, err)
|
||||
}
|
||||
}
|
||||
return file, config, nil
|
||||
}
|
||||
|
||||
func main() {
|
||||
file, config, err := getConfig()
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
c := mastodon.NewClient(config)
|
||||
|
||||
if config.AccessToken == "" {
|
||||
email, password, err := prompt()
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
err = c.Authenticate(email, password)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
b, err := json.MarshalIndent(config, "", " ")
|
||||
if err != nil {
|
||||
log.Fatal("failed to store file:", err)
|
||||
}
|
||||
err = ioutil.WriteFile(file, b, 0700)
|
||||
if err != nil {
|
||||
log.Fatal("failed to store file:", err)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
timeline, err := c.GetTimeline("/api/v1/timelines/home")
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
for _, t := range timeline {
|
||||
doc, err := html.Parse(strings.NewReader(t.Content))
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
var buf bytes.Buffer
|
||||
extractText(doc, &buf)
|
||||
fmt.Println(t.Account.Username)
|
||||
fmt.Println(buf.String())
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue