all repos

rss-tools @ c37eeed

get rss feed from sources that(i need and) dont provide one

rss-tools/sources/telegram/sdk.go (view raw)

Oleksandr Smirnov Oleksandr Smirnov
olexsmir@gmail.com
init, 1 month ago
1
package telegram
2
3
import (
4
	"bytes"
5
	"context"
6
	"encoding/json"
7
	"fmt"
8
	"net/http"
9
	"net/url"
10
	"strconv"
11
)
12
13
const apiBase = "https://api.telegram.org"
14
15
type TelegramSDK struct {
16
	client *http.Client
17
	token  string
18
}
19
20
func NewSDK(client *http.Client, token string) *TelegramSDK {
21
	return &TelegramSDK{
22
		token:  token,
23
		client: client,
24
	}
25
}
26
27
type Response[T any] struct {
28
	OK          bool   `json:"ok"`
29
	Result      T      `json:"result"`
30
	Description string `json:"description"`
31
}
32
33
type Update struct {
34
	UpdateID int64    `json:"update_id"`
35
	Message  *Message `json:"message"`
36
}
37
38
type User struct {
39
	ID        int64  `json:"id"`
40
	FirstName string `json:"first_name"`
41
	Username  string `json:"username"`
42
}
43
44
type Chat struct {
45
	ID int64 `json:"id"`
46
}
47
48
type Message struct {
49
	MessageID int64  `json:"message_id"`
50
	From      *User  `json:"from"`
51
	Chat      *Chat  `json:"chat"`
52
	Text      string `json:"text"`
53
	Date      int64  `json:"date"`
54
}
55
56
func (t *TelegramSDK) GetUpdates(ctx context.Context, offset int64) ([]Update, error) {
57
	params := url.Values{}
58
	params.Set("offset", strconv.FormatInt(offset, 10))
59
	params.Set("timeout", "30")
60
61
	var resp Response[[]Update]
62
	if err := t.req(ctx, "getUpdates", params, nil, &resp); err != nil {
63
		return nil, err
64
	}
65
	return resp.Result, nil
66
}
67
68
type messageReactionReq struct {
69
	Type  string `json:"type"`
70
	Emoji string `json:"emoji"`
71
}
72
73
type setReactionReq struct {
74
	ChatID    int64                `json:"chat_id"`
75
	MessageID int64                `json:"message_id"`
76
	Reaction  []messageReactionReq `json:"reaction"`
77
}
78
79
func (t *TelegramSDK) SetReaction(ctx context.Context, chatID, messageID int64, emoji string) error {
80
	var resp Response[bool]
81
	return t.req(ctx, "setMessageReaction", nil, setReactionReq{
82
		ChatID:    chatID,
83
		MessageID: messageID,
84
		Reaction:  []messageReactionReq{{Type: "emoji", Emoji: emoji}},
85
	}, &resp)
86
}
87
88
func (t *TelegramSDK) req(ctx context.Context, method string, params url.Values, body any, out any) error {
89
	u := fmt.Sprintf("%s/bot%s/%s", apiBase, t.token, method)
90
	if params != nil {
91
		u += "?" + params.Encode()
92
	}
93
94
	var req *http.Request
95
	var err error
96
	if body != nil {
97
		var data []byte
98
		data, err = json.Marshal(body)
99
		if err != nil {
100
			return err
101
		}
102
		req, err = http.NewRequestWithContext(ctx, http.MethodPost, u, bytes.NewReader(data))
103
		if err != nil {
104
			return err
105
		}
106
		req.Header.Set("Content-Type", "application/json")
107
	} else {
108
		req, err = http.NewRequestWithContext(ctx, http.MethodGet, u, nil)
109
		if err != nil {
110
			return err
111
		}
112
	}
113
114
	res, err := t.client.Do(req)
115
	if err != nil {
116
		return err
117
	}
118
	defer res.Body.Close()
119
	return json.NewDecoder(res.Body).Decode(out)
120
}