sqreen-alt 1.10.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/CODE_OF_CONDUCT.md +22 -0
- data/README.md +77 -0
- data/Rakefile +20 -0
- data/lib/sqreen-alt.rb +1 -0
- data/lib/sqreen.rb +68 -0
- data/lib/sqreen/attack_detected.html +2 -0
- data/lib/sqreen/binding_accessor.rb +288 -0
- data/lib/sqreen/ca.crt +72 -0
- data/lib/sqreen/call_countable.rb +67 -0
- data/lib/sqreen/callback_tree.rb +78 -0
- data/lib/sqreen/callbacks.rb +100 -0
- data/lib/sqreen/capped_queue.rb +23 -0
- data/lib/sqreen/condition_evaluator.rb +235 -0
- data/lib/sqreen/conditionable.rb +50 -0
- data/lib/sqreen/configuration.rb +168 -0
- data/lib/sqreen/context.rb +26 -0
- data/lib/sqreen/deliveries/batch.rb +84 -0
- data/lib/sqreen/deliveries/simple.rb +39 -0
- data/lib/sqreen/event.rb +16 -0
- data/lib/sqreen/events/attack.rb +61 -0
- data/lib/sqreen/events/remote_exception.rb +54 -0
- data/lib/sqreen/events/request_record.rb +62 -0
- data/lib/sqreen/exception.rb +34 -0
- data/lib/sqreen/frameworks.rb +40 -0
- data/lib/sqreen/frameworks/generic.rb +446 -0
- data/lib/sqreen/frameworks/rails.rb +148 -0
- data/lib/sqreen/frameworks/rails3.rb +36 -0
- data/lib/sqreen/frameworks/request_recorder.rb +69 -0
- data/lib/sqreen/frameworks/sinatra.rb +57 -0
- data/lib/sqreen/frameworks/sqreen_test.rb +26 -0
- data/lib/sqreen/instrumentation.rb +542 -0
- data/lib/sqreen/log.rb +119 -0
- data/lib/sqreen/metrics.rb +6 -0
- data/lib/sqreen/metrics/average.rb +39 -0
- data/lib/sqreen/metrics/base.rb +45 -0
- data/lib/sqreen/metrics/collect.rb +22 -0
- data/lib/sqreen/metrics/sum.rb +20 -0
- data/lib/sqreen/metrics_store.rb +96 -0
- data/lib/sqreen/middleware.rb +34 -0
- data/lib/sqreen/payload_creator.rb +137 -0
- data/lib/sqreen/performance_notifications.rb +86 -0
- data/lib/sqreen/performance_notifications/log.rb +36 -0
- data/lib/sqreen/performance_notifications/metrics.rb +36 -0
- data/lib/sqreen/performance_notifications/newrelic.rb +36 -0
- data/lib/sqreen/remote_command.rb +93 -0
- data/lib/sqreen/rule_attributes.rb +26 -0
- data/lib/sqreen/rule_callback.rb +108 -0
- data/lib/sqreen/rules.rb +126 -0
- data/lib/sqreen/rules_callbacks.rb +29 -0
- data/lib/sqreen/rules_callbacks/binding_accessor_matcher.rb +77 -0
- data/lib/sqreen/rules_callbacks/binding_accessor_metrics.rb +79 -0
- data/lib/sqreen/rules_callbacks/blacklist_ips.rb +44 -0
- data/lib/sqreen/rules_callbacks/count_http_codes.rb +40 -0
- data/lib/sqreen/rules_callbacks/crawler_user_agent_matches.rb +24 -0
- data/lib/sqreen/rules_callbacks/crawler_user_agent_matches_metrics.rb +24 -0
- data/lib/sqreen/rules_callbacks/custom_error.rb +64 -0
- data/lib/sqreen/rules_callbacks/execjs.rb +241 -0
- data/lib/sqreen/rules_callbacks/headers_insert.rb +22 -0
- data/lib/sqreen/rules_callbacks/inspect_rule.rb +25 -0
- data/lib/sqreen/rules_callbacks/matcher_rule.rb +138 -0
- data/lib/sqreen/rules_callbacks/rails_parameters.rb +14 -0
- data/lib/sqreen/rules_callbacks/record_request_context.rb +39 -0
- data/lib/sqreen/rules_callbacks/reflected_xss.rb +254 -0
- data/lib/sqreen/rules_callbacks/regexp_rule.rb +36 -0
- data/lib/sqreen/rules_callbacks/shell_env.rb +32 -0
- data/lib/sqreen/rules_callbacks/url_matches.rb +25 -0
- data/lib/sqreen/rules_callbacks/user_agent_matches.rb +22 -0
- data/lib/sqreen/rules_signature.rb +151 -0
- data/lib/sqreen/runner.rb +365 -0
- data/lib/sqreen/runtime_infos.rb +138 -0
- data/lib/sqreen/safe_json.rb +60 -0
- data/lib/sqreen/sdk.rb +22 -0
- data/lib/sqreen/serializer.rb +46 -0
- data/lib/sqreen/session.rb +317 -0
- data/lib/sqreen/shared_storage.rb +31 -0
- data/lib/sqreen/stats.rb +18 -0
- data/lib/sqreen/version.rb +5 -0
- metadata +148 -0
@@ -0,0 +1,50 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
require 'sqreen/condition_evaluator'
|
5
|
+
|
6
|
+
module Sqreen
|
7
|
+
# A module that will dynamically had preconditions to the pre/post/failing
|
8
|
+
# callbacks
|
9
|
+
module Conditionable
|
10
|
+
# Hook the necessary callback function
|
11
|
+
#
|
12
|
+
# @param conditions [Hash] hash of callback names => conditions
|
13
|
+
def condition_callbacks(conditions)
|
14
|
+
conditions = {} if conditions.nil?
|
15
|
+
base = self.class
|
16
|
+
%w(pre post failing).each do |cb|
|
17
|
+
conds = conditions[cb]
|
18
|
+
next unless base.method_defined?(cb)
|
19
|
+
send("#{cb}_conditions=", ConditionEvaluator.new(conds)) unless conds.nil?
|
20
|
+
defd = base.instance_variable_defined?("@conditional_hooked_#{cb}")
|
21
|
+
next if defd && base.instance_variable_get("@conditional_hooked_#{cb}")
|
22
|
+
base.send(:alias_method, "#{cb}_without_conditions", cb)
|
23
|
+
base.send(:alias_method, cb, "#{cb}_with_conditions")
|
24
|
+
base.instance_variable_set("@conditional_hooked_#{cb}", true)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
def pre_with_conditions(inst, *args, &block)
|
29
|
+
eargs = [binding, framework, inst, args, @data, nil]
|
30
|
+
return nil if !pre_conditions.nil? && !pre_conditions.evaluate(*eargs)
|
31
|
+
pre_without_conditions(inst, *args, &block)
|
32
|
+
end
|
33
|
+
|
34
|
+
def post_with_conditions(rv, inst, *args, &block)
|
35
|
+
eargs = [binding, framework, inst, args, @data, rv]
|
36
|
+
return nil if !post_conditions.nil? && !post_conditions.evaluate(*eargs)
|
37
|
+
post_without_conditions(rv, inst, *args, &block)
|
38
|
+
end
|
39
|
+
|
40
|
+
def failing_with_conditions(rv, inst, *args, &block)
|
41
|
+
eargs = [binding, framework, inst, args, @data, rv]
|
42
|
+
return nil if !failing_conditions.nil? && !failing_conditions.evaluate(*eargs)
|
43
|
+
failing_without_conditions(rv, inst, *args, &block)
|
44
|
+
end
|
45
|
+
|
46
|
+
protected
|
47
|
+
|
48
|
+
attr_accessor :pre_conditions, :post_conditions, :failing_conditions
|
49
|
+
end
|
50
|
+
end
|
@@ -0,0 +1,168 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
require 'yaml'
|
5
|
+
require 'erb'
|
6
|
+
require 'sqreen/performance_notifications/newrelic'
|
7
|
+
|
8
|
+
module Sqreen
|
9
|
+
@config = nil
|
10
|
+
|
11
|
+
def self.config_init(framework = nil)
|
12
|
+
@config = Configuration.new(framework)
|
13
|
+
@config.load!
|
14
|
+
if @config && config_get(:report_perf_newrelic)
|
15
|
+
Sqreen::PerformanceNotifications::NewRelic.enable
|
16
|
+
end
|
17
|
+
@config
|
18
|
+
end
|
19
|
+
|
20
|
+
def self.config_get(name)
|
21
|
+
raise 'No configuration defined' if @config.nil?
|
22
|
+
@config.get(name)
|
23
|
+
end
|
24
|
+
|
25
|
+
CONFIG_FILE_BY_ENV = 'SQREEN_CONFIG_FILE'.freeze
|
26
|
+
|
27
|
+
CONFIG_DESCRIPTION = [
|
28
|
+
{ :env => :SQREEN_DISABLE, :name => :disable,
|
29
|
+
:default => false, :convert => :to_bool },
|
30
|
+
{ :env => :SQREEN_URL, :name => :url,
|
31
|
+
:default => 'https://back.sqreen.io' },
|
32
|
+
{ :env => :SQREEN_TOKEN, :name => :token,
|
33
|
+
:default => nil },
|
34
|
+
{ :env => :SQREEN_RULES, :name => :local_rules,
|
35
|
+
:default => nil },
|
36
|
+
{ :env => :SQREEN_RULES_SIGNATURE, :name => :rules_verify_signature,
|
37
|
+
:default => true },
|
38
|
+
{ :env => :SQREEN_LOG_LEVEL, :name => :log_level,
|
39
|
+
:default => 'WARN', :choice => %w[UNKNOWN FATAL ERROR WARN INFO DEBUG] },
|
40
|
+
{ :env => :SQREEN_LOG_LOCATION, :name => :log_location,
|
41
|
+
:default => 'log/sqreen.log' },
|
42
|
+
{ :env => :SQREEN_RUN_IN_TEST, :name => :run_in_test,
|
43
|
+
:default => false, :convert => :to_bool },
|
44
|
+
{ :env => :SQREEN_BLOCK_ALL_RULES, :name => :block_all_rules,
|
45
|
+
:default => nil },
|
46
|
+
{ :env => :SQREEN_REPORT_PERF_NR, :name => :report_perf_newrelic,
|
47
|
+
:default => false, :convert => :to_bool },
|
48
|
+
{ :env => :SQREEN_INITIAL_FEATURES, :name => :initial_features,
|
49
|
+
:default => nil },
|
50
|
+
|
51
|
+
].freeze
|
52
|
+
|
53
|
+
CONFIG_FILE_NAME = 'sqreen.yml'.freeze
|
54
|
+
|
55
|
+
def self.to_bool(value)
|
56
|
+
%w[1 true].include?(value.to_s.downcase.strip)
|
57
|
+
end
|
58
|
+
|
59
|
+
# Class to access configurations variables
|
60
|
+
# This try to load environment by different ways.
|
61
|
+
# 1. By file:
|
62
|
+
# a. From path in environment variable SQREEN_CONFIG_FILE
|
63
|
+
# b. From path in #{Rails.root}/config/sqreen.yml
|
64
|
+
# c. From home in ~/.sqreen.yml
|
65
|
+
# 2. From the environment, which overrides whatever result we found in 1.
|
66
|
+
class Configuration
|
67
|
+
def initialize(framework = nil)
|
68
|
+
@framework = framework
|
69
|
+
@config = default_values
|
70
|
+
end
|
71
|
+
|
72
|
+
def load!
|
73
|
+
path = find_configuration_file
|
74
|
+
if path
|
75
|
+
file_config = parse_configuration_file(path)
|
76
|
+
@config.merge!(file_config)
|
77
|
+
end
|
78
|
+
|
79
|
+
env_config = from_environment
|
80
|
+
@config.merge!(env_config)
|
81
|
+
end
|
82
|
+
|
83
|
+
def get(name)
|
84
|
+
@config[name.to_sym]
|
85
|
+
end
|
86
|
+
|
87
|
+
def default_values
|
88
|
+
res = {}
|
89
|
+
Sqreen::CONFIG_DESCRIPTION.each do |param|
|
90
|
+
name = param[:name]
|
91
|
+
value = param[:default]
|
92
|
+
choices = param[:choices]
|
93
|
+
if choices && !choices.include?(value)
|
94
|
+
msg = format("Invalid value '%s' for env '%s' (allowed: %s)", value, name, choices)
|
95
|
+
raise Sqreen::Exception, msg
|
96
|
+
end
|
97
|
+
res[name] = param[:convert] ? send(param[:convert], value) : value
|
98
|
+
end
|
99
|
+
res
|
100
|
+
end
|
101
|
+
|
102
|
+
def from_environment
|
103
|
+
res = {}
|
104
|
+
Sqreen::CONFIG_DESCRIPTION.each do |param|
|
105
|
+
name = param[:name]
|
106
|
+
value = ENV[param[:env].to_s]
|
107
|
+
next unless value
|
108
|
+
res[name] = param[:convert] ? send(param[:convert], value) : value
|
109
|
+
end
|
110
|
+
res
|
111
|
+
end
|
112
|
+
|
113
|
+
def parse_configuration_file(path)
|
114
|
+
yaml = YAML.load(ERB.new(File.read(path)).result)
|
115
|
+
return {} unless yaml.is_a?(Hash)
|
116
|
+
if @framework
|
117
|
+
env = @framework.framework_infos[:environment]
|
118
|
+
yaml = yaml[env] if env && yaml[env].is_a?(Hash)
|
119
|
+
end
|
120
|
+
res = {}
|
121
|
+
# hash keys loaded by YAML are strings instead of symbols
|
122
|
+
Sqreen::CONFIG_DESCRIPTION.each do |param|
|
123
|
+
name = param[:name]
|
124
|
+
value = yaml[name.to_s]
|
125
|
+
next unless value
|
126
|
+
res[name] = param[:convert] ? send(param[:convert], value) : value
|
127
|
+
end
|
128
|
+
res
|
129
|
+
end
|
130
|
+
|
131
|
+
def find_user_home
|
132
|
+
homes = %w[HOME HOMEPATH]
|
133
|
+
homes.detect { |h| !ENV[h].nil? }
|
134
|
+
end
|
135
|
+
|
136
|
+
def find_configuration_file
|
137
|
+
config_file_from_env || local_config_file || config_file_from_home
|
138
|
+
end
|
139
|
+
|
140
|
+
protected
|
141
|
+
|
142
|
+
def config_file_from_env
|
143
|
+
path = ENV[Sqreen::CONFIG_FILE_BY_ENV]
|
144
|
+
return path if path && File.exist?(path)
|
145
|
+
end
|
146
|
+
|
147
|
+
def local_config_file
|
148
|
+
if @framework && @framework.root
|
149
|
+
path = File.join(@framework.root.to_s, 'config', CONFIG_FILE_NAME)
|
150
|
+
return path if File.exist?(path)
|
151
|
+
else
|
152
|
+
path = File.expand_path(File.join('config', 'sqreen.yml'))
|
153
|
+
return path if File.exist?(path)
|
154
|
+
end
|
155
|
+
end
|
156
|
+
|
157
|
+
def config_file_from_home
|
158
|
+
home = find_user_home
|
159
|
+
return unless home
|
160
|
+
path = File.join(ENV[home], '.' + CONFIG_FILE_NAME)
|
161
|
+
return path if File.exist?(path)
|
162
|
+
end
|
163
|
+
|
164
|
+
def to_bool(value)
|
165
|
+
Sqreen::to_bool(value)
|
166
|
+
end
|
167
|
+
end
|
168
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
module Sqreen
|
5
|
+
# Context
|
6
|
+
class Context
|
7
|
+
attr_accessor :bt
|
8
|
+
|
9
|
+
def self.bt
|
10
|
+
Context.new.bt
|
11
|
+
end
|
12
|
+
|
13
|
+
def initialize
|
14
|
+
@bt = get_current_backtrace
|
15
|
+
end
|
16
|
+
|
17
|
+
def get_current_backtrace
|
18
|
+
# Force caller to be resolved now
|
19
|
+
caller.map(&:to_s)
|
20
|
+
end
|
21
|
+
|
22
|
+
def ==(other)
|
23
|
+
other.bt == @bt
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,84 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
require 'sqreen/deliveries/simple'
|
5
|
+
require 'sqreen/events/remote_exception'
|
6
|
+
module Sqreen
|
7
|
+
module Deliveries
|
8
|
+
# Simple delivery method that batch event already seen in a batch
|
9
|
+
class Batch < Simple
|
10
|
+
attr_accessor :max_batch, :max_staleness
|
11
|
+
attr_accessor :current_batch, :first_seen
|
12
|
+
|
13
|
+
def initialize(session,
|
14
|
+
max_batch,
|
15
|
+
max_staleness,
|
16
|
+
randomize_staleness = true)
|
17
|
+
super(session)
|
18
|
+
self.max_batch = max_batch
|
19
|
+
self.max_staleness = max_staleness
|
20
|
+
@original_max_staleness = max_staleness
|
21
|
+
self.current_batch = []
|
22
|
+
@first_seen = {}
|
23
|
+
@randomize_staleness = randomize_staleness
|
24
|
+
end
|
25
|
+
|
26
|
+
def post_event(event)
|
27
|
+
current_batch.push(event)
|
28
|
+
post_batch if post_batch_needed?(event)
|
29
|
+
end
|
30
|
+
|
31
|
+
def drain
|
32
|
+
post_batch unless current_batch.empty?
|
33
|
+
end
|
34
|
+
|
35
|
+
def tick
|
36
|
+
post_batch if !current_batch.empty? && stale?
|
37
|
+
end
|
38
|
+
|
39
|
+
protected
|
40
|
+
|
41
|
+
def stale?
|
42
|
+
min = @first_seen.values.min
|
43
|
+
return false if min.nil?
|
44
|
+
(min + max_staleness) < Time.now
|
45
|
+
end
|
46
|
+
|
47
|
+
def post_batch_needed?(event)
|
48
|
+
now = Time.now
|
49
|
+
event_keys(event).map do |key|
|
50
|
+
was = @first_seen[key]
|
51
|
+
@first_seen[key] ||= now
|
52
|
+
was.nil? || current_batch.size > max_batch || (was + max_staleness) < now
|
53
|
+
end.any?
|
54
|
+
end
|
55
|
+
|
56
|
+
def post_batch
|
57
|
+
session.post_batch(current_batch)
|
58
|
+
current_batch.clear
|
59
|
+
now = Time.now
|
60
|
+
@first_seen.each_key do |key|
|
61
|
+
@first_seen[key] = now
|
62
|
+
end
|
63
|
+
return unless @randomize_staleness
|
64
|
+
self.max_staleness = @original_max_staleness
|
65
|
+
# Adds up to 10% of lateness
|
66
|
+
self.max_staleness += rand(@original_max_staleness / 10)
|
67
|
+
end
|
68
|
+
|
69
|
+
def event_keys(event)
|
70
|
+
return [event_key(event)] unless event.is_a?(Sqreen::RequestRecord)
|
71
|
+
event.observed.fetch(:attacks, []).map { |e| "att-#{e[:rule_name]}" } + event.observed.fetch(:sqreen_exceptions, []).map { |e| "rex-#{e[:exception].class}" }
|
72
|
+
end
|
73
|
+
|
74
|
+
def event_key(event)
|
75
|
+
case event
|
76
|
+
when Sqreen::Attack
|
77
|
+
"att-#{event.type}"
|
78
|
+
when Sqreen::RemoteException
|
79
|
+
"rex-#{event.klass}"
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
require 'sqreen/events/remote_exception'
|
5
|
+
require 'sqreen/events/request_record'
|
6
|
+
|
7
|
+
module Sqreen
|
8
|
+
module Deliveries
|
9
|
+
# Simple delivery method that directly call session on event
|
10
|
+
class Simple
|
11
|
+
attr_accessor :session
|
12
|
+
|
13
|
+
def initialize(session)
|
14
|
+
self.session = session
|
15
|
+
end
|
16
|
+
|
17
|
+
def post_event(event)
|
18
|
+
case event
|
19
|
+
when Sqreen::Attack
|
20
|
+
session.post_attack(event)
|
21
|
+
when Sqreen::RemoteException
|
22
|
+
session.post_sqreen_exception(event)
|
23
|
+
when Sqreen::RequestRecord
|
24
|
+
session.post_request_record(event)
|
25
|
+
else
|
26
|
+
session.post_event(event)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def drain
|
31
|
+
# Since everything is posted at once nothing needs to be done here
|
32
|
+
end
|
33
|
+
|
34
|
+
def tick
|
35
|
+
# Since everything is posted at once nothing needs to be done here
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
data/lib/sqreen/event.rb
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
module Sqreen
|
5
|
+
# Master interface for point in time events (e.g. Attack, RemoteException)
|
6
|
+
class Event
|
7
|
+
attr_reader :payload
|
8
|
+
def initialize(payload)
|
9
|
+
@payload = payload
|
10
|
+
end
|
11
|
+
|
12
|
+
def to_hash
|
13
|
+
payload.to_hash
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
# Copyright (c) 2015 Sqreen. All Rights Reserved.
|
2
|
+
# Please refer to our terms for more information: https://www.sqreen.io/terms.html
|
3
|
+
|
4
|
+
require 'sqreen/event'
|
5
|
+
|
6
|
+
module Sqreen
|
7
|
+
# Attack
|
8
|
+
# When creating a new attack, it gets automatically pushed to the event's
|
9
|
+
# queue.
|
10
|
+
class Attack < Event
|
11
|
+
def self.record(payload)
|
12
|
+
attack = Attack.new(payload)
|
13
|
+
attack.enqueue
|
14
|
+
end
|
15
|
+
|
16
|
+
def infos
|
17
|
+
payload['infos']
|
18
|
+
end
|
19
|
+
|
20
|
+
def rulespack_id
|
21
|
+
return nil unless payload['rule']
|
22
|
+
payload['rule']['rulespack_id']
|
23
|
+
end
|
24
|
+
|
25
|
+
def type
|
26
|
+
return nil unless payload['rule']
|
27
|
+
payload['rule']['name']
|
28
|
+
end
|
29
|
+
|
30
|
+
def time
|
31
|
+
return nil unless payload['local']
|
32
|
+
payload['local']['time']
|
33
|
+
end
|
34
|
+
|
35
|
+
def backtrace
|
36
|
+
return nil unless payload['context']
|
37
|
+
payload['context']['backtrace']
|
38
|
+
end
|
39
|
+
|
40
|
+
def enqueue
|
41
|
+
Sqreen.queue.push(self)
|
42
|
+
end
|
43
|
+
|
44
|
+
def to_hash
|
45
|
+
res = {}
|
46
|
+
rule_p = payload['rule']
|
47
|
+
request_p = payload['request']
|
48
|
+
res[:rule_name] = rule_p['name'] if rule_p && rule_p['name']
|
49
|
+
res[:rulespack_id] = rule_p['rulespack_id'] if rule_p && rule_p['rulespack_id']
|
50
|
+
res[:test] = rule_p['test'] if rule_p && rule_p['test']
|
51
|
+
res[:infos] = payload['infos'] if payload['infos']
|
52
|
+
res[:time] = time if time
|
53
|
+
res[:client_ip] = request_p[:addr] if request_p && request_p[:addr]
|
54
|
+
res[:request] = request_p if request_p
|
55
|
+
res[:params] = payload['params'] if payload['params']
|
56
|
+
res[:context] = payload['context'] if payload['context']
|
57
|
+
res[:headers] = payload['headers'] if payload['headers']
|
58
|
+
res
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|