Skip to content

Commit 24cce56

Browse files
committed
Prevent injection in help.
1 parent 5feac05 commit 24cce56

File tree

5 files changed

+54
-11
lines changed

5 files changed

+54
-11
lines changed

.rubocop_todo.yml

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# This configuration was generated by
22
# `rubocop --auto-gen-config`
3-
# on 2025-10-01 17:05:23 UTC using RuboCop version 1.81.1.
3+
# on 2025-10-01 17:50:25 UTC using RuboCop version 1.81.1.
44
# The point is for the user to remove these configuration records
55
# one by one as the offenses are removed from the code base.
66
# Note that changes in the inspected code, or installation of new
@@ -44,7 +44,7 @@ RSpec/ContextWording:
4444
- 'spec/slack-api-explorer/commands/slack_spec.rb'
4545
- 'spec/support/api/endpoints/it_behaves_like_a_cursor_api.rb'
4646

47-
# Offense count: 10
47+
# Offense count: 12
4848
# Configuration parameters: CountAsOne.
4949
RSpec/ExampleLength:
5050
Max: 27
@@ -88,7 +88,7 @@ RSpec/RepeatedExampleGroupDescription:
8888
Exclude:
8989
- 'spec/api/endpoints/teams_endpoint_spec.rb'
9090

91-
# Offense count: 8
91+
# Offense count: 9
9292
# Configuration parameters: CustomTransform, IgnoreMethods, IgnoreMetadata.
9393
RSpec/SpecFilePathFormat:
9494
Exclude:
@@ -98,6 +98,7 @@ RSpec/SpecFilePathFormat:
9898
- 'spec/api/robots_spec.rb'
9999
- 'spec/api/swagger_documentation_spec.rb'
100100
- 'spec/slack-api-explorer/commands/default_spec.rb'
101+
- 'spec/slack-api-explorer/commands/help_spec.rb'
101102
- 'spec/slack-api-explorer/commands/slack_spec.rb'
102103
- 'spec/slack-api-explorer/commands/unknown_spec.rb'
103104
- 'spec/slack-api-explorer/version_spec.rb'
@@ -123,4 +124,4 @@ RSpec/VoidExpect:
123124
# Configuration parameters: AllowHeredoc, AllowURI, AllowQualifiedName, URISchemes, IgnoreCopDirectives, AllowedPatterns, SplitStrings.
124125
# URISchemes: http, https
125126
Layout/LineLength:
126-
Max: 175
127+
Max: 226

slack-api-explorer/commands/help.rb

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,9 @@ module Commands
33
class Help < SlackRubyBot::Commands::Base
44
def self.help_for(expression = nil)
55
@help ||= {}
6-
@help[expression] ||= '```' + `slack help #{expression}`.gsub(/^( )/, '') + '```'
6+
expression = Shellwords.join(['slack', 'help', Shellwords.parse(expression).compact].flatten)
7+
result, _ = Open3.capture2e(expression)
8+
@help[expression] ||= "```\n" + result.gsub(/^( )/, '').strip + "\n```"
79
end
810

911
def self.commands
@@ -46,9 +48,12 @@ def self.commands
4648

4749
def self.call(client, data, match)
4850
expression = match['expression'] if match.names.include?('expression')
49-
help = expression && !expression.empty? ? help_for(expression) : HELP
50-
client.say(channel: data.channel, text: [help, SlackApiExplorer::INFO].join("\n"))
51-
logger.info "HELP: #{client.owner} - #{data.user}"
51+
if expression && !expression.empty?
52+
client.say(channel: data.channel, text: help_for(expression))
53+
else
54+
client.say(channel: data.channel, text: [HELP, INFO].join("\n"))
55+
end
56+
logger.info "HELP: #{client.owner}, user=#{data.user}, for=#{expression || 'help'}"
5257
end
5358
end
5459
end

slack-api-explorer/commands/slack.rb

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,10 @@ def self.call(client, data, match)
99
expression = match['expression']
1010
expression = ::Slack::Messages::Formatting.unescape(expression)
1111
expression.gsub! '—', '--'
12-
logger.info "SLACK: #{client.owner} - #{expression}"
12+
logger.info "SLACK: #{client.owner}, cmd=#{expression}"
1313
args, pipe = Shellwords.parse(expression)
14-
output, error, _ = Open3.capture3(* ['slack', '--slack-api-token', client.owner.token, args].flatten)
14+
cmd = Shellwords.shelljoin(['slack', '--slack-api-token', client.owner.token, args].flatten)
15+
output, error, _ = Open3.capture3(cmd)
1516
error&.strip!
1617
output&.strip!
1718
if error && !error.blank?
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
require 'spec_helper'
2+
3+
describe SlackApiExplorer::Commands::Help do
4+
let!(:team) { Fabricate(:team) }
5+
let(:app) { SlackApiExplorer::Server.new(team: team) }
6+
let(:client) { app.send(:client) }
7+
let(:message_hook) { SlackRubyBot::Hooks::Message.new }
8+
9+
it 'displays help' do
10+
expect(message: "#{SlackRubyBot.config.user} help").to respond_with_slack_message(
11+
[
12+
SlackApiExplorer::Commands::Help::HELP,
13+
SlackApiExplorer::INFO
14+
].join("\n")
15+
)
16+
end
17+
18+
it 'displays command help' do
19+
expect(message: "#{SlackRubyBot.config.user} help auth").to respond_with_slack_message(
20+
"```\nNAME\nauth - Auth methods.\n\nSYNOPSIS\n\nslack [global options] auth revoke [--test arg]\n\nslack [global options] auth test\n\nCOMMANDS\nrevoke - Revokes a token.\ntest - Checks authentication & identity.\n```"
21+
)
22+
end
23+
24+
it 'does not inject ;' do
25+
expect(message: "#{SlackRubyBot.config.user} help auth ; ls").to respond_with_slack_message(
26+
"```\nerror: Unknown command ';'. Use 'slack help' for a list of commands.\n```"
27+
)
28+
end
29+
end

spec/slack-api-explorer/commands/slack_spec.rb

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,14 @@
9393
context 'chat postMessage' do
9494
it 'unescapes channel' do
9595
allow(Open3).to receive(:capture3).and_return(JSON.dump(ok: true), nil)
96-
expect(Open3).to receive(:capture3).with('slack', '--slack-api-token', client.token, 'chat', 'postMessage', '--text', 'Hello World', '--channel', '#C04KB5X4D')
96+
expect(Open3).to receive(:capture3).with(
97+
Shellwords.join(
98+
[
99+
'slack', '--slack-api-token', client.token, 'chat', 'postMessage', '--text', 'Hello World', '--channel',
100+
'#C04KB5X4D'
101+
]
102+
)
103+
)
97104
expect(message: "#{SlackRubyBot.config.user} chat postMessage --text 'Hello World' --channel <#C04KB5X4D>").to respond_with_slack_message("```\n{\n \"ok\": true\n}```")
98105
end
99106
end

0 commit comments

Comments
 (0)