securenative 0.1.23 → 0.1.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Gemfile.lock +3 -5
- data/README.md +36 -36
- data/lib/securenative/api_manager.rb +41 -0
- data/lib/securenative/config/configuration_builder.rb +29 -0
- data/lib/securenative/config/configuration_manager.rb +58 -0
- data/lib/securenative/config/securenative_options.rb +25 -0
- data/lib/securenative/context/hanami_context.rb +44 -0
- data/lib/securenative/context/rails_context.rb +46 -0
- data/lib/securenative/context/securenative_context.rb +69 -0
- data/lib/securenative/context/sinatra_context.rb +44 -0
- data/lib/securenative/enums/api_route.rb +8 -0
- data/lib/securenative/enums/event_types.rb +25 -0
- data/lib/securenative/enums/failover_strategy.rb +8 -0
- data/lib/securenative/enums/risk_level.rb +9 -0
- data/lib/securenative/errors/securenative_config_error.rb +6 -0
- data/lib/securenative/errors/securenative_http_error.rb +6 -0
- data/lib/securenative/errors/securenative_invalid_options_error.rb +6 -0
- data/lib/securenative/errors/securenative_invalid_uri_error.rb +6 -0
- data/lib/securenative/errors/securenative_parse_error.rb +6 -0
- data/lib/securenative/errors/securenative_sdk_Illegal_state_error.rb +6 -0
- data/lib/securenative/errors/securenative_sdk_error.rb +6 -0
- data/lib/securenative/event_manager.rb +159 -0
- data/lib/securenative/http/secure_native_http_response.rb +14 -0
- data/lib/securenative/http/securenative_http_client.rb +52 -0
- data/lib/securenative/models/client_token.rb +14 -0
- data/lib/securenative/models/device.rb +12 -0
- data/lib/securenative/models/event_options.rb +39 -0
- data/lib/securenative/models/request_context.rb +20 -0
- data/lib/securenative/models/request_options.rb +14 -0
- data/lib/securenative/models/sdk_event.rb +51 -0
- data/lib/securenative/models/user_traits.rb +15 -0
- data/lib/securenative/models/verify_result.rb +18 -0
- data/lib/securenative/sdk.rb +85 -0
- data/lib/securenative/utils/date_utils.rb +11 -0
- data/lib/securenative/utils/encryption_utils.rb +51 -0
- data/lib/securenative/utils/ip_utils.rb +25 -0
- data/lib/securenative/utils/request_utils.rb +71 -0
- data/lib/securenative/utils/secure_native_logger.rb +46 -0
- data/lib/securenative/utils/signature_utils.rb +18 -0
- data/lib/securenative/utils/utils.rb +11 -0
- data/lib/securenative/utils/version_utils.rb +13 -0
- data/securenative.gemspec +16 -14
- metadata +40 -40
- data/lib/api_manager.rb +0 -39
- data/lib/config/configuration_builder.rb +0 -27
- data/lib/config/configuration_manager.rb +0 -56
- data/lib/config/securenative_options.rb +0 -23
- data/lib/context/hanami_context.rb +0 -42
- data/lib/context/rails_context.rb +0 -44
- data/lib/context/securenative_context.rb +0 -67
- data/lib/context/sinatra_context.rb +0 -42
- data/lib/enums/api_route.rb +0 -6
- data/lib/enums/event_types.rb +0 -23
- data/lib/enums/failover_strategy.rb +0 -6
- data/lib/enums/risk_level.rb +0 -7
- data/lib/errors/securenative_config_error.rb +0 -4
- data/lib/errors/securenative_http_error.rb +0 -4
- data/lib/errors/securenative_invalid_options_error.rb +0 -4
- data/lib/errors/securenative_invalid_uri_error.rb +0 -4
- data/lib/errors/securenative_parse_error.rb +0 -4
- data/lib/errors/securenative_sdk_Illegal_state_error.rb +0 -4
- data/lib/errors/securenative_sdk_error.rb +0 -4
- data/lib/event_manager.rb +0 -157
- data/lib/http/secure_native_http_response.rb +0 -12
- data/lib/http/securenative_http_client.rb +0 -50
- data/lib/models/client_token.rb +0 -12
- data/lib/models/device.rb +0 -10
- data/lib/models/event_options.rb +0 -37
- data/lib/models/request_context.rb +0 -18
- data/lib/models/request_options.rb +0 -12
- data/lib/models/sdk_event.rb +0 -49
- data/lib/models/user_traits.rb +0 -13
- data/lib/models/verify_result.rb +0 -16
- data/lib/securenative.rb +0 -83
- data/lib/utils/date_utils.rb +0 -9
- data/lib/utils/encryption_utils.rb +0 -49
- data/lib/utils/ip_utils.rb +0 -23
- data/lib/utils/request_utils.rb +0 -69
- data/lib/utils/secure_native_logger.rb +0 -44
- data/lib/utils/signature_utils.rb +0 -16
- data/lib/utils/utils.rb +0 -9
- data/lib/utils/version_utils.rb +0 -11
@@ -1,42 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
class SinatraContext
|
4
|
-
SECURENATIVE_COOKIE = '_sn'
|
5
|
-
|
6
|
-
def self.get_client_token(request)
|
7
|
-
begin
|
8
|
-
request.env[SECURENATIVE_COOKIE]
|
9
|
-
rescue StandardError
|
10
|
-
begin
|
11
|
-
request.cookies[SECURENATIVE_COOKIE]
|
12
|
-
rescue StandardError
|
13
|
-
nil
|
14
|
-
end
|
15
|
-
end
|
16
|
-
end
|
17
|
-
|
18
|
-
def self.get_url(request)
|
19
|
-
begin
|
20
|
-
request.env['REQUEST_URI']
|
21
|
-
rescue StandardError
|
22
|
-
nil
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
def self.get_method(request)
|
27
|
-
begin
|
28
|
-
request.env['REQUEST_METHOD']
|
29
|
-
rescue StandardError
|
30
|
-
nil
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
def self.get_headers(request)
|
35
|
-
begin
|
36
|
-
# Note: At the moment we're filtering out everything but user-agent since ruby's payload is way too big
|
37
|
-
{ 'user-agent' => request.env['HTTP_USER_AGENT'] }
|
38
|
-
rescue StandardError
|
39
|
-
nil
|
40
|
-
end
|
41
|
-
end
|
42
|
-
end
|
data/lib/enums/api_route.rb
DELETED
data/lib/enums/event_types.rb
DELETED
@@ -1,23 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module EventTypes
|
4
|
-
LOG_IN = 'sn.user.login'
|
5
|
-
LOG_IN_CHALLENGE = 'sn.user.login.challenge'
|
6
|
-
LOG_IN_FAILURE = 'sn.user.login.failure'
|
7
|
-
LOG_OUT = 'sn.user.logout'
|
8
|
-
SIGN_UP = 'sn.user.signup'
|
9
|
-
AUTH_CHALLENGE = 'sn.user.auth.challenge'
|
10
|
-
AUTH_CHALLENGE_SUCCESS = 'sn.user.auth.challenge.success'
|
11
|
-
AUTH_CHALLENGE_FAILURE = 'sn.user.auth.challenge.failure'
|
12
|
-
TWO_FACTOR_DISABLE = 'sn.user.2fa.disable'
|
13
|
-
EMAIL_UPDATE = 'sn.user.email.update'
|
14
|
-
PASSWORD_REST = 'sn.user.password.reset'
|
15
|
-
PASSWORD_REST_SUCCESS = 'sn.user.password.reset.success'
|
16
|
-
PASSWORD_UPDATE = 'sn.user.password.update'
|
17
|
-
PASSWORD_REST_FAILURE = 'sn.user.password.reset.failure'
|
18
|
-
USER_INVITE = 'sn.user.invite'
|
19
|
-
ROLE_UPDATE = 'sn.user.role.update'
|
20
|
-
PROFILE_UPDATE = 'sn.user.profile.update'
|
21
|
-
PAGE_VIEW = 'sn.user.page.view'
|
22
|
-
VERIFY = 'sn.verify'
|
23
|
-
end
|
data/lib/enums/risk_level.rb
DELETED
data/lib/event_manager.rb
DELETED
@@ -1,157 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require 'utils/secure_native_logger'
|
4
|
-
require 'config/securenative_options'
|
5
|
-
require 'http/securenative_http_client'
|
6
|
-
require 'errors/securenative_sdk_error'
|
7
|
-
require 'errors/securenative_http_error'
|
8
|
-
|
9
|
-
class QueueItem
|
10
|
-
attr_reader :url, :body, :retry_sending
|
11
|
-
attr_writer :url, :body, :retry_sending
|
12
|
-
|
13
|
-
def initialize(url, body, retry_sending)
|
14
|
-
@url = url
|
15
|
-
@body = body
|
16
|
-
@retry = retry_sending
|
17
|
-
end
|
18
|
-
end
|
19
|
-
|
20
|
-
class EventManager
|
21
|
-
def initialize(options = SecureNativeOptions.new, http_client = nil)
|
22
|
-
if options.api_key.nil?
|
23
|
-
raise SecureNativeSDKError, 'API key cannot be None, please get your API key from SecureNative console.'
|
24
|
-
end
|
25
|
-
|
26
|
-
@http_client = if http_client.nil?
|
27
|
-
SecureNativeHttpClient.new(options)
|
28
|
-
else
|
29
|
-
http_client
|
30
|
-
end
|
31
|
-
|
32
|
-
@queue = []
|
33
|
-
@semaphore = Mutex.new
|
34
|
-
@interval = options.interval
|
35
|
-
@options = options
|
36
|
-
@send_enabled = false
|
37
|
-
@attempt = 0
|
38
|
-
@coefficients = [1, 1, 2, 3, 5, 8, 13]
|
39
|
-
|
40
|
-
@thread = Thread.new { run }
|
41
|
-
end
|
42
|
-
|
43
|
-
def send_async(event, resource_path)
|
44
|
-
if @options.disable
|
45
|
-
SecureNativeLogger.warning('SDK is disabled. no operation will be performed')
|
46
|
-
return
|
47
|
-
end
|
48
|
-
|
49
|
-
item = QueueItem.new(resource_path, EventManager.serialize(event).to_json, false)
|
50
|
-
@queue.append(item)
|
51
|
-
end
|
52
|
-
|
53
|
-
def flush
|
54
|
-
@queue.each do |item|
|
55
|
-
@http_client.post(item.url, item.body)
|
56
|
-
end
|
57
|
-
end
|
58
|
-
|
59
|
-
def send_sync(event, resource_path, retry_sending)
|
60
|
-
if @options.disable
|
61
|
-
SecureNativeLogger.warning('SDK is disabled. no operation will be performed')
|
62
|
-
return
|
63
|
-
end
|
64
|
-
|
65
|
-
SecureNativeLogger.debug("Attempting to send event #{event}")
|
66
|
-
res = @http_client.post(resource_path, EventManager.serialize(event).to_json)
|
67
|
-
|
68
|
-
if res.nil? || res.code != '200'
|
69
|
-
SecureNativeLogger.info("SecureNative failed to call endpoint #{resource_path} with event #{event}. adding back to queue")
|
70
|
-
item = QueueItem.new(resource_path, EventManager.serialize(event).to_json, retry_sending)
|
71
|
-
@queue.append(item)
|
72
|
-
end
|
73
|
-
|
74
|
-
res
|
75
|
-
end
|
76
|
-
|
77
|
-
def run
|
78
|
-
loop do
|
79
|
-
@semaphore.synchronize do
|
80
|
-
next unless !@queue.empty? && @send_enabled
|
81
|
-
|
82
|
-
@queue.each do |item|
|
83
|
-
begin
|
84
|
-
res = @http_client.post(item.url, item.body)
|
85
|
-
if res.code == '401'
|
86
|
-
item.retry_sending = false
|
87
|
-
elsif res.code != '200'
|
88
|
-
raise SecureNativeHttpError, res.status_code
|
89
|
-
end
|
90
|
-
SecureNativeLogger.debug("Event successfully sent; #{item.body}")
|
91
|
-
return res
|
92
|
-
rescue StandardError => e
|
93
|
-
SecureNativeLogger.error("Failed to send event; #{e}")
|
94
|
-
if item.retry_sending
|
95
|
-
@attempt = 0 if @coefficients.length == @attempt + 1
|
96
|
-
|
97
|
-
back_off = @coefficients[@attempt] * @options.interval
|
98
|
-
SecureNativeLogger.debug("Automatic back-off of #{back_off}")
|
99
|
-
@send_enabled = false
|
100
|
-
sleep back_off
|
101
|
-
@send_enabled = true
|
102
|
-
end
|
103
|
-
end
|
104
|
-
end
|
105
|
-
end
|
106
|
-
sleep @interval / 1000
|
107
|
-
end
|
108
|
-
end
|
109
|
-
|
110
|
-
def start_event_persist
|
111
|
-
SecureNativeLogger.debug('Starting automatic event persistence')
|
112
|
-
if @options.auto_send || @send_enabled
|
113
|
-
@send_enabled = true
|
114
|
-
else
|
115
|
-
SecureNativeLogger.debug('Automatic event persistence is disabled, you should persist events manually')
|
116
|
-
end
|
117
|
-
end
|
118
|
-
|
119
|
-
def stop_event_persist
|
120
|
-
if @send_enabled
|
121
|
-
SecureNativeLogger.debug('Attempting to stop automatic event persistence')
|
122
|
-
begin
|
123
|
-
flush
|
124
|
-
@thread&.stop?
|
125
|
-
SecureNativeLogger.debug('Stopped event persistence')
|
126
|
-
rescue StandardError => e
|
127
|
-
SecureNativeLogger.error("Could not stop event scheduler; #{e}")
|
128
|
-
end
|
129
|
-
end
|
130
|
-
end
|
131
|
-
|
132
|
-
def self.serialize(obj)
|
133
|
-
{
|
134
|
-
rid: obj.rid,
|
135
|
-
eventType: obj.event_type,
|
136
|
-
userId: obj.user_id,
|
137
|
-
userTraits: {
|
138
|
-
name: obj.user_traits.name,
|
139
|
-
email: obj.user_traits.email,
|
140
|
-
phone: obj.user_traits.phone,
|
141
|
-
createdAt: obj.user_traits.created_at
|
142
|
-
},
|
143
|
-
request: {
|
144
|
-
cid: obj.request.cid,
|
145
|
-
vid: obj.request.vid,
|
146
|
-
fp: obj.request.fp,
|
147
|
-
ip: obj.request.ip,
|
148
|
-
remoteIp: obj.request.remote_ip,
|
149
|
-
method: obj.request.http_method || '',
|
150
|
-
url: obj.request.url,
|
151
|
-
headers: obj.request.headers
|
152
|
-
},
|
153
|
-
timestamp: obj.timestamp,
|
154
|
-
properties: obj.properties
|
155
|
-
}
|
156
|
-
end
|
157
|
-
end
|
@@ -1,50 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require 'net/http'
|
4
|
-
require 'uri'
|
5
|
-
require 'json'
|
6
|
-
require 'utils/version_utils'
|
7
|
-
require 'utils/secure_native_logger'
|
8
|
-
|
9
|
-
class SecureNativeHttpClient
|
10
|
-
AUTHORIZATION_HEADER = 'Authorization'
|
11
|
-
VERSION_HEADER = 'SN-Version'
|
12
|
-
USER_AGENT_HEADER = 'User-Agent'
|
13
|
-
USER_AGENT_HEADER_VALUE = 'SecureNative-ruby'
|
14
|
-
CONTENT_TYPE_HEADER = 'Content-Type'
|
15
|
-
CONTENT_TYPE_HEADER_VALUE = 'application/json'
|
16
|
-
|
17
|
-
def initialize(securenative_options)
|
18
|
-
@options = securenative_options
|
19
|
-
end
|
20
|
-
|
21
|
-
def _headers
|
22
|
-
{
|
23
|
-
CONTENT_TYPE_HEADER => CONTENT_TYPE_HEADER_VALUE,
|
24
|
-
USER_AGENT_HEADER => USER_AGENT_HEADER_VALUE,
|
25
|
-
VERSION_HEADER => VersionUtils.version,
|
26
|
-
AUTHORIZATION_HEADER => @options.api_key
|
27
|
-
}
|
28
|
-
end
|
29
|
-
|
30
|
-
def post(path, body)
|
31
|
-
uri = URI.parse("#{@options.api_url}/#{path}")
|
32
|
-
headers = _headers
|
33
|
-
|
34
|
-
client = Net::HTTP.new(uri.host, uri.port)
|
35
|
-
client.use_ssl = true
|
36
|
-
client.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
37
|
-
|
38
|
-
request = Net::HTTP::Post.new(uri.request_uri, headers)
|
39
|
-
request.body = body
|
40
|
-
|
41
|
-
res = nil
|
42
|
-
begin
|
43
|
-
res = client.request(request)
|
44
|
-
rescue StandardError => e
|
45
|
-
SecureNativeLogger.error("Failed to send request; #{e}")
|
46
|
-
return res
|
47
|
-
end
|
48
|
-
res
|
49
|
-
end
|
50
|
-
end
|
data/lib/models/client_token.rb
DELETED
data/lib/models/device.rb
DELETED
data/lib/models/event_options.rb
DELETED
@@ -1,37 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require 'models/event_options'
|
4
|
-
require 'models/user_traits'
|
5
|
-
require 'errors/securenative_invalid_options_error'
|
6
|
-
|
7
|
-
class EventOptions
|
8
|
-
attr_reader :event, :user_id, :user_traits, :context, :properties, :timestamp
|
9
|
-
attr_writer :event, :user_id, :user_traits, :context, :properties, :timestamp
|
10
|
-
|
11
|
-
MAX_PROPERTIES_SIZE = 10
|
12
|
-
|
13
|
-
def initialize(event: nil, user_id: nil, user_traits: nil, user_name: nil, email: nil, phone: nil, created_at: nil, context: nil, properties: nil, timestamp: nil)
|
14
|
-
if !properties.nil? && properties.length > MAX_PROPERTIES_SIZE
|
15
|
-
raise SecureNativeInvalidOptionsError, "You can have only up to #{MAX_PROPERTIES_SIZE} custom properties"
|
16
|
-
end
|
17
|
-
|
18
|
-
if user_traits.nil?
|
19
|
-
if user_name && email && phone && created_at
|
20
|
-
user_traits = UserTraits(user_name, email, phone, created_at)
|
21
|
-
elsif user_name && email && phone
|
22
|
-
user_traits = UserTraits(user_name, email, phone)
|
23
|
-
elsif user_name && email
|
24
|
-
user_traits = UserTraits(user_name, email)
|
25
|
-
else
|
26
|
-
user_traits = UserTraits.new
|
27
|
-
end
|
28
|
-
end
|
29
|
-
|
30
|
-
@event = event
|
31
|
-
@user_id = user_id
|
32
|
-
@user_traits = user_traits
|
33
|
-
@context = context
|
34
|
-
@properties = properties
|
35
|
-
@timestamp = timestamp
|
36
|
-
end
|
37
|
-
end
|
@@ -1,18 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
class RequestContext
|
4
|
-
attr_reader :cid, :vid, :fp, :ip, :remote_ip, :headers, :url, :http_method
|
5
|
-
attr_writer :cid, :vid, :fp, :ip, :remote_ip, :headers, :url, :http_method
|
6
|
-
|
7
|
-
def initialize(cid: nil, vid: nil, fp: nil, ip: nil, remote_ip: nil, headers: nil, url: nil, http_method: nil)
|
8
|
-
@cid = cid
|
9
|
-
@vid = vid
|
10
|
-
@fp = fp
|
11
|
-
@ip = ip
|
12
|
-
@remote_ip = remote_ip
|
13
|
-
@headers = headers
|
14
|
-
@url = url
|
15
|
-
@method = http_method
|
16
|
-
end
|
17
|
-
end
|
18
|
-
|
@@ -1,12 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
class RequestOptions
|
4
|
-
attr_reader :url, :body, :retry_sending
|
5
|
-
attr_writer :url, :body, :retry_sending
|
6
|
-
|
7
|
-
def initialize(url, body, retry_sending)
|
8
|
-
@url = url
|
9
|
-
@body = body
|
10
|
-
@retry_sending = retry_sending
|
11
|
-
end
|
12
|
-
end
|