splitclient-rb 1.0.4 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGES.txt +3 -0
- data/NEWS +8 -0
- data/README.md +29 -3
- data/lib/splitclient-engine/parser/split_adapter.rb +6 -4
- data/lib/splitclient-rb.rb +4 -1
- data/lib/splitclient-rb/localhost_split_factory.rb +169 -0
- data/lib/splitclient-rb/localhost_split_factory_builder.rb +13 -0
- data/lib/splitclient-rb/split_factory.rb +245 -0
- data/lib/splitclient-rb/split_factory_builder.rb +8 -0
- data/lib/splitclient-rb/version.rb +1 -1
- data/tasks/benchmark_get_treatment.rake +1 -1
- metadata +7 -4
- data/lib/splitclient-rb/split_client.rb +0 -156
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 420c299078bd2e0eddaeb7d2a189ab7202cb1ab9
|
4
|
+
data.tar.gz: e97bec34c8db25dcc2e3ab593b6528137b0cd505
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 01782b77e052714c779981ead8dd8e5baeae674647390dc3a89d91d00d687d16a2de2f09f8d4cd44257dc3f903537a3021cc88fb56aebfda9a52120298e0782e
|
7
|
+
data.tar.gz: 08306361a858ea57450cf182b19a52ca6c734d13038786c4edb7e25b62daff81ebb903f952370bb0e56fbd52896804fe03999a3a320215f8ed6bd57804fe5a88
|
data/CHANGES.txt
CHANGED
data/NEWS
CHANGED
@@ -1,3 +1,11 @@
|
|
1
|
+
2.0.0
|
2
|
+
|
3
|
+
Instantiation of the split client is now through a factory:
|
4
|
+
|
5
|
+
factory = SplitIoClient::SplitFactory.new("rbk5je8be5qflpa047m17fe4ra", options)
|
6
|
+
client = factory.client
|
7
|
+
manager = factory.manager
|
8
|
+
|
1
9
|
1.0.4
|
2
10
|
|
3
11
|
Added AND combiner for conditions support. Added events_uri config param which is the url where the metrics post are send to.
|
data/README.md
CHANGED
@@ -47,15 +47,22 @@ require 'splitclient-rb'
|
|
47
47
|
|
48
48
|
Create a new split client instance with your API key:
|
49
49
|
```ruby
|
50
|
-
|
50
|
+
factory = SplitIoClient::SplitFactory.new("your_api_key").client
|
51
|
+
split_client = factory.client
|
51
52
|
```
|
53
|
+
|
54
|
+
For advance use cases you can also obtain a `manager` instance from the factory.
|
55
|
+
```ruby
|
56
|
+
manager = factory.manager
|
57
|
+
```
|
58
|
+
|
52
59
|
###Ruby on Rails
|
53
60
|
----
|
54
61
|
If you're using Ruby on Rails
|
55
62
|
|
56
63
|
Create an initializer file at config/initializers/splitclient.rb and then initialize the split client :
|
57
64
|
```ruby
|
58
|
-
Rails.configuration.split_client = SplitIoClient::
|
65
|
+
Rails.configuration.split_client = SplitIoClient::SplitFactory.new("your_api_key").client
|
59
66
|
```
|
60
67
|
In your controllers, access the client using
|
61
68
|
|
@@ -108,7 +115,7 @@ options = {base_uri: 'https://my.app.api/',
|
|
108
115
|
impressions_refresh_rate: 360,
|
109
116
|
logger: Logger.new('logfile.log')}
|
110
117
|
|
111
|
-
split_client = SplitIoClient::
|
118
|
+
split_client = SplitIoClient::SplitFactory.new("your_api_key", options).client
|
112
119
|
```
|
113
120
|
### Execution
|
114
121
|
---
|
@@ -124,6 +131,25 @@ if split_client.get_treatment('employee_user_01','view_main_list', {age: 35})
|
|
124
131
|
end
|
125
132
|
```
|
126
133
|
|
134
|
+
Also you can use the split manager:
|
135
|
+
|
136
|
+
```ruby
|
137
|
+
split_manager = SplitIoClient::SplitFactory.new("your_api_key", options).manager
|
138
|
+
```
|
139
|
+
|
140
|
+
With the manager you can get a list of your splits by doing:
|
141
|
+
|
142
|
+
```ruby
|
143
|
+
manager.splits
|
144
|
+
```
|
145
|
+
|
146
|
+
And you should get something like this:
|
147
|
+
|
148
|
+
```bash
|
149
|
+
=> [{:name=>"some_feature", :traffic_type_name=>nil, :killed=>false, :treatments=>nil, :change_number=>1469134003507}, {:name=>"another_feature", :traffic_type_name=>nil, :killed=>false, :treatments=>nil, :change_number=>1469134003414}, {:name=>"even_more_features", :traffic_type_name=>nil, :killed=>false, :treatments=>nil, :change_number=>1469133991063}, {:name=>"yet_another_feature", :traffic_type_name=>nil, :killed=>false, :treatments=>nil, :change_number=>1469133757521}]
|
150
|
+
```
|
151
|
+
|
152
|
+
|
127
153
|
## Development
|
128
154
|
|
129
155
|
After checking out the repo, run `bin/setup` to install dependencies. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
@@ -70,8 +70,10 @@ module SplitIoClient
|
|
70
70
|
#splits fetcher
|
71
71
|
splits_arr = []
|
72
72
|
data = get_splits(@parsed_splits.since)
|
73
|
-
data
|
74
|
-
|
73
|
+
if data
|
74
|
+
data[:splits].each do |split|
|
75
|
+
splits_arr << SplitIoClient::Split.new(split)
|
76
|
+
end
|
75
77
|
end
|
76
78
|
|
77
79
|
if @parsed_splits.is_empty?
|
@@ -126,7 +128,7 @@ module SplitIoClient
|
|
126
128
|
def call_api(path, params = {})
|
127
129
|
@api_client.get @config.base_uri + path, params do |req|
|
128
130
|
req.headers['Authorization'] = 'Bearer ' + @api_key
|
129
|
-
req.headers['SplitSDKVersion'] = SplitIoClient::
|
131
|
+
req.headers['SplitSDKVersion'] = SplitIoClient::SplitFactory.sdk_version
|
130
132
|
req.headers['SplitSDKMachineName'] = @config.machine_name
|
131
133
|
req.headers['SplitSDKMachineIP'] = @config.machine_ip
|
132
134
|
req.headers['Accept-Encoding'] = 'gzip'
|
@@ -147,7 +149,7 @@ module SplitIoClient
|
|
147
149
|
@api_client.post (@config.events_uri + path) do |req|
|
148
150
|
req.headers['Authorization'] = 'Bearer ' + @api_key
|
149
151
|
req.headers['Content-Type'] = 'application/json'
|
150
|
-
req.headers['SplitSDKVersion'] = SplitIoClient::
|
152
|
+
req.headers['SplitSDKVersion'] = SplitIoClient::SplitFactory.sdk_version
|
151
153
|
req.headers['SplitSDKMachineName'] = @config.machine_name
|
152
154
|
req.headers['SplitSDKMachineIP'] = @config.machine_ip
|
153
155
|
req.body = param.to_json
|
data/lib/splitclient-rb.rb
CHANGED
@@ -1,5 +1,8 @@
|
|
1
1
|
require 'splitclient-rb/version'
|
2
|
-
require 'splitclient-rb/
|
2
|
+
require 'splitclient-rb/split_factory'
|
3
|
+
require 'splitclient-rb/split_factory_builder'
|
4
|
+
require 'splitclient-rb/localhost_split_factory_builder'
|
5
|
+
require 'splitclient-rb/localhost_split_factory'
|
3
6
|
require 'splitclient-rb/split_config'
|
4
7
|
require 'splitclient-cache/local_store'
|
5
8
|
require 'splitclient-engine/parser/split'
|
@@ -0,0 +1,169 @@
|
|
1
|
+
require 'logger'
|
2
|
+
module SplitIoClient
|
3
|
+
|
4
|
+
#
|
5
|
+
# main class for localhost split client sdk
|
6
|
+
#
|
7
|
+
class LocalhostSplitFactory < NoMethodError
|
8
|
+
class LocalhostSplitManager < NoMethodError
|
9
|
+
#
|
10
|
+
# constant that defines the localhost mode
|
11
|
+
LOCALHOST_MODE = 'localhost'
|
12
|
+
|
13
|
+
#
|
14
|
+
# object that acts as an api adapter connector. used to get and post to api endpoints
|
15
|
+
attr_reader :adapter
|
16
|
+
|
17
|
+
#
|
18
|
+
# Creates a new split manager instance that holds the splits from a given file
|
19
|
+
#
|
20
|
+
# @param splits_file [File] the .split file that contains the splits
|
21
|
+
#
|
22
|
+
# @return [LocalhostSplitIoManager] split.io localhost manager instance
|
23
|
+
def initialize(splits_file)
|
24
|
+
@localhost_mode = true
|
25
|
+
@localhost_mode_features = []
|
26
|
+
load_localhost_mode_features(splits_file)
|
27
|
+
end
|
28
|
+
|
29
|
+
#
|
30
|
+
# method to set localhost mode features by reading the given .splits
|
31
|
+
#
|
32
|
+
# @param splits_file [File] the .split file that contains the splits
|
33
|
+
# @returns [void]
|
34
|
+
def load_localhost_mode_features(splits_file)
|
35
|
+
if File.exists?(splits_file)
|
36
|
+
line_num=0
|
37
|
+
File.open(splits_file).each do |line|
|
38
|
+
line_data = line.strip.split(" ")
|
39
|
+
@localhost_mode_features << {feature: line_data[0], treatment: line_data[1]} unless line.start_with?('#') || line.strip.empty?
|
40
|
+
end
|
41
|
+
end
|
42
|
+
@localhost_mode_features
|
43
|
+
end
|
44
|
+
|
45
|
+
#
|
46
|
+
# method to get the split list from the client
|
47
|
+
#
|
48
|
+
# @returns [object] array of splits
|
49
|
+
def splits
|
50
|
+
@localhost_mode_features
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
class LocalhostSplitClient < NoMethodError
|
55
|
+
#
|
56
|
+
# constant that defines the localhost mode
|
57
|
+
LOCALHOST_MODE = 'localhost'
|
58
|
+
|
59
|
+
#
|
60
|
+
# variables to if the sdk is being used in localhost mode and store the list of features
|
61
|
+
attr_reader :localhost_mode
|
62
|
+
attr_reader :localhost_mode_features
|
63
|
+
|
64
|
+
#
|
65
|
+
# Creates a new split client instance that reads from the given splits file
|
66
|
+
#
|
67
|
+
# @param splits_file [File] file that contains some splits
|
68
|
+
#
|
69
|
+
# @return [LocalhostSplitIoClient] split.io localhost client instance
|
70
|
+
def initialize(splits_file)
|
71
|
+
@localhost_mode = true
|
72
|
+
@localhost_mode_features = []
|
73
|
+
load_localhost_mode_features(splits_file)
|
74
|
+
end
|
75
|
+
|
76
|
+
#
|
77
|
+
# obtains the treatment for a given feature
|
78
|
+
#
|
79
|
+
# @param id [string] user id
|
80
|
+
# @param feature [string] name of the feature that is being validated
|
81
|
+
#
|
82
|
+
# @return [Treatment] treatment constant value
|
83
|
+
def get_treatment(id, feature, attributes = nil)
|
84
|
+
unless id
|
85
|
+
@config.logger.warn('id was null for feature: ' + feature)
|
86
|
+
return Treatments::CONTROL
|
87
|
+
end
|
88
|
+
|
89
|
+
unless feature
|
90
|
+
@config.logger.warn('feature was null for id: ' + id)
|
91
|
+
return Treatments::CONTROL
|
92
|
+
end
|
93
|
+
result = get_localhost_treatment(feature)
|
94
|
+
end
|
95
|
+
|
96
|
+
|
97
|
+
#
|
98
|
+
# auxiliary method to get the treatments avoding exceptions
|
99
|
+
#
|
100
|
+
# @param id [string] user id
|
101
|
+
# @param feature [string] name of the feature that is being validated
|
102
|
+
#
|
103
|
+
# @return [Treatment] tretment constant value
|
104
|
+
def get_treatment_without_exception_handling(id, feature, attributes = nil)
|
105
|
+
get_treatment(id, feature, attributes)
|
106
|
+
end
|
107
|
+
|
108
|
+
#
|
109
|
+
# method that returns the sdk gem version
|
110
|
+
#
|
111
|
+
# @return [string] version value for this sdk
|
112
|
+
def self.sdk_version
|
113
|
+
'RubyClientSDK-'+SplitIoClient::VERSION
|
114
|
+
end
|
115
|
+
|
116
|
+
#
|
117
|
+
# method to check if the sdk is running in localhost mode based on api key
|
118
|
+
#
|
119
|
+
# @return [boolean] True if is in localhost mode, false otherwise
|
120
|
+
def is_localhost_mode?
|
121
|
+
true
|
122
|
+
end
|
123
|
+
|
124
|
+
#
|
125
|
+
# method to set localhost mode features by reading .splits file located at home directory
|
126
|
+
#
|
127
|
+
# @returns [void]
|
128
|
+
def load_localhost_mode_features(splits_file)
|
129
|
+
if File.exists?(splits_file)
|
130
|
+
line_num=0
|
131
|
+
File.open(splits_file).each do |line|
|
132
|
+
line_data = line.strip.split(" ")
|
133
|
+
@localhost_mode_features << {feature: line_data[0], treatment: line_data[1]} unless line.start_with?('#') || line.strip.empty?
|
134
|
+
end
|
135
|
+
end
|
136
|
+
end
|
137
|
+
|
138
|
+
#
|
139
|
+
# method to check the treatment for the given feature in localhost mode
|
140
|
+
#
|
141
|
+
# @return [boolean] true if the feature is available in localhost mode, false otherwise
|
142
|
+
def get_localhost_treatment(feature)
|
143
|
+
localhost_result = Treatments::CONTROL
|
144
|
+
treatment = @localhost_mode_features.select{|h| h[:feature] == feature}.last
|
145
|
+
localhost_result = treatment[:treatment] if !treatment.nil?
|
146
|
+
localhost_result
|
147
|
+
end
|
148
|
+
|
149
|
+
private :get_treatment_without_exception_handling, :is_localhost_mode?,
|
150
|
+
:load_localhost_mode_features, :get_localhost_treatment
|
151
|
+
|
152
|
+
end
|
153
|
+
|
154
|
+
private_constant :LocalhostSplitClient
|
155
|
+
private_constant :LocalhostSplitManager
|
156
|
+
|
157
|
+
def initialize(splits_file)
|
158
|
+
@splits_file = splits_file
|
159
|
+
end
|
160
|
+
|
161
|
+
def client
|
162
|
+
@client ||= LocalhostSplitClient.new(@splits_file)
|
163
|
+
end
|
164
|
+
|
165
|
+
def manager
|
166
|
+
@manager ||= LocalhostSplitManager.new(@splits_file)
|
167
|
+
end
|
168
|
+
end
|
169
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
module SplitIoClient
|
2
|
+
class LocalhostSplitFactoryBuilder < NoMethodError
|
3
|
+
def self.build(directory)
|
4
|
+
splits_file = File.join(directory, ".split")
|
5
|
+
LocalhostSplitFactory.new(splits_file)
|
6
|
+
end
|
7
|
+
|
8
|
+
def self.build_from_path(path)
|
9
|
+
splits_file = File.join(path)
|
10
|
+
LocalhostSplitFactory.new(splits_file)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
@@ -0,0 +1,245 @@
|
|
1
|
+
require 'logger'
|
2
|
+
module SplitIoClient
|
3
|
+
#
|
4
|
+
# main class for split client sdk
|
5
|
+
#
|
6
|
+
class SplitFactory < NoMethodError
|
7
|
+
class SplitManager < NoMethodError
|
8
|
+
#
|
9
|
+
# constant that defines the localhost mode
|
10
|
+
LOCALHOST_MODE = 'localhost'
|
11
|
+
|
12
|
+
#
|
13
|
+
# Creates a new split manager instance that connects to split.io API.
|
14
|
+
#
|
15
|
+
# @param api_key [String] the API key for your split account
|
16
|
+
#
|
17
|
+
# @return [SplitIoManager] split.io client instance
|
18
|
+
def initialize(api_key, config = {}, adapter = nil, localhost_mode = false)
|
19
|
+
@localhost_mode_features = []
|
20
|
+
@config = config
|
21
|
+
@localhost_mode = localhost_mode
|
22
|
+
if @localhost_mode
|
23
|
+
load_localhost_mode_features
|
24
|
+
else
|
25
|
+
@adapter = adapter
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
#
|
30
|
+
# method to set localhost mode features by reading .splits file located at home directory
|
31
|
+
#
|
32
|
+
# @returns [void]
|
33
|
+
def load_localhost_mode_features
|
34
|
+
splits_file = File.join(Dir.home, ".split")
|
35
|
+
if File.exists?(splits_file)
|
36
|
+
line_num=0
|
37
|
+
File.open(splits_file).each do |line|
|
38
|
+
line_data = line.strip.split(" ")
|
39
|
+
@localhost_mode_features << {feature: line_data[0], treatment: line_data[1]} unless line.start_with?('#') || line.strip.empty?
|
40
|
+
end
|
41
|
+
end
|
42
|
+
@localhost_mode_features
|
43
|
+
end
|
44
|
+
|
45
|
+
#
|
46
|
+
# method to get the split list from the client
|
47
|
+
#
|
48
|
+
# @returns [object] array of splits
|
49
|
+
def splits
|
50
|
+
return load_localhost_mode_features if @localhost_mode
|
51
|
+
if @adapter
|
52
|
+
@adapter.parsed_splits.splits.map do |split|
|
53
|
+
data = split.data
|
54
|
+
treatments = split.data[:conditions] && split.data[:conditions][0][:partitions] \
|
55
|
+
? split.data[:conditions][0][:partitions].map{ |partition| partition[:treatment] }
|
56
|
+
: []
|
57
|
+
{
|
58
|
+
name: data[:name],
|
59
|
+
traffic_type_name: data[:trafficTypeName],
|
60
|
+
killed: data[:killed],
|
61
|
+
treatments: treatments,
|
62
|
+
change_number: data[:changeNumber]
|
63
|
+
}
|
64
|
+
end
|
65
|
+
else
|
66
|
+
@localhost_mode_features
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
class SplitClient < NoMethodError
|
72
|
+
#
|
73
|
+
# constant that defines the localhost mode
|
74
|
+
LOCALHOST_MODE = 'localhost'
|
75
|
+
|
76
|
+
#
|
77
|
+
# variables to if the sdk is being used in localhost mode and store the list of features
|
78
|
+
attr_reader :localhost_mode
|
79
|
+
attr_reader :localhost_mode_features
|
80
|
+
|
81
|
+
#
|
82
|
+
# Creates a new split client instance that connects to split.io API.
|
83
|
+
#
|
84
|
+
# @param api_key [String] the API key for your split account
|
85
|
+
#
|
86
|
+
# @return [SplitIoClient] split.io client instance
|
87
|
+
def initialize(api_key, config = {}, adapter = nil, localhost_mode = false)
|
88
|
+
@localhost_mode = localhost_mode
|
89
|
+
@localhost_mode_features = []
|
90
|
+
|
91
|
+
@config = config
|
92
|
+
|
93
|
+
if api_key == LOCALHOST_MODE
|
94
|
+
@localhost_mode = true
|
95
|
+
load_localhost_mode_features
|
96
|
+
else
|
97
|
+
@adapter = adapter
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
#
|
102
|
+
# obtains the treatment for a given feature
|
103
|
+
#
|
104
|
+
# @param id [string] user id
|
105
|
+
# @param feature [string] name of the feature that is being validated
|
106
|
+
#
|
107
|
+
# @return [Treatment] treatment constant value
|
108
|
+
def get_treatment(id, feature, attributes = nil)
|
109
|
+
unless id
|
110
|
+
@config.logger.warn('id was null for feature: ' + feature)
|
111
|
+
return Treatments::CONTROL
|
112
|
+
end
|
113
|
+
|
114
|
+
unless feature
|
115
|
+
@config.logger.warn('feature was null for id: ' + id)
|
116
|
+
return Treatments::CONTROL
|
117
|
+
end
|
118
|
+
|
119
|
+
if is_localhost_mode?
|
120
|
+
result = get_localhost_treatment(feature)
|
121
|
+
else
|
122
|
+
start = Time.now
|
123
|
+
result = nil
|
124
|
+
|
125
|
+
begin
|
126
|
+
result = get_treatment_without_exception_handling(id, feature, attributes)
|
127
|
+
rescue StandardError => error
|
128
|
+
@config.log_found_exception(__method__.to_s, error)
|
129
|
+
end
|
130
|
+
|
131
|
+
result = result.nil? ? Treatments::CONTROL : result
|
132
|
+
|
133
|
+
begin
|
134
|
+
@adapter.impressions.log(id, feature, result, (Time.now.to_f * 1000.0))
|
135
|
+
latency = (Time.now - start) * 1000.0
|
136
|
+
if (@adapter.impressions.queue.length >= @adapter.impressions.max_number_of_keys)
|
137
|
+
@adapter.impressions_producer.wakeup
|
138
|
+
end
|
139
|
+
rescue StandardError => error
|
140
|
+
@config.log_found_exception(__method__.to_s, error)
|
141
|
+
end
|
142
|
+
|
143
|
+
end
|
144
|
+
|
145
|
+
result
|
146
|
+
end
|
147
|
+
|
148
|
+
#
|
149
|
+
# auxiliary method to get the treatments avoding exceptions
|
150
|
+
#
|
151
|
+
# @param id [string] user id
|
152
|
+
# @param feature [string] name of the feature that is being validated
|
153
|
+
#
|
154
|
+
# @return [Treatment] tretment constant value
|
155
|
+
def get_treatment_without_exception_handling(id, feature, attributes = nil)
|
156
|
+
@adapter.parsed_splits.segments = @adapter.parsed_segments
|
157
|
+
split = @adapter.parsed_splits.get_split(feature)
|
158
|
+
|
159
|
+
if split.nil?
|
160
|
+
return Treatments::CONTROL
|
161
|
+
else
|
162
|
+
default_treatment = split.data[:defaultTreatment]
|
163
|
+
return @adapter.parsed_splits.get_split_treatment(id, feature, default_treatment, attributes)
|
164
|
+
end
|
165
|
+
end
|
166
|
+
|
167
|
+
#
|
168
|
+
# method that returns the sdk gem version
|
169
|
+
#
|
170
|
+
# @return [string] version value for this sdk
|
171
|
+
def self.sdk_version
|
172
|
+
'RubyClientSDK-'+SplitIoClient::VERSION
|
173
|
+
end
|
174
|
+
|
175
|
+
#
|
176
|
+
# method to check if the sdk is running in localhost mode based on api key
|
177
|
+
#
|
178
|
+
# @return [boolean] True if is in localhost mode, false otherwise
|
179
|
+
def is_localhost_mode?
|
180
|
+
@localhost_mode
|
181
|
+
end
|
182
|
+
|
183
|
+
#
|
184
|
+
# method to set localhost mode features by reading .splits file located at home directory
|
185
|
+
#
|
186
|
+
# @returns [void]
|
187
|
+
def load_localhost_mode_features
|
188
|
+
splits_file = File.join(Dir.home, ".split")
|
189
|
+
if File.exists?(splits_file)
|
190
|
+
line_num=0
|
191
|
+
File.open(splits_file).each do |line|
|
192
|
+
line_data = line.strip.split(" ")
|
193
|
+
@localhost_mode_features << {feature: line_data[0], treatment: line_data[1]} unless line.start_with?('#') || line.strip.empty?
|
194
|
+
end
|
195
|
+
end
|
196
|
+
end
|
197
|
+
|
198
|
+
#
|
199
|
+
# method to check the treatment for the given feature in localhost mode
|
200
|
+
#
|
201
|
+
# @return [boolean] true if the feature is available in localhost mode, false otherwise
|
202
|
+
def get_localhost_treatment(feature)
|
203
|
+
localhost_result = Treatments::CONTROL
|
204
|
+
treatment = @localhost_mode_features.select{|h| h[:feature] == feature}.last
|
205
|
+
localhost_result = treatment[:treatment] if !treatment.nil?
|
206
|
+
localhost_result
|
207
|
+
end
|
208
|
+
|
209
|
+
private :get_treatment_without_exception_handling, :is_localhost_mode?,
|
210
|
+
:load_localhost_mode_features, :get_localhost_treatment
|
211
|
+
|
212
|
+
end
|
213
|
+
|
214
|
+
private_constant :SplitClient
|
215
|
+
private_constant :SplitManager
|
216
|
+
|
217
|
+
def initialize(api_key, config = {})
|
218
|
+
@api_key = api_key
|
219
|
+
@config = SplitConfig.new(config)
|
220
|
+
@adapter = api_key != 'localhost' \
|
221
|
+
? SplitAdapter.new(api_key, @config)
|
222
|
+
: nil
|
223
|
+
@localhost_mode = api_key == 'localhost'
|
224
|
+
end
|
225
|
+
|
226
|
+
def client
|
227
|
+
@client ||= SplitClient.new(@api_key, @config, @adapter, @localhost_mode)
|
228
|
+
end
|
229
|
+
|
230
|
+
def manager
|
231
|
+
@manager ||= SplitManager.new(@api_key, @config, @adapter, @localhost_mode)
|
232
|
+
end
|
233
|
+
|
234
|
+
#
|
235
|
+
# method that returns the sdk gem version
|
236
|
+
#
|
237
|
+
# @return [string] version value for this sdk
|
238
|
+
def self.sdk_version
|
239
|
+
'RubyClientSDK-'+SplitIoClient::VERSION
|
240
|
+
end
|
241
|
+
|
242
|
+
private
|
243
|
+
attr_reader :adapter
|
244
|
+
end
|
245
|
+
end
|
@@ -28,7 +28,7 @@ def execute
|
|
28
28
|
|
29
29
|
threads = []
|
30
30
|
times_per_thread = iterations / 4
|
31
|
-
split_client = SplitIoClient::
|
31
|
+
split_client = SplitIoClient::SplitFactory.new(api_key, {base_uri: base_uri, logger: Logger.new("/dev/null").client })
|
32
32
|
|
33
33
|
puts Benchmark.measure{
|
34
34
|
4.times do |i|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: splitclient-rb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Split Software
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-
|
11
|
+
date: 2016-08-01 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -230,8 +230,11 @@ files:
|
|
230
230
|
- lib/splitclient-engine/parser/split_parser.rb
|
231
231
|
- lib/splitclient-engine/partitions/treatments.rb
|
232
232
|
- lib/splitclient-rb.rb
|
233
|
-
- lib/splitclient-rb/
|
233
|
+
- lib/splitclient-rb/localhost_split_factory.rb
|
234
|
+
- lib/splitclient-rb/localhost_split_factory_builder.rb
|
234
235
|
- lib/splitclient-rb/split_config.rb
|
236
|
+
- lib/splitclient-rb/split_factory.rb
|
237
|
+
- lib/splitclient-rb/split_factory_builder.rb
|
235
238
|
- lib/splitclient-rb/version.rb
|
236
239
|
- lib/splitclient-rb_utilitites.rb
|
237
240
|
- splitclient-rb.gemspec
|
@@ -258,7 +261,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
258
261
|
version: '0'
|
259
262
|
requirements: []
|
260
263
|
rubyforge_project:
|
261
|
-
rubygems_version: 2.
|
264
|
+
rubygems_version: 2.5.2
|
262
265
|
signing_key:
|
263
266
|
specification_version: 4
|
264
267
|
summary: Ruby client for split SDK.
|
@@ -1,156 +0,0 @@
|
|
1
|
-
require 'logger'
|
2
|
-
|
3
|
-
module SplitIoClient
|
4
|
-
|
5
|
-
#
|
6
|
-
# main class for split client sdk
|
7
|
-
#
|
8
|
-
class SplitClient < NoMethodError
|
9
|
-
|
10
|
-
#
|
11
|
-
# constant that defines the localhost mode
|
12
|
-
LOCALHOST_MODE = 'localhost'
|
13
|
-
|
14
|
-
#
|
15
|
-
# object that acts as an api adapter connector. used to get and post to api endpoints
|
16
|
-
attr_reader :adapter
|
17
|
-
|
18
|
-
#
|
19
|
-
# variables to if the sdk is being used in localhost mode and store the list of features
|
20
|
-
attr_reader :localhost_mode
|
21
|
-
attr_reader :localhost_mode_features
|
22
|
-
|
23
|
-
#
|
24
|
-
# Creates a new split client instance that connects to split.io API.
|
25
|
-
#
|
26
|
-
# @param api_key [String] the API key for your split account
|
27
|
-
#
|
28
|
-
# @return [SplitIoClient] split.io client instance
|
29
|
-
def initialize(api_key, config = {})
|
30
|
-
@localhost_mode = false
|
31
|
-
@localhost_mode_features = []
|
32
|
-
|
33
|
-
@config = SplitConfig.new(config)
|
34
|
-
|
35
|
-
if api_key == LOCALHOST_MODE
|
36
|
-
@localhost_mode = true
|
37
|
-
load_localhost_mode_features
|
38
|
-
else
|
39
|
-
@adapter = SplitAdapter.new(api_key, @config)
|
40
|
-
end
|
41
|
-
end
|
42
|
-
|
43
|
-
#
|
44
|
-
# obtains the treatment for a given feature
|
45
|
-
#
|
46
|
-
# @param id [string] user id
|
47
|
-
# @param feature [string] name of the feature that is being validated
|
48
|
-
#
|
49
|
-
# @return [Treatment] treatment constant value
|
50
|
-
def get_treatment(id, feature, attributes = nil)
|
51
|
-
unless id
|
52
|
-
@config.logger.warn('id was null for feature: ' + feature)
|
53
|
-
return Treatments::CONTROL
|
54
|
-
end
|
55
|
-
|
56
|
-
unless feature
|
57
|
-
@config.logger.warn('feature was null for id: ' + id)
|
58
|
-
return Treatments::CONTROL
|
59
|
-
end
|
60
|
-
|
61
|
-
if is_localhost_mode?
|
62
|
-
result = get_localhost_treatment(feature)
|
63
|
-
else
|
64
|
-
start = Time.now
|
65
|
-
result = nil
|
66
|
-
|
67
|
-
begin
|
68
|
-
result = get_treatment_without_exception_handling(id, feature, attributes)
|
69
|
-
rescue StandardError => error
|
70
|
-
@config.log_found_exception(__method__.to_s, error)
|
71
|
-
end
|
72
|
-
|
73
|
-
result = result.nil? ? Treatments::CONTROL : result
|
74
|
-
|
75
|
-
begin
|
76
|
-
@adapter.impressions.log(id, feature, result, (Time.now.to_f * 1000.0))
|
77
|
-
latency = (Time.now - start) * 1000.0
|
78
|
-
if (@adapter.impressions.queue.length >= @adapter.impressions.max_number_of_keys)
|
79
|
-
@adapter.impressions_producer.wakeup
|
80
|
-
end
|
81
|
-
rescue StandardError => error
|
82
|
-
@config.log_found_exception(__method__.to_s, error)
|
83
|
-
end
|
84
|
-
|
85
|
-
end
|
86
|
-
|
87
|
-
result
|
88
|
-
end
|
89
|
-
|
90
|
-
#
|
91
|
-
# auxiliary method to get the treatments avoding exceptions
|
92
|
-
#
|
93
|
-
# @param id [string] user id
|
94
|
-
# @param feature [string] name of the feature that is being validated
|
95
|
-
#
|
96
|
-
# @return [Treatment] tretment constant value
|
97
|
-
def get_treatment_without_exception_handling(id, feature, attributes = nil)
|
98
|
-
@adapter.parsed_splits.segments = @adapter.parsed_segments
|
99
|
-
split = @adapter.parsed_splits.get_split(feature)
|
100
|
-
|
101
|
-
if split.nil?
|
102
|
-
return Treatments::CONTROL
|
103
|
-
else
|
104
|
-
default_treatment = split.data[:defaultTreatment]
|
105
|
-
return @adapter.parsed_splits.get_split_treatment(id, feature, default_treatment, attributes)
|
106
|
-
end
|
107
|
-
end
|
108
|
-
|
109
|
-
#
|
110
|
-
# method that returns the sdk gem version
|
111
|
-
#
|
112
|
-
# @return [string] version value for this sdk
|
113
|
-
def self.sdk_version
|
114
|
-
'RubyClientSDK-'+SplitIoClient::VERSION
|
115
|
-
end
|
116
|
-
|
117
|
-
#
|
118
|
-
# method to check if the sdk is running in localhost mode based on api key
|
119
|
-
#
|
120
|
-
# @return [boolean] True if is in localhost mode, false otherwise
|
121
|
-
def is_localhost_mode?
|
122
|
-
@localhost_mode
|
123
|
-
end
|
124
|
-
|
125
|
-
#
|
126
|
-
# method to set localhost mode features by reading .splits file located at home directory
|
127
|
-
#
|
128
|
-
# @returns [void]
|
129
|
-
def load_localhost_mode_features
|
130
|
-
splits_file = File.join(Dir.home, ".split")
|
131
|
-
if File.exists?(splits_file)
|
132
|
-
line_num=0
|
133
|
-
File.open(splits_file).each do |line|
|
134
|
-
line_data = line.strip.split(" ")
|
135
|
-
@localhost_mode_features << {feature: line_data[0], treatment: line_data[1]} unless line.start_with?('#') || line.strip.empty?
|
136
|
-
end
|
137
|
-
end
|
138
|
-
end
|
139
|
-
|
140
|
-
#
|
141
|
-
# method to check the treatment for the given feature in localhost mode
|
142
|
-
#
|
143
|
-
# @return [boolean] true if the feature is available in localhost mode, false otherwise
|
144
|
-
def get_localhost_treatment(feature)
|
145
|
-
localhost_result = Treatments::CONTROL
|
146
|
-
treatment = @localhost_mode_features.select{|h| h[:feature] == feature}.last
|
147
|
-
localhost_result = treatment[:treatment] if !treatment.nil?
|
148
|
-
localhost_result
|
149
|
-
end
|
150
|
-
|
151
|
-
private :get_treatment_without_exception_handling, :is_localhost_mode?,
|
152
|
-
:load_localhost_mode_features, :get_localhost_treatment
|
153
|
-
|
154
|
-
end
|
155
|
-
|
156
|
-
end
|