Skip to content

Commit d7df856

Browse files
authored
Merge pull request #395 from farit2000/fix-closing-update-channel-add-serverless-method
Fix bug with update channel closing, add ListenForWebhookRespReqFormat method
2 parents f413d82 + 0cbcc04 commit d7df856

File tree

2 files changed

+143
-0
lines changed

2 files changed

+143
-0
lines changed

README.md

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -66,3 +66,124 @@ There are more examples on the [site](https://go-telegram-bot-api.dev/)
6666
with detailed information on how to do many different kinds of things.
6767
It's a great place to get started on using keyboards, commands, or other
6868
kinds of reply markup.
69+
70+
If you need to use webhooks (if you wish to run on Google App Engine),
71+
you may use a slightly different method.
72+
73+
```go
74+
package main
75+
76+
import (
77+
"log"
78+
"net/http"
79+
80+
"github.com/go-telegram-bot-api/telegram-bot-api"
81+
)
82+
83+
func main() {
84+
bot, err := tgbotapi.NewBotAPI("MyAwesomeBotToken")
85+
if err != nil {
86+
log.Fatal(err)
87+
}
88+
89+
bot.Debug = true
90+
91+
log.Printf("Authorized on account %s", bot.Self.UserName)
92+
93+
_, err = bot.SetWebhook(tgbotapi.NewWebhookWithCert("https://www.google.com:8443/"+bot.Token, "cert.pem"))
94+
if err != nil {
95+
log.Fatal(err)
96+
}
97+
info, err := bot.GetWebhookInfo()
98+
if err != nil {
99+
log.Fatal(err)
100+
}
101+
if info.LastErrorDate != 0 {
102+
log.Printf("Telegram callback failed: %s", info.LastErrorMessage)
103+
}
104+
updates := bot.ListenForWebhook("/" + bot.Token)
105+
go http.ListenAndServeTLS("0.0.0.0:8443", "cert.pem", "key.pem", nil)
106+
107+
for update := range updates {
108+
log.Printf("%+v\n", update)
109+
}
110+
}
111+
```
112+
113+
If you need to publish your bot on AWS Lambda(or something like it) and AWS API Gateway,
114+
you can use such example:
115+
116+
In this code used AWS Lambda Go net/http server adapter [algnhsa](https://github.com/akrylysov/algnhsa)
117+
118+
```go
119+
package main
120+
121+
import (
122+
"github.com/akrylysov/algnhsa"
123+
"github.com/go-telegram-bot-api/telegram-bot-api"
124+
"log"
125+
"net/http"
126+
)
127+
128+
func answer(w http.ResponseWriter, r *http.Request) {
129+
bot, err := tgbotapi.NewBotAPI("MyAwesomeBotToken")
130+
if err != nil {
131+
log.Fatal(err)
132+
}
133+
134+
bot.Debug = true
135+
updates := bot.ListenForWebhookRespReqFormat(w, r)
136+
for update := range updates {
137+
if update.Message == nil {
138+
continue
139+
}
140+
log.Printf("[%s] %s", update.Message.From.UserName, update.Message.Text)
141+
142+
msg := tgbotapi.NewMessage(update.Message.Chat.ID, update.Message.Text)
143+
msg.ReplyToMessageID = update.Message.MessageID
144+
_, err := bot.Send(msg)
145+
if err != nil {
146+
log.Printf("Error send message: %s | Error: %s", msg.Text, err.Error())
147+
}
148+
}
149+
}
150+
151+
func setWebhook(_ http.ResponseWriter, _ *http.Request) {
152+
bot, err := tgbotapi.NewBotAPI("MyAwesomeBotToken")
153+
if err != nil {
154+
log.Fatal(err)
155+
}
156+
157+
bot.Debug = true
158+
159+
log.Printf("Authorized on account %s", bot.Self.UserName)
160+
161+
_, err = bot.SetWebhook(tgbotapi.NewWebhook("https://your_api_gateway_address.com/"+bot.Token))
162+
if err != nil {
163+
log.Fatal(err)
164+
}
165+
info, err := bot.GetWebhookInfo()
166+
if err != nil {
167+
log.Fatal(err)
168+
}
169+
if info.LastErrorDate != 0 {
170+
log.Printf("Telegram callback failed: %s", info.LastErrorMessage)
171+
}
172+
}
173+
174+
func main() {
175+
http.HandleFunc("/set_webhook", setWebhook)
176+
http.HandleFunc("/MyAwesomeBotToken", answer)
177+
algnhsa.ListenAndServe(http.DefaultServeMux, nil)
178+
}
179+
```
180+
181+
If you need, you may generate a self signed certficate, as this requires
182+
HTTPS / TLS. The above example tells Telegram that this is your
183+
certificate and that it should be trusted, even though it is not
184+
properly signed.
185+
186+
openssl req -x509 -newkey rsa:2048 -keyout key.pem -out cert.pem -days 3560 -subj "//O=Org\CN=Test" -nodes
187+
188+
Now that [Let's Encrypt](https://letsencrypt.org) is available,
189+
you may wish to generate your free TLS certificate there.

bot.go

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -484,11 +484,33 @@ func (bot *BotAPI) ListenForWebhook(pattern string) UpdatesChannel {
484484
}
485485

486486
ch <- *update
487+
close(ch)
487488
})
488489

489490
return ch
490491
}
491492

493+
// ListenForWebhookRespReqFormat registers a http handler for a webhook.
494+
func (bot *BotAPI) ListenForWebhookRespReqFormat(w http.ResponseWriter, r *http.Request) UpdatesChannel {
495+
ch := make(chan Update, bot.Buffer)
496+
497+
func(w http.ResponseWriter, r *http.Request) {
498+
update, err := bot.HandleUpdate(r)
499+
if err != nil {
500+
errMsg, _ := json.Marshal(map[string]string{"error": err.Error()})
501+
w.WriteHeader(http.StatusBadRequest)
502+
w.Header().Set("Content-Type", "application/json")
503+
_, _ = w.Write(errMsg)
504+
return
505+
}
506+
507+
ch <- *update
508+
close(ch)
509+
}(w, r)
510+
511+
return ch
512+
}
513+
492514
// HandleUpdate parses and returns update received via webhook
493515
func (bot *BotAPI) HandleUpdate(r *http.Request) (*Update, error) {
494516
if r.Method != http.MethodPost {

0 commit comments

Comments
 (0)