-
Notifications
You must be signed in to change notification settings - Fork 0
/
core.clj
99 lines (85 loc) · 2.87 KB
/
core.clj
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
(ns clobot.core
(:require [ring.adapter.jetty :refer [run-jetty]]
[compojure.core :refer [routes context POST GET]]
[ring.middleware.json :refer [wrap-json-body wrap-json-response]]
[clj-http.client :as http]
[clojure.data.json :as json]))
(def telegram-api-host "https://api.telegram.org/bot")
(def telegram-api-methods
{:sendMessage "sendMessage"
:bot-info "getMe"})
(defn make-url
"Creates full Telegram api url"
[token method]
(str telegram-api-host (format "%s/%s" token method)))
(defn make-payload
"Creates json payload for clj-http"
[params-map]
{:body (json/write-str params-map)
:content-type :json
:accept :json})
(defn get-message
"Returns message sent to the bot from request object"
[req]
(get-in req [:body "message"]))
(defn get-command
"Returns command sent to the bot from request object"
[msg]
(get-in msg ["text"]))
(defn get-chat-id
"Returns chat id sent to the bot from request object"
[msg]
(get-in msg ["chat" "id"]))
(defn get-no-command
"Returns custom error handler if exists"
[handlers]
(get-in handlers ["no-command"]))
(defn text-message
"Sends message from the bot to the chat"
[text token chat-id]
(http/post
(make-url token (:sendMessage telegram-api-methods))
(make-payload {:text text
:chat_id chat-id})))
(defn no-command-default
"Sends error message to the chat if appropriate handler is not found"
[command token chat-id]
(text-message (str command " - Unknown command.") token chat-id))
(defn bot-info
"Returns basic information about the bot"
[config]
(fn [req]
(http/get
(make-url (:token config)
(:bot-info telegram-api-methods)))))
(defn update-handler
"Creates a function to resolve the updates got with web-hook
and applies appropriate handler functions"
[handlers config]
(fn [req]
(let [msg (get-message req)
cmd (get-command msg)
handler (get-in handlers [cmd])]
(if handler
(apply handler [msg])
(:else (let [no-command (get-no-command handlers)]
(if no-command
(apply no-command [msg])
(:else (no-command-default
cmd
(:token config)
(get-chat-id msg))))))))))
(defn make-end-point
"Creates endpoint to get and process updates from Telegram's servers"
[handlers config]
(routes
(context (str "/" (:name config)) []
(POST "/" [] (update-handler handlers config))
(GET "/info" [] (bot-info config)))))
(defn start-bot
"Starts a Ring web app on a given port"
[handlers config]
(println (str "Starting bot with token: " (:token config)))
(run-jetty (-> (make-end-point handlers config)
(wrap-json-body)
(wrap-json-response)) {:port (:port config)}))