slack-smart-bot 1.3.1 → 1.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (32) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +3 -4
  3. data/lib/slack-smart-bot.rb +5 -11
  4. data/lib/slack/smart-bot/comm.rb +7 -253
  5. data/lib/slack/smart-bot/comm/ask.rb +48 -0
  6. data/lib/slack/smart-bot/comm/dont_understand.rb +61 -0
  7. data/lib/slack/smart-bot/comm/respond.rb +51 -0
  8. data/lib/slack/smart-bot/comm/respond_direct.rb +6 -0
  9. data/lib/slack/smart-bot/comm/send_file.rb +25 -0
  10. data/lib/slack/smart-bot/comm/send_msg_channel.rb +30 -0
  11. data/lib/slack/smart-bot/comm/send_msg_user.rb +37 -0
  12. data/lib/slack/smart-bot/commands.rb +25 -0
  13. data/lib/slack/smart-bot/commands/on_bot/admin/pause_bot.rb +1 -0
  14. data/lib/slack/smart-bot/commands/on_bot/admin/start_bot.rb +1 -0
  15. data/lib/slack/smart-bot/listen.rb +1 -2
  16. data/lib/slack/smart-bot/process.rb +0 -26
  17. data/lib/slack/smart-bot/process_first.rb +0 -1
  18. data/lib/slack/smart-bot/treat_message.rb +16 -1
  19. data/lib/slack/smart-bot/utils.rb +12 -337
  20. data/lib/slack/smart-bot/utils/build_help.rb +15 -0
  21. data/lib/slack/smart-bot/utils/create_routine_thread.rb +86 -0
  22. data/lib/slack/smart-bot/utils/get_bots_created.rb +24 -0
  23. data/lib/slack/smart-bot/utils/get_channels_name_and_id.rb +21 -0
  24. data/lib/slack/smart-bot/utils/get_help.rb +131 -0
  25. data/lib/slack/smart-bot/utils/get_routines.rb +11 -0
  26. data/lib/slack/smart-bot/utils/get_rules_imported.rb +15 -0
  27. data/lib/slack/smart-bot/utils/remove_hash_keys.rb +17 -0
  28. data/lib/slack/smart-bot/utils/update_bots_file.rb +11 -0
  29. data/lib/slack/smart-bot/utils/update_routines.rb +16 -0
  30. data/lib/slack/smart-bot/utils/update_rules_imported.rb +8 -0
  31. data/lib/slack/smart-bot/utils/update_shortcuts_file.rb +7 -0
  32. metadata +29 -10
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 53175e003bbaf58181aecd71f350c0534f66541443bf486075197af040127e72
4
- data.tar.gz: 7872fc51317b5501bb0ee7ec87595bafdcefbdcebbfa702159bbae282e24ee9b
3
+ metadata.gz: d3f64ad6c12b868d2d0111788ebe402eeae5f10a8b44be42f28969a38612c3e6
4
+ data.tar.gz: 310d7d62aff408f5973e955b7097113e4a02c7bc4ae7d92fb3f35d4b0fa23eb4
5
5
  SHA512:
6
- metadata.gz: f11099c6edbc90ff63ee1f5bf01154997386614d5e201a981a223ef4e73208cf2615ba1492bc0ca34f5b0c0ba318083205e2668518104e2d382d656d03cf7241
7
- data.tar.gz: 69041e01eff53c3157702a47ee45501541bafffde9e5d2c3e082ba36ac7f4b77e1c53f2ed116ee8616b76faffade6414350ff025bbeaff212ed769144af51b2a
6
+ metadata.gz: 9d431f88c4ad743df3278728830dfec7ba97d8dd9944e216231a7483039e0494b6e7ca10153d15c79ccf2f4bd7feebf71ffe96eb7c62ae4cb73ef7e16b03cc54
7
+ data.tar.gz: 1fc052a88c2b6a47230a1c08f7e8bfcb2dabaa392d897fae02ec3005ae33a91851dd476393bd6f69d74ccd2c2c73a9de63c58d9d11a7c5739e45e594ae70f2b5
data/README.md CHANGED
@@ -47,7 +47,6 @@ settings = {
47
47
  # the channel that will act like the master channel, main channel
48
48
  master_channel: 'my_master_channel',
49
49
  masters: ["mario"], #names of the master users
50
- nick: 'smart-bot', # the smart bot name
51
50
  token: 'xxxxxxxxxxxxxxxxxx' # the API Slack token
52
51
  }
53
52
 
@@ -286,13 +285,13 @@ Example:
286
285
 
287
286
  In case you want to use a shortcut as a inline shortcut inside a command you can do it by adding a $:
288
287
  Example:
289
- >**_Peter>_** `!add shortcut cust1: 3488823-1233`
288
+ >**_Peter>_** `!add shortcut cust1: 3488823-1233`
290
289
  >**_Smart-Bot>_** `shortcut added`
291
- >**_Peter>_** `!add shortcut cust2: 1111555-6688`
290
+ >**_Peter>_** `!add shortcut cust2: 1111555-6688`
292
291
  >**_Smart-Bot>_** `shortcut added`
293
292
  >**_Peter>_** `!run tests $cust1`
294
293
  >**_Smart-Bot>_** `Running tests for customers 3488823-1233`
295
- >**_Peter>_** `!run tests $cust1 $cust2`
294
+ >**_Peter>_** `!run tests $cust1 $cust2`
296
295
  >**_Smart-Bot>_** `Running tests for customers 3488823-1233 1111555-6688`
297
296
 
298
297
  To see available shortcuts: **_`see shortcuts`_** and to delete a particular shortcut: **_`delete shortcut NAME`_**
@@ -14,6 +14,7 @@ require_relative "slack/smart-bot/comm"
14
14
  require_relative "slack/smart-bot/listen"
15
15
  require_relative "slack/smart-bot/treat_message"
16
16
  require_relative "slack/smart-bot/process_first"
17
+ require_relative "slack/smart-bot/commands"
17
18
  require_relative "slack/smart-bot/process"
18
19
  require_relative "slack/smart-bot/utils"
19
20
 
@@ -163,17 +164,6 @@ class SlackSmartBot
163
164
 
164
165
  get_rules_imported()
165
166
 
166
- begin
167
- user_info = client.web_client.users_info(user: "#{"@" if config[:nick][0] != "@"}#{config[:nick]}")
168
- config[:nick_id] = user_info.user.id
169
- rescue Slack::Web::Api::Errors::TooManyRequestsError
170
- @logger.fatal "TooManyRequestsError"
171
- abort("TooManyRequestsError please re run the bot and be sure of executing first: killall ruby")
172
- rescue Exception => stack
173
- @logger.fatal stack
174
- abort("The bot user specified on settings: #{config[:nick]}, doesn't exist on Slack. Execution aborted")
175
- end
176
-
177
167
  begin
178
168
  @admin_users_id = []
179
169
  config.admins.each do |au|
@@ -191,6 +181,10 @@ class SlackSmartBot
191
181
  m = "Successfully connected, welcome '#{client.self.name}' to the '#{client.team.name}' team at https://#{client.team.domain}.slack.com."
192
182
  puts m
193
183
  @logger.info m
184
+ config.nick = client.self.name
185
+ config.nick_id = client.self.id
186
+ @salutations = [config[:nick], "<@#{config[:nick_id]}>", "bot", "smart"]
187
+
194
188
  gems_remote = `gem list slack-smart-bot --remote`
195
189
  version_remote = gems_remote.to_s().scan(/slack-smart-bot \((\d+\.\d+\.\d+)/).join
196
190
  version_message = ""
@@ -1,253 +1,7 @@
1
- class SlackSmartBot
2
- def respond(msg, dest = nil)
3
- if dest.nil? and Thread.current.key?(:dest)
4
- dest = Thread.current[:dest]
5
- end
6
- dest = @channels_id[dest] if @channels_id.key?(dest) #it is a name of channel
7
-
8
- if dest.nil?
9
- if config[:simulate]
10
- open("#{config.path}/buffer_complete.log", "a") { |f|
11
- f.puts "|#{@channel_id}|#{config[:nick_id]}|#{msg}$$$"
12
- }
13
- else
14
- client.message(channel: @channel_id, text: msg, as_user: true)
15
- end
16
- if config[:testing] and config.on_master_bot
17
- open("#{config.path}/buffer.log", "a") { |f|
18
- f.puts "|#{@channel_id}|#{config[:nick_id]}|#{msg}"
19
- }
20
- end
21
- elsif dest[0] == "C" or dest[0] == "G" # channel
22
- if config[:simulate]
23
- open("#{config.path}/buffer_complete.log", "a") { |f|
24
- f.puts "|#{dest}|#{config[:nick_id]}|#{msg}$$$"
25
- }
26
- else
27
- client.message(channel: dest, text: msg, as_user: true)
28
- end
29
- if config[:testing] and config.on_master_bot
30
- open("#{config.path}/buffer.log", "a") { |f|
31
- f.puts "|#{dest}|#{config[:nick_id]}|#{msg}"
32
- }
33
- end
34
- elsif dest[0] == "D" or dest[0] == "U" # Direct message
35
- send_msg_user(dest, msg)
36
- elsif dest[0] == "@"
37
- begin
38
- user_info = client.web_client.users_info(user: dest)
39
- send_msg_user(user_info.user.id, msg)
40
- rescue Exception => stack
41
- @logger.warn("user #{dest} not found.")
42
- @logger.warn stack
43
- if Thread.current.key?(:dest)
44
- respond("User #{dest} not found.")
45
- end
46
- end
47
- else
48
- @logger.warn("method respond not treated correctly: msg:#{msg} dest:#{dest}")
49
- end
50
- end
51
-
52
- def respond_direct(msg)
53
- dest = Thread.current[:user].id
54
- respond(msg, dest)
55
- end
56
-
57
- #context: previous message
58
- #to: user that should answer
59
- def ask(question, context = nil, to = nil, dest = nil)
60
- if dest.nil? and Thread.current.key?(:dest)
61
- dest = Thread.current[:dest]
62
- end
63
- if to.nil?
64
- to = Thread.current[:user].name
65
- end
66
- if context.nil?
67
- context = Thread.current[:command]
68
- end
69
- message = "#{to}: #{question}"
70
- if dest.nil?
71
- if config[:simulate]
72
- open("#{config.path}/buffer_complete.log", "a") { |f|
73
- f.puts "|#{@channel_id}|#{config[:nick_id]}|#{message}$$$"
74
- }
75
- else
76
- client.message(channel: @channel_id, text: message, as_user: true)
77
- end
78
- if config[:testing] and config.on_master_bot
79
- open("#{config.path}/buffer.log", "a") { |f|
80
- f.puts "|#{@channel_id}|#{config[:nick_id]}|#{message}"
81
- }
82
- end
83
- elsif dest[0] == "C" or dest[0] == "G" # channel
84
- if config[:simulate]
85
- open("#{config.path}/buffer_complete.log", "a") { |f|
86
- f.puts "|#{dest}|#{config[:nick_id]}|#{message}$$$"
87
- }
88
- else
89
- client.message(channel: dest, text: message, as_user: true)
90
- end
91
- if config[:testing] and config.on_master_bot
92
- open("#{config.path}/buffer.log", "a") { |f|
93
- f.puts "|#{dest}|#{config[:nick_id]}|#{message}"
94
- }
95
- end
96
- elsif dest[0] == "D" #private message
97
- send_msg_user(dest, message)
98
- end
99
- @questions[to] = context
100
- end
101
-
102
- # to: (String) Channel name or id
103
- # msg: (String) message to send
104
- def send_msg_channel(to, msg)
105
- unless msg == ""
106
- get_channels_name_and_id() unless @channels_name.key?(to) or @channels_id.key?(to)
107
- if @channels_name.key?(to) #it is an id
108
- channel_id = to
109
- elsif @channels_id.key?(to) #it is a channel name
110
- channel_id = @channels_id[to]
111
- else
112
- @logger.fatal "Channel: #{to} not found. Message: #{msg}"
113
- end
114
- if config[:simulate]
115
- open("#{config.path}/buffer_complete.log", "a") { |f|
116
- f.puts "|#{channel_id}|#{config[:nick_id]}|#{msg}$$$"
117
- }
118
- else
119
- client.message(channel: channel_id, text: msg, as_user: true)
120
- end
121
- if config[:testing] and config.on_master_bot
122
- open("#{config.path}/buffer.log", "a") { |f|
123
- f.puts "|#{channel_id}|#{config[:nick_id]}|#{msg}"
124
- }
125
- end
126
- end
127
- end
128
-
129
- #to send messages without listening for a response to users
130
- def send_msg_user(id_user, msg)
131
- unless msg == ""
132
- if id_user[0] == "D"
133
- if config[:simulate]
134
- open("#{config.path}/buffer_complete.log", "a") { |f|
135
- f.puts "|#{id_user}|#{config[:nick_id]}|#{msg}$$$"
136
- }
137
- else
138
- client.message(channel: id_user, as_user: true, text: msg)
139
- end
140
- if config[:testing] and config.on_master_bot
141
- open("#{config.path}/buffer.log", "a") { |f|
142
- f.puts "|#{id_user}|#{config[:nick_id]}|#{msg}"
143
- }
144
- end
145
- else
146
- im = client.web_client.im_open(user: id_user)
147
- if config[:simulate]
148
- open("#{config.path}/buffer_complete.log", "a") { |f|
149
- f.puts "|#{im["channel"]["id"]}|#{config[:nick_id]}|#{msg}$$$"
150
- }
151
- else
152
- client.message(channel: im["channel"]["id"], as_user: true, text: msg)
153
- end
154
- if config[:testing] and config.on_master_bot
155
- open("#{config.path}/buffer.log", "a") { |f|
156
- f.puts "|#{im["channel"]["id"]}|#{config[:nick_id]}|#{msg}"
157
- }
158
- end
159
- end
160
- end
161
- end
162
-
163
- #to send a file to an user or channel
164
- #send_file(dest, 'the message', "#{project_folder}/temp/logs_ptBI.log", 'message to be sent', 'text/plain', "text")
165
- #send_file(dest, 'the message', "#{project_folder}/temp/example.jpeg", 'message to be sent', 'image/jpeg', "jpg")
166
- def send_file(to, msg, file, title, format, type = "text")
167
- if to[0] == "U" #user
168
- im = client.web_client.im_open(user: to)
169
- channel = im["channel"]["id"]
170
- else
171
- channel = to
172
- end
173
-
174
- client.web_client.files_upload(
175
- channels: channel,
176
- as_user: true,
177
- file: Faraday::UploadIO.new(file, format),
178
- title: title,
179
- filename: file,
180
- filetype: type,
181
- initial_comment: msg,
182
- )
183
- end
184
-
185
- def dont_understand(rules_file = nil, command = nil, user = nil, dest = nil, answer = ["what?", "huh?", "sorry?", "what do you mean?", "I don't understand"], channel_rules: config.channel, typem: nil)
186
- command = Thread.current[:command] if command.nil?
187
- user = Thread.current[:user] if user.nil?
188
- dest = Thread.current[:dest] if dest.nil?
189
- rules_file = Thread.current[:rules_file] if rules_file.nil?
190
- typem = Thread.current[:typem] if typem.nil?
191
- if typem==:on_extended
192
- get_bots_created()
193
- end
194
-
195
- if typem!=:on_extended or (typem==:on_extended and @extended_from[@channels_name[dest]][0]==@channel_id )
196
- #only will be treated on the first extended channel in case more than one channel extended on DEST channel
197
- text = get_help(rules_file, dest, user.name, typem==:on_extended)
198
-
199
- ff = text.scan(/\s*`\s*([^`]+)\s*`\s*/i).flatten
200
- ff.delete("!THE_COMMAND")
201
- ff.delete("@NAME_OF_BOT THE_COMMAND")
202
- ff.delete("NAME_OF_BOT THE_COMMAND")
203
- ff.delete("@BOT_NAME on #CHANNEL_NAME COMMAND")
204
-
205
- ff2 = {}
206
- acommand = command.split(/\s+/)
207
- ff.each do |f|
208
- ff2[f] = ""
209
- af = f.split(/\s+/)
210
- af.each_with_index do |word, i|
211
- if acommand.size >= (i - 1) and word.match?(/[A-Z_\-#@]+/)
212
- ff2[f] += "#{acommand[i]} "
213
- else
214
- ff2[f] += "#{word} "
215
- end
216
- end
217
- ff2[f].rstrip!
218
- end
219
-
220
- spell_checker = DidYouMean::SpellChecker.new(dictionary: ff2.values)
221
- res = spell_checker.correct(command).uniq
222
- res_final = []
223
- res.each do |r|
224
- res_final << (ff2.select { |k, v| v == r }).keys
225
- end
226
- res_final.flatten!
227
-
228
- if typem==:on_extended and @extended_from[@channels_name[dest]][0]==@channel_id
229
- if rules_file == config.rules_file
230
- respond "#{user.profile.display_name}, I don't understand.", dest
231
- end
232
- if @extended_from[@channels_name[dest]].size > 1 and rules_file == config.rules_file
233
- @extended_from[@channels_name[dest]][1..-1].each do |ch|
234
- rf = @bots_created[ch].rules_file
235
- dont_understand(rf, command, nil, dest, answer, channel_rules: @channels_name[ch], typem: typem)
236
- end
237
- end
238
- unless res_final.empty?
239
- respond "Similar rules on : *#{channel_rules}*\n`#{res_final[0..4].join("`\n`")}`", dest
240
- end
241
- elsif typem!=:on_extended
242
- message = ''
243
- message = "\nTake in consideration when on external calls, not all the commands are availalbe." if typem==:on_call
244
- if res_final.empty?
245
- resp = answer.sample
246
- respond "#{user.profile.display_name}, #{resp}#{message}", dest
247
- else
248
- respond "#{user.profile.display_name}, I don't understand. Maybe you are trying to say:\n`#{res_final[0..4].join("`\n`")}`#{message}", dest
249
- end
250
- end
251
- end
252
- end
253
- end
1
+ require_relative 'comm/ask'
2
+ require_relative 'comm/dont_understand'
3
+ require_relative 'comm/respond_direct'
4
+ require_relative 'comm/respond'
5
+ require_relative 'comm/send_file'
6
+ require_relative 'comm/send_msg_channel'
7
+ require_relative 'comm/send_msg_user'
@@ -0,0 +1,48 @@
1
+ class SlackSmartBot
2
+
3
+ #context: previous message
4
+ #to: user that should answer
5
+ def ask(question, context = nil, to = nil, dest = nil)
6
+ if dest.nil? and Thread.current.key?(:dest)
7
+ dest = Thread.current[:dest]
8
+ end
9
+ if to.nil?
10
+ to = Thread.current[:user].name
11
+ end
12
+ if context.nil?
13
+ context = Thread.current[:command]
14
+ end
15
+ message = "#{to}: #{question}"
16
+ if dest.nil?
17
+ if config[:simulate]
18
+ open("#{config.path}/buffer_complete.log", "a") { |f|
19
+ f.puts "|#{@channel_id}|#{config[:nick_id]}|#{message}~~~"
20
+ }
21
+ else
22
+ client.message(channel: @channel_id, text: message, as_user: true)
23
+ end
24
+ if config[:testing] and config.on_master_bot
25
+ open("#{config.path}/buffer.log", "a") { |f|
26
+ f.puts "|#{@channel_id}|#{config[:nick_id]}|#{message}"
27
+ }
28
+ end
29
+ elsif dest[0] == "C" or dest[0] == "G" # channel
30
+ if config[:simulate]
31
+ open("#{config.path}/buffer_complete.log", "a") { |f|
32
+ f.puts "|#{dest}|#{config[:nick_id]}|#{message}~~~"
33
+ }
34
+ else
35
+ client.message(channel: dest, text: message, as_user: true)
36
+ end
37
+ if config[:testing] and config.on_master_bot
38
+ open("#{config.path}/buffer.log", "a") { |f|
39
+ f.puts "|#{dest}|#{config[:nick_id]}|#{message}"
40
+ }
41
+ end
42
+ elsif dest[0] == "D" #private message
43
+ send_msg_user(dest, message)
44
+ end
45
+ @questions[to] = context
46
+ end
47
+
48
+ end
@@ -0,0 +1,61 @@
1
+ class SlackSmartBot
2
+
3
+ def dont_understand(rules_file = nil, command = nil, user = nil, dest = nil, answer = ["what?", "huh?", "sorry?", "what do you mean?", "I don't understand"], channel_rules: config.channel, typem: nil)
4
+ command = Thread.current[:command] if command.nil?
5
+ user = Thread.current[:user] if user.nil?
6
+ dest = Thread.current[:dest] if dest.nil?
7
+ rules_file = Thread.current[:rules_file] if rules_file.nil?
8
+ typem = Thread.current[:typem] if typem.nil?
9
+ if typem==:on_extended
10
+ get_bots_created()
11
+ end
12
+ text = get_help(rules_file, dest, user.name, typem==:on_extended)
13
+
14
+ ff = text.scan(/\s*`\s*([^`]+)\s*`\s*/i).flatten
15
+ ff.delete("!THE_COMMAND")
16
+ ff.delete("@NAME_OF_BOT THE_COMMAND")
17
+ ff.delete("NAME_OF_BOT THE_COMMAND")
18
+ ff.delete("@BOT_NAME on #CHANNEL_NAME COMMAND")
19
+
20
+ ff2 = {}
21
+ acommand = command.split(/\s+/)
22
+ ff.each do |f|
23
+ ff2[f] = ""
24
+ af = f.split(/\s+/)
25
+ af.each_with_index do |word, i|
26
+ if acommand.size >= (i - 1) and word.match?(/[A-Z_\-#@]+/)
27
+ ff2[f] += "#{acommand[i]} "
28
+ else
29
+ ff2[f] += "#{word} "
30
+ end
31
+ end
32
+ ff2[f].rstrip!
33
+ end
34
+
35
+ spell_checker = DidYouMean::SpellChecker.new(dictionary: ff2.values)
36
+ res = spell_checker.correct(command).uniq
37
+ res_final = []
38
+ res.each do |r|
39
+ res_final << (ff2.select { |k, v| v == r }).keys
40
+ end
41
+ res_final.flatten!
42
+
43
+ if typem==:on_extended
44
+ if @extended_from[@channels_name[dest]].size == 1
45
+ respond "#{user.profile.display_name}, I don't understand.", dest
46
+ end
47
+ unless res_final.empty?
48
+ respond "Similar rules on : *#{channel_rules}*\n`#{res_final[0..4].join("`\n`")}`", dest
49
+ end
50
+ else
51
+ message = ''
52
+ message = "\nTake in consideration when on external calls, not all the commands are availalbe." if typem==:on_call
53
+ if res_final.empty?
54
+ resp = answer.sample
55
+ respond "#{user.profile.display_name}, #{resp}#{message}", dest
56
+ else
57
+ respond "#{user.profile.display_name}, I don't understand. Maybe you are trying to say:\n`#{res_final[0..4].join("`\n`")}`#{message}", dest
58
+ end
59
+ end
60
+ end
61
+ end
@@ -0,0 +1,51 @@
1
+ class SlackSmartBot
2
+ def respond(msg, dest = nil)
3
+ if dest.nil? and Thread.current.key?(:dest)
4
+ dest = Thread.current[:dest]
5
+ end
6
+ dest = @channels_id[dest] if @channels_id.key?(dest) #it is a name of channel
7
+ if dest.nil?
8
+ if config[:simulate]
9
+ open("#{config.path}/buffer_complete.log", "a") { |f|
10
+ f.puts "|#{@channel_id}|#{config[:nick_id]}|#{msg}~~~"
11
+ }
12
+ else
13
+ client.message(channel: @channel_id, text: msg, as_user: true)
14
+ end
15
+ if config[:testing] and config.on_master_bot
16
+ open("#{config.path}/buffer.log", "a") { |f|
17
+ f.puts "|#{@channel_id}|#{config[:nick_id]}|#{msg}"
18
+ }
19
+ end
20
+ elsif dest[0] == "C" or dest[0] == "G" # channel
21
+ if config[:simulate]
22
+ open("#{config.path}/buffer_complete.log", "a") { |f|
23
+ f.puts "|#{dest}|#{config[:nick_id]}|#{msg}~~~"
24
+ }
25
+ else
26
+ client.message(channel: dest, text: msg, as_user: true)
27
+ end
28
+ if config[:testing] and config.on_master_bot
29
+ open("#{config.path}/buffer.log", "a") { |f|
30
+ f.puts "|#{dest}|#{config[:nick_id]}|#{msg}"
31
+ }
32
+ end
33
+ elsif dest[0] == "D" or dest[0] == "U" # Direct message
34
+ send_msg_user(dest, msg)
35
+ elsif dest[0] == "@"
36
+ begin
37
+ user_info = client.web_client.users_info(user: dest)
38
+ send_msg_user(user_info.user.id, msg)
39
+ rescue Exception => stack
40
+ @logger.warn("user #{dest} not found.")
41
+ @logger.warn stack
42
+ if Thread.current.key?(:dest)
43
+ respond("User #{dest} not found.")
44
+ end
45
+ end
46
+ else
47
+ @logger.warn("method respond not treated correctly: msg:#{msg} dest:#{dest}")
48
+ end
49
+ end
50
+
51
+ end