Skip to content

Commit a214cff

Browse files
authored
Merge branch 'master' into appsec-56456-add-telemetry-metrics-to-rasp-calls
2 parents 9e07af4 + a72b341 commit a214cff

File tree

9 files changed

+255
-144
lines changed

9 files changed

+255
-144
lines changed

.circleci/config.yml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -275,6 +275,8 @@ orbs:
275275
name: Upload JUnit reports to Datadog
276276
when: always
277277
command: |
278+
sed -i 's/file="\.\//file="/g' tmp/rspec/*.xml
279+
278280
ls -l tmp/rspec/*.xml
279281
280282
curl -L --fail --retry 3 "https://github.com/DataDog/datadog-ci/releases/latest/download/datadog-ci_linux-x64" --output "/usr/local/bin/datadog-ci" && chmod +x /usr/local/bin/datadog-ci

.github/CODEOWNERS

Lines changed: 30 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,39 +1,39 @@
11
* @DataDog/ruby-guild
22

33
# Public Documentation
4-
/docs/Compatibility.md @DataDog/documentation
5-
/docs/GettingStarted.md @DataDog/documentation
4+
docs/Compatibility.md @DataDog/documentation
5+
docs/GettingStarted.md @DataDog/documentation
66

77
# Library
8-
/lib/datadog/appsec/ @DataDog/asm-ruby
9-
/lib/datadog/appsec.rb @DataDog/asm-ruby
10-
/lib/datadog/tracing/ @DataDog/tracing-ruby
11-
/lib/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
12-
/lib/datadog/tracing.rb @DataDog/tracing-ruby
13-
/lib/datadog/opentelemetry/ @DataDog/tracing-ruby
14-
/lib/datadog/opentelemetry.rb @DataDog/tracing-ruby
15-
/lib-injection/ @DataDog/tracing-ruby
16-
/lib/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
17-
/lib/datadog/profiling.rb @DataDog/profiling-rb @DataDog/ruby-guild
18-
/ext/ @DataDog/profiling-rb @DataDog/ruby-guild
8+
lib/datadog/appsec/ @DataDog/asm-ruby
9+
lib/datadog/appsec.rb @DataDog/asm-ruby
10+
lib/datadog/tracing/ @DataDog/tracing-ruby
11+
lib/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
12+
lib/datadog/tracing.rb @DataDog/tracing-ruby
13+
lib/datadog/opentelemetry/ @DataDog/tracing-ruby
14+
lib/datadog/opentelemetry.rb @DataDog/tracing-ruby
15+
lib-injection/ @DataDog/tracing-ruby
16+
lib/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
17+
lib/datadog/profiling.rb @DataDog/profiling-rb @DataDog/ruby-guild
18+
ext/ @DataDog/profiling-rb @DataDog/ruby-guild
1919

2020
# RBS signatures
21-
/sig/datadog/appsec/ @DataDog/asm-ruby
22-
/sig/datadog/appsec.rbs @DataDog/asm-ruby
23-
/sig/datadog/tracing/ @DataDog/tracing-ruby
24-
/sig/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
25-
/sig/datadog/tracing.rbs @DataDog/tracing-ruby
26-
/sig/datadog/opentelemetry/ @DataDog/tracing-ruby
27-
/sig/datadog/opentelemetry.rbs @DataDog/tracing-ruby
28-
/sig/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
29-
/sig/datadog/profiling.rbs @DataDog/profiling-rb @DataDog/ruby-guild
21+
sig/datadog/appsec/ @DataDog/asm-ruby
22+
sig/datadog/appsec.rbs @DataDog/asm-ruby
23+
sig/datadog/tracing/ @DataDog/tracing-ruby
24+
sig/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
25+
sig/datadog/tracing.rbs @DataDog/tracing-ruby
26+
sig/datadog/opentelemetry/ @DataDog/tracing-ruby
27+
sig/datadog/opentelemetry.rbs @DataDog/tracing-ruby
28+
sig/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
29+
sig/datadog/profiling.rbs @DataDog/profiling-rb @DataDog/ruby-guild
3030

3131
# Specs
32-
/spec/datadog/appsec/ @DataDog/asm-ruby
33-
/spec/datadog/tracing/ @DataDog/tracing-ruby
34-
/spec/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
35-
/spec/datadog/tracing_spec.rb @DataDog/tracing-ruby
36-
/spec/datadog/opentelemetry/ @DataDog/tracing-ruby
37-
/spec/datadog/opentelemetry_spec.rb @DataDog/tracing-ruby
38-
/spec/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
39-
/spec/datadog/profiling_spec.rb @DataDog/profiling-rb @DataDog/ruby-guild
32+
spec/datadog/appsec/ @DataDog/asm-ruby
33+
spec/datadog/tracing/ @DataDog/tracing-ruby
34+
spec/datadog/tracing/contrib/ @DataDog/apm-idm-ruby
35+
spec/datadog/tracing_spec.rb @DataDog/tracing-ruby
36+
spec/datadog/opentelemetry/ @DataDog/tracing-ruby
37+
spec/datadog/opentelemetry_spec.rb @DataDog/tracing-ruby
38+
spec/datadog/profiling/ @DataDog/profiling-rb @DataDog/ruby-guild
39+
spec/datadog/profiling_spec.rb @DataDog/profiling-rb @DataDog/ruby-guild

lib/datadog/appsec.rb

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,10 @@ def enabled?
1414
Datadog.configuration.appsec.enabled
1515
end
1616

17+
def rasp_enabled?
18+
Datadog.configuration.appsec.rasp_enabled
19+
end
20+
1721
def active_context
1822
Datadog::AppSec::Context.active
1923
end

lib/datadog/appsec/configuration/settings.rb

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,15 @@ def self.add_settings!(base)
4949
end
5050
end
5151

52+
# RASP or Runtime Application Self-Protection
53+
# is a collection of techniques and heuristics aimed at detecting malicious inputs and preventing
54+
# any potential side-effects on the application resulting from the use of said malicious inputs.
55+
option :rasp_enabled do |o|
56+
o.type :bool, nilable: true
57+
o.env 'DD_APPSEC_RASP_ENABLED'
58+
o.default true
59+
end
60+
5261
option :ruleset do |o|
5362
o.env 'DD_APPSEC_RULES'
5463
o.default :recommended

lib/datadog/appsec/contrib/active_record/instrumentation.rb

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ module Instrumentation
99
module_function
1010

1111
def detect_sql_injection(sql, adapter_name)
12+
return unless AppSec.rasp_enabled?
13+
1214
context = AppSec.active_context
1315
return unless context
1416

spec/datadog/appsec/configuration/settings_spec.rb

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,28 @@ def patcher
7777
end
7878
end
7979

80+
describe '#rasp_enabled' do
81+
context 'when DD_APPSEC_RASP_ENABLED' do
82+
around do |example|
83+
ClimateControl.modify('DD_APPSEC_RASP_ENABLED' => rasp_enabled_env_var) do
84+
example.run
85+
end
86+
end
87+
88+
context 'is not defined' do
89+
let(:rasp_enabled_env_var) { nil }
90+
91+
it { expect(settings.appsec.rasp_enabled).to eq(true) }
92+
end
93+
94+
context 'is defined' do
95+
let(:rasp_enabled_env_var) { 'false' }
96+
97+
it { expect(settings.appsec.rasp_enabled).to eq(false) }
98+
end
99+
end
100+
end
101+
80102
describe '#instrument' do
81103
let(:registry) { {} }
82104
let(:integration_name) { :fake }

spec/datadog/appsec/contrib/active_record/mysql2_adapter_spec.rb

Lines changed: 60 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -64,46 +64,70 @@
6464
processor.finalize
6565
end
6666

67-
it 'calls waf with correct arguments when querying using .where' do
68-
expect(Datadog::AppSec.active_context).to(
69-
receive(:run_rasp).with(
70-
Datadog::AppSec::Ext::RASP_SQLI,
71-
{},
72-
{
73-
'server.db.statement' => "SELECT `users`.* FROM `users` WHERE `users`.`name` = 'Bob'",
74-
'server.db.system' => 'mysql2'
75-
},
76-
Datadog.configuration.appsec.waf_timeout
77-
).and_call_original
78-
)
79-
80-
User.where(name: 'Bob').to_a
81-
end
67+
context 'when RASP is disabled' do
68+
before do
69+
allow(Datadog::AppSec).to receive(:rasp_enabled?).and_return(false)
70+
end
8271

83-
it 'calls waf with correct arguments when querying using .find_by_sql' do
84-
expect(Datadog::AppSec.active_context).to(
85-
receive(:run_rasp).with(
86-
Datadog::AppSec::Ext::RASP_SQLI,
87-
{},
88-
{
89-
'server.db.statement' => "SELECT * FROM users WHERE name = 'Bob'",
90-
'server.db.system' => 'mysql2'
91-
},
92-
Datadog.configuration.appsec.waf_timeout
93-
).and_call_original
94-
)
95-
96-
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
72+
it 'does not call waf when querying using .where' do
73+
expect(Datadog::AppSec.active_context).not_to receive(:run_rasp)
74+
75+
User.where(name: 'Bob').to_a
76+
end
77+
78+
it 'does not call waf when querying using .find_by_sql' do
79+
expect(Datadog::AppSec.active_context).not_to receive(:run_rasp)
80+
81+
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
82+
end
9783
end
9884

99-
it 'adds an event to processor context if waf result is a match' do
100-
result = Datadog::AppSec::SecurityEngine::Result::Match.new(
101-
events: [], actions: {}, derivatives: {}, timeout: false, duration_ns: 0, duration_ext_ns: 0
102-
)
85+
context 'when RASP is enabled' do
86+
before do
87+
allow(Datadog::AppSec).to receive(:rasp_enabled?).and_return(true)
88+
end
89+
90+
it 'calls waf with correct arguments when querying using .where' do
91+
expect(Datadog::AppSec.active_context).to(
92+
receive(:run_rasp).with(
93+
Datadog::AppSec::Ext::RASP_SQLI,
94+
{},
95+
{
96+
'server.db.statement' => "SELECT `users`.* FROM `users` WHERE `users`.`name` = 'Bob'",
97+
'server.db.system' => 'mysql2'
98+
},
99+
Datadog.configuration.appsec.waf_timeout
100+
).and_call_original
101+
)
102+
103+
User.where(name: 'Bob').to_a
104+
end
103105

104-
expect(Datadog::AppSec.active_context).to receive(:run_rasp).and_return(result)
105-
expect(Datadog::AppSec.active_context.events).to receive(:<<).and_call_original
106+
it 'calls waf with correct arguments when querying using .find_by_sql' do
107+
expect(Datadog::AppSec.active_context).to(
108+
receive(:run_rasp).with(
109+
Datadog::AppSec::Ext::RASP_SQLI,
110+
{},
111+
{
112+
'server.db.statement' => "SELECT * FROM users WHERE name = 'Bob'",
113+
'server.db.system' => 'mysql2'
114+
},
115+
Datadog.configuration.appsec.waf_timeout
116+
).and_call_original
117+
)
118+
119+
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
120+
end
106121

107-
User.where(name: 'Bob').to_a
122+
it 'adds an event to processor context if waf result is a match' do
123+
result = Datadog::AppSec::SecurityEngine::Result::Match.new(
124+
events: [], actions: {}, derivatives: {}, timeout: false, duration_ns: 0, duration_ext_ns: 0
125+
)
126+
127+
expect(Datadog::AppSec.active_context).to receive(:run_rasp).and_return(result)
128+
expect(Datadog::AppSec.active_context.events).to receive(:<<).and_call_original
129+
130+
User.where(name: 'Bob').to_a
131+
end
108132
end
109133
end

spec/datadog/appsec/contrib/active_record/postgresql_adapter_spec.rb

Lines changed: 66 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -65,52 +65,76 @@
6565
processor.finalize
6666
end
6767

68-
it 'calls waf with correct arguments when querying using .where' do
69-
expected_db_statement = if PlatformHelpers.jruby?
70-
'SELECT "users".* FROM "users" WHERE "users"."name" = ?'
71-
else
72-
'SELECT "users".* FROM "users" WHERE "users"."name" = $1'
73-
end
74-
75-
expect(Datadog::AppSec.active_context).to(
76-
receive(:run_rasp).with(
77-
Datadog::AppSec::Ext::RASP_SQLI,
78-
{},
79-
{
80-
'server.db.statement' => expected_db_statement,
81-
'server.db.system' => 'postgresql'
82-
},
83-
Datadog.configuration.appsec.waf_timeout
84-
).and_call_original
85-
)
86-
87-
User.where(name: 'Bob').to_a
88-
end
68+
context 'when RASP is disabled' do
69+
before do
70+
allow(Datadog::AppSec).to receive(:rasp_enabled?).and_return(false)
71+
end
8972

90-
it 'calls waf with correct arguments when querying using .find_by_sql' do
91-
expect(Datadog::AppSec.active_context).to(
92-
receive(:run_rasp).with(
93-
Datadog::AppSec::Ext::RASP_SQLI,
94-
{},
95-
{
96-
'server.db.statement' => "SELECT * FROM users WHERE name = 'Bob'",
97-
'server.db.system' => 'postgresql'
98-
},
99-
Datadog.configuration.appsec.waf_timeout
100-
).and_call_original
101-
)
102-
103-
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
73+
it 'does not call waf when querying using .where' do
74+
expect(Datadog::AppSec.active_context).not_to receive(:run_rasp)
75+
76+
User.where(name: 'Bob').to_a
77+
end
78+
79+
it 'does not call waf when querying using .find_by_sql' do
80+
expect(Datadog::AppSec.active_context).not_to receive(:run_rasp)
81+
82+
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
83+
end
10484
end
10585

106-
it 'adds an event to processor context if waf result is a match' do
107-
result = Datadog::AppSec::SecurityEngine::Result::Match.new(
108-
events: [], actions: {}, derivatives: {}, timeout: false, duration_ns: 0, duration_ext_ns: 0
109-
)
86+
context 'when RASP is enabled' do
87+
before do
88+
allow(Datadog::AppSec).to receive(:rasp_enabled?).and_return(true)
89+
end
90+
91+
it 'calls waf with correct arguments when querying using .where' do
92+
expected_db_statement = if PlatformHelpers.jruby?
93+
'SELECT "users".* FROM "users" WHERE "users"."name" = ?'
94+
else
95+
'SELECT "users".* FROM "users" WHERE "users"."name" = $1'
96+
end
97+
98+
expect(Datadog::AppSec.active_context).to(
99+
receive(:run_rasp).with(
100+
Datadog::AppSec::Ext::RASP_SQLI,
101+
{},
102+
{
103+
'server.db.statement' => expected_db_statement,
104+
'server.db.system' => 'postgresql'
105+
},
106+
Datadog.configuration.appsec.waf_timeout
107+
).and_call_original
108+
)
109+
110+
User.where(name: 'Bob').to_a
111+
end
110112

111-
expect(Datadog::AppSec.active_context).to receive(:run_rasp).and_return(result)
112-
expect(Datadog::AppSec.active_context.events).to receive(:<<).and_call_original
113+
it 'calls waf with correct arguments when querying using .find_by_sql' do
114+
expect(Datadog::AppSec.active_context).to(
115+
receive(:run_rasp).with(
116+
Datadog::AppSec::Ext::RASP_SQLI,
117+
{},
118+
{
119+
'server.db.statement' => "SELECT * FROM users WHERE name = 'Bob'",
120+
'server.db.system' => 'postgresql'
121+
},
122+
Datadog.configuration.appsec.waf_timeout
123+
).and_call_original
124+
)
125+
126+
User.find_by_sql("SELECT * FROM users WHERE name = 'Bob'").to_a
127+
end
113128

114-
User.where(name: 'Bob').to_a
129+
it 'adds an event to processor context if waf result is a match' do
130+
result = Datadog::AppSec::SecurityEngine::Result::Match.new(
131+
events: [], actions: {}, derivatives: {}, timeout: false, duration_ns: 0, duration_ext_ns: 0
132+
)
133+
134+
expect(Datadog::AppSec.active_context).to receive(:run_rasp).and_return(result)
135+
expect(Datadog::AppSec.active_context.events).to receive(:<<).and_call_original
136+
137+
User.where(name: 'Bob').to_a
138+
end
115139
end
116140
end

0 commit comments

Comments
 (0)