sqreen 1.18.2-java → 1.19.0-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (184) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +35 -0
  3. data/LICENSE +3 -0
  4. data/lib/sqreen.rb +2 -0
  5. data/lib/sqreen/actions.rb +13 -337
  6. data/lib/sqreen/actions/actions_index.rb +16 -0
  7. data/lib/sqreen/actions/base.rb +104 -0
  8. data/lib/sqreen/actions/block_ip.rb +34 -0
  9. data/lib/sqreen/actions/block_user.rb +46 -0
  10. data/lib/sqreen/actions/ip_range_indexed_action_class.rb +16 -0
  11. data/lib/sqreen/actions/ip_ranges_index.rb +57 -0
  12. data/lib/sqreen/actions/redirect_ip.rb +42 -0
  13. data/lib/sqreen/actions/redirect_user.rb +47 -0
  14. data/lib/sqreen/actions/repository.rb +43 -0
  15. data/lib/sqreen/actions/unknown_action_type.rb +20 -0
  16. data/lib/sqreen/actions/user_action_class.rb +16 -0
  17. data/lib/sqreen/actions/users_index.rb +35 -0
  18. data/lib/sqreen/agent.rb +6 -2
  19. data/lib/sqreen/attack_blocked.rb +19 -0
  20. data/lib/sqreen/backport.rb +2 -0
  21. data/lib/sqreen/backport/clock_gettime.rb +74 -0
  22. data/lib/sqreen/backport/original_name.rb +2 -0
  23. data/lib/sqreen/binding_accessor.rb +11 -102
  24. data/lib/sqreen/binding_accessor/path_elem.rb +10 -0
  25. data/lib/sqreen/binding_accessor/transforms.rb +114 -0
  26. data/lib/sqreen/call_countable.rb +2 -0
  27. data/lib/sqreen/capped_queue.rb +4 -0
  28. data/lib/sqreen/{callbacks.rb → cb.rb} +3 -53
  29. data/lib/sqreen/{callback_tree.rb → cb_tree.rb} +4 -2
  30. data/lib/sqreen/condition_evaluator.rb +24 -5
  31. data/lib/sqreen/conditionable.rb +2 -0
  32. data/lib/sqreen/configuration.rb +19 -0
  33. data/lib/sqreen/context.rb +2 -0
  34. data/lib/sqreen/default_cb.rb +22 -0
  35. data/lib/sqreen/deferred_logger.rb +65 -0
  36. data/lib/sqreen/deliveries.rb +12 -0
  37. data/lib/sqreen/deliveries/batch.rb +9 -1
  38. data/lib/sqreen/deliveries/simple.rb +7 -0
  39. data/lib/sqreen/dependency.rb +3 -1
  40. data/lib/sqreen/dependency/detector.rb +22 -14
  41. data/lib/sqreen/dependency/libsqreen.rb +32 -0
  42. data/lib/sqreen/dependency/new_relic.rb +2 -0
  43. data/lib/sqreen/dependency/rack.rb +10 -5
  44. data/lib/sqreen/dependency/rails.rb +8 -0
  45. data/lib/sqreen/dependency/sentry.rb +2 -0
  46. data/lib/sqreen/dependency/sinatra.rb +58 -14
  47. data/lib/sqreen/encoding_sanitizer.rb +2 -0
  48. data/lib/sqreen/error_handling_middleware.rb +32 -0
  49. data/lib/sqreen/event.rb +4 -0
  50. data/lib/sqreen/events/attack.rb +4 -0
  51. data/lib/sqreen/events/remote_exception.rb +2 -0
  52. data/lib/sqreen/events/request_record.rb +13 -56
  53. data/lib/sqreen/exception.rb +11 -40
  54. data/lib/sqreen/formatter_with_tid.rb +47 -0
  55. data/lib/sqreen/framework_cb.rb +30 -0
  56. data/lib/sqreen/frameworks.rb +9 -0
  57. data/lib/sqreen/frameworks/generic.rb +22 -2
  58. data/lib/sqreen/frameworks/rails.rb +3 -0
  59. data/lib/sqreen/frameworks/rails3.rb +2 -0
  60. data/lib/sqreen/frameworks/request_recorder.rb +5 -0
  61. data/lib/sqreen/frameworks/sinatra.rb +4 -0
  62. data/lib/sqreen/frameworks/sqreen_test.rb +4 -0
  63. data/lib/sqreen/graft.rb +12 -0
  64. data/lib/sqreen/graft/call.rb +150 -0
  65. data/lib/sqreen/{dependency → graft}/callback.rb +12 -4
  66. data/lib/sqreen/graft/hook.rb +316 -0
  67. data/lib/sqreen/{dependency → graft}/hook_point.rb +152 -33
  68. data/lib/sqreen/graft/hook_point_error.rb +10 -0
  69. data/lib/sqreen/invalid_signature_exception.rb +10 -0
  70. data/lib/sqreen/js.rb +11 -0
  71. data/lib/sqreen/js/call_context.rb +12 -0
  72. data/lib/sqreen/js/context_pool.rb +62 -0
  73. data/lib/sqreen/js/exec_js_runnable.rb +22 -0
  74. data/lib/sqreen/js/execjs_adapter.rb +8 -47
  75. data/lib/sqreen/js/executable_js.rb +14 -0
  76. data/lib/sqreen/js/js_service.rb +4 -22
  77. data/lib/sqreen/js/js_service_adapter.rb +20 -0
  78. data/lib/sqreen/js/mini_racer_adapter.rb +8 -180
  79. data/lib/sqreen/js/mini_racer_executable_js.rb +144 -0
  80. data/lib/sqreen/js/thread_local_exec_js_runnable.rb +49 -0
  81. data/lib/{sqreen-alt.rb → sqreen/legacy.rb} +5 -1
  82. data/lib/sqreen/{instrumentation.rb → legacy/instrumentation.rb} +44 -15
  83. data/lib/sqreen/log.rb +10 -188
  84. data/lib/sqreen/log/loggable.rb +28 -0
  85. data/lib/sqreen/logger.rb +85 -0
  86. data/lib/sqreen/metrics.rb +2 -0
  87. data/lib/sqreen/metrics/average.rb +2 -0
  88. data/lib/sqreen/metrics/base.rb +2 -0
  89. data/lib/sqreen/metrics/binning.rb +2 -0
  90. data/lib/sqreen/metrics/collect.rb +2 -0
  91. data/lib/sqreen/metrics/sum.rb +2 -0
  92. data/lib/sqreen/metrics_store.rb +5 -11
  93. data/lib/sqreen/metrics_store/already_registered_metric.rb +13 -0
  94. data/lib/sqreen/metrics_store/unknown_metric.rb +13 -0
  95. data/lib/sqreen/metrics_store/unregistered_metric.rb +13 -0
  96. data/lib/sqreen/middleware.rb +2 -34
  97. data/lib/sqreen/mono_time.rb +4 -0
  98. data/lib/sqreen/node.rb +46 -0
  99. data/lib/sqreen/not_implemented_yet.rb +10 -0
  100. data/lib/sqreen/null_logger.rb +26 -0
  101. data/lib/sqreen/payload_creator.rb +4 -19
  102. data/lib/sqreen/payload_creator/header_section.rb +30 -0
  103. data/lib/sqreen/performance_notifications.rb +2 -0
  104. data/lib/sqreen/performance_notifications/binned_metrics.rb +2 -0
  105. data/lib/sqreen/performance_notifications/log.rb +2 -0
  106. data/lib/sqreen/performance_notifications/log_performance.rb +2 -0
  107. data/lib/sqreen/performance_notifications/metrics.rb +2 -0
  108. data/lib/sqreen/performance_notifications/newrelic.rb +2 -0
  109. data/lib/sqreen/prefix.rb +35 -0
  110. data/lib/sqreen/rails_middleware.rb +16 -0
  111. data/lib/sqreen/remote_command.rb +3 -8
  112. data/lib/sqreen/remote_command/failure_output.rb +16 -0
  113. data/lib/sqreen/rules.rb +34 -2
  114. data/lib/sqreen/{rule_attributes.rb → rules/attrs.rb} +2 -0
  115. data/lib/sqreen/{rules_callbacks/sdk_auth_track.rb → rules/auth_track_cb.rb} +4 -2
  116. data/lib/sqreen/{rules_callbacks/binding_accessor_matcher.rb → rules/binding_accessor_matcher_cb.rb} +6 -8
  117. data/lib/sqreen/{rules_callbacks → rules}/binding_accessor_metrics.rb +3 -1
  118. data/lib/sqreen/{rules_callbacks/blacklist_ips.rb → rules/blacklist_ips_cb.rb} +5 -2
  119. data/lib/sqreen/{rules_callbacks → rules}/count_http_codes.rb +4 -2
  120. data/lib/sqreen/{rules_callbacks/crawler_user_agent_matches.rb → rules/crawler_user_agent_matches_cb.rb} +3 -1
  121. data/lib/sqreen/{rules_callbacks/crawler_user_agent_matches_metrics.rb → rules/crawler_user_agent_matches_metrics_cb.rb} +3 -1
  122. data/lib/sqreen/{rules_callbacks/custom_error.rb → rules/custom_error_cb.rb} +3 -1
  123. data/lib/sqreen/{rules_callbacks/devise_auth_track.rb → rules/devise_auth_track_cb.rb} +4 -2
  124. data/lib/sqreen/{rules_callbacks/devise_signup_track.rb → rules/devise_signup_track_cb.rb} +4 -2
  125. data/lib/sqreen/{rules_callbacks/execjs.rb → rules/execjs_cb.rb} +51 -50
  126. data/lib/sqreen/{rules_callbacks/headers_insert.rb → rules/headers_insert_cb.rb} +8 -1
  127. data/lib/sqreen/{rules_callbacks → rules}/matcher_rule.rb +4 -2
  128. data/lib/sqreen/{rules_callbacks/not_found.rb → rules/not_found_cb.rb} +7 -2
  129. data/lib/sqreen/{rules_callbacks/rails_parameters.rb → rules/rails_parameters_cb.rb} +3 -1
  130. data/lib/sqreen/{rules_callbacks → rules}/record_request_context.rb +3 -1
  131. data/lib/sqreen/{rules_callbacks/regexp_rule.rb → rules/regexp_rule_cb.rb} +3 -1
  132. data/lib/sqreen/{rule_callback.rb → rules/rule_cb.rb} +4 -2
  133. data/lib/sqreen/{rules_callbacks → rules}/run_req_start_actions.rb +7 -3
  134. data/lib/sqreen/{rules_callbacks → rules}/run_user_actions.rb +4 -2
  135. data/lib/sqreen/{rules_callbacks/shell_env.rb → rules/shell_env_cb.rb} +3 -1
  136. data/lib/sqreen/{rules_callbacks/sdk_signup_track.rb → rules/signup_track_cb.rb} +4 -2
  137. data/lib/sqreen/rules/update_request_context.rb +22 -0
  138. data/lib/sqreen/{rules_callbacks/url_matches.rb → rules/url_matches_cb.rb} +3 -1
  139. data/lib/sqreen/{rules_callbacks/user_agent_matches.rb → rules/user_agent_matches_cb.rb} +3 -1
  140. data/lib/sqreen/{rules_callbacks/waf.rb → rules/waf_cb.rb} +41 -21
  141. data/lib/sqreen/{rules_callbacks/reflected_xss.rb → rules/xss_cb.rb} +12 -7
  142. data/lib/sqreen/run_when_called_cb.rb +23 -0
  143. data/lib/sqreen/runner.rb +25 -7
  144. data/lib/sqreen/runtime_infos.rb +4 -9
  145. data/lib/sqreen/safe_json.rb +2 -0
  146. data/lib/sqreen/sdk.rb +4 -0
  147. data/lib/sqreen/sensitive_data_redactor.rb +113 -0
  148. data/lib/sqreen/serializer.rb +2 -0
  149. data/lib/sqreen/session.rb +2 -0
  150. data/lib/sqreen/shared_storage.rb +2 -0
  151. data/lib/sqreen/shared_storage23.rb +2 -0
  152. data/lib/sqreen/shrink_wrap.rb +16 -0
  153. data/lib/sqreen/signature_verifier.rb +22 -0
  154. data/lib/sqreen/sinatra_middleware.rb +16 -0
  155. data/lib/sqreen/{rules_signature.rb → sqreen_signed_verifier.rb} +7 -17
  156. data/lib/sqreen/token_invalid_exception.rb +10 -0
  157. data/lib/sqreen/token_not_found_exception.rb +11 -0
  158. data/lib/sqreen/trie.rb +5 -64
  159. data/lib/sqreen/unauthorized.rb +10 -0
  160. data/lib/sqreen/util.rb +7 -0
  161. data/lib/sqreen/util/capped_array.rb +35 -0
  162. data/lib/sqreen/util/capped_hash.rb +41 -0
  163. data/lib/sqreen/util/capped_string.rb +26 -0
  164. data/lib/sqreen/util/capper.rb +67 -0
  165. data/lib/sqreen/version.rb +3 -1
  166. data/lib/sqreen/waf_error.rb +20 -0
  167. data/lib/sqreen/weave.rb +12 -0
  168. data/lib/sqreen/weave/hardcoded.rb +19 -0
  169. data/lib/sqreen/weave/instrumentor.rb +48 -0
  170. data/lib/sqreen/weave/legacy.rb +12 -0
  171. data/lib/sqreen/weave/legacy/instrumentation.rb +406 -0
  172. data/lib/sqreen/web_server.rb +2 -0
  173. data/lib/sqreen/web_server/generic.rb +2 -0
  174. data/lib/sqreen/web_server/passenger.rb +2 -0
  175. data/lib/sqreen/web_server/puma.rb +2 -0
  176. data/lib/sqreen/web_server/rainbows.rb +2 -0
  177. data/lib/sqreen/web_server/thin.rb +2 -0
  178. data/lib/sqreen/web_server/unicorn.rb +2 -0
  179. data/lib/sqreen/web_server/webrick.rb +2 -0
  180. data/lib/sqreen/worker.rb +2 -0
  181. metadata +105 -39
  182. data/lib/sqreen/dependency/hook.rb +0 -102
  183. data/lib/sqreen/rules_callbacks.rb +0 -35
  184. data/lib/sqreen/rules_callbacks/inspect_rule.rb +0 -25
@@ -0,0 +1,104 @@
1
+ # typed: false
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ # TODO: remove class vars
7
+
8
+ require 'sqreen/sdk'
9
+ require 'sqreen/exception'
10
+
11
+ module Sqreen
12
+ # Implements actions (behavior taken in response to agent signals)
13
+ module Actions
14
+ # Base class for actions
15
+ # subclasses must also implement some methods in their singleton classes
16
+ # (actions_matching, index and clear)
17
+ class Base
18
+ attr_reader :id, :expiry, :send_response
19
+
20
+ def initialize(id, opts)
21
+ @id = id
22
+ duration = opts[:duration]
23
+ @expiry = Time.new + duration unless duration.nil?
24
+ @send_response = if opts[:send_response].nil?
25
+ true
26
+ else
27
+ opts[:send_response] ? true : false
28
+ end
29
+ end
30
+
31
+ # See Sqreen::CB for return values
32
+ def run(*args)
33
+ return if expiry && Time.new > expiry
34
+ ret = do_run(*args)
35
+ unless ret.nil? || !@send_response
36
+ Sqreen.internal_track(event_name,
37
+ 'properties' => {
38
+ 'output' => event_properties(*args),
39
+ 'action_id' => id,
40
+ })
41
+ end
42
+ ret
43
+ end
44
+
45
+ protected
46
+
47
+ def do_run(*_args)
48
+ raise ::Sqreen::NotImplementedYet, "do_run not implemented in #{self.class}"
49
+ # implement in subclasses
50
+ end
51
+
52
+ def event_properties(*_run_args)
53
+ raise ::Sqreen::NotImplementedYet, "event_properties not implemented in #{self.class}"
54
+ # implement in subclasses
55
+ end
56
+
57
+ private
58
+
59
+ def event_name
60
+ "sq.action.#{self.class.type_name}"
61
+ end
62
+
63
+ @@subclasses = {} # rubocop:disable Style/ClassVars
64
+ class << self
65
+ private :new
66
+
67
+ attr_reader :type_name
68
+
69
+ def get_type_class(name)
70
+ subclasses[name]
71
+ end
72
+
73
+ def known_subclasses
74
+ subclasses.values
75
+ end
76
+
77
+ def known_types
78
+ subclasses.keys
79
+ end
80
+
81
+ def new_index
82
+ raise 'implement in singletons of subclasses'
83
+ end
84
+
85
+ def inherited(subclass)
86
+ class << subclass
87
+ public :new
88
+ end
89
+ end
90
+
91
+ protected
92
+
93
+ def subclasses
94
+ @@subclasses
95
+ end
96
+
97
+ def type_name=(name)
98
+ @type_name = name
99
+ subclasses[name] = self
100
+ end
101
+ end
102
+ end
103
+ end
104
+ end
@@ -0,0 +1,34 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/exception'
7
+ require 'sqreen/actions/base'
8
+ require 'sqreen/actions/ip_range_indexed_action_class'
9
+
10
+ module Sqreen
11
+ module Actions
12
+ # Block a list of IP address ranges. Standard "raise" behavior.
13
+ class BlockIp < Base
14
+ extend IpRangeIndexedActionClass
15
+
16
+ self.type_name = 'block_ip'
17
+
18
+ def initialize(id, opts, _params = {})
19
+ # no need to store the ranges for this action, the index filter the class
20
+ super(id, opts)
21
+ end
22
+
23
+ def do_run(client_ip)
24
+ e = Sqreen::AttackBlocked.new("Blocked client's IP #{client_ip} " \
25
+ "(action: #{id}). No action is required")
26
+ { :status => :raise, :exception => e, :skip_rem_cbs => true }
27
+ end
28
+
29
+ def event_properties(client_ip)
30
+ { 'ip_address' => client_ip }
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,46 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/log'
7
+ require 'sqreen/exception'
8
+ require 'sqreen/actions/base'
9
+ require 'sqreen/actions/user_action_class'
10
+
11
+ module Sqreen
12
+ module Actions
13
+ # Blocks a user at the point Sqreen::identify()
14
+ # or Sqreen::auth_track() are called
15
+ class BlockUser < Base
16
+ extend UserActionClass
17
+
18
+ self.type_name = 'block_user'
19
+
20
+ def initialize(id, opts, _params = {})
21
+ super(id, opts)
22
+ end
23
+
24
+ def do_run(identity_params)
25
+ Sqreen.log.info(
26
+ "Will raise due to user being blocked by action #{id}. " \
27
+ "Blocked user identity: #{identity_params}"
28
+ )
29
+
30
+ e = Sqreen::AttackBlocked.new(
31
+ "Blocked user with identity #{identity_params} " \
32
+ 'due to automatic security response. No action is required'
33
+ )
34
+
35
+ {
36
+ :status => :raise,
37
+ :exception => e,
38
+ }
39
+ end
40
+
41
+ def event_properties(identity_params)
42
+ { 'user' => identity_params }
43
+ end
44
+ end
45
+ end
46
+ end
@@ -0,0 +1,16 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/actions/ip_ranges_index'
7
+
8
+ module Sqreen
9
+ module Actions
10
+ module IpRangeIndexedActionClass
11
+ def new_index
12
+ IpRangesIndex.new
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,57 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'ipaddr'
7
+ require 'sqreen/actions/actions_index'
8
+ require 'sqreen/trie'
9
+ require 'sqreen/prefix'
10
+
11
+ module Sqreen
12
+ module Actions
13
+ class IpRangesIndex < ActionsIndex
14
+ def initialize
15
+ @trie_v4 = Sqreen::Trie.new
16
+ @trie_v6 = Sqreen::Trie.new(nil, nil, Socket::AF_INET6)
17
+ end
18
+
19
+ def index(params, action)
20
+ ranges = parse_ip_ranges params
21
+
22
+ ranges.each do |r|
23
+ add_prefix r, action
24
+ end
25
+ end
26
+
27
+ def actions_matching(client_ip)
28
+ parsed_ip = IPAddr.new(client_ip.gsub(/%[^%\/]+/, ''))
29
+ trie = parsed_ip.family == Socket::AF_INET6 ? @trie_v6 : @trie_v4
30
+ return [] unless trie
31
+ found = trie.search_matching(parsed_ip.to_i, parsed_ip.family)
32
+ return [] unless found.size > 0
33
+
34
+ Sqreen.log.debug("Client ip #{client_ip} matches #{found.inspect}")
35
+ found.map(&:data)
36
+ end
37
+
38
+ private
39
+
40
+ # returns array of prefixes in string form
41
+ def parse_ip_ranges(params)
42
+ ranges = params['ip_cidr']
43
+ unless ranges && ranges.is_a?(Array) && !ranges.empty?
44
+ raise 'no non-empty ip_cidr array present'
45
+ end
46
+
47
+ ranges
48
+ end
49
+
50
+ def add_prefix(prefix_str, data)
51
+ prefix = Sqreen::Prefix.from_str(prefix_str, data)
52
+ trie = prefix.family == Socket::AF_INET6 ? @trie_v6 : @trie_v4
53
+ trie.insert prefix
54
+ end
55
+ end
56
+ end
57
+ end
@@ -0,0 +1,42 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/log'
7
+ require 'sqreen/exception'
8
+ require 'sqreen/actions/base'
9
+
10
+ module Sqreen
11
+ module Actions
12
+ # Block a list of IP address ranges by forcefully redirecting the user
13
+ # to a specific URL.
14
+ class RedirectIp < Base
15
+ extend IpRangeIndexedActionClass
16
+
17
+ self.type_name = 'redirect_ip'
18
+
19
+ attr_reader :redirect_url
20
+
21
+ def initialize(id, opts, params = {})
22
+ super(id, opts)
23
+ @redirect_url = params['url']
24
+ raise "no url provided for action #{id}" unless @redirect_url
25
+ end
26
+
27
+ def do_run(client_ip)
28
+ Sqreen.log.info "Will request redirect for client with IP #{client_ip} " \
29
+ "(action: #{id})."
30
+ {
31
+ :status => :skip,
32
+ :new_return_value => [303, { 'Location' => @redirect_url }, ['']],
33
+ :skip_rem_cbs => true,
34
+ }
35
+ end
36
+
37
+ def event_properties(client_ip)
38
+ { 'ip_address' => client_ip, 'url' => @redirect_url }
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,47 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/log'
7
+ require 'sqreen/exception'
8
+ require 'sqreen/actions/base'
9
+ require 'sqreen/actions/user_action_class'
10
+
11
+ module Sqreen
12
+ module Actions
13
+ # Redirects a user at the point Sqreen::identify()
14
+ # or Sqreen::auth_track() are called
15
+ class RedirectUser < Base
16
+ extend UserActionClass
17
+
18
+ self.type_name = 'redirect_user'
19
+
20
+ def initialize(id, opts, params = {})
21
+ super(id, opts)
22
+ @redirect_url = params['url']
23
+ raise "no url provided for action #{id}" unless @redirect_url
24
+ end
25
+
26
+ def do_run(identity_params)
27
+ Sqreen.log.info 'Will request redirect for user with identity ' \
28
+ "#{identity_params} (action: #{id})."
29
+
30
+ e = Sqreen::AttackBlocked.new(
31
+ "Redirected user with identity #{identity_params} " \
32
+ 'due to automatic security response. No action is required'
33
+ )
34
+ e.redirect_url = @redirect_url
35
+
36
+ {
37
+ :status => :raise,
38
+ :exception => e,
39
+ }
40
+ end
41
+
42
+ def event_properties(identity_params)
43
+ { 'user' => identity_params }
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,43 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ module Sqreen
7
+ module Actions
8
+ # Where the actions are stored
9
+ # The current ones are stored in Repository.current
10
+ class Repository
11
+ def initialize
12
+ @indexes = Hash[Base.known_subclasses.map do |clazz|
13
+ [clazz.type_name, clazz.new_index]
14
+ end]
15
+ end
16
+
17
+ def add(params, action)
18
+ @indexes[action.class.type_name].index(params || {}, action)
19
+ end
20
+
21
+ # type is either a class or a type name
22
+ def get(type, key)
23
+ type = type.type_name if type.class == Class
24
+ @indexes[type].actions_matching key
25
+ end
26
+
27
+ singleton_class.class_eval do
28
+ attr_reader :current
29
+ def current=(new_inst)
30
+ raise 'nil is unacceptable' if new_inst.nil?
31
+ @current = new_inst
32
+ end
33
+
34
+ def clear
35
+ self.current = Repository.new
36
+ end
37
+ end
38
+
39
+ # initialize current to empty repository
40
+ clear
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,20 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/exception'
7
+
8
+ module Sqreen
9
+ # Implements actions (behavior taken in response to agent signals)
10
+ module Actions
11
+ # Exception for when an unknown action type is gotten from the server
12
+ class UnknownActionType < ::Sqreen::Exception
13
+ attr_reader :action_type
14
+ def initialize(action_type)
15
+ super("no such action type: #{action_type}. Must be one of #{Base.known_types}")
16
+ @action_type = action_type
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,16 @@
1
+ # typed: true
2
+
3
+ # Copyright (c) 2015 Sqreen. All Rights Reserved.
4
+ # Please refer to our terms for more information: https://www.sqreen.com/terms.html
5
+
6
+ require 'sqreen/actions/users_index'
7
+
8
+ module Sqreen
9
+ module Actions
10
+ module UserActionClass
11
+ def new_index
12
+ UsersIndex.new
13
+ end
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,35 @@
1
+ # typed: true
2
+ require 'sqreen/actions/actions_index'
3
+
4
+ module Sqreen
5
+ module Actions
6
+ class UsersIndex < ActionsIndex
7
+ def actions_matching(identity_params)
8
+ return [] unless @idx
9
+ key = stringify_keys(identity_params)
10
+ actions = @idx[key]
11
+ actions || []
12
+ end
13
+
14
+ def index(params, action)
15
+ @idx ||= {}
16
+ users = params['users']
17
+ raise ::Sqreen::Exception, 'nil "users" param for block_user action' if users.nil?
18
+ raise ::Sqreen::Exception, '"users" param must be an array' unless users.is_a? Array
19
+
20
+ users.each do |u|
21
+ @idx[u] ||= []
22
+ @idx[u] << action
23
+ end
24
+ end
25
+
26
+ private
27
+
28
+ def stringify_keys(hash)
29
+ Hash[
30
+ hash.map { |k, v| [k.to_s, v] }
31
+ ]
32
+ end
33
+ end
34
+ end
35
+ end