slack-smart-bot 1.5.1 → 1.6.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.
- checksums.yaml +4 -4
- data/README.md +89 -2
- data/lib/slack-smart-bot.rb +6 -1
- data/lib/slack/smart-bot/commands.rb +5 -0
- data/lib/slack/smart-bot/commands/general/bot_help.rb +44 -40
- data/lib/slack/smart-bot/commands/general/bot_status.rb +32 -28
- data/lib/slack/smart-bot/commands/general/bye_bot.rb +9 -1
- data/lib/slack/smart-bot/commands/general/hi_bot.rb +6 -1
- data/lib/slack/smart-bot/commands/general/use_rules.rb +33 -29
- data/lib/slack/smart-bot/commands/on_bot/add_shortcut.rb +40 -35
- data/lib/slack/smart-bot/commands/on_bot/admin/run_routine.rb +1 -0
- data/lib/slack/smart-bot/commands/on_bot/delete_repl.rb +32 -0
- data/lib/slack/smart-bot/commands/on_bot/delete_shortcut.rb +30 -25
- data/lib/slack/smart-bot/commands/on_bot/get_repl.rb +43 -0
- data/lib/slack/smart-bot/commands/on_bot/repl.rb +202 -0
- data/lib/slack/smart-bot/commands/on_bot/ruby_code.rb +33 -29
- data/lib/slack/smart-bot/commands/on_bot/run_repl.rb +73 -0
- data/lib/slack/smart-bot/commands/on_bot/see_repls.rb +24 -0
- data/lib/slack/smart-bot/commands/on_bot/see_shortcuts.rb +23 -18
- data/lib/slack/smart-bot/commands/on_extended/bot_rules.rb +32 -27
- data/lib/slack/smart-bot/commands/on_master/create_bot.rb +79 -74
- data/lib/slack/smart-bot/listen.rb +2 -0
- data/lib/slack/smart-bot/process.rb +61 -9
- data/lib/slack/smart-bot/process_first.rb +17 -3
- data/lib/slack/smart-bot/treat_message.rb +24 -3
- data/lib/slack/smart-bot/utils.rb +3 -0
- data/lib/slack/smart-bot/utils/get_help.rb +1 -1
- data/lib/slack/smart-bot/utils/get_repls.rb +11 -0
- data/lib/slack/smart-bot/utils/update_repls.rb +8 -0
- metadata +28 -19
@@ -0,0 +1,73 @@
|
|
1
|
+
class SlackSmartBot
|
2
|
+
# help: ----------------------------------------------
|
3
|
+
# help: `run repl SESSION_NAME`
|
4
|
+
# help: `run repl SESSION_NAME ENV_VAR=VALUE ENV_VAR=VALUE`
|
5
|
+
# help: `run live SESSION_NAME`
|
6
|
+
# help: `run irb SESSION_NAME`
|
7
|
+
# help:
|
8
|
+
# help: Will run the repl session specified and return the output.
|
9
|
+
# help: You can supply the Environmental Variables you need for the Session
|
10
|
+
# help: It will return only the values that were print out on the repl with puts, print, p or pp
|
11
|
+
# help: Example:
|
12
|
+
# help: _run repl CreateCustomer LOCATION=spain HOST='https://10.30.40.50:8887'_
|
13
|
+
# help:
|
14
|
+
def run_repl(dest, user, session_name, env_vars, rules_file)
|
15
|
+
#todo: add tests
|
16
|
+
from = user.name
|
17
|
+
if config[:allow_access].key?(__method__) and !config[:allow_access][__method__].include?(user.name) and !config[:allow_access][__method__].include?(user.id)
|
18
|
+
respond "You don't have access to use this command, please contact an Admin to be able to use it: <@#{config.admins.join(">, <@")}>"
|
19
|
+
else
|
20
|
+
save_stats(__method__)
|
21
|
+
Dir.mkdir("#{config.path}/repl") unless Dir.exist?("#{config.path}/repl")
|
22
|
+
Dir.mkdir("#{config.path}/repl/#{@channel_id}") unless Dir.exist?("#{config.path}/repl/#{@channel_id}")
|
23
|
+
if File.exist?("#{config.path}/repl/#{@channel_id}/#{session_name}.input")
|
24
|
+
if @repls.key?(session_name) and @repls[session_name][:type] == :private and
|
25
|
+
@repls[session_name][:creator_name]!=user.name and
|
26
|
+
!config.admins.include?(user.name)
|
27
|
+
respond "The REPL with session name: #{session_name} is private", dest
|
28
|
+
else
|
29
|
+
if @repls.key?(session_name) #not temp
|
30
|
+
@repls[session_name][:accessed] = Time.now.to_s
|
31
|
+
if @repls[session_name].creator_name == user.name
|
32
|
+
@repls[session_name][:runs_by_creator] += 1
|
33
|
+
else
|
34
|
+
@repls[session_name][:runs_by_others] += 1
|
35
|
+
end
|
36
|
+
update_repls()
|
37
|
+
end
|
38
|
+
|
39
|
+
content = env_vars.join("\n")
|
40
|
+
content += "\nrequire 'nice_http'\n"
|
41
|
+
unless rules_file.empty? # to get the project_folder
|
42
|
+
begin
|
43
|
+
eval(File.new(config.path+rules_file).read) if File.exist?(config.path+rules_file)
|
44
|
+
end
|
45
|
+
end
|
46
|
+
if File.exist?("#{project_folder}/.smart-bot-repl")
|
47
|
+
content += File.read("#{project_folder}/.smart-bot-repl")
|
48
|
+
content += "\n"
|
49
|
+
end
|
50
|
+
content += File.read("#{config.path}/repl/#{@channel_id}/#{session_name}.input").gsub(/^(quit|exit|bye)$/i,'')
|
51
|
+
Dir.mkdir("#{project_folder}/tmp") unless Dir.exist?("#{project_folder}/tmp")
|
52
|
+
Dir.mkdir("#{project_folder}/tmp/repl") unless Dir.exist?("#{project_folder}/tmp/repl")
|
53
|
+
File.write("#{project_folder}/tmp/repl/#{session_name}.rb", content, mode: "w+")
|
54
|
+
process_to_run = "ruby #{project_folder}/tmp/repl/#{session_name}.rb"
|
55
|
+
process_to_run = ("cd #{project_folder} && #{process_to_run}") if defined?(project_folder)
|
56
|
+
respond "Running REPL #{session_name}"
|
57
|
+
stdout, stderr, status = Open3.capture3(process_to_run)
|
58
|
+
if stderr == ""
|
59
|
+
if stdout == ""
|
60
|
+
respond "*#{session_name}*: Nothing returned."
|
61
|
+
else
|
62
|
+
respond "*#{session_name}*: #{stdout}"
|
63
|
+
end
|
64
|
+
else
|
65
|
+
respond "*#{session_name}*: #{stdout} #{stderr}"
|
66
|
+
end
|
67
|
+
end
|
68
|
+
else
|
69
|
+
respond "The REPL with session name: #{session_name} doesn't exist on this Smart Bot Channel", dest
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
class SlackSmartBot
|
2
|
+
# help: ----------------------------------------------
|
3
|
+
# help: `see repls`
|
4
|
+
# help: `see irbs`
|
5
|
+
# help: It will display the repls
|
6
|
+
# help:
|
7
|
+
def see_repls(dest, user, typem)
|
8
|
+
#todo: add tests
|
9
|
+
save_stats(__method__)
|
10
|
+
from = user.name
|
11
|
+
if config[:allow_access].key?(__method__) and !config[:allow_access][__method__].include?(user.name) and !config[:allow_access][__method__].include?(user.id)
|
12
|
+
respond "You don't have access to use this command, please contact an Admin to be able to use it: <@#{config.admins.join(">, <@")}>"
|
13
|
+
else
|
14
|
+
message = ""
|
15
|
+
@repls.sort.to_h.each do |session_name, repl|
|
16
|
+
if (repl.creator_name == user.name or repl.type == :public) or (config.admins.include?(user.name) and typem == :on_dm)
|
17
|
+
message += "(#{repl.type}) *#{session_name}*: #{repl.description} / created: #{repl.created} / accessed: #{repl.accessed} / creator: #{repl.creator} / runs: #{repl.runs_by_creator+repl.runs_by_others} / gets: #{repl.gets} \n"
|
18
|
+
end
|
19
|
+
end
|
20
|
+
message = "No repls created" if message == ''
|
21
|
+
respond message
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -4,30 +4,35 @@ class SlackSmartBot
|
|
4
4
|
# help: `see sc`
|
5
5
|
# help: It will display the shortcuts stored for the user and for :all
|
6
6
|
# help:
|
7
|
-
def see_shortcuts(dest,
|
7
|
+
def see_shortcuts(dest, user, typem)
|
8
8
|
save_stats(__method__)
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
if @shortcuts.keys.include?(from) and @shortcuts[from].keys.size > 0
|
20
|
-
new_hash = @shortcuts[from].dup
|
21
|
-
@shortcuts[:all].keys.each { |k| new_hash.delete(k) }
|
22
|
-
if new_hash.keys.size > 0
|
23
|
-
msg = "*Available shortcuts for #{from}:*\n"
|
24
|
-
new_hash.each { |name, value|
|
9
|
+
from = user.name
|
10
|
+
if config[:allow_access].key?(__method__) and !config[:allow_access][__method__].include?(user.name) and !config[:allow_access][__method__].include?(user.id)
|
11
|
+
respond "You don't have access to use this command, please contact an Admin to be able to use it: <@#{config.admins.join(">, <@")}>"
|
12
|
+
else
|
13
|
+
unless typem == :on_extended
|
14
|
+
msg = ""
|
15
|
+
if @shortcuts[:all].keys.size > 0
|
16
|
+
msg = "*Available shortcuts for all:*\n"
|
17
|
+
@shortcuts[:all].each { |name, value|
|
25
18
|
msg += " _#{name}: #{value}_\n"
|
26
19
|
}
|
27
20
|
respond msg, dest
|
28
21
|
end
|
22
|
+
|
23
|
+
if @shortcuts.keys.include?(from) and @shortcuts[from].keys.size > 0
|
24
|
+
new_hash = @shortcuts[from].dup
|
25
|
+
@shortcuts[:all].keys.each { |k| new_hash.delete(k) }
|
26
|
+
if new_hash.keys.size > 0
|
27
|
+
msg = "*Available shortcuts for #{from}:*\n"
|
28
|
+
new_hash.each { |name, value|
|
29
|
+
msg += " _#{name}: #{value}_\n"
|
30
|
+
}
|
31
|
+
respond msg, dest
|
32
|
+
end
|
33
|
+
end
|
34
|
+
respond "No shortcuts found", dest if msg == ""
|
29
35
|
end
|
30
|
-
respond "No shortcuts found", dest if msg == ""
|
31
36
|
end
|
32
37
|
end
|
33
38
|
end
|
@@ -1,37 +1,42 @@
|
|
1
1
|
class SlackSmartBot
|
2
|
-
def bot_rules(dest, help_command, typem, rules_file,
|
2
|
+
def bot_rules(dest, help_command, typem, rules_file, user)
|
3
3
|
save_stats(__method__)
|
4
|
-
|
5
|
-
|
4
|
+
from = user.name
|
5
|
+
if config[:allow_access].key?(__method__) and !config[:allow_access][__method__].include?(user.name) and !config[:allow_access][__method__].include?(user.id)
|
6
|
+
respond "You don't have access to use this command, please contact an Admin to be able to use it: <@#{config.admins.join(">, <@")}>"
|
7
|
+
else
|
8
|
+
if typem == :on_extended or typem == :on_call #for the other cases above.
|
9
|
+
help_filtered = get_help(rules_file, dest, from, true)
|
6
10
|
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
11
|
+
if help_command.to_s != ""
|
12
|
+
help_found = false
|
13
|
+
help_filtered.split(/^\s*-------*$/).each do |h|
|
14
|
+
if h.match?(/[`_]#{help_command}/i)
|
15
|
+
respond "*#{config.channel}*:#{h}", dest
|
16
|
+
help_found = true
|
17
|
+
end
|
13
18
|
end
|
19
|
+
respond("*#{config.channel}*: I didn't find any command starting by `#{help_command}`", dest) unless help_found
|
20
|
+
else
|
21
|
+
message = "-\n\n\n===================================\n*Rules from channel #{config.channel}*\n"
|
22
|
+
if typem == :on_extended
|
23
|
+
message += "To run the commands on this extended channel, add `!`, `!!` or `^` before the command.\n"
|
24
|
+
end
|
25
|
+
message += help_filtered
|
26
|
+
respond message, dest
|
14
27
|
end
|
15
|
-
respond("*#{config.channel}*: I didn't find any command starting by `#{help_command}`", dest) unless help_found
|
16
|
-
else
|
17
|
-
message = "-\n\n\n===================================\n*Rules from channel #{config.channel}*\n"
|
18
|
-
if typem == :on_extended
|
19
|
-
message += "To run the commands on this extended channel, add `!`, `!!` or `^` before the command.\n"
|
20
|
-
end
|
21
|
-
message += help_filtered
|
22
|
-
respond message, dest
|
23
|
-
end
|
24
28
|
|
25
|
-
|
26
|
-
|
27
|
-
|
29
|
+
unless rules_file.empty?
|
30
|
+
begin
|
31
|
+
eval(File.new(config.path+rules_file).read) if File.exist?(config.path+rules_file)
|
32
|
+
end
|
33
|
+
end
|
34
|
+
if defined?(git_project) and git_project.to_s != "" and help_command.to_s == ""
|
35
|
+
respond "Git project: #{git_project}", dest
|
36
|
+
else
|
37
|
+
def git_project() "" end
|
38
|
+
def project_folder() "" end
|
28
39
|
end
|
29
|
-
end
|
30
|
-
if defined?(git_project) and git_project.to_s != "" and help_command.to_s == ""
|
31
|
-
respond "Git project: #{git_project}", dest
|
32
|
-
else
|
33
|
-
def git_project() "" end
|
34
|
-
def project_folder() "" end
|
35
40
|
end
|
36
41
|
end
|
37
42
|
end
|
@@ -7,87 +7,92 @@ class SlackSmartBot
|
|
7
7
|
# helpmaster: the admins will be the master admins, the creator of the bot and the creator of the channel
|
8
8
|
# helpmaster: follow the instructions in case creating cloud bots
|
9
9
|
# helpmaster:
|
10
|
-
def create_bot(dest,
|
10
|
+
def create_bot(dest, user, cloud, channel)
|
11
11
|
save_stats(__method__)
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
channel
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
12
|
+
from = user.name
|
13
|
+
if config[:allow_access].key?(__method__) and !config[:allow_access][__method__].include?(user.name) and !config[:allow_access][__method__].include?(user.id)
|
14
|
+
respond "You don't have access to use this command, please contact an Admin to be able to use it: <@#{config.admins.join(">, <@")}>"
|
15
|
+
else
|
16
|
+
if config.on_master_bot
|
17
|
+
get_channels_name_and_id() unless @channels_name.keys.include?(channel) or @channels_id.keys.include?(channel)
|
18
|
+
channel_id = nil
|
19
|
+
if @channels_name.key?(channel) #it is an id
|
20
|
+
channel_id = channel
|
21
|
+
channel = @channels_name[channel_id]
|
22
|
+
elsif @channels_id.key?(channel) #it is a channel name
|
23
|
+
channel_id = @channels_id[channel]
|
24
|
+
end
|
25
|
+
#todo: add pagination for case more than 1000 channels on the workspace
|
26
|
+
channels = client.web_client.conversations_list(
|
27
|
+
types: "private_channel,public_channel",
|
28
|
+
limit: "1000",
|
29
|
+
exclude_archived: "true",
|
30
|
+
).channels
|
31
|
+
channel_found = channels.detect { |c| c.name == channel }
|
32
|
+
members = client.web_client.conversations_members(channel: @channels_id[channel]).members unless channel_found.nil?
|
29
33
|
|
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
|
-
|
34
|
+
if channel_id.nil?
|
35
|
+
respond "There is no channel with that name: #{channel}, please be sure is written exactly the same", dest
|
36
|
+
elsif channel == config.master_channel
|
37
|
+
respond "There is already a bot in this channel: #{channel}", dest
|
38
|
+
elsif @bots_created.keys.include?(channel_id)
|
39
|
+
respond "There is already a bot in this channel: #{channel}, kill it before", dest
|
40
|
+
elsif config[:nick_id] != channel_found.creator and !members.include?(config[:nick_id])
|
41
|
+
respond "You need to add first to the channel the smart bot user: #{config[:nick]}", dest
|
42
|
+
else
|
43
|
+
if channel_id != config[:channel]
|
44
|
+
begin
|
45
|
+
rules_file = "slack-smart-bot_rules_#{channel_id}_#{from.gsub(" ", "_")}.rb"
|
46
|
+
if defined?(RULES_FOLDER)
|
47
|
+
rules_file = RULES_FOLDER + rules_file
|
48
|
+
else
|
49
|
+
Dir.mkdir("#{config.path}/rules") unless Dir.exist?("#{config.path}/rules")
|
50
|
+
Dir.mkdir("#{config.path}/rules/#{channel_id}") unless Dir.exist?("#{config.path}/rules/#{channel_id}")
|
51
|
+
rules_file = "/rules/#{channel_id}/" + rules_file
|
52
|
+
end
|
53
|
+
default_rules = (__FILE__).gsub(/slack\/smart-bot\/commands\/on_master\/create_bot\.rb$/, "slack-smart-bot_rules.rb")
|
54
|
+
File.delete(config.path + rules_file) if File.exist?(config.path + rules_file)
|
55
|
+
FileUtils.copy_file(default_rules, config.path + rules_file) unless File.exist?(config.path + rules_file)
|
56
|
+
admin_users = Array.new()
|
57
|
+
creator_info = client.web_client.users_info(user: channel_found.creator)
|
58
|
+
admin_users = [from, creator_info.user.name] + config.masters
|
59
|
+
admin_users.uniq!
|
60
|
+
@logger.info "ruby #{config.file_path} \"#{channel}\" \"#{admin_users.join(",")}\" \"#{rules_file}\" on"
|
61
|
+
|
62
|
+
if cloud
|
63
|
+
respond "Copy the bot folder to your cloud location and run `ruby #{config.file} \"#{channel}\" \"#{admin_users.join(",")}\" \"#{rules_file}\" on&`", dest
|
64
|
+
else
|
65
|
+
t = Thread.new do
|
66
|
+
`BOT_SILENT=false ruby #{config.file_path} \"#{channel}\" \"#{admin_users.join(",")}\" \"#{rules_file}\" on`
|
67
|
+
end
|
63
68
|
end
|
69
|
+
@bots_created[channel_id] = {
|
70
|
+
creator_name: from,
|
71
|
+
channel_id: channel_id,
|
72
|
+
channel_name: @channels_name[channel_id],
|
73
|
+
status: :on,
|
74
|
+
created: Time.now.strftime("%Y-%m-%dT%H:%M:%S.000Z")[0..18],
|
75
|
+
rules_file: rules_file,
|
76
|
+
admins: admin_users.join(","),
|
77
|
+
extended: [],
|
78
|
+
cloud: cloud,
|
79
|
+
thread: t,
|
80
|
+
}
|
81
|
+
respond "The bot has been created on channel: #{channel}. Rules file: #{File.basename rules_file}. Admins: #{admin_users.join(", ")}", dest
|
82
|
+
update_bots_file()
|
83
|
+
rescue Exception => stack
|
84
|
+
@logger.fatal stack
|
85
|
+
message = "Problem creating the bot on channel #{channel}. Error: <#{stack}>."
|
86
|
+
@logger.error message
|
87
|
+
respond message, dest
|
64
88
|
end
|
65
|
-
|
66
|
-
|
67
|
-
channel_id: channel_id,
|
68
|
-
channel_name: @channels_name[channel_id],
|
69
|
-
status: :on,
|
70
|
-
created: Time.now.strftime("%Y-%m-%dT%H:%M:%S.000Z")[0..18],
|
71
|
-
rules_file: rules_file,
|
72
|
-
admins: admin_users.join(","),
|
73
|
-
extended: [],
|
74
|
-
cloud: cloud,
|
75
|
-
thread: t,
|
76
|
-
}
|
77
|
-
respond "The bot has been created on channel: #{channel}. Rules file: #{File.basename rules_file}. Admins: #{admin_users.join(", ")}", dest
|
78
|
-
update_bots_file()
|
79
|
-
rescue Exception => stack
|
80
|
-
@logger.fatal stack
|
81
|
-
message = "Problem creating the bot on channel #{channel}. Error: <#{stack}>."
|
82
|
-
@logger.error message
|
83
|
-
respond message, dest
|
89
|
+
else
|
90
|
+
respond "There is already a bot in this channel: #{channel}, and it is the Master Channel!", dest
|
84
91
|
end
|
85
|
-
else
|
86
|
-
respond "There is already a bot in this channel: #{channel}, and it is the Master Channel!", dest
|
87
92
|
end
|
93
|
+
else
|
94
|
+
respond "Sorry I cannot create bots from this channel, please visit the master channel: <##{@master_bot_id}>", dest
|
88
95
|
end
|
89
|
-
else
|
90
|
-
respond "Sorry I cannot create bots from this channel, please visit the master channel: <##{@master_bot_id}>", dest
|
91
96
|
end
|
92
97
|
end
|
93
98
|
end
|
@@ -2,6 +2,7 @@ class SlackSmartBot
|
|
2
2
|
def listen_simulate
|
3
3
|
@salutations = [config[:nick], "<@#{config[:nick_id]}>", "bot", "smart"]
|
4
4
|
@pings = []
|
5
|
+
@last_activity_check = Time.now
|
5
6
|
get_bots_created()
|
6
7
|
@buffer_complete = [] unless defined?(@buffer_complete)
|
7
8
|
b = File.read("#{config.path}/buffer_complete.log")
|
@@ -41,6 +42,7 @@ class SlackSmartBot
|
|
41
42
|
|
42
43
|
def listen
|
43
44
|
@pings = []
|
45
|
+
@last_activity_check = Time.now
|
44
46
|
get_bots_created()
|
45
47
|
|
46
48
|
client.on :message do |data|
|
@@ -1,6 +1,7 @@
|
|
1
1
|
class SlackSmartBot
|
2
2
|
def process(user, command, dest, dchannel, rules_file, typem, files, ts)
|
3
3
|
from = user.name
|
4
|
+
|
4
5
|
if user.profile.display_name.to_s.match?(/\A\s*\z/)
|
5
6
|
user.profile.display_name = user.profile.real_name
|
6
7
|
end
|
@@ -56,7 +57,7 @@ class SlackSmartBot
|
|
56
57
|
when /^\s*pause\s(this\s)?bot$/i
|
57
58
|
pause_bot(dest, from)
|
58
59
|
when /^\s*bot\sstatus/i
|
59
|
-
bot_status(dest,
|
60
|
+
bot_status(dest, user)
|
60
61
|
when /\Anotify\s+<#(C\w+)\|.+>\s+(.+)\s*\z/im, /\Anotify\s+(all)?\s*(.+)\s*\z/im
|
61
62
|
where = $1
|
62
63
|
message = $2
|
@@ -64,7 +65,7 @@ class SlackSmartBot
|
|
64
65
|
when /^\s*create\s+(cloud\s+)?bot\s+on\s+<#C\w+\|(.+)>\s*/i, /^create\s+(cloud\s+)?bot\s+on\s+(.+)\s*/i
|
65
66
|
cloud = !$1.nil?
|
66
67
|
channel = $2
|
67
|
-
create_bot(dest,
|
68
|
+
create_bot(dest, user, cloud, channel)
|
68
69
|
when /^\s*kill\sbot\son\s<#C\w+\|(.+)>\s*$/i, /^kill\sbot\son\s(.+)\s*$/i
|
69
70
|
channel = $1
|
70
71
|
kill_bot_on_channel(dest, from, channel)
|
@@ -119,8 +120,13 @@ class SlackSmartBot
|
|
119
120
|
|
120
121
|
# only when :on and (listening or on demand or direct message)
|
121
122
|
if @status == :on and
|
122
|
-
(@questions.
|
123
|
-
|
123
|
+
(@questions.key?(from) or
|
124
|
+
(@repl_sessions.key?(from) and dest==@repl_sessions[from][:dest] and
|
125
|
+
((@repl_sessions[from][:on_thread] and Thread.current[:thread_ts] == @repl_sessions[from][:thread_ts]) or
|
126
|
+
(!@repl_sessions[from][:on_thread] and !Thread.current[:on_thread]))) or
|
127
|
+
(@listening.key?(from) and typem != :on_extended and
|
128
|
+
((@listening[from].key?(dest) and !Thread.current[:on_thread]) or
|
129
|
+
(@listening[from].key?(Thread.current[:thread_ts]) and Thread.current[:on_thread] ) )) or
|
124
130
|
typem == :on_dm or typem == :on_pg or on_demand)
|
125
131
|
processed2 = true
|
126
132
|
|
@@ -129,17 +135,17 @@ class SlackSmartBot
|
|
129
135
|
# bot rules for extended channels
|
130
136
|
when /^bot\s+rules\s*(.+)?$/i
|
131
137
|
help_command = $1
|
132
|
-
bot_rules(dest, help_command, typem, rules_file,
|
138
|
+
bot_rules(dest, help_command, typem, rules_file, user)
|
133
139
|
when /^\s*(add\s)?shortcut\s(for\sall)?\s*([^:]+)\s*:\s*(.+)/i, /^(add\s)sc\s(for\sall)?\s*([^:]+)\s*:\s*(.+)/i
|
134
140
|
for_all = $2
|
135
141
|
shortcut_name = $3.to_s.downcase
|
136
142
|
command_to_run = $4
|
137
|
-
add_shortcut(dest,
|
143
|
+
add_shortcut(dest, user, typem, for_all, shortcut_name, command, command_to_run)
|
138
144
|
when /^\s*(delete|remove)\s+shortcut\s+(.+)/i, /^(delete|remove)\s+sc\s+(.+)/i
|
139
145
|
shortcut = $2.to_s.downcase
|
140
|
-
delete_shortcut(dest,
|
146
|
+
delete_shortcut(dest, user, shortcut, typem, command)
|
141
147
|
when /^\s*see\sshortcuts/i, /^see\ssc/i
|
142
|
-
see_shortcuts(dest,
|
148
|
+
see_shortcuts(dest, user, typem)
|
143
149
|
|
144
150
|
#kept to be backwards compatible
|
145
151
|
when /^\s*id\schannel\s<#C\w+\|(.+)>\s*/i, /^id channel (.+)/
|
@@ -157,7 +163,53 @@ class SlackSmartBot
|
|
157
163
|
code.gsub!("\\n", "\n")
|
158
164
|
code.gsub!("\\r", "\r")
|
159
165
|
@logger.info code
|
160
|
-
ruby_code(dest, code, rules_file)
|
166
|
+
ruby_code(dest, user, code, rules_file)
|
167
|
+
when /^\s*(private\s+)?(repl|irb|live)\s*()()()$/i,
|
168
|
+
/^\s*(private\s+)?(repl|irb|live)\s+([\w\-]+)()()\s*$/i,
|
169
|
+
/^\s*(private\s+)?(repl|irb|live)\s+([\w\-]+)\s*:\s*"(.+)"()\s*$/i,
|
170
|
+
/^\s*(private\s+)?(repl|irb|live)\s+([\w\-]+)\s*:\s*"(.+)"\s+(.+)\s*$/i,
|
171
|
+
/^\s*(private\s+)?(repl|irb|live)\s+([\w\-]+)()\s+(.+)\s*$/i,
|
172
|
+
/^\s*(private\s+)?(repl|irb|live)()\s+()(.+)\s*$/i
|
173
|
+
if $1.to_s!=''
|
174
|
+
type = :private
|
175
|
+
else
|
176
|
+
type = :public
|
177
|
+
end
|
178
|
+
session_name = $3
|
179
|
+
description = $4
|
180
|
+
opts = " #{$5}"
|
181
|
+
env_vars = opts.scan(/\s+[\w\-]+="[^"]+"/i) + opts.scan(/\s+[\w\-]+='[^']+'/i)
|
182
|
+
opts.scan(/\s+[\w\-]+=[^'"\s]+/i).flatten.each do |ev|
|
183
|
+
env_vars << ev.gsub('=',"='") + "'"
|
184
|
+
end
|
185
|
+
env_vars.each_with_index do |ev, idx|
|
186
|
+
ev.gsub!("=","']=")
|
187
|
+
ev.lstrip!
|
188
|
+
env_vars[idx] = "ENV['#{ev}"
|
189
|
+
end
|
190
|
+
repl(dest, user, session_name, env_vars.flatten, rules_file, command, description, type)
|
191
|
+
when /^\s*get\s+(repl|irb|live)\s+([\w\-]+)\s*/i
|
192
|
+
session_name = $2
|
193
|
+
get_repl(dest, user, session_name)
|
194
|
+
when /^\s*run\s+(repl|irb|live)\s+([\w\-]+)()\s*$/i,
|
195
|
+
/^\s*run\s+(repl|irb|live)\s+([\w\-]+)\s+(.+)\s*$/i
|
196
|
+
session_name = $2
|
197
|
+
opts = " #{$3}"
|
198
|
+
env_vars = opts.scan(/\s+[\w\-]+="[^"]+"/i) + opts.scan(/\s+[\w\-]+='[^']+'/i)
|
199
|
+
opts.scan(/\s+[\w\-]+=[^'"\s]+/i).flatten.each do |ev|
|
200
|
+
env_vars << ev.gsub('=',"='") + "'"
|
201
|
+
end
|
202
|
+
env_vars.each_with_index do |ev, idx|
|
203
|
+
ev.gsub!("=","']=")
|
204
|
+
ev.lstrip!
|
205
|
+
env_vars[idx] = "ENV['#{ev}"
|
206
|
+
end
|
207
|
+
run_repl(dest, user, session_name, env_vars.flatten, rules_file)
|
208
|
+
when /^\s*(delete|remove)\s+(repl|irb|live)\s+([\w\-]+)\s*$/i
|
209
|
+
repl_name = $3.downcase
|
210
|
+
delete_repl(dest, user, repl_name)
|
211
|
+
when /^\s*see\s+(repls|repl|irb|irbs)\s*$/i
|
212
|
+
see_repls(dest, user, typem)
|
161
213
|
else
|
162
214
|
processed2 = false
|
163
215
|
end #of case
|