Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 19 additions & 3 deletions lib/datadog/appsec/metrics/collector.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,28 @@ module AppSec
module Metrics
# A class responsible for collecting WAF and RASP call metrics.
class Collector
Store = Struct.new(:evals, :matches, :errors, :timeouts, :duration_ns, :duration_ext_ns, keyword_init: true)
Store = Struct.new(
:evals,
:matches,
:errors,
:timeouts,
:duration_ns,
:duration_ext_ns,
:inputs_truncated,
keyword_init: true
)

attr_reader :waf, :rasp

def initialize
@mutex = Mutex.new
@waf = Store.new(evals: 0, matches: 0, errors: 0, timeouts: 0, duration_ns: 0, duration_ext_ns: 0)
@rasp = Store.new(evals: 0, matches: 0, errors: 0, timeouts: 0, duration_ns: 0, duration_ext_ns: 0)

@waf = Store.new(
evals: 0, matches: 0, errors: 0, timeouts: 0, duration_ns: 0, duration_ext_ns: 0, inputs_truncated: 0
)
@rasp = Store.new(
evals: 0, matches: 0, errors: 0, timeouts: 0, duration_ns: 0, duration_ext_ns: 0, inputs_truncated: 0
)
end

def record_waf(result)
Expand All @@ -23,6 +37,7 @@ def record_waf(result)
@waf.timeouts += 1 if result.timeout?
@waf.duration_ns += result.duration_ns
@waf.duration_ext_ns += result.duration_ext_ns
@waf.inputs_truncated += 1 if result.input_truncated?
end
end

Expand All @@ -34,6 +49,7 @@ def record_rasp(result)
@rasp.timeouts += 1 if result.timeout?
@rasp.duration_ns += result.duration_ns
@rasp.duration_ext_ns += result.duration_ext_ns
@rasp.inputs_truncated += 1 if result.input_truncated?
end
end
end
Expand Down
3 changes: 2 additions & 1 deletion lib/datadog/appsec/metrics/telemetry_exporter.rb
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,8 @@ def export_waf_request_metrics(metrics, context)
waf_timeout: metrics.timeouts.positive?.to_s,
request_blocked: context.interrupted?.to_s,
block_failure: 'false',
rate_limited: (!context.trace.sampled?).to_s
rate_limited: (!context.trace.sampled?).to_s,
input_truncated: metrics.inputs_truncated.positive?.to_s,
}
)
end
Expand Down
14 changes: 12 additions & 2 deletions lib/datadog/appsec/security_engine/result.rb
Original file line number Diff line number Diff line change
Expand Up @@ -9,14 +9,15 @@ module Result
class Base
attr_reader :events, :actions, :derivatives, :duration_ns, :duration_ext_ns

def initialize(events:, actions:, derivatives:, timeout:, duration_ns:, duration_ext_ns:)
def initialize(events:, actions:, derivatives:, timeout:, duration_ns:, duration_ext_ns:, input_truncated:)
@events = events
@actions = actions
@derivatives = derivatives

@timeout = timeout
@duration_ns = duration_ns
@duration_ext_ns = duration_ext_ns
@input_truncated = input_truncated
end

def timeout?
Expand All @@ -30,6 +31,10 @@ def match?
def error?
raise NotImplementedError
end

def input_truncated?
@input_truncated
end
end

# A result that indicates a security rule match
Expand Down Expand Up @@ -58,11 +63,12 @@ def error?
class Error
attr_reader :events, :actions, :derivatives, :duration_ns, :duration_ext_ns

def initialize(duration_ext_ns:)
def initialize(duration_ext_ns:, input_truncated:)
@events = []
@actions = @derivatives = {}
@duration_ns = 0
@duration_ext_ns = duration_ext_ns
@input_truncated = input_truncated
end

def timeout?
Expand All @@ -76,6 +82,10 @@ def match?
def error?
true
end

def input_truncated?
@input_truncated
end
end
end
end
Expand Down
5 changes: 3 additions & 2 deletions lib/datadog/appsec/security_engine/runner.rb
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ def run(persistent_data, ephemeral_data, timeout = WAF::LibDDWAF::DDWAF_RUN_TIME
report_execution(result)

unless SUCCESSFUL_EXECUTION_CODES.include?(result.status)
return Result::Error.new(duration_ext_ns: stop_ns - start_ns)
return Result::Error.new(duration_ext_ns: stop_ns - start_ns, input_truncated: result.input_truncated?)
end

klass = (result.status == :match) ? Result::Match : Result::Ok
Expand All @@ -52,7 +52,8 @@ def run(persistent_data, ephemeral_data, timeout = WAF::LibDDWAF::DDWAF_RUN_TIME
derivatives: result.derivatives,
timeout: result.timeout,
duration_ns: result.total_runtime,
duration_ext_ns: (stop_ns - start_ns)
duration_ext_ns: (stop_ns - start_ns),
input_truncated: result.input_truncated?
)
ensure
@mutex.unlock
Expand Down
4 changes: 3 additions & 1 deletion sig/datadog/appsec/metrics/collector.rbs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,9 @@ module Datadog

attr_accessor duration_ext_ns: ::Integer

def self.new: (evals: ::Integer, matches: ::Integer, errors: ::Integer, timeouts: ::Integer, duration_ns: ::Integer, duration_ext_ns: ::Integer) -> void
attr_accessor inputs_truncated: ::Integer

def self.new: (evals: ::Integer, matches: ::Integer, errors: ::Integer, timeouts: ::Integer, duration_ns: ::Integer, duration_ext_ns: ::Integer, inputs_truncated: ::Integer) -> void
end

@mutex: Mutex
Expand Down
12 changes: 10 additions & 2 deletions sig/datadog/appsec/security_engine/result.rbs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ module Datadog

@duration_ext_ns: ::Integer

@input_truncated: bool

attr_reader events: events

attr_reader actions: actions
Expand All @@ -31,13 +33,15 @@ module Datadog

attr_reader duration_ext_ns: ::Integer

def initialize: (events: events, actions: actions, derivatives: derivatives, timeout: bool, duration_ns: ::Integer, duration_ext_ns: ::Integer) -> void
def initialize: (events: events, actions: actions, derivatives: derivatives, timeout: bool, duration_ns: ::Integer, duration_ext_ns: ::Integer, input_truncated: bool) -> void

def timeout?: () -> bool

def match?: () -> bool

def error?: () -> bool

def input_truncated?: () -> bool
end

# A result that indicates a security rule match
Expand Down Expand Up @@ -66,6 +70,8 @@ module Datadog

@duration_ext_ns: ::Integer

@input_truncated: bool

attr_reader events: events

attr_reader actions: actions
Expand All @@ -76,13 +82,15 @@ module Datadog

attr_reader duration_ext_ns: ::Integer

def initialize: (duration_ext_ns: ::Integer) -> void
def initialize: (duration_ext_ns: ::Integer, input_truncated: bool) -> void

def timeout?: () -> false

def match?: () -> false

def error?: () -> true

def input_truncated?: () -> bool
end
end
end
Expand Down
2 changes: 1 addition & 1 deletion spec/datadog/appsec/context_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -166,7 +166,7 @@
end

let(:run_result) do
Datadog::AppSec::SecurityEngine::Result::Error.new(duration_ext_ns: 0)
Datadog::AppSec::SecurityEngine::Result::Error.new(duration_ext_ns: 0, input_truncated: false)
end
let(:persistent_data) do
{'server.request.query' => {'q' => "1' OR 1=1;"}}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,8 @@
derivatives: {},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,8 @@
derivatives: {},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,8 @@
derivatives: {},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down
12 changes: 8 additions & 4 deletions spec/datadog/appsec/event_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,8 @@
},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down Expand Up @@ -210,7 +211,8 @@
derivatives: {},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down Expand Up @@ -282,7 +284,8 @@
derivatives: {'dd.appsec.fp.http.endpoint' => 'http-post-c1525143-2d711642-1234567890'},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down Expand Up @@ -364,7 +367,8 @@
},
timeout: false,
duration_ns: 0,
duration_ext_ns: 0
duration_ext_ns: 0,
input_truncated: false
)
end

Expand Down
Loading