betula.go 1.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. package betula
  2. import (
  3. "fmt"
  4. "net/http"
  5. "net/url"
  6. "strings"
  7. "time"
  8. "miniflux.app/v2/internal/urllib"
  9. "miniflux.app/v2/internal/version"
  10. )
  11. const defaultClientTimeout = 10 * time.Second
  12. type Client struct {
  13. url string
  14. token string
  15. }
  16. func NewClient(url, token string) *Client {
  17. return &Client{url: url, token: token}
  18. }
  19. func (c *Client) CreateBookmark(entryURL, entryTitle string, tags []string) error {
  20. apiEndpoint, err := urllib.JoinBaseURLAndPath(c.url, "/save-link")
  21. if err != nil {
  22. return fmt.Errorf("betula: unable to generate save-link endpoint: %v", err)
  23. }
  24. values := url.Values{}
  25. values.Add("url", entryURL)
  26. values.Add("title", entryTitle)
  27. values.Add("tags", strings.Join(tags, ","))
  28. request, err := http.NewRequest(http.MethodPost, apiEndpoint+"?"+values.Encode(), nil)
  29. if err != nil {
  30. return fmt.Errorf("betula: unable to create request: %v", err)
  31. }
  32. request.Header.Set("Content-Type", "application/x-www-form-urlencoded")
  33. request.Header.Set("User-Agent", "Miniflux/"+version.Version)
  34. request.AddCookie(&http.Cookie{Name: "betula-token", Value: c.token})
  35. httpClient := &http.Client{Timeout: defaultClientTimeout}
  36. response, err := httpClient.Do(request)
  37. if err != nil {
  38. return fmt.Errorf("betula: unable to send request: %v", err)
  39. }
  40. defer response.Body.Close()
  41. if response.StatusCode >= 400 {
  42. return fmt.Errorf("betula: unable to create bookmark: url=%s status=%d", apiEndpoint, response.StatusCode)
  43. }
  44. return nil
  45. }